c++qtqmlqquickviewqqmlapplicationengine

Use QQuickView or QQmlApplicationEngine to switch between pages from ApplicationWindow


I'd like to use an ApplicationWindow as a main file and be able to switch to other QML files from C++ with QQuickView::setSource(const QUrl & url). Basically it would do this:

start-up => loads main.qml (ApplicationWindow) => click on help button => C++ loads help.qml file => etc.

int main(int argc, char *argv[])
{
    QApplication app{argc, argv};
    CustomQQuickView view;

    view.setSource(QUrl{"qrc:/main.qml"});
    view->show();

    return app.exec();
}

main.qml

ApplicationWindow
{
    visible: true
    width: 640
    height: 480

    Loader
    {
        anchors.fill: parent
        id: mainPageLoader
    }

    Button
    {
        text: "Help"
        onClicked: { mainPageLoader.source = "help.qml"}
    }
}

(I am wondering if the Loader here is really necessary here)

However QQuickView only supports loading of root objects that derive from QQuickItem. Therefore it doesn't work with ApplicationWindow.

I'm thinking about using QQmlApplicationEngine instead of QQuickView but the usage seems different, this class being only equipped with QQmlApplicationEngine::load(const QUrl & url)

What would be the best course of action for my purpose? Do I really need an ApplicationWindow in my main.qml file?


Solution

  • Use QQmlApplicationEngine as you suggest, and with the main.qml as you say, but set a context property from C++ with the content page URL, e.g. help.qml - then bind to this context property in the Loader's source property.

    This is the normal way of controlling QML from C++ - expose context properties or singleton objects with properties, drive them from C++, and have QML bindings respond to changes.