on 4126d90 help sign in
unity8/qml/Notifications/Notification.qml
391 lines 13 kB history raw
1/*
2 * Copyright (C) 2013 Canonical, Ltd.
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; version 3.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 */
17import QtQuick 2.0
18import Ubuntu.Components 0.1
19import Unity.Notifications 1.0
20import QMenuModel 0.1
21import Utils 0.1
23Item {
24 id: notification
26 property alias iconSource: icon.fileSource
27 property alias secondaryIconSource: secondaryIcon.source
28 property alias summary: summaryLabel.text
29 property alias body: bodyLabel.text
30 property var actions
31 property var notificationId
32 property var type
33 property var hints
34 property var notification
35 property color color
36 property bool fullscreen
37 property int maxHeight
38 property int margins
40 fullscreen: false
41 objectName: "background"
42 implicitHeight: type !== Notification.PlaceHolder ? (fullscreen ? maxHeight : contentColumn.height + contentColumn.spacing * 2) : 0
44 color: Qt.rgba(0.132, 0.117, 0.109, 0.97)
45 opacity: 0
47 state: {
48 var result = "";
50 if (type == Notification.SnapDecision) {
51 if (ListView.view.currentIndex == index) {
52 result = "expanded";
53 } else {
54 if (ListView.view.count > 2) {
55 if (ListView.view.currentIndex == -1 && index == 1) {
56 result = "expanded";
57 } else {
58 result = "contracted";
59 }
60 } else {
61 result = "expanded";
62 }
63 }
64 }
66 return result;
67 }
69 Behavior on height {
70 id: normalHeightBehavior
72 //enabled: menuItemFactory.progress == 1
73 enabled: true
74 SequentialAnimation {
75 PauseAnimation {
76 duration: UbuntuAnimation.SnapDuration
77 }
78 UbuntuNumberAnimation {
79 duration: UbuntuAnimation.SnapDuration
80 }
81 }
82 }
84 states:[
85 State {
86 name: "contracted"
87 PropertyChanges {target: notification; height: units.gu(8)}
88 },
89 State {
90 name: "expanded"
91 PropertyChanges {target: notification; height: implicitHeight}
92 }
93 ]
95 clip: fullscreen ? false : true
97 visible: type != Notification.PlaceHolder
99 UbuntuShape {
100 id: shapedBack
102 visible: !fullscreen
103 anchors {
104 fill: parent
105 leftMargin: notification.margins
106 rightMargin: notification.margins
107 }
108 color: parent.color
109 opacity: parent.opacity
110 radius: "medium"
111 }
113 Rectangle {
114 id: nonShapedBack
116 visible: fullscreen
117 anchors.fill: parent
118 color: parent.color
119 opacity: parent.opacity
120 }
122 Item {
123 id: contents
124 anchors.fill: fullscreen ? nonShapedBack : shapedBack
126 UnityMenuModelPaths {
127 id: paths
129 source: hints["x-canonical-private-menu-model"]
131 busNameHint: "busName"
132 actionsHint: "actions"
133 menuObjectPathHint: "menuPath"
134 }
136 UnityMenuModel {
137 id: unityMenuModel
139 busName: paths.busName
140 actions: paths.actions
141 menuObjectPath: paths.menuObjectPath
142 }
144 Behavior on implicitHeight {
145 id: heightBehavior
147 enabled: false
148 UbuntuNumberAnimation {
149 duration: UbuntuAnimation.SnapDuration
150 }
151 }
153 // delay enabling height behavior until the add transition is complete
154 onOpacityChanged: if (opacity == 1) heightBehavior.enabled = true
156 MouseArea {
157 id: interactiveArea
159 anchors.fill: parent
160 objectName: "interactiveArea"
161 onClicked: {
162 if (notification.type == Notification.Interactive) {
163 notification.notification.invokeAction(actionRepeater.itemAt(0).actionId)
164 } else {
165 notificationList.currentIndex = index;
166 }
167 }
168 }
170 Column {
171 id: contentColumn
173 anchors {
174 left: parent.left
175 right: parent.right
176 top: parent.top
177 margins: fullscreen ? 0 : spacing
178 }
180 spacing: units.gu(1)
182 Row {
183 id: topRow
185 spacing: contentColumn.spacing
186 anchors {
187 left: parent.left
188 right: parent.right
189 }
191 ShapedIcon {
192 id: icon
194 objectName: "icon"
195 width: units.gu(6)
196 height: units.gu(6)
197 shaped: notification.hints["x-canonical-non-shaped-icon"] == "true" ? false : true
198 visible: iconSource !== undefined && iconSource != ""
199 }
201 Image {
202 id: secondaryIcon
204 objectName: "secondaryIcon"
205 width: units.gu(2)
206 height: units.gu(2)
207 visible: source !== undefined && source != ""
208 fillMode: Image.PreserveAspectCrop
209 }
211 Column {
212 id: labelColumn
213 width: parent.width - x
215 anchors.verticalCenter: (icon.visible && !bodyLabel.visible) ? icon.verticalCenter : undefined
217 Label {
218 id: summaryLabel
220 objectName: "summaryLabel"
221 anchors {
222 left: parent.left
223 right: parent.right
224 }
225 fontSize: "medium"
226 font.bold: true
227 color: Theme.palette.selected.backgroundText
228 elide: Text.ElideRight
229 }
231 Label {
232 id: bodyLabel
234 objectName: "bodyLabel"
235 anchors {
236 left: parent.left
237 right: parent.right
238 }
239 visible: body != ""
240 fontSize: "small"
241 color: Theme.palette.selected.backgroundText
242 opacity: 0.6
243 wrapMode: Text.WordWrap
244 maximumLineCount: 10
245 elide: Text.ElideRight
246 }
247 }
248 }
250 Column {
251 objectName: "dialogListView"
252 spacing: units.gu(2)
254 visible: count > 0
256 anchors.left: parent.left; anchors.right: parent.right
257 anchors.top: fullscreen ? parent.top : undefined
258 anchors.bottom: fullscreen ? parent.bottom : undefined
260 Repeater {
261 model: unityMenuModel
263 NotificationMenuItemFactory {
264 id: menuItemFactory
266 anchors.left: parent.left; anchors.right: parent.right
268 menuModel: unityMenuModel
269 menuData: model
270 menuIndex: index
271 maxHeight: notification.maxHeight
273 onLoaded: {
274 notification.fullscreen = Qt.binding(function() { return fullscreen; });
275 }
276 }
277 }
278 }
280 Item {
281 id: buttonRow
283 objectName: "buttonRow"
284 anchors {
285 left: parent.left
286 right: parent.right
287 }
288 visible: notification.type == Notification.SnapDecision && actionRepeater.count > 0
289 height: units.gu(5)
291 property real buttonWidth: (width - contentColumn.spacing) / 2
292 property bool expanded
294 Button {
295 id: leftButton
297 objectName: "button1"
298 width: parent.expanded ? parent.width : parent.buttonWidth
299 anchors {
300 top: parent.top
301 bottom: parent.bottom
302 }
303 text: notification.type == Notification.SnapDecision && actionRepeater.count >= 2 ? actionRepeater.itemAt(1).actionLabel : ""
304 gradient: UbuntuColors.greyGradient
305 onClicked: {
306 if (actionRepeater.count > 2) {
307 buttonRow.expanded = !buttonRow.expanded
308 } else {
309 notification.notification.invokeAction(actionRepeater.itemAt(1).actionId)
310 }
311 }
313 Behavior on width {
314 UbuntuNumberAnimation {
315 duration: UbuntuAnimation.SnapDuration
316 }
317 }
318 }
320 Button {
321 id: rightButton
323 objectName: "button0"
324 anchors {
325 left: leftButton.right
326 leftMargin: contentColumn.spacing
327 right: parent.right
328 }
329 text: notification.type == Notification.SnapDecision && actionRepeater.count >= 1 ? actionRepeater.itemAt(0).actionLabel : ""
330 anchors {
331 top: parent.top
332 bottom: parent.bottom
333 }
334 gradient: notification.hints["x-canonical-private-button-tint"] == "true" ? UbuntuColors.orangeGradient : UbuntuColors.greyGradient
335 visible: width > 0
336 onClicked: notification.notification.invokeAction(actionRepeater.itemAt(0).actionId)
337 }
338 }
340 Column {
341 objectName: "buttonColumn"
342 spacing: contentColumn.spacing
343 anchors {
344 left: parent.left
345 right: parent.right
346 }
348 // calculate initial position before Column takes over
349 y: buttonRow.y + buttonRow.height + contentColumn.spacing
351 visible: notification.type == Notification.SnapDecision && buttonRow.expanded
352 height: buttonRow.expanded ? implicitHeight : 0
354 Repeater {
355 id: actionRepeater
357 model: notification.actions
358 delegate: Loader {
359 id: loader
361 property string actionId: id
362 property string actionLabel: label
364 anchors {
365 left: parent.left
366 right: parent.right
367 }
369 Component {
370 id: actionButton
372 Button {
373 objectName: "button" + index
374 anchors {
375 left: parent.left
376 right: parent.right
377 }
379 text: loader.actionLabel
380 height: units.gu(5)
381 gradient: UbuntuColors.greyGradient
382 onClicked: notification.notification.invokeAction(loader.actionId)
383 }
384 }
385 sourceComponent: (index == 0 || index == 1) ? undefined : actionButton
386 }
387 }
388 }
389 }
390 }