Merge lp:~nik90/component-store/add-listitem-component into lp:component-store
- add-listitem-component
- Merge into trunk.14.10
Proposed by
Nekhelesh Ramananthan
Status: | Merged |
---|---|
Merged at revision: | 38 |
Proposed branch: | lp:~nik90/component-store/add-listitem-component |
Merge into: | lp:component-store |
Diff against target: |
810 lines (+741/-7) 7 files modified
ComponentStore/ListItemWithActions/ListItemWithActions.qml (+454/-0) ComponentStore/ListItemWithActions/ListItemWithActionsCheckBox.qml (+25/-0) GallerySRC/ListItemWithActionsWidget.qml (+63/-0) GallerySRC/WidgetsModel.qml (+13/-7) docs/_components/listitemwithactions.rst (+184/-0) docs/index.rst (+1/-0) docs/release.rst (+1/-0) |
To merge this branch: | bzr merge lp:~nik90/component-store/add-listitem-component |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Ubuntu Touch Community Dev | Pending | ||
Review via email: mp+241581@code.launchpad.net |
Commit message
Added listitemwithactions component
Description of the change
Added listitemwithactions component
To post a comment you must log in.
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | === added directory 'ComponentStore/ListItemWithActions' |
2 | === added file 'ComponentStore/ListItemWithActions/ListItemWithActions.qml' |
3 | --- ComponentStore/ListItemWithActions/ListItemWithActions.qml 1970-01-01 00:00:00 +0000 |
4 | +++ ComponentStore/ListItemWithActions/ListItemWithActions.qml 2014-11-12 16:25:42 +0000 |
5 | @@ -0,0 +1,454 @@ |
6 | +/* |
7 | + * Copyright (C) 2012-2014 Canonical, Ltd. |
8 | + * |
9 | + * This program is free software; you can redistribute it and/or modify |
10 | + * it under the terms of the GNU General Public License as published by |
11 | + * the Free Software Foundation; version 3. |
12 | + * |
13 | + * This program is distributed in the hope that it will be useful, |
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
16 | + * GNU General Public License for more details. |
17 | + * |
18 | + * You should have received a copy of the GNU General Public License |
19 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
20 | + */ |
21 | + |
22 | +import QtQuick 2.2 |
23 | +import Ubuntu.Components 1.1 |
24 | + |
25 | +Item { |
26 | + id: root |
27 | + |
28 | + property Action leftSideAction: null |
29 | + property list<Action> rightSideActions |
30 | + property double defaultHeight: units.gu(8) |
31 | + property bool locked: false |
32 | + property Action activeAction: null |
33 | + property var activeItem: null |
34 | + property bool triggerActionOnMouseRelease: false |
35 | + property color color: Theme.palette.normal.background |
36 | + property color selectedColor: "#E6E6E6" |
37 | + property bool selected: false |
38 | + property bool selectionMode: false |
39 | + property alias internalAnchors: mainContents.anchors |
40 | + default property alias contents: mainContents.children |
41 | + |
42 | + readonly property double actionWidth: units.gu(4) |
43 | + readonly property double leftActionWidth: units.gu(10) |
44 | + readonly property double actionThreshold: actionWidth * 0.4 |
45 | + readonly property double threshold: 0.4 |
46 | + readonly property string swipeState: main.x == 0 ? "Normal" : main.x > 0 ? "LeftToRight" : "RightToLeft" |
47 | + readonly property alias swipping: mainItemMoving.running |
48 | + readonly property bool _showActions: mouseArea.pressed || swipeState != "Normal" || swipping |
49 | + |
50 | + /* internal */ |
51 | + property var _visibleRightSideActions: filterVisibleActions(rightSideActions) |
52 | + |
53 | + signal itemClicked(var mouse) |
54 | + signal itemPressAndHold(var mouse) |
55 | + |
56 | + function returnToBoundsRTL(direction) |
57 | + { |
58 | + var actionFullWidth = actionWidth + units.gu(2) |
59 | + |
60 | + // go back to normal state if swipping reverse |
61 | + if (direction === "LTR") { |
62 | + updatePosition(0) |
63 | + return |
64 | + } else if (!triggerActionOnMouseRelease) { |
65 | + updatePosition(-rightActionsView.width + units.gu(2)) |
66 | + return |
67 | + } |
68 | + |
69 | + var xOffset = Math.abs(main.x) |
70 | + var index = Math.min(Math.floor(xOffset / actionFullWidth), _visibleRightSideActions.length) |
71 | + var newX = 0 |
72 | + if (index === _visibleRightSideActions.length) { |
73 | + newX = -(rightActionsView.width - units.gu(2)) |
74 | + } else if (index >= 1) { |
75 | + newX = -(actionFullWidth * index) |
76 | + } |
77 | + updatePosition(newX) |
78 | + } |
79 | + |
80 | + function returnToBoundsLTR(direction) |
81 | + { |
82 | + var finalX = leftActionWidth |
83 | + if ((direction === "RTL") || (main.x <= (finalX * root.threshold))) |
84 | + finalX = 0 |
85 | + updatePosition(finalX) |
86 | + } |
87 | + |
88 | + function returnToBounds(direction) |
89 | + { |
90 | + if (main.x < 0) { |
91 | + returnToBoundsRTL(direction) |
92 | + } else if (main.x > 0) { |
93 | + returnToBoundsLTR(direction) |
94 | + } else { |
95 | + updatePosition(0) |
96 | + } |
97 | + } |
98 | + |
99 | + function contains(item, point, marginX) |
100 | + { |
101 | + var itemStartX = item.x - marginX |
102 | + var itemEndX = item.x + item.width + marginX |
103 | + return (point.x >= itemStartX) && (point.x <= itemEndX) && |
104 | + (point.y >= item.y) && (point.y <= (item.y + item.height)); |
105 | + } |
106 | + |
107 | + function getActionAt(point) |
108 | + { |
109 | + if (contains(leftActionView, point, 0)) { |
110 | + return leftSideAction |
111 | + } else if (contains(rightActionsView, point, 0)) { |
112 | + var newPoint = root.mapToItem(rightActionsView, point.x, point.y) |
113 | + for (var i = 0; i < rightActionsRepeater.count; i++) { |
114 | + var child = rightActionsRepeater.itemAt(i) |
115 | + if (contains(child, newPoint, units.gu(1))) { |
116 | + return i |
117 | + } |
118 | + } |
119 | + } |
120 | + return -1 |
121 | + } |
122 | + |
123 | + function updateActiveAction() |
124 | + { |
125 | + if (triggerActionOnMouseRelease && |
126 | + (main.x <= -(root.actionWidth + units.gu(2))) && |
127 | + (main.x > -(rightActionsView.width - units.gu(2)))) { |
128 | + var actionFullWidth = actionWidth + units.gu(2) |
129 | + var xOffset = Math.abs(main.x) |
130 | + var index = Math.min(Math.floor(xOffset / actionFullWidth), _visibleRightSideActions.length) |
131 | + index = index - 1 |
132 | + if (index > -1) { |
133 | + root.activeItem = rightActionsRepeater.itemAt(index) |
134 | + root.activeAction = root._visibleRightSideActions[index] |
135 | + } |
136 | + } else { |
137 | + root.activeAction = null |
138 | + } |
139 | + } |
140 | + |
141 | + function resetSwipe() |
142 | + { |
143 | + updatePosition(0) |
144 | + } |
145 | + |
146 | + function filterVisibleActions(actions) |
147 | + { |
148 | + var visibleActions = [] |
149 | + for(var i = 0; i < actions.length; i++) { |
150 | + var action = actions[i] |
151 | + if (action.visible) { |
152 | + visibleActions.push(action) |
153 | + } |
154 | + } |
155 | + return visibleActions |
156 | + } |
157 | + |
158 | + function updatePosition(pos) |
159 | + { |
160 | + if (!root.triggerActionOnMouseRelease && (pos !== 0)) { |
161 | + mouseArea.state = pos > 0 ? "RightToLeft" : "LeftToRight" |
162 | + } else { |
163 | + mouseArea.state = "" |
164 | + } |
165 | + main.x = pos |
166 | + } |
167 | + |
168 | + states: [ |
169 | + State { |
170 | + name: "select" |
171 | + when: selectionMode || selected |
172 | + PropertyChanges { |
173 | + target: selectionIcon |
174 | + source: Qt.resolvedUrl("ListItemWithActionsCheckBox.qml") |
175 | + anchors.leftMargin: units.gu(2) |
176 | + } |
177 | + PropertyChanges { |
178 | + target: root |
179 | + locked: true |
180 | + } |
181 | + PropertyChanges { |
182 | + target: main |
183 | + x: 0 |
184 | + } |
185 | + } |
186 | + ] |
187 | + |
188 | + height: defaultHeight |
189 | + clip: height !== defaultHeight |
190 | + |
191 | + Rectangle { |
192 | + id: leftActionView |
193 | + |
194 | + anchors { |
195 | + top: parent.top |
196 | + bottom: parent.bottom |
197 | + right: main.left |
198 | + } |
199 | + width: root.leftActionWidth + actionThreshold |
200 | + visible: leftSideAction |
201 | + color: UbuntuColors.red |
202 | + |
203 | + Icon { |
204 | + anchors { |
205 | + centerIn: parent |
206 | + horizontalCenterOffset: actionThreshold / 2 |
207 | + } |
208 | + name: leftSideAction && _showActions ? leftSideAction.iconName : "" |
209 | + color: Theme.palette.selected.field |
210 | + height: units.gu(3) |
211 | + width: units.gu(3) |
212 | + } |
213 | + } |
214 | + |
215 | + Rectangle { |
216 | + id: rightActionsView |
217 | + |
218 | + anchors { |
219 | + top: main.top |
220 | + left: main.right |
221 | + bottom: main.bottom |
222 | + } |
223 | + visible: _visibleRightSideActions.length > 0 |
224 | + width: rightActionsRepeater.count > 0 ? rightActionsRepeater.count * (root.actionWidth + units.gu(2)) + root.actionThreshold + units.gu(2) : 0 |
225 | + color: "white" |
226 | + Row { |
227 | + anchors{ |
228 | + top: parent.top |
229 | + left: parent.left |
230 | + leftMargin: units.gu(2) |
231 | + right: parent.right |
232 | + rightMargin: units.gu(2) |
233 | + bottom: parent.bottom |
234 | + } |
235 | + spacing: units.gu(2) |
236 | + Repeater { |
237 | + id: rightActionsRepeater |
238 | + |
239 | + model: _showActions ? _visibleRightSideActions : [] |
240 | + Item { |
241 | + property alias image: img |
242 | + |
243 | + height: rightActionsView.height |
244 | + width: root.actionWidth |
245 | + |
246 | + Icon { |
247 | + id: img |
248 | + |
249 | + anchors.centerIn: parent |
250 | + width: units.gu(3) |
251 | + height: units.gu(3) |
252 | + name: modelData.iconName |
253 | + color: root.activeAction === modelData ? UbuntuColors.lightAubergine : UbuntuColors.lightGrey |
254 | + } |
255 | + } |
256 | + } |
257 | + } |
258 | + } |
259 | + |
260 | + |
261 | + Rectangle { |
262 | + id: main |
263 | + objectName: "mainItem" |
264 | + |
265 | + anchors { |
266 | + top: parent.top |
267 | + bottom: parent.bottom |
268 | + } |
269 | + |
270 | + width: parent.width |
271 | + color: root.selected ? root.selectedColor : root.color |
272 | + |
273 | + Loader { |
274 | + id: selectionIcon |
275 | + |
276 | + anchors { |
277 | + left: main.left |
278 | + verticalCenter: main.verticalCenter |
279 | + } |
280 | + width: (status === Loader.Ready) ? item.implicitWidth : 0 |
281 | + visible: (status === Loader.Ready) && (item.width === item.implicitWidth) |
282 | + Behavior on width { |
283 | + NumberAnimation { |
284 | + duration: UbuntuAnimation.SnapDuration |
285 | + } |
286 | + } |
287 | + } |
288 | + |
289 | + |
290 | + Item { |
291 | + id: mainContents |
292 | + |
293 | + anchors { |
294 | + left: selectionIcon.right |
295 | + leftMargin: units.gu(2) |
296 | + top: parent.top |
297 | + topMargin: units.gu(1) |
298 | + right: parent.right |
299 | + rightMargin: units.gu(2) |
300 | + bottom: parent.bottom |
301 | + bottomMargin: units.gu(1) |
302 | + } |
303 | + } |
304 | + |
305 | + Behavior on x { |
306 | + UbuntuNumberAnimation { |
307 | + id: mainItemMoving |
308 | + |
309 | + easing.type: Easing.OutElastic |
310 | + duration: UbuntuAnimation.SlowDuration |
311 | + } |
312 | + } |
313 | + Behavior on color { |
314 | + ColorAnimation {} |
315 | + } |
316 | + } |
317 | + |
318 | + SequentialAnimation { |
319 | + id: triggerAction |
320 | + |
321 | + property var currentItem: root.activeItem ? root.activeItem.image : null |
322 | + |
323 | + running: false |
324 | + ParallelAnimation { |
325 | + UbuntuNumberAnimation { |
326 | + target: triggerAction.currentItem |
327 | + property: "opacity" |
328 | + from: 1.0 |
329 | + to: 0.0 |
330 | + duration: UbuntuAnimation.SlowDuration |
331 | + easing {type: Easing.InOutBack; } |
332 | + } |
333 | + UbuntuNumberAnimation { |
334 | + target: triggerAction.currentItem |
335 | + properties: "width, height" |
336 | + from: units.gu(3) |
337 | + to: root.actionWidth |
338 | + duration: UbuntuAnimation.SlowDuration |
339 | + easing {type: Easing.InOutBack; } |
340 | + } |
341 | + } |
342 | + PropertyAction { |
343 | + target: triggerAction.currentItem |
344 | + properties: "width, height" |
345 | + value: units.gu(3) |
346 | + } |
347 | + PropertyAction { |
348 | + target: triggerAction.currentItem |
349 | + properties: "opacity" |
350 | + value: 1.0 |
351 | + } |
352 | + ScriptAction { |
353 | + script: { |
354 | + root.activeAction.triggered(root) |
355 | + mouseArea.state = "" |
356 | + } |
357 | + } |
358 | + PauseAnimation { |
359 | + duration: 500 |
360 | + } |
361 | + UbuntuNumberAnimation { |
362 | + target: main |
363 | + property: "x" |
364 | + to: 0 |
365 | + |
366 | + } |
367 | + } |
368 | + |
369 | + MouseArea { |
370 | + id: mouseArea |
371 | + |
372 | + property bool locked: root.locked || ((root.leftSideAction === null) && (root._visibleRightSideActions.count === 0)) |
373 | + property bool manual: false |
374 | + property string direction: "None" |
375 | + property real lastX: -1 |
376 | + |
377 | + anchors.fill: parent |
378 | + drag { |
379 | + target: locked ? null : main |
380 | + axis: Drag.XAxis |
381 | + minimumX: rightActionsView.visible ? -(rightActionsView.width) : 0 |
382 | + maximumX: leftActionView.visible ? leftActionView.width : 0 |
383 | + threshold: root.actionThreshold |
384 | + } |
385 | + |
386 | + states: [ |
387 | + State { |
388 | + name: "LeftToRight" |
389 | + PropertyChanges { |
390 | + target: mouseArea |
391 | + drag.maximumX: 0 |
392 | + } |
393 | + }, |
394 | + State { |
395 | + name: "RightToLeft" |
396 | + PropertyChanges { |
397 | + target: mouseArea |
398 | + drag.minimumX: 0 |
399 | + } |
400 | + } |
401 | + ] |
402 | + |
403 | + onMouseXChanged: { |
404 | + var offset = (lastX - mouseX) |
405 | + if (Math.abs(offset) <= root.actionThreshold) { |
406 | + return |
407 | + } |
408 | + lastX = mouseX |
409 | + direction = offset > 0 ? "RTL" : "LTR"; |
410 | + } |
411 | + |
412 | + onPressed: { |
413 | + lastX = mouse.x |
414 | + } |
415 | + |
416 | + onReleased: { |
417 | + if (root.triggerActionOnMouseRelease && root.activeAction) { |
418 | + triggerAction.start() |
419 | + } else { |
420 | + root.returnToBounds(direction) |
421 | + root.activeAction = null |
422 | + } |
423 | + lastX = -1 |
424 | + direction = "None" |
425 | + } |
426 | + onClicked: { |
427 | + if (main.x === 0) { |
428 | + root.itemClicked(mouse) |
429 | + } else if (main.x > 0) { |
430 | + var action = getActionAt(Qt.point(mouse.x, mouse.y)) |
431 | + if (action && action !== -1) { |
432 | + action.triggered(root) |
433 | + } |
434 | + } else { |
435 | + var actionIndex = getActionAt(Qt.point(mouse.x, mouse.y)) |
436 | + if (actionIndex !== -1) { |
437 | + root.activeItem = rightActionsRepeater.itemAt(actionIndex) |
438 | + root.activeAction = root._visibleRightSideActions[actionIndex] |
439 | + triggerAction.start() |
440 | + return |
441 | + } |
442 | + } |
443 | + root.resetSwipe() |
444 | + } |
445 | + |
446 | + onPositionChanged: { |
447 | + if (mouseArea.pressed) { |
448 | + updateActiveAction() |
449 | + } |
450 | + } |
451 | + onPressAndHold: { |
452 | + if (main.x === 0) { |
453 | + root.itemPressAndHold(mouse) |
454 | + } |
455 | + } |
456 | + z: -1 |
457 | + } |
458 | +} |
459 | + |
460 | |
461 | === added file 'ComponentStore/ListItemWithActions/ListItemWithActionsCheckBox.qml' |
462 | --- ComponentStore/ListItemWithActions/ListItemWithActionsCheckBox.qml 1970-01-01 00:00:00 +0000 |
463 | +++ ComponentStore/ListItemWithActions/ListItemWithActionsCheckBox.qml 2014-11-12 16:25:42 +0000 |
464 | @@ -0,0 +1,25 @@ |
465 | +/* |
466 | + * Copyright (C) 2012-2014 Canonical, Ltd. |
467 | + * |
468 | + * This program is free software; you can redistribute it and/or modify |
469 | + * it under the terms of the GNU General Public License as published by |
470 | + * the Free Software Foundation; version 3. |
471 | + * |
472 | + * This program is distributed in the hope that it will be useful, |
473 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
474 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
475 | + * GNU General Public License for more details. |
476 | + * |
477 | + * You should have received a copy of the GNU General Public License |
478 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
479 | + */ |
480 | + |
481 | +import QtQuick 2.2 |
482 | +import Ubuntu.Components 1.1 |
483 | + |
484 | +CheckBox { |
485 | + checked: root.selected |
486 | + width: implicitWidth |
487 | + // disable item mouse area to avoid conflicts with parent mouse area |
488 | + __mouseArea.enabled: false |
489 | +} |
490 | |
491 | === added file 'GallerySRC/ListItemWithActionsWidget.qml' |
492 | --- GallerySRC/ListItemWithActionsWidget.qml 1970-01-01 00:00:00 +0000 |
493 | +++ GallerySRC/ListItemWithActionsWidget.qml 2014-11-12 16:25:42 +0000 |
494 | @@ -0,0 +1,63 @@ |
495 | +import QtQuick 2.0 |
496 | +import Ubuntu.Components 1.1 |
497 | +import "../ComponentStore/ListItemWithActions" |
498 | + |
499 | +TemplateWidgetPage { |
500 | + id: listitemwithactionswidget |
501 | + |
502 | + title: "List Item With Actions" |
503 | + author: "Renato Araujo Oliveira Filho" |
504 | + email: "renato.filho@canonical.com" |
505 | + license: "GNU General Public License v3.0" |
506 | + description: "This widget provides an updated listitem which is what the core apps \ |
507 | +currently use. These listitems will be provided by the SDK with vivid onwards. However \ |
508 | +current RMT devices will ship with the ubuntu-sdk-14.10 framework which wouldn't have \ |
509 | +these latest listitems." |
510 | + |
511 | + ListModel { |
512 | + id: testModel |
513 | + ListElement { title: "Slide me right to delete" } |
514 | + ListElement { title: "Slide me left to show more options" } |
515 | + } |
516 | + |
517 | + content: ListView { |
518 | + id: nameListView |
519 | + anchors.fill: parent |
520 | + |
521 | + clip: true |
522 | + model: testModel |
523 | + |
524 | + delegate: ListItemWithActions { |
525 | + height: units.gu(9) |
526 | + width: parent.width |
527 | + color: "White" |
528 | + triggerActionOnMouseRelease: true |
529 | + |
530 | + leftSideAction: Action { |
531 | + iconName: "delete" |
532 | + text: i18n.tr("Delete") |
533 | + onTriggered: { |
534 | + testModel.remove(nameListView.index) |
535 | + } |
536 | + } |
537 | + |
538 | + rightSideActions: [ |
539 | + Action { |
540 | + iconName: "alarm-clock" |
541 | + text: i18n.tr("Alarm") |
542 | + }, |
543 | + |
544 | + Action { |
545 | + iconName: "add" |
546 | + text: i18n.tr("Add") |
547 | + } |
548 | + ] |
549 | + |
550 | + contents: Label { |
551 | + text: title |
552 | + anchors.left: parent.left |
553 | + anchors.verticalCenter: parent.verticalCenter |
554 | + } |
555 | + } |
556 | + } |
557 | +} |
558 | |
559 | === modified file 'GallerySRC/WidgetsModel.qml' |
560 | --- GallerySRC/WidgetsModel.qml 2014-11-08 20:59:00 +0000 |
561 | +++ GallerySRC/WidgetsModel.qml 2014-11-12 16:25:42 +0000 |
562 | @@ -2,23 +2,29 @@ |
563 | |
564 | ListModel { |
565 | id: widgetsModel |
566 | + |
567 | + ListElement { |
568 | + label: "Circle Image" |
569 | + source: "GallerySRC/CircleImageWidget.qml" |
570 | + } |
571 | + |
572 | ListElement { |
573 | label: "Empty State" |
574 | source: "GallerySRC/EmptyStateWidget.qml" |
575 | } |
576 | |
577 | ListElement { |
578 | - label: "Circle Image" |
579 | - source: "GallerySRC/CircleImageWidget.qml" |
580 | + label: "Fast Scroll" |
581 | + source: "GallerySRC/FastScrollWidget.qml" |
582 | + } |
583 | + |
584 | + ListElement { |
585 | + label: "List Item With Actions" |
586 | + source: "GallerySRC/ListItemWithActionsWidget.qml" |
587 | } |
588 | |
589 | ListElement { |
590 | label: "Page With Bottom Edge" |
591 | source: "GallerySRC/BottomEdgeWidget.qml" |
592 | } |
593 | - |
594 | - ListElement { |
595 | - label: "Fast Scroll" |
596 | - source: "GallerySRC/FastScrollWidget.qml" |
597 | - } |
598 | } |
599 | |
600 | === added file 'docs/_components/listitemwithactions.rst' |
601 | --- docs/_components/listitemwithactions.rst 1970-01-01 00:00:00 +0000 |
602 | +++ docs/_components/listitemwithactions.rst 2014-11-12 16:25:42 +0000 |
603 | @@ -0,0 +1,184 @@ |
604 | +List Item With Actions |
605 | +====================== |
606 | + |
607 | ++----------+---------------------------------+ |
608 | +| Author | Renato Araujo Oliveira Filho | |
609 | ++----------+-------------+-------------------+ |
610 | +| License | GNU General Public License v3.0 | |
611 | ++----------+---------------------------------+ |
612 | +| Contact | renato.filho@canonical.com | |
613 | ++----------+---------------------------------+ |
614 | + |
615 | +This widget provides an updated listitem which is what the core apps currently use. |
616 | +These listitems will be provided by the SDK with vivid onwards. However current RMT |
617 | +devices will ship with the ubuntu-sdk-14.10 framework which wouldn't have these latest listitems. |
618 | + |
619 | +Example: |
620 | + |
621 | +.. code-block:: qml |
622 | + |
623 | + Page { |
624 | + id: listitemwithactionspage |
625 | + |
626 | + ListModel { |
627 | + id: testModel |
628 | + ListElement { title: "Slide me right to delete" } |
629 | + ListElement { title: "Slide me left to show more options" } |
630 | + } |
631 | + |
632 | + ListView { |
633 | + id: nameListView |
634 | + anchors.fill: parent |
635 | + |
636 | + clip: true |
637 | + model: testModel |
638 | + |
639 | + delegate: ListItemWithActions { |
640 | + height: units.gu(9) |
641 | + width: parent.width |
642 | + color: "White" |
643 | + triggerActionOnMouseRelease: true |
644 | + |
645 | + leftSideAction: Action { |
646 | + iconName: "delete" |
647 | + text: i18n.tr("Delete") |
648 | + onTriggered: { |
649 | + testModel.remove(nameListView.index) |
650 | + } |
651 | + } |
652 | + |
653 | + rightSideActions: [ |
654 | + Action { |
655 | + iconName: "alarm-clock" |
656 | + text: i18n.tr("Alarm") |
657 | + }, |
658 | + |
659 | + Action { |
660 | + iconName: "add" |
661 | + text: i18n.tr("Add") |
662 | + } |
663 | + ] |
664 | + |
665 | + contents: Label { |
666 | + text: title |
667 | + anchors.left: parent.left |
668 | + anchors.verticalCenter: parent.verticalCenter |
669 | + } |
670 | + } |
671 | + } |
672 | + } |
673 | + |
674 | +.. image:: ../_images/listitemwithactions.png |
675 | + :align: center |
676 | + |
677 | +Properties |
678 | +---------- |
679 | + |
680 | +- :ref:`color`: color |
681 | +- :ref:`contents`: Item |
682 | +- :ref:`internalAnchors`: anchors |
683 | +- :ref:`leftSideAction`: Action |
684 | +- :ref:`rightSideActions`: Action <List> |
685 | +- :ref:`locked`: boolean (false by default) |
686 | +- :ref:`triggerActionOnMouseRelease`: boolean (false by default) |
687 | + |
688 | +Property Documentation |
689 | +---------------------- |
690 | + |
691 | +.. _color: |
692 | + |
693 | +color |
694 | +^^^^^ |
695 | + |
696 | +The background color of the list item. |
697 | + |
698 | +.. _contents: |
699 | + |
700 | +contents |
701 | +^^^^^^^^ |
702 | + |
703 | +This property is used to define the contents of the list item. Unlike the SDK |
704 | +list items which only assigning values to the text property, the contents allows |
705 | +you to define whatever content you so wish. In the example above, a Label is used |
706 | +to show content in the list item. This could very well be replaced with a column |
707 | +with multiple labels with whatever formatting you choose. For example, :: |
708 | + |
709 | + contents: Column { |
710 | + spacing: units.gu(2) |
711 | + anchors.fill: parent |
712 | + Label { |
713 | + id: title |
714 | + text: Test" |
715 | + font.bold: true |
716 | + } |
717 | + |
718 | + Label { |
719 | + id: subTitle |
720 | + text: "SubTitle |
721 | + } |
722 | + } |
723 | + |
724 | +.. _internalAnchors: |
725 | + |
726 | +internalAnchors |
727 | +^^^^^^^^^^^^^^^ |
728 | + |
729 | +Internal anchors allows you to define the anchors of the contents. The values are |
730 | +already defined by default, but if you so wish, you could change the anchors to |
731 | +better suit your application. For instance changing the top anchor of the contents |
732 | +can be done by, :: |
733 | + |
734 | + internalAnchors.topMargin: units.gu(0) |
735 | + |
736 | +.. _leftSideAction: |
737 | + |
738 | +leftSideAction |
739 | +^^^^^^^^^^^^^^ |
740 | + |
741 | +According to design, the left side of a list item can include only one action. An action |
742 | +can be defined easily by, :: |
743 | + |
744 | + Action { |
745 | + iconName: "add" |
746 | + text: "Add" |
747 | + onTriggered { |
748 | + doSomething() |
749 | + } |
750 | + } |
751 | + |
752 | + |
753 | +.. _rightSideActions: |
754 | + |
755 | +rightSideActions |
756 | +^^^^^^^^^^^^^^^^ |
757 | + |
758 | +On right side of a list item, one can include a list of actions. Obviously it would be |
759 | +recommended to not add more than 3 actions since space is limited. :: |
760 | + |
761 | + rightSideActions: [ |
762 | + Action { |
763 | + iconName: "alarm-clock" |
764 | + text: i18n.tr("Alarm") |
765 | + }, |
766 | + |
767 | + Action { |
768 | + iconName: "add" |
769 | + text: i18n.tr("Add") |
770 | + } |
771 | + ] |
772 | + |
773 | +.. _locked: |
774 | + |
775 | +locked |
776 | +^^^^^^ |
777 | + |
778 | +This property can be used to lock the actions of a list item (essentially enabling/disabling them). |
779 | + |
780 | +.. _triggerActionOnMouseRelease: |
781 | + |
782 | +triggerActionOnMouseRelease |
783 | +^^^^^^^^^^^^^^^^^^^^^^^^^^^ |
784 | + |
785 | +This property affects the right side actions behavior. If set to true, the user can swipe left to |
786 | +reveal the right side actions and execute an action by just hovering over it. By default, this is |
787 | +set to false meaning that the user needs to press on the action to trigger it. |
788 | |
789 | === added file 'docs/_images/listitemwithactions.png' |
790 | Binary files docs/_images/listitemwithactions.png 1970-01-01 00:00:00 +0000 and docs/_images/listitemwithactions.png 2014-11-12 16:25:42 +0000 differ |
791 | === modified file 'docs/index.rst' |
792 | --- docs/index.rst 2014-11-09 16:01:02 +0000 |
793 | +++ docs/index.rst 2014-11-12 16:25:42 +0000 |
794 | @@ -51,4 +51,5 @@ |
795 | _components/circleimage |
796 | _components/emptystate |
797 | _components/fastscroll |
798 | + _components/listitemwithactions |
799 | _components/pagewithbottomedge |
800 | |
801 | === modified file 'docs/release.rst' |
802 | --- docs/release.rst 2014-11-12 14:36:24 +0000 |
803 | +++ docs/release.rst 2014-11-12 16:25:42 +0000 |
804 | @@ -4,6 +4,7 @@ |
805 | **12th November 2014** |
806 | |
807 | * Fixed typos in the installation guide |
808 | +* Added ListItemWithActions component |
809 | |
810 | **9th November 2014** |
811 |