从 Delegate 访问 Listview currentIndex

Posted

技术标签:

【中文标题】从 Delegate 访问 Listview currentIndex【英文标题】:Access Listview currentIndex from Delegate 【发布时间】:2015-08-12 13:03:33 【问题描述】:

我有一个 QML ListView,委托从另一个文件加载它的组件。单击委托项目时,我想更新ListViewCurrentIndexhighlight 选择的项目。

当我明确设置ListViewid 时,它起作用了。但是,由于我想将委托的 Component 也用于其他 ListViews,因此我正在努力寻找一种通用方法,如何从委托 Component 中访问 ListView.currentIndex

代码如下:

ma​​in.qml

import QtQuick 2.4
import QtQuick.Controls 1.3
import QtQuick.Window 2.2
import QtQuick.Dialogs 1.2

ApplicationWindow 
    title: qsTr("Hello World")
    width: 640
    height: 480
    visible: true

    ListModel 
        id: contactsModel
        ListElement 
            name: "Bill Smith"
        
        ListElement 
            name: "John Brown"
        
        ListElement 
            name: "Sam Wise"
        
    

    ListView
        id: contactsView
        anchors.left: parent.left
        anchors.top: parent.top
        width: parent.width
        height: parent.height
        orientation: Qt.Vertical
        spacing: 10
        model: contactsModel
        delegate: Contact
    

Contact.qml(委托使用的组件)

import QtQuick 2.0

Component
    id: contact
    Rectangle
        width: 200
        height: 50
        color: ListView.isCurrentItem ? "#003366" : "#585858"
        border.color: "gray"
        border.width: 1

        MouseArea
            anchors.fill: parent
            onClicked: 
                ListView.currentIndex = index; // <---- does not work
                //  contactsView.currentIndex = index; // <---- Works
            
        

        Text
            anchors.centerIn: parent
            color: "white"
            text: name
        
    

非常感谢任何帮助!

【问题讨论】:

【参考方案1】:

这里有两个问题:

您需要使用访问它们的项目名称来限定ListView 的附加属性。 currentIndex 属性是 a property of the ListView item type,而不是 attached property object。

要同时修复它们,首先要更改:

ListView.currentIndex = index;

到这里:

delegate.ListView.view.currentIndex = index;

然后给你的代表一个id

Component 
    id: contact

    Rectangle 
        id: delegate
    // ...

文档的Example Usage 部分(部分)证明了这一点:

ListView 将许多属性附加到委托的根项,例如 ListView:isCurrentItem。在下面的示例中,根委托项可以直接以 ListView.isCurrentItem 访问此附加属性,而子 contactInfo 对象必须将此属性引用为 wrapper.ListView.isCurrentItem。

【讨论】:

【参考方案2】:

使用附加属性ListView.view

此附加属性包含管理此委托的视图 实例

小例子:

import QtQuick 2.4
import QtQuick.Window 2.2
import QtQuick.Layouts 1.1

Window 
    width: 600
    height: 400
    visible: true

    Component 
        id: listDelegate
        Rectangle 
            height: 30
            width: parent.width
            color:  ListView.isCurrentItem ? "orange" : "white"
            property var view: ListView.view
            property int itemIndex: index
            Text  anchors.centerIn: parent; text: name 
            MouseArea 
                anchors.fill: parent
                onClicked: 
                    view.currentIndex = itemIndex;
                
            
        
    

    RowLayout 
        anchors.fill: parent
        ListView 
            Layout.minimumWidth: parent.width / 2
            Layout.fillHeight: true
            model: ListModel 
                ListElement name: "item1.1"
                ListElement name: "item1.2"
                ListElement name: "item1.3"
            
            delegate: listDelegate
        
        ListView 
            Layout.minimumWidth: parent.width / 2
            Layout.fillHeight: true
            model: ListModel 
                ListElement name: "item2.1"
                ListElement name: "item2.2"
                ListElement name: "item2.3"
            
            delegate: listDelegate
        
    

【讨论】:

以上是关于从 Delegate 访问 Listview currentIndex的主要内容,如果未能解决你的问题,请参考以下文章

使用 TableView 作为 ListView-delegate

在 QML ListView 中显示 QVariantList 并根据类型使用不同的 Delegate

如何从 UI 测试访问 App Delegate?

如何从app delegate访问NSViewController?

如何从另一个对象访问我的 Application Delegate 的窗口访问器方法?

如何从二进制访问 App Delegate? [关闭]