Drag and Drop within a GridView: Difference between revisions

From Qt Wiki
Jump to navigation Jump to search
mNo edit summary
(Replaced code because copy/paste of previous code clearly went wrong, resulting in some parts being mixed up)
Line 30: Line 30:


'''IconItem.qml'''
'''IconItem.qml'''
<code>import QtQuick 1.0
import QtQuick 2.0
Component
 
Item
Component {
id: main
    Item {
width: grid.cellWidth; height: grid.cellHeight
    id: main
Image
    width: grid.cellWidth; height: grid.cellHeight
id: item; parent: loc
 
x: main.x + 5; y: main.y + 5
    Image {
width: main.width - 10; height: main.height - 10;
        id: item; parent: loc
fillMode: Image.PreserveAspectFit; smooth: true
        x: main.x + 5; y: main.y + 5
source: icon
        width: main.width - 10; height: main.height - 10;
Rectangle {
        fillMode: Image.PreserveAspectFit; smooth: true
anchors.fill: parent;
        source: icon
border.color: "#326487"; border.width: 6
 
color: "transparent"; radius: 5
        Rectangle {
visible: item.state "active"}
            anchors.fill: parent;
Behavior on x { enabled: item.state != "active"; NumberAnimation { duration: 400; easing.type: Easing.OutBack }
            border.color: "#326487"; border.width: 6
}
            color: "transparent"; radius: 5
Behavior on y { enabled: item.state != "active"; NumberAnimation { duration: 400; easing.type: Easing.OutBack }
            visible: item.state = "active"
}
        }
SequentialAnimation on rotation {NumberAnimation { to:  2; duration: 60 }
 
NumberAnimation { to: -2; duration: 120 }
        Behavior on x {
NumberAnimation { to:  0; duration: 60 }
            enabled: item.state != "active"
running: loc.currentId != -1 && item.state != "active"loops: Animation.Infinite; alwaysRunToEnd: true}
            NumberAnimation { duration: 400; easing.type: Easing.OutBack }
states: State {name: "active"; when: loc.currentId gridId
        }
PropertyChanges { target: item; x: loc.mouseX - width/2; y: loc.mouseY - height/2; scale: 0.5; z: 10 }
 
}
        Behavior on y {
transitions: Transition { NumberAnimation { property: "scale"; duration: 200} }
            enabled: item.state != "active"
}
            NumberAnimation { duration: 400; easing.type: Easing.OutBack }
}
        }
}
 
        SequentialAnimation on rotation {
            NumberAnimation { to:  2; duration: 60 }
            NumberAnimation { to: -2; duration: 120 }
            NumberAnimation { to:  0; duration: 60 }
            running: loc.currentId !== -1 && item.state !== "active"
            loops: Animation.Infinite; alwaysRunToEnd: true
        }
 
        states: State {
            name: "active"; when: loc.currentId === gridId
            PropertyChanges { target: item; x: loc.mouseX - width/2; y: loc.mouseY - height/2; scale: 0.5; z: 10 }
        }
 
        transitions: Transition { NumberAnimation { property: "scale"; duration: 200} }
        } //Image
    } //Item
} //Component
</code>
</code>


'''Main.qml'''
'''Main.qml'''
<code>
<code>
import QtQuick 1.0
import QtQuick 2.0
Rectangle {
import QtQuick.Controls 2.2
width: 640; height: 480
 
color: "#222222"
ApplicationWindow {
GridView {
    width: 640; height: 480
id: grid
    color: "#222222"
interactive: false
    visible: true
anchors
 
topMargin: 60; bottomMargin: 60
    GridView {
leftMargin: 140; rightMargin: 140
        id: grid
fill: parent
        interactive: false
}
        anchors.fill: parent
cellWidth: 120; cellHeight: 120;
        topMargin: 60
model: WidgetModel { id: icons }
        bottomMargin: 60
delegate: IconItem { }
        leftMargin: 140
MouseArea {
        rightMargin: 140
property int currentId: –1 // Original position in model
 
property int newIndex // Current Position in model
        cellWidth: 120
property int index: grid.indexAt(mouseX, mouseY) // Item underneath cursor
        cellHeight: 120
id: loc
        model: WidgetModel { id: icons }
anchors.fill: parent
        delegate: IconItem { }
onPressAndHold: currentId = icons.get(newIndex = index).gridId
    }
onReleased: currentId = –1
 
onMousePositionChanged:
    MouseArea {
if (loc.currentId [[Image:= -1 && index |= -1 && index ]]= –1 && index != newIndex)
        property int currentId: -1 // Original position in model
icons.move(newIndex, newIndex = index, 1)
        property int newIndex // Current Position in model
}
        property int index: grid.indexAt(mouseX, mouseY) // Item underneath cursor
 
        id: loc
        anchors.fill: parent
        onPressAndHold: currentId = icons.get(newIndex = index).gridId
        onReleased: currentId = -1
        onPositionChanged: {
            if (loc !== currentId && index !== -1 && index !== newIndex)
                icons.move(newIndex, newIndex = index, 1)
        }
    }
}
}
</code>
</code>

