Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to access a ListView's ListModel's ListElement's mapped delegate's data in QML?

Tags:

javascript

qt

qml

Essentially, I have an usual ListView:

Rectangle {
    id: mylist

    ListModel {
        id: mylistModel
        ListElement {
            text: "blah1"
        }
        ListElement {
            text: "blah2"
        }
        ListElement {
            text: "blah3"
        }
    }

    Component {
        id: mylistDelegate

        Text {
            id: mylistDelegateText
            text: text
            property bool mylistDelegateTextEnabled: false
        }
    }

    ListView {
        id: mylistView
        model: mylistModel
        delegate: mylistDelegate
    }
}

Please ignore any problems I might have introduced by truncating the code to focus on what's important.

Anyway, now my problem is that I want to access a ListElement's assigned delegate and see what the value of mylistDelegateTextEnabled is in a javascript loop. For instance, this loop iterates over current list and gives me the text of the ListElements in the model:

for(var i = 0; i < mylistModel.count; ++i) {
    console.log(mylistModel.get(i).text);
}

This obviously works fine.

Now what I want is essentially this:

for(var i = 0; i < mylistModel.count; ++i) {
    console.log(mylistModel.get(i).text);
    console.log(mylistModel.get(i).delegate.mylistDelegateTextEnabled);
}

Alas, that it doesn't seem to be that easy.

Help appreciated.

like image 246
svenstaro Avatar asked Mar 19 '12 18:03

svenstaro


2 Answers

You can't access delegates in that way because they are transient objects that are created and destroyed at the discretion of the ListView. As explained in the documentation for delegates:

Delegates are instantiated as needed and may be destroyed at any time. State should never be stored in a delegate.

Is there a particular reason why you can't just add a textEnabled flag to the ListModel? For example:

import QtQuick 1.0

Rectangle {
    id: mylist
    width:300
    height:300

    ListModel {
        id: mylistModel
        ListElement {
            name: "blah1"
            textEnabled:false
        }
        ListElement {
            name: "blah2"
            textEnabled:false
        }
        ListElement {
            name: "blah3"
            textEnabled:false
        }
    }

    Component {
        id: mylistDelegate

        Text {
            id: mylistDelegateText
            text: name
            color: textEnabled?"red":"black"


            MouseArea {
                anchors.fill:parent;
                onClicked: {
                    mylistModel.setProperty(index, "textEnabled", !textEnabled);
                }
            }
        }
    }

    ListView {
        id: mylistView
        model: mylistModel
        delegate: mylistDelegate
        width:100;
        height:100

    }      
}
like image 94
Paul Drummond Avatar answered Oct 14 '22 13:10

Paul Drummond


Try this code:-

 for (var i = 0; i < mylistView.count; i ++) {
      // this will get list item at index i
      console.log(mylistView.contentItem.children[i]);

      // lets set it height to 100
      mylistView.contentItem.children[i].height=100;
   }

Hope this helps, cheers!!! @navi

like image 34
Navjot Singh Avatar answered Oct 14 '22 11:10

Navjot Singh