[Bf-blender-cvs] [1cf64434ed1] master: Fix accessing cursor position for GHOST/Wayland

Campbell Barton noreply at git.blender.org
Thu Jun 30 15:49:17 CEST 2022


Commit: 1cf64434ed1aa2a3be65c73c61e030745a597858
Author: Campbell Barton
Date:   Thu Jun 30 22:53:24 2022 +1000
Branches: master
https://developer.blender.org/rB1cf64434ed1aa2a3be65c73c61e030745a597858

Fix accessing cursor position for GHOST/Wayland

GHOST_GetCursorPosition wasn't working properly under Wayland because
the last focused window didn't necessarily match the window used to call
wm_cursor_position_get(..).

Now the window passed into wm_cursor_position_get is passed to GHOST
so that window is used to access cursor coordinates.

===================================================================

M	intern/ghost/intern/GHOST_SystemWayland.cpp
M	intern/ghost/intern/GHOST_SystemWayland.h

===================================================================

diff --git a/intern/ghost/intern/GHOST_SystemWayland.cpp b/intern/ghost/intern/GHOST_SystemWayland.cpp
index af629e83b19..cec06ed6a50 100644
--- a/intern/ghost/intern/GHOST_SystemWayland.cpp
+++ b/intern/ghost/intern/GHOST_SystemWayland.cpp
@@ -2649,58 +2649,100 @@ uint8_t GHOST_SystemWayland::getNumDisplays() const
   return d ? uint8_t(d->outputs.size()) : 0;
 }
 
