如何通过窗口系统通知QApplication?

时间:2013-02-18 06:16:38

标签: c++ qt qt4

我开始用C ++学习Qt,并试图找出事件机制的工作原理。我有点理解它在应用程序本身中是如何工作的,以及QApplication如何处理事件并将它们排队以进行处理并通知对象/小部件。

我仍然有一些悬而未决的问题:

  1. 窗口系统如何通知QApplication本身有关事件的信息?
  2. 窗口系统如何知道我的小部件的内部命名,以便它可以告诉QApplication小部件" x"点击,集中等等。
  3. 如果窗口系统不知道窗口小部件名称或者没有引用所单击的窗口小部件(或任何其他类型的事件),QApplication如何确定需要通知哪个窗口小部件。
  4. 提前感谢您的帮助。

2 个答案:

答案 0 :(得分:2)

在X11上,Qt轮询xlib(Qt4)或XCB(Qt5)的事件。使用xlib,这将是XNextEvent()函数和其他相关的函数:

http://www.x.org/archive/X11R7.5/doc/man/man3/XMaskEvent.3.html

如果你通过“XNextEvent”的Qt源代码,你可以找到它使用的地方。例如,在Qt 4.8.4来源中:

$ grep -r XNextEvent
tools/qvfb/x11keyfaker.cpp:         XNextEvent(dpy, &event);
src/plugins/platforms/xlib/qxlibscreen.cpp:            XNextEvent(mDisplay->nativeDisplay(), &event);
src/gui/kernel/qwidget_x11.cpp:            XNextEvent(X11->display, &ev);
src/gui/kernel/qguieventdispatcher_glib.cpp:            XNextEvent(X11->display, &event);
src/gui/kernel/qeventdispatcher_x11.cpp:                XNextEvent(X11->display, &event);
src/gui/kernel/qapplication_x11.cpp:            XNextEvent(X11->display, &nextEvent);

使用XCB,有xcb_wait_for_event()。

一旦Qt拥有该事件,它就可以开始通过窗口小部件层次结构和QML进行调度。

这仅适用于X11(意味着Unix和Linux。)其他平台有不同的方式向应用程序提供事件。

答案 1 :(得分:1)

在Windows中,例如,QWidget只是一个带有hwnd和所有其他相关内容的普通窗口。 您甚至可以通过调用effectiveWinId()方法来获取hwnd。它使用标准的Windows Messages Loop来获取有关所有Windows事件的通知,您可以通过QCoreApplication :: setEventFilter安装适当的过滤器来获取这些事件。 但Qt也有QML部分和其他非原生的东西,为了工作它使用一些内部簿记,这取决于“外星人小部件”的性质

所有上述内容都适用于非外星小部件,而外星小部件则有些不同。外星人小部件由Qt本身管理,它是一个Qt工作,用于识别应该传播的QWidget操作以及操作是什么。自4.4以来,Qt默认使用外星小部件,但如果需要,它们可以很容易地被修改。

其他操作系统的实现有所不同,但想法是一样的。