避免QQuickView延迟qml加载

时间:2016-09-05 09:35:36

标签: qt qml

这是我的情况。我试图将qml与基于小部件的UI结合起来。为此,我使用QQuickView和QWidget :: createWindowContainer。我无法使用QQuickWidget,因为我需要将窗口转换为本机窗口,而QQuickWidget并不喜欢。但回到这个问题。

我的问题是第一次显示视图时,加载需要半秒才会导致非常明显的闪烁。之后,我可以隐藏/显示我想要的视图,它立即显示。它只是第一次加载qml。而且我相当肯定是导致问题的qml的加载。因为我有两个不同的QQuickViews,它们的源代码与qml相同。但是,在其中任何一个加载一次后,另一个没有立即显示问题。

我试图尽早调用show()以及时加载它。但是这会导致qml在任何小部件显示之前出现一小段时间。

有没有人遇到过类似的问题?如何让QQuickView表现出来。

编辑:我使用的是Qt 5.4.2,由于种种原因,我无法更新到新版本。

1 个答案:

答案 0 :(得分:3)

我打算说你可以使用与this回答中相同的方法,但似乎即使加载QML还为时过早。这很hacky,但我能想到的另一件事就是使用非常短的Timer

<强>的main.cpp

#include <QtWidgets>
#include <QtQuick>

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = 0) :
        QMainWindow(parent)
    {
        QQuickView *view = new QQuickView();
        QWidget *container = QWidget::createWindowContainer(view, this);
        container->setFocusPolicy(Qt::TabFocus);
        view->rootContext()->setContextProperty("window", view);
        view->setSource(QUrl("qrc:/main.qml"));
        setCentralWidget(container);
        resize(400, 400);
    }
};

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    MainWindow w;
    w.show();

    return a.exec();
}

#include "main.moc"

<强> main.qml

import QtQuick 2.0
import QtQuick.Window 2.0
import QtQuick.Controls 2.0

Item {
    anchors.fill: parent

//    Connections {
//        target: window
//        onAfterSynchronizing: loader.active = true
//    }

    Timer {
        running: true
        repeat: true
        interval: 50
        onTriggered: {
            loader.active = true
        }
    }

    Loader {
        id: loader
        active: false
        sourceComponent: Column {
            anchors.fill: parent

            Repeater {
                model: 30000
                delegate: Button {
                    text: index
                }
            }
        }
    }

    BusyIndicator {
        running: loader.status === Loader.Null
        anchors.centerIn: parent
    }
}

为简洁起见,我将“重”QML放入sourceComponent,但您也可以使用source属性指向网址。

BusyIndicator在渲染线程上运行动画,因此在GUI线程被阻止时它可以继续旋转。