QML DelegateModel:从委托访问DelegateModel

时间:2018-12-10 09:50:58

标签: qt qml qtquick2 loader

我正在尝试创建具有不同委托和拖放功能的ListView。代表应装有装载器。

QML文档提供了一个不带加载器的ListView的工作示例: http://doc.qt.io/qt-5/qtquick-tutorials-dynamicview-dynamicview3-example.html

但是,使用加载程序时出现错误:无法读取未定义的属性'DelegateModel'

我不明白如何从加载程序访问DelegateModel。

高度赞赏该解决方案的提示!

main.qml:

select name, group_concat(type) as shape1Types, group_concat(type) as shape2Types 
from table 
where name = 'name1' 
  and shape1Types in (select type from table2 where shape = 'shape1') 
  and shape2Times in (select type from table3 where shape = 'shape2') 
group by name

TestDelegate.qml:

import QtQuick 2.7
import QtQuick.Controls 2.0
import QtQuick.Window 2.0
import QtQuick.Dialogs 1.1
import QtQml.Models 2.3

Window {
    id: mainroot

    visible: true
    width: 640
    height: 480

    Rectangle{
        id:viewContainer

        anchors.fill: parent

        DelegateModel {
            id: visualModel

            model: ListModel{
                id:m_model

                ListElement{
                    type:1
                    m_text :"Text1"
                }

                ListElement{
                    type:1
                    m_text :"Text2"
                }
            }

            delegate:        Loader{
                id:idLoader

                width: view.width
                height: childrenRect.height

                Component.onCompleted: {
                    switch(type){
                    case 1:
                        idLoader.setSource("TestDelegate.qml", {"m_text": m_text})
                        break;
                    }
                }
            }
        }

        ListView{
            id: view

            anchors.fill: parent
            spacing: 5

            model: visualModel
        }
    }
}

1 个答案:

答案 0 :(得分:1)

在Loader加载的文件中定义的项或通常与其他任何导入的.qml文件定义的项不应该直接依赖于主文件,因为id具有作用域,因此在您的情况下,最好公开属性:

╭------------------------------------------╮
|                   bool held        ------┿--->
|  TestDelegate     string m_text    ------┿--->
|  ============     DelegateModel md ------┿--->
|                   int index        ------┿--->
╰------------------------------------------╯

考虑到上述情况,解决方案如下:

main.qml

import QtQuick 2.7
import QtQuick.Window 2.0
import QtQml.Models 2.3

Window {
    id: mainroot
    visible: true
    width: 640
    height: 480

    Rectangle{
        id:viewContainer
        anchors.fill: parent

        DelegateModel {
            id: visualModel
            model: ListModel{
                id:m_model
                Component.onCompleted: {
                    for(var i=0; i< 40; i++){
                        m_model.append({"type": 1, "m_text": "Text" + i})
                    }
                }
            }
            delegate:
                Loader{
                id: idLoader
                width: view.width
                height: childrenRect.height
                property int index: DelegateModel.itemsIndex
                onIndexChanged: if(status == Loader.Ready) idLoader.item.index = index
                Component.onCompleted: {
                    switch(type){
                    case 1:
                        idLoader.setSource("TestDelegate.qml", {
                                               "m_text": m_text,
                                               "index": index,
                                               "md": visualModel
                                           })
                        break;
                    }
                }
            }
        }
        ListView{
            id: view
            anchors.fill: parent
            spacing: 5
            model: visualModel
        }
    }
}

TestDelegate.qml

import QtQuick 2.7
import QtQml.Models 2.3

MouseArea {
    id: dragArea
    property bool held: false
    property string m_text
    property DelegateModel md: null
    property int index : -1;
    anchors { left: parent.left; right: parent.right }
    height: 50
    width: view.width
    drag.target: held ? content : undefined
    drag.axis: Drag.YAxis
    onPressAndHold: held = true
    onReleased: held = false
    Rectangle {
        id: content
        anchors {
            horizontalCenter: parent.horizontalCenter
            verticalCenter: parent.verticalCenter
        }
        width: dragArea.width
        height: textfield.implicitHeight
        Drag.active: dragArea.held
        Drag.source: dragArea
        Drag.hotSpot.x: width / 2
        Drag.hotSpot.y: height / 2
        border.width: 1
        border.color: "lightsteelblue"
        color: dragArea.held ? "lightsteelblue" : "white"
        Behavior on color { ColorAnimation { duration: 100 } }
        radius: 2
        states: State {
            when: dragArea.held
            ParentChange { target: content; parent: viewContainer }
            AnchorChanges {
                target: content
                anchors { horizontalCenter: undefined; verticalCenter: undefined }
            }
        }
        Text{
            id: textfield
            anchors.centerIn: parent
            text: m_text
        }
    }
    DropArea {
        anchors { fill: parent; margins: 10 }
        onEntered: {
            if(md !== null)
                md.items.move(drag.source.index, dragArea.index)
        }
    }
}