Revision as of 03:06, 8 March 2018

En Ar Bg De El Es Fa Fi Fr Hi Hu It Ja Kn Ko Ms Nl Pl Pt Ru Sq Th Tr Uk Zh

This wiki entry is created in response to a few forum threads (links at bottom) asking for this method. Feel free to contribute to this article with explanations or code.

Drag and Drop within a GridView

This example will demonstrate the iOS style (video here ) of dragging and dropping ListModel elements within a GridView.

There are three files in this example. One for the model (WidgetModel.qml), one for the delegate (IconItem.qml) and one for the GridView (Main.qml).

WidgetModel.qml

import QtQuick 1.0
ListModel {
ListElement { icon: "Images/widget1.png"; gridId: 0}
ListElement { icon: "Images/widget2.png"; gridId: 1}
ListElement { icon: "Images/widget3.png"; gridId: 2}
ListElement { icon: "Images/widget4.png"; gridId: 3}
ListElement { icon: "Images/widget5.png"; gridId: 4}
ListElement { icon: "Images/widget6.png"; gridId: 5}
ListElement { icon: "Images/widget7.png"; gridId: 6}
ListElement { icon: "Images/widget8.png"; gridId: 7}
ListElement { icon: "Images/widget9.png"; gridId: 8}
}

IconItem.qml import QtQuick 2.0

Component {

   Item {
   id: main
   width: grid.cellWidth; height: grid.cellHeight
   Image {
       id: item; parent: loc
       x: main.x + 5; y: main.y + 5
       width: main.width - 10; height: main.height - 10;
       fillMode: Image.PreserveAspectFit; smooth: true
       source: icon
       Rectangle {
           anchors.fill: parent;
           border.color: "#326487"; border.width: 6
           color: "transparent"; radius: 5
           visible: item.state = "active"
       }
       Behavior on x {
           enabled: item.state != "active"
           NumberAnimation { duration: 400; easing.type: Easing.OutBack }
       }
       Behavior on y {
           enabled: item.state != "active"
           NumberAnimation { duration: 400; easing.type: Easing.OutBack }
       }
       SequentialAnimation on rotation {
           NumberAnimation { to:  2; duration: 60 }
           NumberAnimation { to: -2; duration: 120 }
           NumberAnimation { to:  0; duration: 60 }
           running: loc.currentId !== -1 && item.state !== "active"
           loops: Animation.Infinite; alwaysRunToEnd: true
       }
       states: State {
           name: "active"; when: loc.currentId === gridId
           PropertyChanges { target: item; x: loc.mouseX - width/2; y: loc.mouseY - height/2; scale: 0.5; z: 10 }
       }
       transitions: Transition { NumberAnimation { property: "scale"; duration: 200} }
       } //Image
   } //Item

} //Component

Main.qml

import QtQuick 2.0
import QtQuick.Controls 2.2

ApplicationWindow {
    width: 640; height: 480
    color: "#222222"
    visible: true

    GridView {
        id: grid
        interactive: false
        anchors.fill: parent
        topMargin: 60
        bottomMargin: 60
        leftMargin: 140
        rightMargin: 140

        cellWidth: 120
        cellHeight: 120
        model: WidgetModel { id: icons }
        delegate: IconItem { }
    }

    MouseArea {
        property int currentId: -1 // Original position in model
        property int newIndex // Current Position in model
        property int index: grid.indexAt(mouseX, mouseY) // Item underneath cursor

        id: loc
        anchors.fill: parent
        onPressAndHold: currentId = icons.get(newIndex = index).gridId
        onReleased: currentId = -1
        onPositionChanged: {
            if (loc !== currentId && index !== -1 && index !== newIndex)
                icons.move(newIndex, newIndex = index, 1)
        }
    }
}


Video


Relevant forum threads:
iOS Style Rearrange of Icons