Search code examples
qtevent-handlingqt4qthread

Qt Main-Gui and other thread + events loops


I'm trying to understand the whole internal process of Qt and how it works when I'm working with different threads.

As I've understood (googling and exploring the Qt source code), is as following:

  • Each thread has a local "pending event list" and a local event loop (if I call to exec) that interacts with that list.
  • QCoreApplication::postEvent(obj, e) appends the pair (obj, e) on the "pending event list" of the obj's thread.
  • Each thread has a local "event dispatcher" (QAbstractEventDispatcher specializations), which purpose is reading system events. So, it exists a QEventDispatchWin, a QEventDispatchUnix, a QEventDispatchSymbian and so on, for different platforms. For gui events, Qt has also QEventDispatchX11 (inherits from QEventDispatchUnix), S60 (from Symbian), etc.

With of all this in mind, a exec call works as following:

Thread's `exec`:
 ├ create a QEventLoop object.
 └ call QEventLoop.exec()
   └ call repeatedly eventDispatcher's processEvents with WaitForMoreEvents flag.
     ├ call to QCoreApplication::sendPostedEvents
     ├ while (!pending system events)
     │  ├ read system event
     │  ├ create an appropiate QEvent e and detect its target QObject o.
     │  └ call to QCoreApplication::sendSpontaneousEvent(o, e)
     └ call to QCoreApplication::sendPostedEvents
       (for new generated user events in the previous step).

If quit or exit is called, it finalices the current processEvents call and exec returns with the value passed to exit.

Some points to take in consideration:

  1. System events are never pushed/posted: when they are generated from the system and translated as QEvents, they are directly sended to its target object.
  2. Target object member functions (o.event()) are called in the same thread where processEvent takes place.

And now, doubts:

  1. Since postEvent is a static and thread-safe function, what role does QCoreApplication play in this event processing system? And QApplication? Why are they mandatory to being created as soon as possible?
  2. Why QApplication/QCoreApplication are mandatory to get system events, if each Thread has its own "event dispatcher"?

Any correction about my supositions are welcome.


Solution

  • In response to your second question, "Why QApplication/QCoreApplication are mandatory to get system events, if each Thread has its own "event dispatcher"?"

    The 4.8 documenation states:

    "Note that QCoreApplication::exec() must always be called from the main thread (the thread that executes main()), not from a QThread. In GUI applications, the main thread is also called the GUI thread because it's the only thread that is allowed to perform GUI-related operations."

    But regarding QThreads in general - you'll find the the link provided describes QThreads as QObjects that is a wrapper around threads. So QThreads, like any other QObjects, require the QCoreApplication to interact with in order to coordinate notifications/events, e.g. when the thread finishes.

    http://qt-project.org/forums/viewthread/14806

    In Maya's article, she provides an example where tasks are ASSIGNED to a QThread instead of being defined within [i.e. use signals/slots and don't overload the run() method]. In this way, you clearly see that the main event loop provided by QCoreApplication still plays a crucial role.

    As you probably already know, there has already been an abundant amount of discussion revolving around the topic of QThreads on this site - and Qt4 is pretty well-documented... can't say the same for Qt5 =(