Post events without specifying a target in Qt

I need help to understand the use of QEvents in QT, it drives me crazy.

I am writing an application using custom events, but, like in the QApplication::postEvent , you must specify the target object.

As I understand it, you can send events to the Qt event loop with

 QApplication::postEvent(obj_target, QEvent myevent); 

This means that I am trying to catch the "myevent" event in obj_target to do some things.

But I need to post events without specifying the target, since QMouseEvent or QKeyEvent do

  • I mean, when I click in QMainWindow with a lot of buttons, how can I click any button and this button is pressed?

  • What is the target when publishing the click event?

  • Is it possible to register objects for "listening" for a specific event?

I'm really confused, can I send an event without specifying a target?

Thank you in advance

+6
source share
2 answers

There is no trivial way of posting events β€œglobally,” as Dan said. All event dispatching for individual events is done using the private Qt implementation code.

An important difference is:

  • There are native messages / events provided by the operating system, usually received by a window-dependent event loop.

  • There are QEvents.

Internally, Qt monitors top-level widgets (indeed windows), so when it receives an event from the OS, it knows which window it should go to - it can match it using the platform window identifier, for example.

QEvent delivery does not make sense without a receiving object, since sending an event to an object really only means that the QObject::event(QEvent*) method is called on this object. It is not possible to call this method without an instance of the object!

If you want to synthesize a global keystroke or mouse click event, you need to find out which object the event is going to. Namely:

  • Determine which top-level window (widget) the event should go through. You can list top-level widgets through qApp->topLevelWidgets() .

  • Define the child widget to which the event should pass. If this is a keyboard event, then sending the event to the current focused widget via qApp->focusWidget() is sufficient. You need to list the child widgets to find the deepest in the tree that overlaps the coordinates of the mouse.

  • Submit the correct QEvent subclass to the widget you just specified. Events delivered to top-level widgets will be redirected to the correct child widget.

When sending mouse events, you also need to synthesize the corresponding input and output events, or you risk leaving the widgets in an invalid state. The application.cpp source file should give you some ideas.

This does not give you access to native graphical elements, such as menus in OS X.

Please tell us exactly what you are trying to do. Why do you want to publish the broadcast? Who gets it? Since your own classes receiving a QObject will receive these broadcasts, I suppose it's simple enough to use the signal slot mechanism. You just connect(...) those receiver classes for any QObject signal (s) of the global broadcaster.

+1
source

For this purpose, I have a specific singleton class that I call GuiSignalHub . It regroups all the signals of the entire system.

Objects that want to initiate an action at the application level (for example, opening context-sensitive help) simply connect their signal to the GuiSignalHub signal. The receivers simply plug the GuiSignalHub into their slot.

+1
source

Source: https://habr.com/ru/post/908245/


All Articles