Во-первых, Qt и почти все другие фреймворки (по крайней мере те, что я знаю), которые имеют дело с элементами пользовательского интерфейса, имеют очень специфические требования для поддержки многопоточности.
Qt необходимо, чтобы каждый потомок QObject
(например, QWidget
) был назначен потоку (см. QObject::thread()).
Это свойство автоматически назначается при создании объекта потоку, в котором создается объект.
Проблема в том, что Qt также требует, чтобы виджет получал события только в том случае, если он принадлежит к тому же потоку, в котором выполняется цикл обработки событий (и он правильно добавлен в родительский виджет).
Если вы создаете свой огромный виджет в каком-то другом потоке, он не будет получать события, пока он не будет перемещен в поток с помощью цикла событий и не будет переподчинен.
Вы можете переместить QWidget
в другой поток, вызвав QObject::moveToThread() метод. Предположим, что mParent
— это ваш QMainWindow
, а mMyWidget
— ваш огромный виджет:
mMyWidget->setParent(0);
mMyWidget->moveToThread(mParent->thread());
mMyWidget->setParent(mParent); // change this to match your layout requirements.
Проверьте QWidget::setParent() для получения дополнительной информации.
Создание вашего огромного виджета должно выполняться не в том же потоке, что и ваш основной поток. Это остается в качестве упражнения, так как это довольно прямолинейно, а документация Qt обширна по потокам.
Будьте осторожны, если ваша кнопка нажата до завершения создания виджета: вы должны синхронизировать доступ к переменной, чтобы избежать неопределенного поведения.
Это очень общий взгляд на проблему, но это только начало, и, поскольку вы не предоставили никакого кода, я даю вам минимум; D
Другой вариант (и, вероятно, лучший) — посмотреть, почему ваш виджет так долго создается, но без дополнительной информации я не могу помочь.
person
Vinícius Gobbo A. de Oliveira
schedule
27.07.2014