-GHOST_TSuccess GHOST_SystemWayland::getCursorPosition(int32_t &x, int32_t &y) const
+static GHOST_TSuccess getCursorPositionClientRelative_impl(
+    const input_state_pointer_t *input_state,
+    const GHOST_WindowWayland *win,
+    int32_t &x,
+    int32_t &y)
 {
-  if (d->inputs.empty()) {
+  const wl_fixed_t scale = win->scale();
+  x = wl_fixed_to_int(scale * input_state->xy[0]);
+  y = wl_fixed_to_int(scale * input_state->xy[1]);
+  return GHOST_kSuccess;
+}
+
+static GHOST_TSuccess setCursorPositionClientRelative_impl(input_t *input,
+                                                           GHOST_WindowWayland *win,
+                                                           const int32_t x,
+                                                           const int32_t y)
+{
+  /* NOTE: WAYLAND doesn't support warping the cursor.
+   * However when grab is enabled, we already simulate a cursor location
+   * so that can be set to a new location. */
+  if (!input->relative_pointer) {
     return GHOST_kFailure;
   }
+  const wl_fixed_t scale = win->scale();
+  const wl_fixed_t xy_next[2] = {
+      wl_fixed_from_int(x) / scale,
+      wl_fixed_from_int(y) / scale,
+  };
 
+  /* As the cursor was "warped" generate an event at the new location. */
+  relative_pointer_handle_relative_motion_impl(input, win, xy_next);
+
+  return GHOST_kSuccess;
+}
+
+GHOST_TSuccess GHOST_SystemWayland::getCursorPositionClientRelative(const GHOST_IWindow *window,
+                                                                    int32_t &x,
+                                                                    int32_t &y) const
+{
+  if (d->inputs.empty()) {
+    return GHOST_kFailure;
+  }
   input_t *input = d->inputs[0];
   input_state_pointer_t *input_state = input_state_pointer_active(input);
-
   if (!input_state || !input_state->wl_surface) {
     return GHOST_kFailure;
   }
+  const GHOST_WindowWayland *win = static_cast<const GHOST_WindowWayland *>(window);
+  return getCursorPositionClientRelative_impl(input_state, win, x, y);
+}
 
-  GHOST_WindowWayland *win = static_cast<GHOST_WindowWayland *>(
-      wl_surface_get_user_data(input_state->wl_surface));
-  if (!win) {
+GHOST_TSuccess GHOST_SystemWayland::setCursorPositionClientRelative(GHOST_IWindow *window,
+                                                                    const int32_t x,
+                                                                    const int32_t y)
+{
+  if (d->inputs.empty()) {
     return GHOST_kFailure;
   }
+  input_t *input = d->inputs[0];
+  GHOST_WindowWayland *win = static_cast<GHOST_WindowWayland *>(window);
+  return setCursorPositionClientRelative_impl(input, win, x, y);
+}
 
-  const wl_fixed_t scale = win->scale();
-  x = wl_fixed_to_int(scale * input_state->xy[0]);
-  y = wl_fixed_to_int(scale * input_state->xy[1]);
-  return GHOST_kSuccess;
+GHOST_TSuccess GHOST_SystemWayland::getCursorPosition(int32_t &x, int32_t &y) const
+{
+  if (d->inputs.empty()) {
+    return GHOST_kFailure;
+  }
+  input_t *input = d->inputs[0];
+  input_state_pointer_t *input_state = input_state_pointer_active(input);
+  if (!input_state || !input_state->wl_surface) {
+    return GHOST_kFailure;
+  }
+  GHOST_WindowWayland *win = window_from_surface(input->pointer.wl_surface);
+  if (!win) {
+    return GHOST_kFailure;
+  }
+  return getCursorPositionClientRelative_impl(input_state, win, x, y);
 }
 
 GHOST_TSuccess GHOST_SystemWayland::setCursorPosition(const int32_t x, const int32_t y)
 {
-  /* NOTE: WAYLAND doesn't support warping the cursor.
-   * However when grab is enabled, we already simulate a cursor location
-   * so that can be set to a new location. */
   if (d->inputs.empty()) {
     return GHOST_kFailure;
   }
   input_t *input = d->inputs[0];
-  if (!input->relative_pointer) {
+  if (!input->pointer.wl_surface) {
     return GHOST_kFailure;
   }
-
   GHOST_WindowWayland *win = window_from_surface(input->pointer.wl_surface);
   if (!win) {
     return GHOST_kFailure;
   }
-  const wl_fixed_t scale = win->scale();
-  const wl_fixed_t xy_next[2] = {
-      wl_fixed_from_int(x) / scale,
-      wl_fixed_from_int(y) / scale,
-  };
-
-  /* As the cursor was "warped" generate an event at the new location. */
-  relative_pointer_handle_relative_motion_impl(input, win, xy_next);
-
-  return GHOST_kSuccess;
+  return setCursorPositionClientRelative_impl(input, win, x, y);
 }
 
 void GHOST_SystemWayland::getMainDisplayDimensions(uint32_t &width, uint32_t &height) const
diff --git a/intern/ghost/intern/GHOST_SystemWayland.h b/intern/ghost/intern/GHOST_SystemWayland.h
index 972d16257eb..7f7bd021bda 100644
--- a/intern/ghost/intern/GHOST_SystemWayland.h
+++ b/intern/ghost/intern/GHOST_SystemWayland.h
@@ -79,8 +79,14 @@ class GHOST_SystemWayland : public GHOST_System {
 
   uint8_t getNumDisplays() const override;
 
-  GHOST_TSuccess getCursorPosition(int32_t &x, int32_t &y) const override;
+  GHOST_TSuccess getCursorPositionClientRelative(const GHOST_IWindow *window,
+                                                 int32_t &x,
+                                                 int32_t &y) const override;
+  GHOST_TSuccess setCursorPositionClientRelative(GHOST_IWindow *window,
+                                                 int32_t x,
+                                                 int32_t y) override;
 
+  GHOST_TSuccess getCursorPosition(int32_t &x, int32_t &y) const override;
   GHOST_TSuccess setCursorPosition(int32_t x, int32_t y) override;
 
   void getMainDisplayDimensions(uint32_t &width, uint32_t &height) const override;



More information about the Bf-blender-cvs mailing list