July 12, 2011

omersaleem omersaleem
Lab Rat
2 posts

[solved] QML dynamic object creation in C++

 

Hi, I’m just out on QML and am looking for some assistance in the following…

I’m trying to dynamically create a QML object from C++ and do this without using any of the QGraphics* classes. As QGraphicsView is the current backend and will be removed I wanted to stick to using QDeclarative* classes only.

Dynamic object creation from QML works using…

  1.     myDialog = Qt.createComponent("BaseDialog.qml").createObject(baseObj);

Dynamic object creation from C++ using QGraphicsView works using…

  1.     QDeclarativeEngine* engine = m_view.engine();
  2.     QDeclarativeContext* context = engine->rootContext();
  3.     QObject* rootObj = context->findChild<QObject*>("baseObj");
  4.     QDeclarativeItem *rootitem = qobject_cast<QDeclarativeItem*>(rootObj);
  5.  
  6.     QDeclarativeComponent component(engine, QUrl::fromLocalFile("qml/NativeInteg/BaseDialog.qml"));
  7.     QObject *myObject = component.create();
  8.     QDeclarativeItem *item = qobject_cast<QDeclarativeItem*>(myObject);
  9.  
  10.     item->setParentItem(rootitem);
  11.     m_view.scene()->addItem(item);

But using pure QDeclarative* classes I can’t seem to achieve it, so far I have…

  1.     QDeclarativeContext* context = m_view.engine()->rootContext();
  2.     QDeclarativeComponent* component = new QDeclarativeComponent(m_view.engine(), QUrl::fromLocalFile("qml/NativeInteg/BaseDialog.qml"), m_view.engine());
  3.     QDeclarativeItem* myDialog = qobject_cast<QDeclarativeItem*>(component->create());
  4.  
  5.     QObject* child = context->findChild<QObject*>("baseObj");
  6.     QDeclarativeItem *rootitem = qobject_cast<QDeclarativeItem*>(child);
  7.     myDialog->setParentItem(rootitem);

The component.onCompleted gets fired but nothing is displayed.

Any ideas on what I need to do next?

Thanks in advanced.

Omer

6 replies

July 13, 2011

Vijay Bhaska Reddy Vijay Bhaska Reddy
Lab Rat
383 posts

what is “baseObj”, is it the objectName of your root qml component??

July 13, 2011

omersaleem omersaleem
Lab Rat
2 posts

Yeah, sorry about the naming, still in prototyping phase. ‘baseObj’ is the name of the root element that I have loaded by my main.qml. It is intended to be the parent of the object that I trying to dynamically create.

July 13, 2011

Vijay Bhaska Reddy Vijay Bhaska Reddy
Lab Rat
383 posts

then the below code seems to work

  1. int main(int argc, char *argv[])
  2. {
  3.     QApplication app(argc, argv);
  4.  
  5.     QDeclarativeView m_view;// =  new QDeclarativeView();
  6.     m_view.setSource(QUrl::fromLocalFile("qml/Example/main.qml"));
  7.  
  8.     QDeclarativeComponent* component = new QDeclarativeComponent(m_view.engine(), QUrl::fromLocalFile("qml/Example/QML1.qml"));
  9.     QDeclarativeItem* myDialog = qobject_cast<QDeclarativeItem*>(component->create());
  10.  
  11.     myDialog->setParentItem(qobject_cast<QDeclarativeItem*>(m_view.rootObject()));
  12.     m_view.showFullScreen();
  13.  
  14.     return app.exec();
  15. }

July 13, 2011

omersaleem omersaleem
Lab Rat
2 posts

Ok cool, that works. The only thing is rootObject() in line 11 returns a QGraphicsObject so presumably this method will be removed/changed when the backend is migrated from QGraphicsView to Scene Graph?

July 13, 2011

Vijay Bhaska Reddy Vijay Bhaska Reddy
Lab Rat
383 posts

so, I guess so and mark the thread as solved by appending (Solved) to the title of the thread.

November 22, 2013

nidhi.sharma nidhi.sharma
Lab Rat
1 posts

hello,

I have an application, in which i am using the same approach.
now if i want to access the properties of baseObj, which meant to be parent of my dynamically created object, what should i do.

Here is example of my code..

main.qml
import FirstButtonClick 1.0
Rectangle{ property string myString : “My String” Text{ text : “main file” } MouseArea{ onClicked:{ buttonClick.openPage(“qrc:qml/FirstButton.qml”) } }

FirstButtonClick{ id : buttonClick } }

FirstButton.qml
Rectangle{ Text{ text : “FirstButton Page” }

Component.onCompleted{ console.log(“main.qml property : “ + myString // main.qml property) } }

main.cpp
#include “FirstButtonClick.h”
#include “main.h”

int main(int argc, char *argv[]) { qmlRegisterType<>(“FirstButtonClick”, 1, 0, “FirstButtonClick”); QApplication app(argc, argv); m_view = new QDeclarativeView; m_view.setSource(QUrl(“qrc:qml/main.qml”)); m_view.showFullScreen(); return app.exec(); }

main.h
QDeclarativeView* m_view;

FirstButtonClick.h
extern QDeclarativeView* m_view;
class FirstButtonClick : public OQbject
{ Q_OBJECT; public : Q_INVOKABLE QObject* openPage(QString fileName);
}

FirstButtonClick.cpp
#include “FirstButtonClick.h”

QObject* FirstButtonClick :: openPage(QString fileName)
{ QDeclarativeContext* context = m_view->engine()->rootContext(); QDeclarativeComponent* component = new QDeclarativeComponent(m_view->engine(), QUrl(fileName), m_view->engine());

QObject * object = component->create(); QDeclarativeItem* myDialog = qobject_cast<QDeclarativeItem*>(object); QDeclarativeItem rootitem = qobject_cast<QDeclarativeItem>(m_view->rootObject()); myDialog->setParentItem(rootitem); return object; }

the problem with the above code is FirstButton.qml page is loaded but when it tries to access the property of main.qml ie. myString it cant access it.

suggest me me a way to use it properly

 
  ‹‹ [solved]tab for TextInput in QML      [SOLVED] Creating a QML Image that will load different source if one source fails to load ››

You must log in to post a reply. Not a member yet? Register here!