Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Best Practice to Add Dynamic QML from C++ data
Forum Updated to NodeBB v4.3 + New Features

Best Practice to Add Dynamic QML from C++ data

Scheduled Pinned Locked Moved Solved General and Desktop
27 Posts 4 Posters 13.4k Views 2 Watching
  • 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.
  • P Offline
    P Offline
    p3c0
    Moderators
    wrote on 22 Sept 2016, 07:38 last edited by
    #21

    @Placeable I have done something similar my project here. So what that particular code does is it creates a QQuickItem from a base QML template as shown here. Then sets some color and font on it. So you can try to do something similar. But remember QQmlComponent requires QQmlEngine. This is the same with which you must have loaded the QML initially. Also remember that dynamic QQuickItem also requires a visual parent which is set using setParent.

    157

    P 1 Reply Last reply 22 Sept 2016, 08:21
    0
    • P p3c0
      22 Sept 2016, 07:38

      @Placeable I have done something similar my project here. So what that particular code does is it creates a QQuickItem from a base QML template as shown here. Then sets some color and font on it. So you can try to do something similar. But remember QQmlComponent requires QQmlEngine. This is the same with which you must have loaded the QML initially. Also remember that dynamic QQuickItem also requires a visual parent which is set using setParent.

      P Offline
      P Offline
      Placeable
      wrote on 22 Sept 2016, 08:21 last edited by Placeable
      #22

      @p3c0 This is great, I like how to create QML from CPP. I came up with a different solution though which I think works but not sure if it is "best practice" - I'd like to experiment the way you did it as well.

      Here's how I have done it now to create "dynamic" Texts in QML from CPP data:

      In my QAbstractListModel data function I have this field that returns a QVariant:

      case TextData:
              return QVariant::fromValue( someData.textList() );
      break;
      

      The implementation of that returns a QList of QObject:

      QList<QObject*> SomeData::textList() const {
          return mTextList;
      }
      

      I can populate this QList with my TextData class that derives QObject

      TextData.cpp:

      class TextData : public QObject {
          Q_OBJECT
      
          Q_PROPERTY(QString text READ testString WRITE setTestString NOTIFY testStringChanged)
      
      public:
          explicit TextData(QObject *parent = 0);
      
          QString testString() const;
          void setTestString(const QString &testString);
      
      signals:
          void testStringChanged(QString);
      
      private:
          QString mTestString;
      };
      

      Then in QML I can do something like this now to create QML Texts and populate them from the CPP data:

      Component.onCompleted: {
          var arr = model.textData;
          var component = Qt.createComponent("SomeTextLayout.qml");
          for ( var i = 0; i < arr.length; i++ ) {
             var txtObject = arr[i];
             var txtQml = component.createObject(someParentId);
             txtQml.text = txtObject.text;
             ... //Etc fill in more props from the txtObject
          }
      }
      

      Again how this is performance wise I am not sure I am inclined to do the QML markup on the CPP side as well.
      I'll mark this topic as Solved as I think there is a lot of great input here that would help anyone else in the future.

      Thanks everyone!

      1 Reply Last reply
      0
      • P Offline
        P Offline
        p3c0
        Moderators
        wrote on 22 Sept 2016, 08:36 last edited by p3c0
        #23

        @Placeable Beware of Component.onCompleted.

        The order of running the onCompleted handlers is undefined.

        Due to this it could be possible that your initialized components may be not be available when required. May be create them when you require them.

        157

        P 1 Reply Last reply 22 Sept 2016, 09:13
        0
        • P p3c0
          22 Sept 2016, 08:36

          @Placeable Beware of Component.onCompleted.

          The order of running the onCompleted handlers is undefined.

          Due to this it could be possible that your initialized components may be not be available when required. May be create them when you require them.

          P Offline
          P Offline
          Placeable
          wrote on 22 Sept 2016, 09:13 last edited by
          #24

          @p3c0

          I am not sure what this means. From my testing I see no issues. You mean there is a chance onCompleted is finished before the nested component.createObject(..) is created for this.

          How would one solve this preferably?

          1 Reply Last reply
          0
          • P Offline
            P Offline
            p3c0
            Moderators
            wrote on 22 Sept 2016, 09:30 last edited by
            #25

            @Placeable

            If you find no issues then continue. Just a warning if you find some odd behavior during your implementaion. In some of my cases I found that onCompleted is not the most reliable place for initialization of components. Sometimes it triggered earlier causing problems to the objects which were intialized in it and which were dependent on others.

            157

            P 1 Reply Last reply 22 Sept 2016, 10:01
            0
            • P p3c0
              22 Sept 2016, 09:30

              @Placeable

              If you find no issues then continue. Just a warning if you find some odd behavior during your implementaion. In some of my cases I found that onCompleted is not the most reliable place for initialization of components. Sometimes it triggered earlier causing problems to the objects which were intialized in it and which were dependent on others.

              P Offline
              P Offline
              Placeable
              wrote on 22 Sept 2016, 10:01 last edited by
              #26

              @p3c0 Alrighty, I'll bare that in mind. Thanks again!

              1 Reply Last reply
              0
              • K kshegunov
                21 Sept 2016, 15:07

                @VRonin

                Haven't tried it, but I'd do something along the lines of:

                ApplicationWindow  {
                    visible: true
                    width: 640
                    height: 480
                    title: "Testing Model"
                
                    ListView  {
                        model: testModel
                        delegate: Rectangle  {
                            height: 25
                            width: 100
                            Text  {
                                id: tmText
                                text: modelData.text
                                anchors.left: parent.left
                                anchors.top: parent.top
                                anchors.bottom: parent.bottom
                            }
                            Text  {
                                text: modelData.desctiption
                                anchors.left: tmText.right
                                anchors.right: parent.right
                                anchors.top: parent.top
                                anchors.bottom: parent.bottom
                            }
                        }
                    }
                }
                
                VRoninV Offline
                VRoninV Offline
                VRonin
                wrote on 10 Jan 2018, 19:27 last edited by
                #27

                Since this was something new from me and the issue popped up again after a while
                I prepared a small wiki article that summarises the technique

                "La mort n'est rien, mais vivre vaincu et sans gloire, c'est mourir tous les jours"
                ~Napoleon Bonaparte

                On a crusade to banish setIndexWidget() from the holy land of Qt

                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