如何将 X11 事件传递给 QDialog

Posted

技术标签:

【中文标题】如何将 X11 事件传递给 QDialog【英文标题】:How to pass X11 events to QDialog 【发布时间】:2012-01-27 23:30:24 【问题描述】:

目前,我正在尝试将系统 X11 事件(在 Linux 上)传递给我创建的对象。为此,我从我的 QApplication 将一个 eventFilter 安装到我的对象上。这很有效,因为它获取了应用程序的所有事件。但是我也需要传递对象 X11 事件。

我继续在我的对象中创建了一个 x11Event,希望它会接收来自 X11 的事件,但事实并非如此。

有没有办法在我的应用程序内部将 X11 事件直接传递给我的对象?

【问题讨论】:

您介意从更广泛的角度解释您要做什么吗?您的应用需要接收 X11 事件的目的是什么? 你的“对象”是QDialog 吗?您对QApplication::x11EventFilter 的重新实现是否返回false 以允许重新实现QDialog::x11Event 函数也接收事件? @alexisdm 我的印象是,如果 x11Event 没有被 QApplication 或父小部件传递,它就无法接收 XEvent?这是正确的吗? 【参考方案1】:

您可以通过以下方式接收XEvents:

使用QAbstractEventDispatcher::instance()->setEventFilter() 设置的过滤器函数将接收所有XEvents。 使用qApp->setEventFilter() 设置的过滤器函数,仅接收针对应用程序的事件。 虚函数QApplication::x11EventFilter的重新实现 为您的***窗口重新实现虚函数 QWidget::x11Event(子小部件不接收 XEvents)。

按这个顺序。如果这些函数中的任何一个为任何事件返回 true,则下一个函数将不会接收该事件。

Qt 也可以在这些函数之间过滤一些事件,例如QWidget::x11Event 不接收XKeyEvents(由具有键盘焦点的小部件的QInputContext::x11FilterEvent 函数过滤)。

有关更多详细信息,您应该查看 Qt 源:QEventDispatcher_x11.cpp 和函数 QApplication::x11ProcessEvent in QApplication_x11.cpp

所以在大多数情况下,如果您只在您的QDialog 派生类中重新实现x11Event 函数,您应该已经收到了大部分XEvent。如果您希望您的子小部件也接收它们,您可以从您的 QDialog::x11Event 重新实现中手动调用它们的 x11Event 函数。

【讨论】:

我最终重新实现了 QApplication::x11EventFilter。混合了我的 return false 和 return true,但是它捕获了所有 X11 事件并破坏了一些东西。但是解决了这个问题,现在似乎工作得很好:)【参考方案2】:

我现在没有我的开发机器,所以请原谅我的语法。我会做以下事情:

    将 XEvent* 声明为元类型:

    int main() qRegisterMetatype<XEvent*>();

    按照 alexisdm 的建议重新实现 QApplication::x11EventFilter

    在您的 QApplication 重新实现中创建一个信号,例如:

    void dialogEvent(XEvent*);

    您可以在应用程序中的任何位置执行以下操作:

    QApplication *inst = QApllication::instance();

    MyApplication *myApp = qobject_cast&lt;MyApplication*&gt;(inst);

    如果(我的应用程序!= 0)

    connect(myApp, SIGNAL(dialogEvent(XEvent*), 
             myDialog, SLOT(onXEvent(XEvent*));
    

这样您就可以全局访问 x11 事件。作为替代方案,您可以随时重新实现:

bool QWidget::x11Event ( XEvent * event )

单个小部件

【讨论】:

我意识到这是矫枉过正,但仍然是一个可能的解决方案。除此之外,您不必在多个小部件上安装事件过滤器。

以上是关于如何将 X11 事件传递给 QDialog的主要内容,如果未能解决你的问题,请参考以下文章

onchange事件如何将日期值传递给javascript

如何将触摸事件传递给 parentViewController?

如何将 DotNetObjectReference 传递给 JS DOM 事件

userInteractionEnabled = YES时如何将触摸事件传递给superview?

如何将任意数据从 Dart 聚合物 Web 组件传递给单击事件处理函数

在ReactJS中使用迭代时如何将onClick事件传递给父组件?