如何使用带有自定义项 QML 的 ListView

How to use a ListView with custom item QML

我是QML的新手。我感谢互联网资源 accordion:

Item {
    default property var contentItem: null
    property string title: "panel"
    id: root
    Layout.fillWidth: true
    height: 30
    Layout.fillHeight: current
    property bool current: false
    ColumnLayout {

        anchors.fill: parent
        spacing: 0
        Rectangle {
            Drag.active: dragArea.drag.active
            id: bar
            Layout.fillWidth: true
            height: 30
            color:  root.current ? "#81BEF7" : "#CEECF5"
            Text {
                anchors.fill: parent
                anchors.margins: 10
                horizontalAlignment: Text.AlignLeft
                verticalAlignment: Text.AlignVCenter
                text: root.title
            }
            Text {
                anchors{
                    right: parent.right
                    top: parent.top
                    bottom: parent.bottom
                    margins: 10
                }
                horizontalAlignment: Text.AlignRight
                verticalAlignment: Text.AlignVCenter
                text: "^"
                rotation: root.current ? "180" : 0
            }
            MouseArea {
                id: dragArea
                anchors.fill: parent
                cursorShape: Qt.PointingHandCursor
                drag.axis: Drag.YAxis

                drag.target: root

                onReleased: {

                    root.Drag.drop()
                }
                onClicked: {
                    if (root.parent.current !== root) {

                        root.current = !root.current;

                        root.parent.currentItem = root;
                    }

                }
            }
        }
        Rectangle {
            id: container
            Layout.fillWidth: true
            anchors.top: bar.bottom
            implicitHeight: root.height - bar.height
            clip: true
            Behavior on implicitHeight {
                PropertyAnimation { duration: 100 }
            }
        }
        Component.onCompleted: {
            if(root.contentItem !== null)
               root.contentItem.parent = container;
        }
    }
}

PanelItem.qml

Window {
    visible: true
    width: 400; height: 400

        ColumnLayout {
            anchors.fill: parent
            spacing: 1
            id: test
            property var currentItem: null
            PanelItem {
                title: "Panel 1"
                Rectangle {
                    color: "orange"
                    anchors.fill: parent
                }
            }
            PanelItem {
                title: "Panel 2"
                Rectangle {
                    color: "lightgreen"
                    anchors.fill: parent
                }
            }
            PanelItem {
                title: "Panel 3"
                Rectangle {
                    color: "lightblue"
                    anchors.fill: parent
                }
            }
            PanelItem {
                title: "Panel 4"
                Rectangle {
                    color: "yellow"
                    anchors.fill: parent
                }
            }
            Item {
                Layout.fillWidth: true
                Layout.fillHeight: true
            }
        }
}

main.qml

但是,由于 "drag & drop" 技术,我希望能够 更改项目索引 (位置)。

我读到在列布局中更改索引不是很好也很容易。 所以我试图将我的手风琴放在 ListView 中,但我迷路了,它根本不起作用。

我试过类似的东西:

Window {
    visible: true
    width: 400; height: 400
    ListView {
        id: my_list
        anchors.fill: parent
        model: 14
        delegate: PanelItem {
                id: my_delegate
                title: "Panel 1"
                Rectangle {
                    color: "orange"
                    anchors.fill: parent
                }
        }
    }
}

main.qml

有人可以帮我解释一下我做错了什么吗?

非常感谢!

好的,这里有一些问题:

  1. 如果您的 PanelItem 不在 *Layout 中,则无法使用附加属性 Layout.*。因此,诸如 Line 5: Layout.fillWidth = true 之类的行将不起作用。使用width: parent.widthanchors { left: parent.left; right: parent.rigth }设置宽度。

  2. 我不推荐使用 default property var contentItem,因为这可能会导致一些遗忘的对象。您可以将多个 Items 分配给此默认值 属性,其中每个新的 Item 踢出前一个 Item

  3. 改用 property Component contentItem,例如 QtQuick.Controls 2.0。然后用一个Loader实例化这个Component,当PanelItem展开时
    如果不应动态加载和卸载,请使用 property Item contentItem
    使用不是 default 的属性确保,通常只有一个 Item 分配。
    通常只建议将 default propertyalias someItem.data 之类的东西一起使用。如果你使用 default property var someData 你应该听 onSomeDataChanged 并将新添加的对象重新分配给一些合适的容器。 所以如果你想允许添加多个Item,就这样:

example.qml

Item {
    default property alias contentItem.data
    Item {
        id: contentItem
        width: childrenRect.width
        height: childrenRect.height
    }
}

使用一些线,例如 implicitHeight: barHeight + contentItemHeight,其中 barHeight 是栏的高度,始终可见,而 contentItemHeight(collapsed ? 0 : loadedContentItem.height)

如果只是为了重新排序 Item,您可以使用 ObjectModel。那么你不应该提供委托,因为 ObjectModel 提供 delegate 本身 - 或者更确切地说是要显示的对象而不是委托。