Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. QML and Qt Quick
  4. Setting the model for a QQuickWidget
Forum Updated to NodeBB v4.3 + New Features

Setting the model for a QQuickWidget

Scheduled Pinned Locked Moved Unsolved QML and Qt Quick
10 Posts 5 Posters 1.1k 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.
  • Chris HennesC Offline
    Chris HennesC Offline
    Chris Hennes
    wrote on last edited by
    #1

    To set the model for a QQuickView you use setInitialProperties, e.g.

    _contents = new QQuickView;
    _contents->setInitialProperties({{QLatin1String("model"), QVariant::fromValue(&_model)}});
    _contents->setSource(QUrl(QStringLiteral("qrc:/Launcher.qml")));
    

    This works fine with my model. If I switch to using a QQuickWidget, however, there is no setInitialProperties method, and I can't figure out what the equivalent is. For example,

    _contents = new QQuickWidget (this);
    _contents->setProperty("model", QVariant::fromValue(&_model));
    _contents->setSource(QUrl(QStringLiteral("qrc:/Launcher.qml")));
    

    (where _model here is the same QAbstractListModel-derived-class that worked with the QQuickView). What am I missing here to get the C++ model to talk to my QML in a QQuickWidget?

    Chris Hennes, Pioneer Library System

    sierdzioS 1 Reply Last reply
    0
    • Chris HennesC Chris Hennes

      To set the model for a QQuickView you use setInitialProperties, e.g.

      _contents = new QQuickView;
      _contents->setInitialProperties({{QLatin1String("model"), QVariant::fromValue(&_model)}});
      _contents->setSource(QUrl(QStringLiteral("qrc:/Launcher.qml")));
      

      This works fine with my model. If I switch to using a QQuickWidget, however, there is no setInitialProperties method, and I can't figure out what the equivalent is. For example,

      _contents = new QQuickWidget (this);
      _contents->setProperty("model", QVariant::fromValue(&_model));
      _contents->setSource(QUrl(QStringLiteral("qrc:/Launcher.qml")));
      

      (where _model here is the same QAbstractListModel-derived-class that worked with the QQuickView). What am I missing here to get the C++ model to talk to my QML in a QQuickWidget?

      sierdzioS Offline
      sierdzioS Offline
      sierdzio
      Moderators
      wrote on last edited by
      #2

      @Chris-Hennes To make a property visible globally in QML, you need to add it to root context object of the QML engine. So:

      _contents = new QQuickWidget (this);
      _contents->setSource(QUrl(QStringLiteral("qrc:/Launcher.qml")));
      _contents->rootContext()->setContextProperty("model", QVariant::fromValue(&_model));
      

      (Z(:^

      Chris HennesC 1 Reply Last reply
      1
      • sierdzioS sierdzio

        @Chris-Hennes To make a property visible globally in QML, you need to add it to root context object of the QML engine. So:

        _contents = new QQuickWidget (this);
        _contents->setSource(QUrl(QStringLiteral("qrc:/Launcher.qml")));
        _contents->rootContext()->setContextProperty("model", QVariant::fromValue(&_model));
        
        Chris HennesC Offline
        Chris HennesC Offline
        Chris Hennes
        wrote on last edited by
        #3

        @sierdzio Thank you for that information. So now I am trying:

            _contents = new QQuickWidget (this);
            _contents->rootContext()->setContextProperty(QLatin1String("model"), QVariant::fromValue(&_model));
        
            _contents->setSource(QUrl(QStringLiteral("qrc:/Launcher.qml")));
            setCentralWidget(_contents);
            _contents->show();
        

        The QML is trivial:

        import QtQuick 2.12
        import QtQuick.Controls 2.12
        import QtQml 2.12
        
        ListView {
            width: 200
            height: 250
        
            delegate: Text {
                required property string baseName
                required property string creationTime
        
                text: "Recent file: " + baseName + ", " + creationTime
            }
        
        }
        

        but all I get is a blank screen. The same QML works fine with QQuickView, and the QQuickWidget works fine if I, e.g. draw a rectangle, etc. So it seems to me the problem is those few lines of C++ -- I'm clearly missing some critical step to connect the model to the widget.

        Chris Hennes, Pioneer Library System

        sierdzioS 1 Reply Last reply
        0
        • Chris HennesC Chris Hennes

          @sierdzio Thank you for that information. So now I am trying:

              _contents = new QQuickWidget (this);
              _contents->rootContext()->setContextProperty(QLatin1String("model"), QVariant::fromValue(&_model));
          
              _contents->setSource(QUrl(QStringLiteral("qrc:/Launcher.qml")));
              setCentralWidget(_contents);
              _contents->show();
          

          The QML is trivial:

          import QtQuick 2.12
          import QtQuick.Controls 2.12
          import QtQml 2.12
          
          ListView {
              width: 200
              height: 250
          
              delegate: Text {
                  required property string baseName
                  required property string creationTime
          
                  text: "Recent file: " + baseName + ", " + creationTime
              }
          
          }
          

          but all I get is a blank screen. The same QML works fine with QQuickView, and the QQuickWidget works fine if I, e.g. draw a rectangle, etc. So it seems to me the problem is those few lines of C++ -- I'm clearly missing some critical step to connect the model to the widget.

          sierdzioS Offline
          sierdzioS Offline
          sierdzio
          Moderators
          wrote on last edited by
          #4

          @Chris-Hennes You are not setting the model anywhere in your ListView so it will display an empty list.

          ListView {
            model: model
          

          Also, having model as the name of your model might clash with model property of ListView, maybe better rename it.

          (Z(:^

          GrecKoG Chris HennesC 2 Replies Last reply
          1
          • sierdzioS sierdzio

            @Chris-Hennes You are not setting the model anywhere in your ListView so it will display an empty list.

            ListView {
              model: model
            

            Also, having model as the name of your model might clash with model property of ListView, maybe better rename it.

            GrecKoG Offline
            GrecKoG Offline
            GrecKo
            Qt Champions 2018
            wrote on last edited by
            #5

            Using context properties should be avoided ( https://doc.qt.io/qt-6/qtqml-cppintegration-contextproperties.html ) and exposing your C++ objects as QML singletons should be preferred :
            https://doc.qt.io/qt-6/qtqml-cppintegration-overview.html#choosing-the-correct-integration-method-between-c-and-qml

            sierdzioS 1 Reply Last reply
            2
            • sierdzioS sierdzio

              @Chris-Hennes You are not setting the model anywhere in your ListView so it will display an empty list.

              ListView {
                model: model
              

              Also, having model as the name of your model might clash with model property of ListView, maybe better rename it.

              Chris HennesC Offline
              Chris HennesC Offline
              Chris Hennes
              wrote on last edited by
              #6

              @sierdzio I'm trying to follow the example here: https://doc.qt.io/qt-6/qtquick-modelviewsdata-cppmodels.html#qabstractitemmodel-subclass

              (and again, this works correctly, with no modifications to the QML, if I put it in a QQuickView instead of a QQuickWidget).

              @GrecKo thanks for the links. I'm not sure how to follow the flowchart there, though, I am new to QML so the terminology doesn't mean anything to me (which is why I was trying to stay close to the example I link to above). I guess for a C++ model interacting with a QML view, I want the C++ side to be a QML_ELEMENT?

              Chris Hennes, Pioneer Library System

              1 Reply Last reply
              0
              • GrecKoG GrecKo

                Using context properties should be avoided ( https://doc.qt.io/qt-6/qtqml-cppintegration-contextproperties.html ) and exposing your C++ objects as QML singletons should be preferred :
                https://doc.qt.io/qt-6/qtqml-cppintegration-overview.html#choosing-the-correct-integration-method-between-c-and-qml

                sierdzioS Offline
                sierdzioS Offline
                sierdzio
                Moderators
                wrote on last edited by
                #7

                @GrecKo said in Setting the model for a QQuickWidget:

                Using context properties should be avoided

                Ah, it shows that I'm still stuck on Qt 5 on my current project :D Thanks for the links and info!

                (Z(:^

                Chris HennesC 1 Reply Last reply
                0
                • sierdzioS sierdzio

                  @GrecKo said in Setting the model for a QQuickWidget:

                  Using context properties should be avoided

                  Ah, it shows that I'm still stuck on Qt 5 on my current project :D Thanks for the links and info!

                  Chris HennesC Offline
                  Chris HennesC Offline
                  Chris Hennes
                  wrote on last edited by
                  #8

                  Ah, it shows that I'm still stuck on Qt 5 on my current project :D Thanks for the links and info!

                  I am too (we support compilation with both Qt5 and Qt6) -- my real problem is that we currently support compilation on Ubuntu 20.04LTS, which is still Qt 5.12, so large amounts of the current best-practices advice and documentation aren't relevant. I have been unable to come up with a working solution when using the non-context-properties methods because I can't get the cMake project to compile using the older setup commands. I think I'm stuck using the context properties, which of course I still can't get to work with QQuickWidget.

                  Chris Hennes, Pioneer Library System

                  B 1 Reply Last reply
                  0
                  • Chris HennesC Chris Hennes

                    Ah, it shows that I'm still stuck on Qt 5 on my current project :D Thanks for the links and info!

                    I am too (we support compilation with both Qt5 and Qt6) -- my real problem is that we currently support compilation on Ubuntu 20.04LTS, which is still Qt 5.12, so large amounts of the current best-practices advice and documentation aren't relevant. I have been unable to come up with a working solution when using the non-context-properties methods because I can't get the cMake project to compile using the older setup commands. I think I'm stuck using the context properties, which of course I still can't get to work with QQuickWidget.

                    B Offline
                    B Offline
                    Bob64
                    wrote on last edited by
                    #9

                    @Chris-Hennes going back to what sierdzio suggested you try, in this line:

                        _contents->rootContext()->setContextProperty(QLatin1String("model"), QVariant::fromValue(&_model));
                    

                    try naming the property something other than "model" (let's say "myModel") and, in your QML, add to your list view:

                    ListView {
                        model: myModel
                        ...
                    
                    1 Reply Last reply
                    1
                    • _ Offline
                      _ Offline
                      _nezticle
                      wrote on last edited by
                      #10

                      I ran into this issue myself when using QQuickWidget (since you're certainly going to want to be communicating between C++ and Qt Quick in that case). The original comment about setInitialProperties really triggered me, since that means there wasn't parity between QQuickWidget and QQuickView in a way that doesn't make sense. The same was true of the more modern loadFromModule pattern. So I created a couple patches to at least to try and rectify this in 6.9:
                      https://codereview.qt-project.org/c/qt/qtdeclarative/+/586483/2
                      https://codereview.qt-project.org/c/qt/qtdeclarative/+/586520/1
                      But also I my case, that doesn't help me "today". I agree that using a QML Singleton is the correct solution over setting a context property, but that still led me to the issue that I wanted to do that the Modern/Correct way, but I didn't really understand from the docs how to get access to that Singleton from the C++ side. I found that this was the correct documentation page that explained that:
                      https://doc.qt.io/qt-6/qtqml-cppintegration-exposecppstate.html
                      But basically this is what the C++ code would look like:

                      Singleton *singleton
                                 = engine->singletonInstance<Singleton *>("MyModule", "Singleton");
                         singleton->setThing(77);
                      
                      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