on xenial help sign in
improve listview animations and handling
0bcac19Michael Zanetti
qml/Stage/Spread/ScreensAndWorkspaces.qml+5−2
@@ -106,10 +106,13 @@ Item {
106 id: workspaces
106 id: workspaces
107 height: parent.height - header.height - units.gu(2)
107 height: parent.height - header.height - units.gu(2)
108 width: {
108 width: {
109+ var width = 0;
109 if (screensProxy.count == 1) {
110 if (screensProxy.count == 1) {
110− return Math.min(implicitWidth, root.width - units.gu(8));
111+ width = Math.min(implicitWidth, root.width - units.gu(8));
112+ } else {
113+ width = Math.min(implicitWidth, model.screen.active ? root.width - units.gu(48) : units.gu(40))
111 }
114 }
112− return Math.min(implicitWidth, model.screen.active ? root.width - units.gu(48) : units.gu(40))
115+ return Math.max(workspaces.minimumWidth, width);
113 }
116 }
114
117
115 Behavior on width { UbuntuNumberAnimation {} }
118 Behavior on width { UbuntuNumberAnimation {} }
qml/Stage/Spread/Workspaces.qml+273−251
@@ -7,6 +7,10 @@ import "../../Components"
7Item {
7Item {
8 id: root
8 id: root
9 implicitWidth: listView.contentWidth
9 implicitWidth: listView.contentWidth
10+ readonly property int minimumWidth: {
11+ var count = Math.min(3, listView.count);
12+ return listView.itemWidth * count + listView.spacing * (count - 1)
13+ }
10
14
11 property QtObject screen: null
15 property QtObject screen: null
12 property alias workspaceModel: listView.model
16 property alias workspaceModel: listView.model
@@ -71,309 +75,327 @@ Item {
71 }
75 }
72 }
76 }
73
77
74− ListView {
78+ Item {
75− id: listView
79+ // We need to clip the listview as it has left/right margins and it would
80+ // overlap with items next to it and eat mouse input. However, we can't
81+ // just clip at the actual bounds as the delegates have the close button
82+ // on hover which reaches a bit outside, so lets some margins for the clipping
76 anchors.fill: parent
83 anchors.fill: parent
84+ anchors.margins: -units.gu(2)
85+ clip: true
86+
87+ ListView {
88+ id: listView
89+ anchors {
90+ fill: parent
91+ topMargin: -parent.anchors.margins
92+ bottomMargin: -parent.anchors.margins
77− anchors.leftMargin: -itemWidth
93+ leftMargin: -itemWidth - parent.anchors.margins
78− anchors.rightMargin: -itemWidth
94+ rightMargin: -itemWidth - parent.anchors.margins
95+ }
79− boundsBehavior: Flickable.StopAtBounds
96+ boundsBehavior: Flickable.StopAtBounds
80−
81− orientation: ListView.Horizontal
82− spacing: units.gu(1)
83− leftMargin: itemWidth
84− rightMargin: itemWidth
85−
86− property var screenSize: screen.availableModes[screen.currentModeIndex].size
87− property int itemWidth: height * screenSize.width / screenSize.height
88− property int foldingAreaWidth: units.gu(10)
89− property real realContentX: contentX - originX + leftMargin
90− property int dropItemIndex: -1
91− property int hoveredWorkspaceIndex: -1
92− property string hoveredHalf: "" // left or right
93−
94− function getDropIndex(drag) {
95− var coords = mapToItem(listView.contentItem, drag.x, drag.y)
96− var index = Math.floor((drag.x + listView.realContentX) / (listView.itemWidth + listView.spacing));
97− if (index < 0) index = 0;
98− var upperLimit = dropItemIndex == -1 ? listView.count : listView.count - 1
99− if (index > upperLimit) index = upperLimit;
100− return index;
101− }
102
97
103− function updateDropProperties(drag) {
98+ Behavior on contentX {
104− var coords = mapToItem(listView.contentItem, drag.x, drag.y)
99+ SmoothedAnimation { duration: 200 }
105− var index = Math.floor(drag.x + listView.realContentX) / (listView.itemWidth + listView.spacing);
106− if (index < 0) {
107− listView.hoveredWorkspaceIndex = -1;
108− listView.hoveredHalf = "";
109− return;
110 }
100 }
111
101
112− var upperLimit = dropItemIndex == -1 ? listView.count : listView.count - 1
102+ orientation: ListView.Horizontal
113− if (index > upperLimit) index = upperLimit;
103+ spacing: units.gu(1)
114− listView.hoveredWorkspaceIndex = index;
104+ leftMargin: itemWidth
115− print("updating drag:", (drag.x + listView.realContentX) % (listView.itemWidth + listView.spacing))
105+ rightMargin: itemWidth
116− var pixelsInTile = (drag.x + listView.realContentX) % (listView.itemWidth + listView.spacing);
117− listView.hoveredHalf = (pixelsInTile / listView.itemWidth) < .5 ? "left" : "right";
118− }
119
106
120− function progressiveScroll(mouseX) {
107+ property var screenSize: screen.availableModes[screen.currentModeIndex].size
121− var progress = Math.max(0, Math.min(1, (mouseX - listView.foldingAreaWidth) / (width - listView.leftMargin * 2 - listView.foldingAreaWidth * 2)))
108+ property int itemWidth: height * screenSize.width / screenSize.height
122− listView.contentX = listView.originX + (listView.contentWidth - listView.width + listView.leftMargin + listView.rightMargin) * progress - listView.leftMargin
109+ property int foldingAreaWidth: itemWidth / 2
123− }
110+ property int maxAngle: 40
124
111
125− displaced: Transition { UbuntuNumberAnimation { properties: "x" } }
112+ property real realContentX: contentX - originX + leftMargin
113+ property int dropItemIndex: -1
114+ property int hoveredWorkspaceIndex: -1
115+ property string hoveredHalf: "" // left or right
116+
117+ function getDropIndex(drag) {
118+ var coords = mapToItem(listView.contentItem, drag.x, drag.y)
119+ var index = Math.floor((drag.x + listView.realContentX) / (listView.itemWidth + listView.spacing));
120+ if (index < 0) index = 0;
121+ var upperLimit = dropItemIndex == -1 ? listView.count : listView.count - 1
122+ if (index > upperLimit) index = upperLimit;
123+ return index;
124+ }
126
125
127− delegate: Item {
126+ function updateDropProperties(drag) {
128− id: workspaceDelegate
127+ var coords = mapToItem(listView.contentItem, drag.x, drag.y)
129− objectName: "delegate" + index
128+ var index = Math.floor(drag.x + listView.realContentX) / (listView.itemWidth + listView.spacing);
130− height: parent.height
129+ if (index < 0) {
131− width: listView.itemWidth
130+ listView.hoveredWorkspaceIndex = -1;
132− Behavior on width { UbuntuNumberAnimation {} }
131+ listView.hoveredHalf = "";
133− visible: listView.dropItemIndex !== index
132+ return;
133+ }
134
134
135+ var upperLimit = dropItemIndex == -1 ? listView.count : listView.count - 1
136+ if (index > upperLimit) index = upperLimit;
137+ listView.hoveredWorkspaceIndex = index;
135− property int itemX: -listView.realContentX + index * (listView.itemWidth + listView.spacing)
138+ print("updating drag:", (drag.x + listView.realContentX) % (listView.itemWidth + listView.spacing))
136− property int distanceFromLeft: itemX //- listView.leftMargin
139+ var pixelsInTile = (drag.x + listView.realContentX) % (listView.itemWidth + listView.spacing);
137− property int distanceFromRight: listView.width - listView.leftMargin - listView.rightMargin - itemX - listView.itemWidth
140+ listView.hoveredHalf = (pixelsInTile / listView.itemWidth) < .5 ? "left" : "right";
141+ }
138
142
139− property int maxAngle: 40
143+ function progressiveScroll(mouseX) {
144+ var progress = Math.max(0, Math.min(1, (mouseX - listView.itemWidth) / (width - listView.leftMargin * 2 - listView.itemWidth * 2)))
145+ listView.contentX = listView.originX + (listView.contentWidth - listView.width + listView.leftMargin + listView.rightMargin) * progress - listView.leftMargin
146+ }
147+
148+ displaced: Transition { UbuntuNumberAnimation { properties: "x" } }
140
149
150+ delegate: Item {
151+ id: workspaceDelegate
152+ objectName: "delegate" + index
153+ height: parent.height
154+ width: listView.itemWidth
155+ Behavior on width { UbuntuNumberAnimation {} }
156+ visible: listView.dropItemIndex !== index
157+
158+ property int itemX: -listView.realContentX + index * (listView.itemWidth + listView.spacing)
159+ property int distanceFromLeft: itemX //- listView.leftMargin
160+ property int distanceFromRight: listView.width - listView.leftMargin - listView.rightMargin - itemX - listView.itemWidth
161+
141− property int itemAngle: {
162+ property int itemAngle: {
142− if (index == 0) {
163+ if (index == 0) {
143− if (distanceFromLeft < 0) {
164+ if (distanceFromLeft < 0) {
144− var progress = (distanceFromLeft + listView.foldingAreaWidth) / listView.foldingAreaWidth
165+ var progress = (distanceFromLeft + listView.foldingAreaWidth) / listView.foldingAreaWidth
145− return MathUtils.linearAnimation(1, -1, 0, maxAngle, Math.max(-1, Math.min(1, progress)));
166+ return MathUtils.linearAnimation(1, -1, 0, listView.maxAngle, Math.max(-1, Math.min(1, progress)));
167+ }
168+ return 0
146 }
169 }
147− return 0
148− }
149− if (index == listView.count - 1) {
170+ if (index == listView.count - 1) {
150− if (distanceFromRight < 0) {
171+ if (distanceFromRight < 0) {
151− var progress = (distanceFromRight + listView.foldingAreaWidth) / listView.foldingAreaWidth
172+ var progress = (distanceFromRight + listView.foldingAreaWidth) / listView.foldingAreaWidth
152− return MathUtils.linearAnimation(1, -1, 0, -maxAngle, Math.max(-1, Math.min(1, progress)));
173+ return MathUtils.linearAnimation(1, -1, 0, -listView.maxAngle, Math.max(-1, Math.min(1, progress)));
174+ }
175+ return 0
153 }
176 }
154− return 0
155− }
156
177
157− if (distanceFromLeft < listView.foldingAreaWidth) {
178+ if (distanceFromLeft < listView.foldingAreaWidth) {
158− // itemX : 10gu = p : 100
179+ // itemX : 10gu = p : 100
159− var progress = distanceFromLeft / listView.foldingAreaWidth
180+ var progress = distanceFromLeft / listView.foldingAreaWidth
160− return MathUtils.linearAnimation(1, -1, 0, maxAngle, Math.max(-1, Math.min(1, progress)));
181+ return MathUtils.linearAnimation(1, -1, 0, listView.maxAngle, Math.max(-1, Math.min(1, progress)));
161− }
162− if (distanceFromRight < listView.foldingAreaWidth) {
163− var progress = distanceFromRight / listView.foldingAreaWidth
164− return MathUtils.linearAnimation(1, -1, 0, -maxAngle, Math.max(-1, Math.min(1, progress)));
165− }
166− return 0
167− }
168−
169− property int itemOffset: {
170− var rotationOffset = (1 - Math.cos(itemAngle * Math.PI / 360)) * listView.itemWidth
171− if (index == 0) {
172− if (distanceFromLeft < 0) {
173− return -distanceFromLeft - rotationOffset
174 }
182 }
175− return 0
176− }
177− if (index == listView.count - 1) {
178− if (distanceFromRight < 0) {
183+ if (distanceFromRight < listView.foldingAreaWidth) {
179− return distanceFromRight + rotationOffset
184+ var progress = distanceFromRight / listView.foldingAreaWidth
185+ return MathUtils.linearAnimation(1, -1, 0, -listView.maxAngle, Math.max(-1, Math.min(1, progress)));
180 }
186 }
181 return 0
187 return 0
182 }
188 }
183
189
184− if (itemX < -listView.foldingAreaWidth) {
190+ property int itemOffset: {
185− return -itemX - rotationOffset
191+ if (index == 0) {
192+ if (distanceFromLeft < 0) {
193+ return -distanceFromLeft
194+ }
195+ return 0
186− }
196+ }
187− if (distanceFromLeft < listView.foldingAreaWidth) {
197+ if (index == listView.count - 1) {
188− return (listView.foldingAreaWidth - distanceFromLeft) / 2 - rotationOffset
198+ if (distanceFromRight < 0) {
199+ return distanceFromRight
200+ }
201+ return 0
189− }
202+ }
190
203
191− if (distanceFromRight < -listView.foldingAreaWidth) {
204+ if (itemX < -listView.foldingAreaWidth) {
192− return distanceFromRight + rotationOffset
205+ return -itemX
206+ }
207+ if (distanceFromLeft < listView.foldingAreaWidth) {
208+ return (listView.foldingAreaWidth - distanceFromLeft) / 2
193− }
209+ }
194
210
195− if (distanceFromRight < listView.foldingAreaWidth) {
211+ if (distanceFromRight < -listView.foldingAreaWidth) {
196− return -(listView.foldingAreaWidth - distanceFromRight) / 2 + rotationOffset
212+ return distanceFromRight
197− }
213+ }
198
214
199− return 0
215+ if (distanceFromRight < listView.foldingAreaWidth) {
216+ return -(listView.foldingAreaWidth - distanceFromRight) / 2
200− }
217+ }
201
218
202−// onItemXChanged: if (index == 1) print("x", itemX, listView.contentX)
219+ return 0
203−
204− z: itemOffset < 0 ? itemOffset : -itemOffset
205− transform: [
206− Rotation {
207− angle: itemAngle
208− axis { x: 0; y: 1; z: 0 }
209− origin { x: itemAngle < 0 ? listView.itemWidth : 0; y: height / 2 }
210− },
211− Translate {
212− x: itemOffset
213 }
220 }
214− ]
215
221
222+ // onItemXChanged: if (index == 1) print("x", itemX, listView.contentX)
223+
224+ z: itemOffset < 0 ? itemOffset : -itemOffset
225+ transform: [
226+ Rotation {
227+ angle: itemAngle
228+ axis { x: 0; y: 1; z: 0 }
229+ origin { x: itemAngle < 0 ? listView.itemWidth : 0; y: height / 2 }
230+ },
231+ Translate {
232+ x: itemOffset
233+ }
234+ ]
235+
216− WorkspacePreview {
236+ WorkspacePreview {
217− height: listView.height
237+ height: listView.height
218− width: listView.itemWidth
238+ width: listView.itemWidth
219− background: root.background
239+ background: root.background
220− screenHeight: screen.availableModes[screen.currentModeIndex].size.height
240+ screenHeight: screen.availableModes[screen.currentModeIndex].size.height
221− containsDragLeft: listView.hoveredWorkspaceIndex == index && listView.hoveredHalf == "left"
241+ containsDragLeft: listView.hoveredWorkspaceIndex == index && listView.hoveredHalf == "left"
222− containsDragRight: listView.hoveredWorkspaceIndex == index && listView.hoveredHalf == "right"
242+ containsDragRight: listView.hoveredWorkspaceIndex == index && listView.hoveredHalf == "right"
223− isActive: model.workspace.active
243+ isActive: model.workspace.active
224− }
225− MouseArea {
226− anchors.fill: parent
227− onClicked: {
228− model.workspace.activate();
229 }
244 }
245+ MouseArea {
246+ anchors.fill: parent
247+ onClicked: {
248+ print("clickkkked!")
249+ model.workspace.activate();
250+ }
230− onDoubleClicked: {
251+ onDoubleClicked: {
231− model.workspace.activate();
252+ model.workspace.activate();
232− root.closeSpread();
253+ root.closeSpread();
254+ }
233 }
255 }
234− }
235
256
236− MouseArea {
257+ MouseArea {
237− id: closeMouseArea
258+ id: closeMouseArea
238− objectName: "closeMouseArea"
259+ objectName: "closeMouseArea"
239− anchors { left: parent.left; top: parent.top; leftMargin: -height / 2; topMargin: -height / 2 }
260+ anchors { left: parent.left; top: parent.top; leftMargin: -height / 2; topMargin: -height / 2 }
240− hoverEnabled: true
261+ hoverEnabled: true
241− height: units.gu(4)
262+ height: units.gu(4)
242− width: height
263+ width: height
243−
264+
244− onClicked: {
265+ onClicked: {
245− model.workspace.unassign();
266+ model.workspace.unassign();
246− root.commitScreenSetup();
267+ root.commitScreenSetup();
247− }
268+ }
248− Image {
269+ Image {
249− id: closeImage
270+ id: closeImage
250− source: "../graphics/window-close.svg"
271+ source: "../graphics/window-close.svg"
251− anchors.fill: closeMouseArea
272+ anchors.fill: closeMouseArea
252− anchors.margins: units.gu(1)
273+ anchors.margins: units.gu(1)
253− sourceSize.width: width
274+ sourceSize.width: width
254− sourceSize.height: height
275+ sourceSize.height: height
255− readonly property var mousePos: hoverMouseArea.mapToItem(workspaceDelegate, hoverMouseArea.mouseX, hoverMouseArea.mouseY)
276+ readonly property var mousePos: hoverMouseArea.mapToItem(workspaceDelegate, hoverMouseArea.mouseX, hoverMouseArea.mouseY)
256− readonly property bool shown: (hoverMouseArea.containsMouse || parent.containsMouse)
277+ readonly property bool shown: (hoverMouseArea.containsMouse || parent.containsMouse)
257− && mousePos.y < workspaceDelegate.width / 4
278+ && mousePos.y < workspaceDelegate.width / 4
258− && mousePos.y > -units.gu(2)
279+ && mousePos.y > -units.gu(2)
259− && mousePos.x > -units.gu(2)
280+ && mousePos.x > -units.gu(2)
260− && mousePos.x < workspaceDelegate.height / 4
281+ && mousePos.x < workspaceDelegate.height / 4
261− opacity: shown ? 1 : 0
282+ opacity: shown ? 1 : 0
262− visible: opacity > 0
283+ visible: opacity > 0
263− Behavior on opacity { UbuntuNumberAnimation { duration: UbuntuAnimation.SnapDuration } }
284+ Behavior on opacity { UbuntuNumberAnimation { duration: UbuntuAnimation.SnapDuration } }
264
285
286+ }
265 }
287 }
266 }
288 }
267− }
268
289
269− MouseArea {
290+ MouseArea {
270− id: hoverMouseArea
291+ id: hoverMouseArea
271− anchors.fill: parent
292+ anchors.fill: parent
272− hoverEnabled: true
293+ hoverEnabled: true
273− propagateComposedEvents: true
294+ propagateComposedEvents: true
274− anchors.leftMargin: listView.leftMargin
295+ anchors.leftMargin: listView.leftMargin
275− anchors.rightMargin: listView.rightMargin
296+ anchors.rightMargin: listView.rightMargin
276
297
277− property int draggedIndex: -1
298+ property int draggedIndex: -1
278
299
279− property int startX: 0
300+ property int startX: 0
280− property int startY: 0
301+ property int startY: 0
281
302
282− onMouseXChanged: {
303+ onMouseXChanged: {
283− if (!pressed || dragging) {
304+ if (!pressed || dragging) {
284− listView.progressiveScroll(mouseX)
305+ listView.progressiveScroll(mouseX)
306+ }
285 }
307 }
286− }
287− onMouseYChanged: {
308+ onMouseYChanged: {
288− if (Math.abs(mouseY - startY) > units.gu(3)) {
309+ if (Math.abs(mouseY - startY) > units.gu(3)) {
289− drag.axis = Drag.XAndYAxis;
310+ drag.axis = Drag.XAndYAxis;
311+ }
290 }
312 }
291− }
292
313
293− onReleased: {
314+ onReleased: {
294− var result = fakeDragItem.Drag.drop();
315+ var result = fakeDragItem.Drag.drop();
295−// if (result == Qt.IgnoreAction) {
316+ // if (result == Qt.IgnoreAction) {
296−// WorkspaceManager.destroyWorkspace(fakeDragItem.workspace);
317+ // WorkspaceManager.destroyWorkspace(fakeDragItem.workspace);
297−// }
318+ // }
298− root.commitScreenSetup();
319+ root.commitScreenSetup();
299− drag.target = null;
320+ drag.target = null;
300− }
321+ }
301
322
302− property bool dragging: drag.active
323+ property bool dragging: drag.active
303− onDraggingChanged: {
324+ onDraggingChanged: {
304− if (drag.active) {
325+ if (drag.active) {
305− print("drai", draggedIndex)
326+ print("drai", draggedIndex)
306− var ws = listView.model.get(draggedIndex);
327+ var ws = listView.model.get(draggedIndex);
307− print("ws:", ws)
328+ print("ws:", ws)
308− ws.unassign();
329+ ws.unassign();
309−// listView.model.remove(draggedIndex, 1)
330+ // listView.model.remove(draggedIndex, 1)
331+ }
310 }
332 }
311− }
312
333
313− onPressed: {
334+ onPressed: {
314− startX = mouseX;
335+ startX = mouseX;
315− startY = mouseY;
336+ startY = mouseY;
316− if (listView.model.count < 2) return;
337+ if (listView.model.count < 2) return;
317
338
318− var coords = mapToItem(listView.contentItem, mouseX, mouseY)
339+ var coords = mapToItem(listView.contentItem, mouseX, mouseY)
319− draggedIndex = listView.indexAt(coords.x, coords.y)
340+ draggedIndex = listView.indexAt(coords.x, coords.y)
320− var clickedItem = listView.itemAt(coords.x, coords.y)
341+ var clickedItem = listView.itemAt(coords.x, coords.y)
321
342
322− var itemCoords = clickedItem.mapToItem(listView, -listView.leftMargin, 0);
343+ var itemCoords = clickedItem.mapToItem(listView, -listView.leftMargin, 0);
323− fakeDragItem.x = itemCoords.x
344+ fakeDragItem.x = itemCoords.x
324− fakeDragItem.y = itemCoords.y
345+ fakeDragItem.y = itemCoords.y
325− fakeDragItem.workspace = listView.model.get(draggedIndex)
346+ fakeDragItem.workspace = listView.model.get(draggedIndex)
326
347
327− var mouseCoordsInItem = mapToItem(clickedItem, mouseX, mouseY);
348+ var mouseCoordsInItem = mapToItem(clickedItem, mouseX, mouseY);
328− fakeDragItem.Drag.hotSpot.x = mouseCoordsInItem.x
349+ fakeDragItem.Drag.hotSpot.x = mouseCoordsInItem.x
329− fakeDragItem.Drag.hotSpot.y = mouseCoordsInItem.y
350+ fakeDragItem.Drag.hotSpot.y = mouseCoordsInItem.y
330
351
331− drag.axis = Drag.YAxis;
352+ drag.axis = Drag.YAxis;
332− drag.target = fakeDragItem;
353+ drag.target = fakeDragItem;
333− }
354+ }
334
355
335− WorkspacePreview {
356+ WorkspacePreview {
336− id: fakeDragItem
357+ id: fakeDragItem
337− height: listView.height
358+ height: listView.height
338− width: listView.itemWidth
359+ width: listView.itemWidth
339− background: root.background
360+ background: root.background
340− screenHeight: screen.availableModes[screen.currentModeIndex].size.height
361+ screenHeight: screen.availableModes[screen.currentModeIndex].size.height
341− visible: Drag.active
362+ visible: Drag.active
342
363
343− Drag.active: hoverMouseArea.drag.active
364+ Drag.active: hoverMouseArea.drag.active
344− Drag.keys: ['workspace']
365+ Drag.keys: ['workspace']
345
366
346− property var workspace
367+ property var workspace
347− property bool inDropArea: false
368+ property bool inDropArea: false
348
369
349− Rectangle {
350− anchors.fill: parent
351− color: "#33000000"
352− opacity: parent.inDropArea ? 0 : 1
353− Behavior on opacity { UbuntuNumberAnimation { } }
354 Rectangle {
370 Rectangle {
355− anchors.centerIn: parent
371+ anchors.fill: parent
372+ color: "#33000000"
373+ opacity: parent.inDropArea ? 0 : 1
374+ Behavior on opacity { UbuntuNumberAnimation { } }
375+ Rectangle {
376+ anchors.centerIn: parent
356− width: units.gu(6)
377+ width: units.gu(6)
357− height: units.gu(6)
378+ height: units.gu(6)
358− radius: width / 2
379+ radius: width / 2
359− color: "#aa000000"
380+ color: "#aa000000"
381+ }
382+
383+ Icon {
384+ height: units.gu(3)
385+ width: height
386+ anchors.centerIn: parent
387+ name: "edit-delete"
388+ color: "white"
389+ }
360 }
390 }
361
391
362− Icon {
392+ states: [
363− height: units.gu(3)
393+ State {
364− width: height
394+ when: fakeDragItem.Drag.active
365− anchors.centerIn: parent
395+ ParentChange { target: fakeDragItem; parent: shell }
366− name: "edit-delete"
396+ }
367− color: "white"
397+ ]
368− }
369 }
398 }
370−
371− states: [
372− State {
373− when: fakeDragItem.Drag.active
374− ParentChange { target: fakeDragItem; parent: shell }
375− }
376− ]
377 }
399 }
378 }
400 }
379 }
401 }