I have this function to update some GUI stuff:
void SavedConnections::renderList()
{
// Do GUI stuff! Must run in Qt thread!!!
...
}
I need to ensure that this function isn't called from other threads. What I plan to do is to defer it into event loop and raise a warning:
void SavedConnections::renderList()
{
if(!this_thread_is_Qt_GUI_thread()) {
qDebug()<< "Warning: GUI operation attempted from non GUI thread!\n";
QCoreApplication::postEvent(this, new UpdateGUIEvent());
return;
}
// Do GUI stuff! Must run in Qt thread!!!
...
}
This pattern is also very convenient to make methods that are guaranteed to run asynchronously in GUI thread without any ugly syntax. I already asked similar question about Java's ExecutorService.
As mentioned, each program has one thread when it is started. This thread is called the "main thread" (also known as the "GUI thread" in Qt applications). The Qt GUI must run in this thread.
In fact, they are handled in a special way by Qt, and are processed only if the running event loop has a smaller degree of "nesting" (w.r.t. event loops) than the one where deleteLater was called. For instance: QObject *object = new QObject; object->deleteLater (); QDialog dialog; dialog.exec ();
Note that the creation of the instance of the Qt Find dialog is happening on the Main (GUI) thread, but it happens each time you click the "Find" menu option. The variable named theApp is a staticly-declared instance of the main application which is derived from CWinApp and utlimately becomes the "parent" object in the QDialog constructor.
This is because the QThread object is living in another thread, namely, the one in which it was created. Qt also requires that all objects living in a thread are deleted before the QThread object that represents the thread is destroyed; this can be easily done by creating all the objects living in that thread on the QThread::run () method's stack.
You can check if the current thread is the thread your object lives in:
if (QThread::currentThread() != this->thread()) {
// Called from different thread
}
Note that this might not be the main GUI-Thread! It is the thread this
lives in (see QObject Thread affinity). If you don't change it using QObject::moveToThread
, it is the thread the object was created in.
This is also what QCoreApplication::postEvent
uses to determine into which thread the event should be posted. The targeted Thread must run a QEventLoop
to respond to the event.
So checking for the main-GUI-Thread (qApp->thread()
), but posting to this
's thread might not work, if your object does not live in the main-GUI-Thread. However, if you do GUI stuff there, it should anyway live in the GUI-Thread
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With