diff options
author | Johan Klokkhammer Helsing <johan.helsing@qt.io> | 2019-02-06 09:30:09 +0100 |
---|---|---|
committer | Johan Helsing <johan.helsing@qt.io> | 2019-02-27 14:05:12 +0000 |
commit | 9b05557a6325497485b582c3891367aa7dfee245 (patch) | |
tree | 1a41664042efc8fab499cf3828e5868d79cc7776 /src/client/qwaylandinputdevice.cpp | |
parent | 539bba3f334843772e2ff9569f2bce633ce191f0 (diff) |
Client: Don't send illegal wl_pointer.set_cursor requests
When the cursor focus' wl_surface is destroyed, or the pointer leaves a
surface, we have to reset the enter serial to avoid sending illegal set_cursor
requests.
Change-Id: I0c886e4123acb4aebd325b07bf15b9d3fa8589da
Reviewed-by: Giulio Camuffo <giulio.camuffo@kdab.com>
Diffstat (limited to 'src/client/qwaylandinputdevice.cpp')
-rw-r--r-- | src/client/qwaylandinputdevice.cpp | 23 |
1 files changed, 21 insertions, 2 deletions
diff --git a/src/client/qwaylandinputdevice.cpp b/src/client/qwaylandinputdevice.cpp index 65267869f..76000e542 100644 --- a/src/client/qwaylandinputdevice.cpp +++ b/src/client/qwaylandinputdevice.cpp @@ -209,7 +209,9 @@ public: void hide() { - m_pointer->set_cursor(m_pointer->mEnterSerial, nullptr, 0, 0); + uint serial = m_pointer->mEnterSerial; + Q_ASSERT(serial); + m_pointer->set_cursor(serial, nullptr, 0, 0); m_setSerial = 0; } @@ -581,7 +583,16 @@ void QWaylandInputDevice::Pointer::pointer_enter(uint32_t serial, struct wl_surf return; QWaylandWindow *window = QWaylandWindow::fromWlSurface(surface); + + if (mFocus) { + qWarning(lcQpaWayland) << "The compositor sent a wl_pointer.enter event before sending a" + << "leave event first, this is not allowed by the wayland protocol" + << "attempting to work around it by invalidating the current focus"; + invalidateFocus(); + } mFocus = window; + connect(mFocus, &QWaylandWindow::wlSurfaceDestroyed, this, &Pointer::handleFocusDestroyed); + mSurfacePos = QPointF(wl_fixed_to_double(sx), wl_fixed_to_double(sy)); mGlobalPos = window->window()->mapToGlobal(mSurfacePos.toPoint()); @@ -611,7 +622,8 @@ void QWaylandInputDevice::Pointer::pointer_leave(uint32_t time, struct wl_surfac QWaylandWindow *window = QWaylandWindow::fromWlSurface(surface); window->handleMouseLeave(mParent); } - mFocus = nullptr; + + invalidateFocus(); mButtons = Qt::NoButton; mParent->mTime = time; @@ -714,6 +726,13 @@ void QWaylandInputDevice::Pointer::pointer_button(uint32_t serial, uint32_t time } } +void QWaylandInputDevice::Pointer::invalidateFocus() +{ + disconnect(mFocus, &QWaylandWindow::wlSurfaceDestroyed, this, &Pointer::handleFocusDestroyed); + mFocus = nullptr; + mEnterSerial = 0; +} + void QWaylandInputDevice::Pointer::releaseButtons() { mButtons = Qt::NoButton; |