Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. Qt for Python
  4. Problem with custom ListView model and a custom item
QtWS25 Last Chance

Problem with custom ListView model and a custom item

Scheduled Pinned Locked Moved Solved Qt for Python
pyside
6 Posts 2 Posters 1.2k Views
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • T Offline
    T Offline
    Tauri
    wrote on last edited by Tauri
    #1

    Hi,
    I'm trying to create a custom ListView model, that each item has 3 properties, qml sees the correct number of items in the model and I can print each property value with Component.onCompleted: print(backend.model[0].property_name) but nothing is displayed in the ListView and I get "cannot assign [undefined] to QString" (same with QColor).

    main.py
    
    import sys
    import os
    
    from PySide6.QtCore import QObject, Property
    from PySide6.QtGui import QGuiApplication
    from PySide6.QtQml import QQmlApplicationEngine
    
    class ItemModel(QObject):
        def __init__(self, value1, value2):
            QObject.__init__(self)
            self._text_value = value1
            self._color_value = value2
    
        @Property(str)
        def text_value(self):
            return self._text_value
    
        @Property(str)
        def color_value(self):
            return self._color_value
    
    
    class ListModel(QObject):
        def __init__(self):
            QObject.__init__(self)
            self.list_of_items = []
    
        def add_item(self, value1, value2):
            item = ItemModel(value1, value2)
            self.list_of_items.append(item)
    
        @Property("QVariantList", constant=True)
        def model(self):
            return self.list_of_items
    
    
    class MainWindow(QObject):
        def __init__(self):
            QObject.__init__(self)
            self._model = ListModel()
            self.test_items()
    
        def test_items(self):
            self._model.add_item("First Item", "Green")
            self._model.add_item("Second Item", "Yellow")
    
        @Property("QVariantList", constant=True)
        def model(self):
            return self._model.model
    
    
    main = MainWindow()
    app = QGuiApplication(sys.argv)
    engine = QQmlApplicationEngine()
    
    engine.rootContext().setContextProperty("backend", main)
    
    cur_dir = os.path.dirname(__file__)
    engine.load(os.path.join(cur_dir, "main.qml"))
    
    if not engine.rootObjects():
        sys.exit(-1)
    
    running = app.exec_()
    sys.exit(running)
    
    
    main.qml
    
    import QtQuick
    import QtQuick.Controls
    
    ApplicationWindow {
        id: root
        width: 200
        height: 300
        visible: true
        title: "test"
    
        Component {
            id: delegateModel
            Text {text: model.text_value; color: model.color_value}
        }
    
        ListView {
            id: itemsListView
            anchors.fill: parent
            model: backend.model
            delegate: delegateModel
        }
    
        Connections {
            target: backend
        }
    
        Component.onCompleted: {
            print("1) text:"+backend.model[0].text_value+", color:"+backend.model[0].color_value)
            print("2) text:"+backend.model[1].text_value+", color:"+backend.model[1].color_value)
        }
    }
    

    From my understanding @Property(str) should have defined it for qml, but I'm kinda lost as to why this doesn't display.
    What am I missing? or not understanding properly? I also tried using QObject instead of QVariantList but got the same result.
    Not sure if it's relevant but I'm using PySide6 for this

    Also, would this approach allow me to update the model just by appending items to self.list_of_items? Or would I need to use a signal?

    Thanks in advance

    1 Reply Last reply
    0
    • T Tauri

      Hey @eyllanesc,

      Thanks for the response, I updated the post with some minimal code that produces the same errors for me and corrected the typos you mentioned.

      eyllanescE Offline
      eyllanescE Offline
      eyllanesc
      wrote on last edited by eyllanesc
      #4

      @Tauri If the model is a list then to access each element then you must use "modelData" which in your case will be an "ItemModel", and then you can access the qproperties:

      import QtQuick
      import QtQuick.Controls
      
      ApplicationWindow {
          id: root
          width: 200
          height: 300
          visible: true
          title: "test"
      
          Component {
              id: delegateModel
              Text {
                  text: model.modelData.text_value
                  color: model.modelData.color_value
              }
          }
      
          ListView {
              id: itemsListView
              anchors.fill: parent
              model: backend.model
              delegate: delegateModel
          }
      }
      

      Screenshot_20210212_234631.png

      Note: as expected, it was necessary that you provide an MRE to understand the cause of the error.

      If you want me to help you develop some work then you can write to my email: e.yllanescucho@gmal.com.

      1 Reply Last reply
      0
      • eyllanescE Offline
        eyllanescE Offline
        eyllanesc
        wrote on last edited by eyllanesc
        #2

        Could you provide a minimum reproducible code? where you include the imports as well as how you add elements to the model and export it. Maybe in those parts this is the error in addition to that it would help us to test your code in a simple way. So please edit your post and add that information

        In addition, it also corrects the TYPOS such as: modelDelagte and delagate

        If you want me to help you develop some work then you can write to my email: e.yllanescucho@gmal.com.

        1 Reply Last reply
        0
        • T Offline
          T Offline
          Tauri
          wrote on last edited by
          #3

          Hey @eyllanesc,

          Thanks for the response, I updated the post with some minimal code that produces the same errors for me and corrected the typos you mentioned.

          eyllanescE 1 Reply Last reply
          0
          • T Tauri

            Hey @eyllanesc,

            Thanks for the response, I updated the post with some minimal code that produces the same errors for me and corrected the typos you mentioned.

            eyllanescE Offline
            eyllanescE Offline
            eyllanesc
            wrote on last edited by eyllanesc
            #4

            @Tauri If the model is a list then to access each element then you must use "modelData" which in your case will be an "ItemModel", and then you can access the qproperties:

            import QtQuick
            import QtQuick.Controls
            
            ApplicationWindow {
                id: root
                width: 200
                height: 300
                visible: true
                title: "test"
            
                Component {
                    id: delegateModel
                    Text {
                        text: model.modelData.text_value
                        color: model.modelData.color_value
                    }
                }
            
                ListView {
                    id: itemsListView
                    anchors.fill: parent
                    model: backend.model
                    delegate: delegateModel
                }
            }
            

            Screenshot_20210212_234631.png

            Note: as expected, it was necessary that you provide an MRE to understand the cause of the error.

            If you want me to help you develop some work then you can write to my email: e.yllanescucho@gmal.com.

            1 Reply Last reply
            0
            • T Offline
              T Offline
              Tauri
              wrote on last edited by
              #5

              Thanks @eyllanesc! Works like a charm now.
              Is there a good learning source you can recommend for stuff like that? specifically having python as a backend to qml.
              Maybe I'm missing it but all I found in the docs are either qml with c++ examples, or just using purely pyside without working with python models/objects in qml directly.

              eyllanescE 1 Reply Last reply
              0
              • T Tauri

                Thanks @eyllanesc! Works like a charm now.
                Is there a good learning source you can recommend for stuff like that? specifically having python as a backend to qml.
                Maybe I'm missing it but all I found in the docs are either qml with c++ examples, or just using purely pyside without working with python models/objects in qml directly.

                eyllanescE Offline
                eyllanescE Offline
                eyllanesc
                wrote on last edited by
                #6

                @Tauri Read https://doc.qt.io/qt-5/qtquick-modelviewsdata-cppmodels.html#qvariantlist-based-model

                If you want me to help you develop some work then you can write to my email: e.yllanescucho@gmal.com.

                1 Reply Last reply
                0

                • Login

                • Login or register to search.
                • First post
                  Last post
                0
                • Categories
                • Recent
                • Tags
                • Popular
                • Users
                • Groups
                • Search
                • Get Qt Extensions
                • Unsolved