Qt Forum

    • Login
    • Search
    • Categories
    • Recent
    • Tags
    • Popular
    • Users
    • Groups
    • Search
    • Unsolved

    [solved] How to create a binding from C++ to a QML property?

    QML and Qt Quick
    2
    8
    1600
    Loading More Posts
    • 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.
    • D
      digorydoo last edited by

      I have a component in an external QML file. The component is dynamically added like this:

      @
      QUrl url = QUrl (QStringLiteral ("qrc:///MyPage.qml"));

      // Delete the current page.
      
      qDeleteAll (m_pContentArea->children());
      
      // Gain access to the engine and context.
      
      QQmlEngine *pEngine = qmlEngine (m_pContentArea);
      QQmlContext *pCtx = pEngine->contextForObject (m_pContentArea);
      
      // Create the new component.
      
      QQmlComponent component (pEngine, url);
      QObject *pNewPage = component.beginCreate (pCtx);
      
      // parent for the object hierarchy:
      pNewPage->setParent (m_pContentArea); 
      
      // parent property for dynamic bindings:
      pNewPage->setProperty ("parent", QVariant::fromValue<QObject *>(m_pContentArea));
      
      // ...
      component.completeCreate();
      

      @

      So far, so clear. I now basically would like to connect the contentArea's property "height" to be the same as the page's height, with the intention that if the page's height changes, the contentArea's height changes also.

      To set the contentArea's height to some constant value, I could write:

      @
      m_pContentArea->setProperty ("height", QVariant::fromValue<qreal>(1000.0f));
      @

      How can I set the value of the property to be a script? The following doesn't work:

      @
      m_pContentArea->setProperty ("height", QVariant::fromValue<QString>QStringLiteral ("parent.height"));
      @

      I tried also:

      @
      QObject::connect (m_pContentArea, SIGNAL (setHeight (qreal)),
      pNewPage, SLOT (height()));
      @

      But this doesn't work either, because there is no signal called setHeight (qreal).

      1 Reply Last reply Reply Quote 0
      • R
        Roumed last edited by

        If i'm not mistaken, you need to process signal heightChanged() at main thread - this signal emits when property is changed. At this slot you can request height and set to another component.

        1 Reply Last reply Reply Quote 0
        • D
          digorydoo last edited by

          Thanks for the reply. I'm going to try this. However, I'm interested if there is any chance to install a JavaScript from C++.

          1 Reply Last reply Reply Quote 0
          • R
            Roumed last edited by

            What do you mean "to install JS from C++"?

            1 Reply Last reply Reply Quote 0
            • D
              digorydoo last edited by

              I mean I want to set the property height to some JavaScript. I tried the following:

              @
              QJSValue wrapper = pEngine->newQObject (pNewPage);
              pEngine->globalObject().setProperty ("curPage", wrapper);
              QJSValue ret = pEngine->evaluate ("curPage.parent.height = curPage.height;");

              if (ret.isError())
              {
                  qDebug() << "Error: replaceContentWith: Couldn't connect height property!";
                  qDebug() << ret.toString();
              }
              

              @

              Unfortunately, this doesn't work, the error message is: "ReferenceError: curPage is not defined". Which is strange, because I set curPage to be a property of globalObject...

              1 Reply Last reply Reply Quote 0
              • R
                Roumed last edited by

                I hope "this article":http://qt-project.org/doc/qt-5/qtqml-cppintegration-interactqmlfromcpp.html#accessing-loaded-qml-objects-by-object-name will help you.
                But are you sure that it is correct to set size of any element from C++?

                1 Reply Last reply Reply Quote 0
                • D
                  digorydoo last edited by

                  I don't just want to set height to some fixed size. I want to set it to a script that will automatically adjust the size of curPage.parent.height as the size of curPage.height changes. In QML, this is very simply done by saying "height: curPage.height;" in the parent object. QML will autmatically create the necessary bindings between slots and signals. I basically want to use the same technique from C++, i.e. I want to set the height property to some script. Your article doesn't mention this, or maybe I missed it...

                  Yeah, maybe it's not the correct way to do this. I'm going to try the slot/signal technique with heightChanged as you suggested.

                  1 Reply Last reply Reply Quote 0
                  • D
                    digorydoo last edited by

                    I finally solved the problem in a most stupidly simple way! In the component that is dynamically loaded, I added the following:

                    @
                    Component.onCompleted:
                    {
                    parent.height = height;
                    }
                    @

                    Cheers!

                    1 Reply Last reply Reply Quote 0
                    • First post
                      Last post