I spent 3 days carefully checking the best reference material I could find on the Internet about Q_RETURN_ARG. I have already included QQmlComponent . When used in C ++ to send a variable mapped to QML, things don't always happen as they seem. Maybe because Qt5 is relatively new, there is not much material that we can rely on.
Basically, the code compiles without problems. When I ask him to start, it accurately displays the qml page on the device, and then receives an error:
QQmlComponent: Component is not ready main.cpp:33 (int main(int, char**)): Got QML return: ""
Besides the invoke.pro and myapplication.cpp files, here are the key parts of a small example that I am trying to develop based on this post , Qt5 Documentation , ICS Tutorial , and link :
./myapplication.h
#include <QObject> #include <QDebug> #include <QQmlComponent> class MyApplication : public QObject { Q_OBJECT public: explicit MyApplication(QObject *parent = 0); ~MyApplication(void) {} QObject *object; QQmlComponent *component; void loadComponent(void) { QQmlEngine engine; QQmlComponent *component = new QQmlComponent(&engine); component->loadUrl(QStringLiteral("qml/invoke/main.qml")); if(!component->isReady()){ qWarning("qPrintable: %s", qPrintable(component->errorString())); } if (component->isLoading()){ cout <<"==== component->isLoading ===="; QObject::connect(component, SIGNAL(statusChanged()), this, SLOT(continueLoading())); } else{ cout <<"==== component is not Loading ===="; continueLoading(); } } signals: public slots: void continueLoading() { QQmlEngine engine; QQmlComponent *component = new QQmlComponent(&engine); component->loadUrl(QStringLiteral("qml/invoke/main.qml")); if (component->isError()) { qWarning() << "component->isError()="<< component->errors(); } else { object = component->create(); cout <<"object created"; } } };
./main.qml
import QtQuick 2.0 Rectangle { width: 360 height: 360 Item { function myQmlFunction(msg_cpp) { console.log("Got msg_cpp:", msg_cpp) return "output" } } }
./main.cpp
#include <QtGui/QGuiApplication> #include "qtquick2applicationviewer.h" #include <QtQuick/QQuickItem> #include <QtQuick/QQuickView> #include <QQmlEngine> #include <QtQml> #include <QDeclarativeEngine> #include <QtCore> #include <QtQuick/QtQuick> #include <QQmlComponent> #include <QtQml/qqml.h> #include "myapplication.h" int main(int argc, char *argv[]) { QGuiApplication app(argc, argv); QtQuick2ApplicationViewer viewer; viewer.setMainQmlFile(QStringLiteral("qml/invoke/main.qml")); MyApplication *myClass = new MyApplication(); myClass->loadComponent(); QObject *object=myClass->object; QVariant returnedValue; QVariant msg_cpp = "C++ message"; QMetaObject::invokeMethod(object, "myQmlFunction", Q_RETURN_ARG(QVariant, returnedValue), Q_ARG(QVariant, msg_cpp)); qDebug() << "Got QML return:" << returnedValue.toString(); viewer.showExpanded(); delete object; return app.exec(); }
Which gives an error:
loadComponent()): qPrintable: file://qml/invoke/main.qml:-1 File not found continueLoading()): component->isError()= (file://qml/invoke/main.qml: File not found) main.cpp:36 (int main(int, char**)): Got QML return: ""
I noticed that main.qml is intended to be loaded on Android using "QtQuick2ApplicationViewer" instead of "QQmlEngine". If "QQmlEngine" is not used at all to load main.qml in an attempt to run Q_RETURN_ARG - when working with Android, and therefore, therefore, the "QQmlComponent" does not load? If I try to use the "QtQuick2ApplicationViewer viewer", replacing the "QQmlEngine engine" with the "QQmlComponent component", it says: "there is no matchning function to call the QQmlComponent."
Any suggestions on how to initialize the QQmlComponent, so Q_RETURN_ARG starts to work? Thanks!