Как создать окно QtQuick вне основного потока
Я хотел бы иметь основной поток, который создает экземпляр класса, который расширяет QQuickView и перемещает его во второй поток.
В идеале я хотел бы сделать что-то вроде этого:
main.cpp
int main(int argc, char *argv[])
{
QGuiApplication app(argc, argv);
MyClass myClassObj;
myClassObj.init();
return 0;
}
MyClass.cpp
void init()
{
MyQtQuickClass view;
QThread* GUIthread = new QThread(this);
view.moveToThread(GUIthread);
QObject::connect(GUIthread, SIGNAL(started()), &view, SLOT(init()));
GUIthread.start();
}
MyQtQuickCLass.cpp
void init()
{
QQmlContext* rootContext = this->rootContext();
// Setup view code here
this->show();
QGuiApplication::instance()->exec();
}
Что-то вроде этого я получаю эту ошибку: QQmlEngine: недопустимая попытка подключения к QQmlContext(0x120fc60), который находится в потоке, отличном от механизма QML QQmlEngine(0xdf6e70).
Есть ли обходной путь? Или способ создать движок QML прямо во втором потоке?
2 ответа
Если вы хотите, чтобы QQuickView жил за пределами main()
нить, то вы должны:
- Создать новый
std::thread
(НЕQThread
потому что этоQObject
так что это не должно быть создано до вашегоQGuiApplication
) - Запустить
init()
функция в этой теме. Пусть это создастQGuiApplication
и запустить цикл событий. - Создайте свой
QQuickView
в этой теме тоже. - Убедитесь, что все ваши объекты GUI доступны только из этого потока.
- Убедитесь, что ваш
main()
поток не создаетQObject
до тех пор, пока послеQGuiApplication
был создан в другой вашей теме.
См. Как избежать Qt app.exec(), блокирующего основной поток, для получения более подробной информации.
QObject
s имеют сродство потока с родителем QObject
или текущий поток, если у них нет родителя. Скорее всего - в вашем примере - некоторые QObject
созданные во время создания MyQtQuickClass
иметь сходство с тем, в котором они были созданы. Создание MyQtQuickClass
в GUIthread
бы решить это.
Однако все окна Qt должны работать в том же потоке, что и QGuiApplication
и ваше приложение, скорее всего, зависнет, если вы попытаетесь.