【问题标题】:Why does my QGestureRecognizer not receive Touch Events?为什么我的 QGestureRecognizer 没有收到触摸事件?
【发布时间】:2014-04-29 15:48:50
【问题描述】:

上下文:我正在尝试创建一个类似推子的小部件,它可以在同一视图中有多个实例,每个实例都可以由不同的手指同时控制。

我想使用 Qt 的gesture recognition system,但我还需要一些超出标准Qt::PanGesture 的功能。为此,我对QGestureQGestureRecognizer 进行了子类化。在FooGestureRecognizer::recognize(...),我目前正在拦截QMouseEvents 和QTouchEvents(至少目前是这样)。

在 Windows 上,我只收到 QMouseEvents - 我处理它们并且一切都按预期工作(尽管当我的输入来自物理鼠标时,显然我不必处理多点触控问题)。我收到的事件(按顺序):

  • QEvent::MouseButtonPress
  • 一串QEvent::MouseMoves
  • QEvent::MouseButtonRelease

在 Android 上,我收到了 QMouseEvents 和 QTouchEvents 的奇怪组合(按顺序):

  • QEvent::TouchBegin
  • QEvent::MouseButtonPress
  • QEvent::MouseMove(位置没有实际变化)
  • 另一个QEvent::MouseButtonPress(不知道为什么我需要另一个)
  • 我的实际字符串QEvent::MouseMoves,如预期的那样
  • QEvent::MouseButtonRelease

全局属性Qt::AA_SynthesizeMouseForUnhandledTouchEvents默认为true。关闭它会将我收到的事件更改为:

  • QEvent::TouchBegin

...没有别的了。

这是一个前兆问题:我可以在QGestureRecognizer::recognize() 中做什么来告诉Qt 我正在处理QEvent::TouchBegin,并且它不需要为我合成QEvent::MouseButtonPressevent->accept() 似乎没有任何区别。

实际问题:如果(看起来)Qt 正在从TouchEvents 合成MouseEvents,为什么我看到我看到QEvent::MouseMoveQEvent::MouseButtonRelease 而不是QEvent::TouchUpdate 或@987654353 @?

代码可用,但为了简洁起见,我没有将其包含在此处。如有需要请询问。

【问题讨论】:

    标签: android c++ qt qt5 qt5.2


    【解决方案1】:

    来自QTouchEvent docs

    QEvent::TouchUpdate 和 QEvent::TouchEnd 事件被发送到接受 QEvent::TouchBegin 事件的小部件或项目。如果 QEvent::TouchBegin 事件未被接受且未被事件过滤器过滤,则在下一个 QEvent::TouchBegin 之前不会发送更多触摸事件。

    这个问题的根源在于QGestureRecognizer 不接受初始的TouchBegin,因此我们不会收到任何进一步的触摸事件。我通过以下方式解决了这个问题:

    1. 创建我的QGestureRecognizer 拥有的精简事件过滤器QObject

    包含以下代码:

    bool FooGestureRecognizer::FooEventFilter::eventFilter(QObject *Object, QEvent *Event)
    {
      if(Event->type() == QEvent::TouchBegin)
      {
        return true;
      }
      else
      {
        return QObject::eventFilter(Object, Event);
      }
    }
    
    1. 安装我的事件过滤器并在通过FooGestureRecognizer::create() 的每个有效* Target 上调用setAttribute(Qt::WA_AcceptTouchEvents)

    eventFilter返回true告诉Qt我的推子有兴趣接收更多的触摸事件,这些触摸事件按预期传递给手势识别器。

    这个解决方案感觉像是一个 hack,在未来的 Qt 版本中可能不需要,所以我会密切关注这个代码。

    注意事项:

    • QGestureRecognizer 的构造过程中,create() 被调用,并带有一个空的Target(期望返回一个虚拟的QGesture)。如果您在所有 Targets 上安装事件过滤器,请注意这一点。
    • 我的应用程序需要以一种方式处理桌面鼠标事件,并以另一种方式处理多指触摸事件,因此我禁用了Qt::AA_SynthesizeMouseForUnhandledTouchEvents。保持此启用可能会导致其他注意事项(例如,我不确定您是否需要 return true 处理 eventFilter 中的所有触摸事件,以避免它们被复制为合成鼠标事件)。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多