diff --git a/patches/patchinstall.sh b/patches/patchinstall.sh index 74f34291..6df2c98f 100755 --- a/patches/patchinstall.sh +++ b/patches/patchinstall.sh @@ -217,6 +217,7 @@ patch_enable_all () enable_user32_message_order="$1" enable_user32_msgbox_Support_WM_COPY_mesg="$1" enable_user32_rawinput_mouse="$1" + enable_user32_rawinput_mouse_experimental="$1" enable_user32_recursive_activation="$1" enable_uxtheme_CloseThemeClass="$1" enable_version_VerQueryValue="$1" @@ -678,6 +679,9 @@ patch_enable () user32-rawinput-mouse) enable_user32_rawinput_mouse="$2" ;; + user32-rawinput-mouse-experimental) + enable_user32_rawinput_mouse_experimental="$2" + ;; user32-recursive-activation) enable_user32_recursive_activation="$2" ;; @@ -1189,6 +1193,13 @@ if test "$enable_wined3d_Indexed_Vertex_Blending" -eq 1; then enable_wined3d_SWVP_shaders=1 fi +if test "$enable_user32_rawinput_mouse_experimental" -eq 1; then + if test "$enable_user32_rawinput_mouse" -gt 1; then + abort "Patchset user32-rawinput-mouse disabled, but user32-rawinput-mouse-experimental depends on that." + fi + enable_user32_rawinput_mouse=1 +fi + if test "$enable_stdole32_tlb_SLTG_Typelib" -eq 1; then if test "$enable_widl_SLTG_Typelib_Support" -gt 1; then abort "Patchset widl-SLTG_Typelib_Support disabled, but stdole32.tlb-SLTG_Typelib depends on that." @@ -3361,6 +3372,26 @@ if test "$enable_user32_rawinput_mouse" -eq 1; then patch_apply user32-rawinput-mouse/0008-winex11.drv-Listen-to-RawMotion-and-RawButton-events.patch fi +# Patchset user32-rawinput-mouse-experimental +# | +# | This patchset has the following (direct or indirect) dependencies: +# | * user32-rawinput-mouse +# | +# | This patchset fixes the following Wine bugs: +# | * [#45882] - Raw Input should use untransformed mouse values (affects Overwatch, several Source games). +# | +# | Modified files: +# | * dlls/user32/rawinput.c, dlls/winex11.drv/mouse.c, server/queue.c +# | +if test "$enable_user32_rawinput_mouse_experimental" -eq 1; then + patch_apply user32-rawinput-mouse-experimental/0001-server-Clear-the-MOUSEEVENTF_-ABSOLUTE-VIRTUALDESK-f.patch + patch_apply user32-rawinput-mouse-experimental/0002-user32-Add-support-for-absolute-rawinput-messages.patch + patch_apply user32-rawinput-mouse-experimental/0003-server-Stop-enforcing-relative-rawinput-mouse-positi.patch + patch_apply user32-rawinput-mouse-experimental/0004-winex11.drv-Simplify-XInput2-valuator-lookup.patch + patch_apply user32-rawinput-mouse-experimental/0005-winex11.drv-Add-support-for-absolute-RawMotion-event.patch + patch_apply user32-rawinput-mouse-experimental/0006-winex11.drv-Send-relative-RawMotion-events-unprocess.patch +fi + # Patchset user32-recursive-activation # | # | This patchset fixes the following Wine bugs: diff --git a/patches/user32-rawinput-mouse-experimental/0001-server-Clear-the-MOUSEEVENTF_-ABSOLUTE-VIRTUALDESK-f.patch b/patches/user32-rawinput-mouse-experimental/0001-server-Clear-the-MOUSEEVENTF_-ABSOLUTE-VIRTUALDESK-f.patch new file mode 100644 index 00000000..c11df517 --- /dev/null +++ b/patches/user32-rawinput-mouse-experimental/0001-server-Clear-the-MOUSEEVENTF_-ABSOLUTE-VIRTUALDESK-f.patch @@ -0,0 +1,28 @@ +From e158845b33737d5b9524a668683e477fd4283b9f Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?R=C3=A9mi=20Bernon?= +Date: Thu, 28 Oct 2021 09:11:02 +0200 +Subject: [PATCH 1/6] server: Clear the MOUSEEVENTF_(ABSOLUTE|VIRTUALDESK) + flags. + +For rawinput messages, as user32 is currently only expecting relative +motion. +--- + server/queue.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/server/queue.c b/server/queue.c +index 6713b58c468..d580f9acf1f 100644 +--- a/server/queue.c ++++ b/server/queue.c +@@ -1803,7 +1803,7 @@ static int queue_mouse_message( struct desktop *desktop, user_handle_t win, cons + msg_data = &raw_msg.data; + msg_data->info = input->mouse.info; + msg_data->size = sizeof(*msg_data); +- msg_data->flags = flags; ++ msg_data->flags = flags & ~(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_VIRTUALDESK); + msg_data->rawinput.type = RIM_TYPEMOUSE; + msg_data->rawinput.mouse.x = x - desktop->cursor.x; + msg_data->rawinput.mouse.y = y - desktop->cursor.y; +-- +2.33.0 + diff --git a/patches/user32-rawinput-mouse-experimental/0001-winex11.drv-Add-support-for-absolute-RawMotion-event.patch b/patches/user32-rawinput-mouse-experimental/0001-winex11.drv-Add-support-for-absolute-RawMotion-event.patch deleted file mode 100644 index 9fee3e5a..00000000 --- a/patches/user32-rawinput-mouse-experimental/0001-winex11.drv-Add-support-for-absolute-RawMotion-event.patch +++ /dev/null @@ -1,303 +0,0 @@ -From 95da86f70402fee377fa67309fa44f0a4f33e2fa Mon Sep 17 00:00:00 2001 -From: Derek Lesho -Date: Tue, 25 Jun 2019 22:37:34 -0400 -Subject: [PATCH] winex11.drv: Add support for absolute RawMotion events. - -When running Xwayland, or using pointing devices, the valuators may -provide absolute values only. In which case, we should translate the -events to the corresponding absolute rawinput messages. - -The server side was trying to convert all rawinput messages to relative -positions, but it may not be correct as the desktop cursor position may -not be initialized yet. Keeping the values absolute if we received them -this way seems more reliable. - -Note that we cannot really trust valuator names, as it is possible to -configure a pointing device to work in relative mode - wacom tablets for -example - while their axis valuators keep their "Abs X/Y" name. We can -however use the valuator mode to distinguish between relative movements -and absolute position events. ---- - dlls/user32/rawinput.c | 12 +++-- - dlls/winex11.drv/mouse.c | 94 +++++++++++++++++++++------------- - dlls/winex11.drv/window.c | 3 +- - dlls/winex11.drv/x11drv.h | 18 +++---- - dlls/winex11.drv/x11drv_main.c | 2 + - server/queue.c | 4 +- - 6 files changed, 83 insertions(+), 50 deletions(-) - -diff --git a/dlls/user32/rawinput.c b/dlls/user32/rawinput.c -index e08d11bc20a..8ea3108560b 100644 ---- a/dlls/user32/rawinput.c -+++ b/dlls/user32/rawinput.c -@@ -316,9 +316,15 @@ BOOL rawinput_from_hardware_message(RAWINPUT *rawinput, const struct hardware_ms - rawinput->header.hDevice = WINE_MOUSE_HANDLE; - rawinput->header.wParam = 0; - -- rawinput->data.mouse.usFlags = MOUSE_MOVE_RELATIVE; -- rawinput->data.mouse.usButtonFlags = 0; -- rawinput->data.mouse.usButtonData = 0; -+ if (msg_data->flags & MOUSEEVENTF_ABSOLUTE) -+ rawinput->data.mouse.usFlags = MOUSE_MOVE_ABSOLUTE; -+ else -+ rawinput->data.mouse.usFlags = MOUSE_MOVE_RELATIVE; -+ if (msg_data->flags & MOUSEEVENTF_VIRTUALDESK) -+ rawinput->data.mouse.usFlags |= MOUSE_VIRTUAL_DESKTOP; -+ rawinput->data.mouse.usButtonFlags = 0; -+ rawinput->data.mouse.usButtonData = 0; -+ - for (i = 1; i < ARRAY_SIZE(button_flags); ++i) - { - if (msg_data->flags & (1 << i)) -diff --git a/dlls/winex11.drv/mouse.c b/dlls/winex11.drv/mouse.c -index 7ff360d5127..76d2ba510da 100644 ---- a/dlls/winex11.drv/mouse.c -+++ b/dlls/winex11.drv/mouse.c -@@ -331,32 +331,40 @@ static void update_relative_valuators(XIAnyClassInfo **valuators, int n_valuator - struct x11drv_thread_data *thread_data = x11drv_thread_data(); - int i; - -- thread_data->x_rel_valuator.number = -1; -- thread_data->y_rel_valuator.number = -1; -+ thread_data->x_pos_valuator.number = -1; -+ thread_data->y_pos_valuator.number = -1; - - for (i = 0; i < n_valuators; i++) - { - XIValuatorClassInfo *class = (XIValuatorClassInfo *)valuators[i]; -- struct x11drv_valuator_data *valuator_data = NULL; - -- if (valuators[i]->type != XIValuatorClass) continue; -- if (class->label == x11drv_atom( Rel_X ) || -- (!class->label && class->number == 0 && class->mode == XIModeRelative)) -- { -- valuator_data = &thread_data->x_rel_valuator; -- } -+ if (valuators[i]->type != XIValuatorClass) -+ continue; -+ else if (class->label == x11drv_atom( Rel_X ) || -+ class->label == x11drv_atom( Abs_X ) || -+ (!class->label && class->number == 0)) -+ thread_data->x_pos_valuator = *class; - else if (class->label == x11drv_atom( Rel_Y ) || -- (!class->label && class->number == 1 && class->mode == XIModeRelative)) -- { -- valuator_data = &thread_data->y_rel_valuator; -- } -+ class->label == x11drv_atom( Abs_Y ) || -+ (!class->label && class->number == 1)) -+ thread_data->y_pos_valuator = *class; -+ } - -- if (valuator_data) { -- valuator_data->number = class->number; -- valuator_data->min = class->min; -- valuator_data->max = class->max; -- } -+ if (thread_data->x_pos_valuator.number < 0 || thread_data->y_pos_valuator.number < 0) -+ { -+ WARN("Only one X/Y axis found, ignoring RawMotion events\n"); - } -+ else if (thread_data->x_pos_valuator.mode != thread_data->y_pos_valuator.mode) -+ { -+ WARN("Relative/Absolute mismatch between X/Y axis, ignoring RawMotion events\n"); -+ thread_data->y_pos_valuator.number = -1; -+ thread_data->y_pos_valuator.number = -1; -+ } -+ -+ if (thread_data->x_pos_valuator.min >= thread_data->x_pos_valuator.max) -+ thread_data->x_pos_valuator.min = thread_data->x_pos_valuator.max = 0; -+ if (thread_data->y_pos_valuator.min >= thread_data->y_pos_valuator.max) -+ thread_data->y_pos_valuator.min = thread_data->y_pos_valuator.max = 0; - } - #endif - -@@ -478,8 +486,8 @@ void x11drv_xinput_disable( Display *display, Window window, long event_mask ) - pXISelectEvents( display, DefaultRootWindow( display ), &mask, 1 ); - - if (!data) return; -- data->x_rel_valuator.number = -1; -- data->y_rel_valuator.number = -1; -+ data->x_pos_valuator.number = -1; -+ data->y_pos_valuator.number = -1; - data->xi2_core_pointer = 0; - data->xi2_state = xi_disabled; - #endif -@@ -1950,16 +1958,22 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) - INPUT input; - int i; - double dx = 0, dy = 0, val; -+ double x_scale = 1, y_scale = 1; - struct x11drv_thread_data *thread_data = x11drv_thread_data(); -- struct x11drv_valuator_data *x_rel, *y_rel; -+ XIValuatorClassInfo *x_pos, *y_pos; - -- if (thread_data->x_rel_valuator.number < 0 || thread_data->y_rel_valuator.number < 0) return FALSE; -+ if (thread_data->x_pos_valuator.number < 0 || thread_data->y_pos_valuator.number < 0) return FALSE; -+ if (thread_data->x_pos_valuator.mode != thread_data->y_pos_valuator.mode) -+ { -+ FIXME("Unsupported relative/absolute X/Y axis mismatch\n."); -+ return FALSE; -+ } - if (!event->valuators.mask_len) return FALSE; - if (thread_data->xi2_state != xi_enabled) return FALSE; - if (event->deviceid != thread_data->xi2_core_pointer) return FALSE; - -- x_rel = &thread_data->x_rel_valuator; -- y_rel = &thread_data->y_rel_valuator; -+ x_pos = &thread_data->x_pos_valuator; -+ y_pos = &thread_data->y_pos_valuator; - - input.type = INPUT_MOUSE; - input.u.mi.mouseData = 0; -@@ -1970,24 +1984,34 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) - input.u.mi.dy = 0; - - virtual_rect = get_virtual_screen_rect(); -+ if (x_pos->min < x_pos->max) -+ x_scale = (x_pos->mode == XIModeAbsolute ? 65535 : (virtual_rect.right - virtual_rect.left)) / -+ (x_pos->max - x_pos->min); -+ if (y_pos->min < y_pos->max) -+ y_scale = (y_pos->mode == XIModeAbsolute ? 65535 : (virtual_rect.bottom - virtual_rect.top)) / -+ (y_pos->max - y_pos->min); - -- for (i = 0; i <= max ( x_rel->number, y_rel->number ); i++) -+ for (i = 0; i <= max( x_pos->number, y_pos->number ); i++) - { - if (!XIMaskIsSet( event->valuators.mask, i )) continue; - val = *values++; -- if (i == x_rel->number) -+ if (i == x_pos->number) - { -- input.u.mi.dx = dx = val; -- if (x_rel->min < x_rel->max) -- input.u.mi.dx = val * (virtual_rect.right - virtual_rect.left) -- / (x_rel->max - x_rel->min); -+ dx = val; -+ input.u.mi.dwFlags |= (x_pos->mode == XIModeAbsolute ? MOUSEEVENTF_ABSOLUTE : 0); -+ if (x_pos->mode == XIModeAbsolute) -+ input.u.mi.dx = (dx - x_pos->min) * x_scale; -+ else -+ input.u.mi.dx = dx * x_scale; - } -- if (i == y_rel->number) -+ if (i == y_pos->number) - { -- input.u.mi.dy = dy = val; -- if (y_rel->min < y_rel->max) -- input.u.mi.dy = val * (virtual_rect.bottom - virtual_rect.top) -- / (y_rel->max - y_rel->min); -+ dy = val; -+ input.u.mi.dwFlags |= (y_pos->mode == XIModeAbsolute ? MOUSEEVENTF_ABSOLUTE : 0); -+ if (y_pos->mode == XIModeAbsolute) -+ input.u.mi.dy = (dy - y_pos->min) * y_scale; -+ else -+ input.u.mi.dy = dy * y_scale; - } - } - -diff --git a/dlls/winex11.drv/window.c b/dlls/winex11.drv/window.c -index 94844fffcdd..da5b8df943f 100644 ---- a/dlls/winex11.drv/window.c -+++ b/dlls/winex11.drv/window.c -@@ -37,6 +37,8 @@ - #include - #endif /* HAVE_LIBXSHAPE */ - -+#include "x11drv.h" -+ - /* avoid conflict with field names in included win32 headers */ - #undef Status - #include "windef.h" -@@ -45,7 +47,6 @@ - #include "winuser.h" - #include "wine/unicode.h" - --#include "x11drv.h" - #include "wine/debug.h" - #include "wine/server.h" - #include "mwm.h" -diff --git a/dlls/winex11.drv/x11drv.h b/dlls/winex11.drv/x11drv.h -index 5f096b5d086..c1ed6eea1de 100644 ---- a/dlls/winex11.drv/x11drv.h -+++ b/dlls/winex11.drv/x11drv.h -@@ -32,6 +32,9 @@ - #include - #include - #include -+#ifdef HAVE_X11_EXTENSIONS_XINPUT2_H -+#include -+#endif - - #define BOOL X_BOOL - #define BYTE X_BYTE -@@ -320,13 +323,6 @@ struct x11drv_escape_flush_gl_drawable - * X11 USER driver - */ - --struct x11drv_valuator_data --{ -- double min; -- double max; -- int number; --}; -- - enum xi2_state - { - xi_unavailable = -1, -@@ -350,11 +346,13 @@ struct x11drv_thread_data - Window clip_window; /* window used for cursor clipping */ - HWND clip_hwnd; /* message window stored in desktop while clipping is active */ - DWORD clip_reset; /* time when clipping was last reset */ -+#ifdef HAVE_X11_EXTENSIONS_XINPUT2_H - enum xi2_state xi2_state; /* XInput2 state */ -- struct x11drv_valuator_data x_rel_valuator; -- struct x11drv_valuator_data y_rel_valuator; -+ XIValuatorClassInfo x_pos_valuator; -+ XIValuatorClassInfo y_pos_valuator; - int xi2_core_pointer; /* XInput2 core pointer id */ - int xi2_rawinput_only; -+#endif - }; - - extern struct x11drv_thread_data *x11drv_init_thread_data(void) DECLSPEC_HIDDEN; -@@ -439,6 +437,8 @@ enum x11drv_atoms - XATOM_RAW_CAP_HEIGHT, - XATOM_Rel_X, - XATOM_Rel_Y, -+ XATOM_Abs_X, -+ XATOM_Abs_Y, - XATOM_WM_PROTOCOLS, - XATOM_WM_DELETE_WINDOW, - XATOM_WM_STATE, -diff --git a/dlls/winex11.drv/x11drv_main.c b/dlls/winex11.drv/x11drv_main.c -index 369515bba71..6f1e8c6cfb6 100644 ---- a/dlls/winex11.drv/x11drv_main.c -+++ b/dlls/winex11.drv/x11drv_main.c -@@ -142,6 +142,8 @@ static const char * const atom_names[NB_XATOMS - FIRST_XATOM] = - "RAW_CAP_HEIGHT", - "Rel X", - "Rel Y", -+ "Abs X", -+ "Abs Y", - "WM_PROTOCOLS", - "WM_DELETE_WINDOW", - "WM_STATE", -diff --git a/server/queue.c b/server/queue.c -index 99cfecf2507..fc86371862d 100644 ---- a/server/queue.c -+++ b/server/queue.c -@@ -1886,8 +1886,8 @@ static int queue_mouse_message( struct desktop *desktop, user_handle_t win, cons - msg_data->size = sizeof(*msg_data); - msg_data->flags = flags; - msg_data->rawinput.type = RIM_TYPEMOUSE; -- msg_data->rawinput.mouse.x = x - desktop->cursor.x; -- msg_data->rawinput.mouse.y = y - desktop->cursor.y; -+ msg_data->rawinput.mouse.x = input->mouse.x; -+ msg_data->rawinput.mouse.y = input->mouse.y; - msg_data->rawinput.mouse.data = input->mouse.data; - - enum_processes( queue_rawinput_message, &raw_msg ); --- -2.30.2 - diff --git a/patches/user32-rawinput-mouse-experimental/0002-user32-Add-support-for-absolute-rawinput-messages.patch b/patches/user32-rawinput-mouse-experimental/0002-user32-Add-support-for-absolute-rawinput-messages.patch new file mode 100644 index 00000000..b41cfbe4 --- /dev/null +++ b/patches/user32-rawinput-mouse-experimental/0002-user32-Add-support-for-absolute-rawinput-messages.patch @@ -0,0 +1,27 @@ +From 0785a15e720e552f65140f69ca40bac7e503dca1 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?R=C3=A9mi=20Bernon?= +Date: Mon, 25 Oct 2021 11:26:43 +0200 +Subject: [PATCH 2/6] user32: Add support for absolute rawinput messages. + +--- + dlls/user32/rawinput.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/dlls/user32/rawinput.c b/dlls/user32/rawinput.c +index 3a316024656..d2c1f1cf2b5 100644 +--- a/dlls/user32/rawinput.c ++++ b/dlls/user32/rawinput.c +@@ -316,7 +316,9 @@ BOOL rawinput_from_hardware_message(RAWINPUT *rawinput, const struct hardware_ms + rawinput->header.hDevice = WINE_MOUSE_HANDLE; + rawinput->header.wParam = 0; + +- rawinput->data.mouse.usFlags = MOUSE_MOVE_RELATIVE; ++ rawinput->data.mouse.usFlags = msg_data->flags & MOUSEEVENTF_ABSOLUTE ? MOUSE_MOVE_ABSOLUTE : MOUSE_MOVE_RELATIVE; ++ if (msg_data->flags & MOUSEEVENTF_VIRTUALDESK) rawinput->data.mouse.usFlags |= MOUSE_VIRTUAL_DESKTOP; ++ + rawinput->data.mouse.usButtonFlags = 0; + rawinput->data.mouse.usButtonData = 0; + for (i = 1; i < ARRAY_SIZE(button_flags); ++i) +-- +2.33.0 + diff --git a/patches/user32-rawinput-mouse-experimental/0002-winex11.drv-Send-relative-RawMotion-events-unprocess.patch b/patches/user32-rawinput-mouse-experimental/0002-winex11.drv-Send-relative-RawMotion-events-unprocess.patch deleted file mode 100644 index 071f1f76..00000000 --- a/patches/user32-rawinput-mouse-experimental/0002-winex11.drv-Send-relative-RawMotion-events-unprocess.patch +++ /dev/null @@ -1,78 +0,0 @@ -From fff35d809015ea53a7195122482e80a2dd366b9e Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?R=C3=A9mi=20Bernon?= -Date: Tue, 10 Sep 2019 12:24:22 +0200 -Subject: [PATCH] winex11.drv: Send relative RawMotion events unprocessed. - -This makes relative raw input independent from cursor speed, as it is -the case on Windows. Absolute raw input is already translated to -virtual desktop space, and cursor speed is meaningless in this case. - -This does not support mixed relative/absolute X/Y axis. ---- - dlls/winex11.drv/mouse.c | 16 +++++++++++----- - 1 file changed, 11 insertions(+), 5 deletions(-) - -diff --git a/dlls/winex11.drv/mouse.c b/dlls/winex11.drv/mouse.c -index dcc9fe82fd1..44e9786cd9f 100644 ---- a/dlls/winex11.drv/mouse.c -+++ b/dlls/winex11.drv/mouse.c -@@ -1953,21 +1953,18 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) - { - XIRawEvent *event = xev->data; - const double *values = event->valuators.values; -+ const double *raw_values = event->raw_values; - RECT virtual_rect; - RAWINPUT rawinput; - INPUT input; - int i; - double dx = 0, dy = 0, val; -+ double raw_dx = 0, raw_dy = 0, raw_val; - double x_scale = 1, y_scale = 1; - struct x11drv_thread_data *thread_data = x11drv_thread_data(); - XIValuatorClassInfo *x_pos, *y_pos; - - if (thread_data->x_pos_valuator.number < 0 || thread_data->y_pos_valuator.number < 0) return FALSE; -- if (thread_data->x_pos_valuator.mode != thread_data->y_pos_valuator.mode) -- { -- FIXME("Unsupported relative/absolute X/Y axis mismatch\n."); -- return FALSE; -- } - if (!event->valuators.mask_len) return FALSE; - if (thread_data->xi2_state != xi_enabled) return FALSE; - if (event->deviceid != thread_data->xi2_core_pointer) return FALSE; -@@ -1995,9 +1992,11 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) - { - if (!XIMaskIsSet( event->valuators.mask, i )) continue; - val = *values++; -+ raw_val = *raw_values++; - if (i == x_pos->number) - { - dx = val; -+ raw_dx = raw_val; - input.u.mi.dwFlags |= (x_pos->mode == XIModeAbsolute ? MOUSEEVENTF_ABSOLUTE : 0); - if (x_pos->mode == XIModeAbsolute) - input.u.mi.dx = (dx - x_pos->min) * x_scale; -@@ -2007,6 +2006,7 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) - if (i == y_pos->number) - { - dy = val; -+ raw_dy = raw_val; - input.u.mi.dwFlags |= (y_pos->mode == XIModeAbsolute ? MOUSEEVENTF_ABSOLUTE : 0); - if (y_pos->mode == XIModeAbsolute) - input.u.mi.dy = (dy - y_pos->min) * y_scale; -@@ -2028,6 +2028,12 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) - } - else - { -+ if (x_pos->mode != XIModeAbsolute) -+ { -+ input.u.mi.dx = raw_dx; -+ input.u.mi.dy = raw_dy; -+ } -+ - TRACE( "raw pos %d,%d (event %f,%f)\n", input.u.mi.dx, input.u.mi.dy, dx, dy ); - - rawinput.header.dwType = RIM_TYPEMOUSE; --- -2.30.2 - diff --git a/patches/user32-rawinput-mouse-experimental/0003-server-Stop-enforcing-relative-rawinput-mouse-positi.patch b/patches/user32-rawinput-mouse-experimental/0003-server-Stop-enforcing-relative-rawinput-mouse-positi.patch new file mode 100644 index 00000000..b275c487 --- /dev/null +++ b/patches/user32-rawinput-mouse-experimental/0003-server-Stop-enforcing-relative-rawinput-mouse-positi.patch @@ -0,0 +1,30 @@ +From 8a34dbf24db2f4b11421889770732c2b65ebca3a Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?R=C3=A9mi=20Bernon?= +Date: Mon, 25 Oct 2021 11:22:04 +0200 +Subject: [PATCH 3/6] server: Stop enforcing relative rawinput mouse positions. + +--- + server/queue.c | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +diff --git a/server/queue.c b/server/queue.c +index d580f9acf1f..c4c97c04f2e 100644 +--- a/server/queue.c ++++ b/server/queue.c +@@ -1803,10 +1803,10 @@ static int queue_mouse_message( struct desktop *desktop, user_handle_t win, cons + msg_data = &raw_msg.data; + msg_data->info = input->mouse.info; + msg_data->size = sizeof(*msg_data); +- msg_data->flags = flags & ~(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_VIRTUALDESK); ++ msg_data->flags = flags; + msg_data->rawinput.type = RIM_TYPEMOUSE; +- msg_data->rawinput.mouse.x = x - desktop->cursor.x; +- msg_data->rawinput.mouse.y = y - desktop->cursor.y; ++ msg_data->rawinput.mouse.x = (flags & MOUSEEVENTF_MOVE) ? input->mouse.x : 0; ++ msg_data->rawinput.mouse.y = (flags & MOUSEEVENTF_MOVE) ? input->mouse.y : 0; + msg_data->rawinput.mouse.data = input->mouse.data; + + enum_processes( queue_rawinput_message, &raw_msg ); +-- +2.33.0 + diff --git a/patches/user32-rawinput-mouse-experimental/0004-winex11.drv-Simplify-XInput2-valuator-lookup.patch b/patches/user32-rawinput-mouse-experimental/0004-winex11.drv-Simplify-XInput2-valuator-lookup.patch new file mode 100644 index 00000000..d068a5f4 --- /dev/null +++ b/patches/user32-rawinput-mouse-experimental/0004-winex11.drv-Simplify-XInput2-valuator-lookup.patch @@ -0,0 +1,57 @@ +From 7fee08463639411efb2b53d7abee8e064afae2b1 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?R=C3=A9mi=20Bernon?= +Date: Sun, 24 Oct 2021 16:27:40 +0200 +Subject: [PATCH 4/6] winex11.drv: Simplify XInput2 valuator lookup. + +Valuator names aren't well specified, and although they usually are +Rel X/Y or Abs X/Y, there are cases where the X/Y names are something +else. Just assume that the first two valuators are the X/Y axes, as it +seems to be generally the case. +--- + dlls/winex11.drv/mouse.c | 21 ++++++++++----------- + 1 file changed, 10 insertions(+), 11 deletions(-) + +diff --git a/dlls/winex11.drv/mouse.c b/dlls/winex11.drv/mouse.c +index 0eaae753f87..0a48be26bd0 100644 +--- a/dlls/winex11.drv/mouse.c ++++ b/dlls/winex11.drv/mouse.c +@@ -328,26 +328,25 @@ void X11DRV_InitMouse( Display *display ) + /*********************************************************************** + * update_relative_valuators + */ +-static void update_relative_valuators(XIAnyClassInfo **valuators, int n_valuators) ++static void update_relative_valuators( XIAnyClassInfo **classes, int num_classes ) + { + struct x11drv_thread_data *thread_data = x11drv_thread_data(); +- int i; ++ XIValuatorClassInfo *valuator; + + thread_data->x_valuator.number = -1; + thread_data->y_valuator.number = -1; + +- for (i = 0; i < n_valuators; i++) ++ while (num_classes--) + { +- XIValuatorClassInfo *class = (XIValuatorClassInfo *)valuators[i]; +- if (valuators[i]->type != XIValuatorClass) continue; +- if (class->label == x11drv_atom( Rel_X ) || +- (!class->label && class->number == 0 && class->mode == XIModeRelative)) +- thread_data->x_valuator = *class; +- else if (class->label == x11drv_atom( Rel_Y ) || +- (!class->label && class->number == 1 && class->mode == XIModeRelative)) +- thread_data->y_valuator = *class; ++ valuator = (XIValuatorClassInfo *)classes[num_classes]; ++ if (classes[num_classes]->type != XIValuatorClass) continue; ++ if (valuator->number == 0 && valuator->mode == XIModeRelative) thread_data->x_valuator = *valuator; ++ if (valuator->number == 1 && valuator->mode == XIModeRelative) thread_data->y_valuator = *valuator; + } + ++ if (thread_data->x_valuator.number < 0 || thread_data->y_valuator.number < 0) ++ WARN( "X/Y axis valuators not found, ignoring RawMotion events\n" ); ++ + thread_data->x_valuator.value = 0; + thread_data->y_valuator.value = 0; + } +-- +2.33.0 + diff --git a/patches/user32-rawinput-mouse-experimental/0005-winex11.drv-Add-support-for-absolute-RawMotion-event.patch b/patches/user32-rawinput-mouse-experimental/0005-winex11.drv-Add-support-for-absolute-RawMotion-event.patch new file mode 100644 index 00000000..220e2dce --- /dev/null +++ b/patches/user32-rawinput-mouse-experimental/0005-winex11.drv-Add-support-for-absolute-RawMotion-event.patch @@ -0,0 +1,80 @@ +From 852b1ef2128c34471f4fc6eaffa32f30a0c05b67 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?R=C3=A9mi=20Bernon?= +Date: Thu, 28 Oct 2021 09:18:37 +0200 +Subject: [PATCH 5/6] winex11.drv: Add support for absolute RawMotion events. + +--- + dlls/winex11.drv/mouse.c | 28 ++++++++++++++++++++++------ + 1 file changed, 22 insertions(+), 6 deletions(-) + +diff --git a/dlls/winex11.drv/mouse.c b/dlls/winex11.drv/mouse.c +index 0a48be26bd0..e6a2266855a 100644 +--- a/dlls/winex11.drv/mouse.c ++++ b/dlls/winex11.drv/mouse.c +@@ -340,12 +340,18 @@ static void update_relative_valuators( XIAnyClassInfo **classes, int num_classes + { + valuator = (XIValuatorClassInfo *)classes[num_classes]; + if (classes[num_classes]->type != XIValuatorClass) continue; +- if (valuator->number == 0 && valuator->mode == XIModeRelative) thread_data->x_valuator = *valuator; +- if (valuator->number == 1 && valuator->mode == XIModeRelative) thread_data->y_valuator = *valuator; ++ if (valuator->number == 0) thread_data->x_valuator = *valuator; ++ if (valuator->number == 1) thread_data->y_valuator = *valuator; + } + + if (thread_data->x_valuator.number < 0 || thread_data->y_valuator.number < 0) + WARN( "X/Y axis valuators not found, ignoring RawMotion events\n" ); ++ else if (thread_data->x_valuator.mode != thread_data->y_valuator.mode) ++ { ++ WARN( "Relative/Absolute mismatch between X/Y axis, ignoring RawMotion events\n" ); ++ thread_data->x_valuator.number = -1; ++ thread_data->y_valuator.number = -1; ++ } + + thread_data->x_valuator.value = 0; + thread_data->y_valuator.value = 0; +@@ -758,7 +764,15 @@ static BOOL map_raw_event_coords( XIRawEvent *event, INPUT *input ) + if (thread_data->xi2_state != xi_enabled) return FALSE; + if (event->deviceid != thread_data->xi2_core_pointer) return FALSE; + +- virtual_rect = get_virtual_screen_rect(); ++ if (x->mode == XIModeRelative && y->mode == XIModeRelative) ++ input->u.mi.dwFlags &= ~(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_VIRTUALDESK); ++ else if (x->mode == XIModeAbsolute && y->mode == XIModeAbsolute) ++ input->u.mi.dwFlags |= MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_VIRTUALDESK; ++ else ++ FIXME( "Unsupported relative/absolute X/Y axis mismatch\n." ); ++ ++ if (input->u.mi.dwFlags & MOUSEEVENTF_VIRTUALDESK) SetRect( &virtual_rect, 0, 0, 65535, 65535 ); ++ else virtual_rect = get_virtual_screen_rect(); + + if (x->max <= x->min) x_scale = 1; + else x_scale = (virtual_rect.right - virtual_rect.left) / (x->max - x->min); +@@ -771,12 +785,14 @@ static BOOL map_raw_event_coords( XIRawEvent *event, INPUT *input ) + if (i == x->number) + { + x_value = *values; +- x->value += x_value * x_scale; ++ if (x->mode == XIModeRelative) x->value += x_value * x_scale; ++ else x->value = (x_value - x->min) * x_scale; + } + if (i == y->number) + { + y_value = *values; +- y->value += y_value * y_scale; ++ if (y->mode == XIModeRelative) y->value += y_value * y_scale; ++ else y->value = (y_value - y->min) * y_scale; + } + values++; + } +@@ -789,7 +805,7 @@ static BOOL map_raw_event_coords( XIRawEvent *event, INPUT *input ) + x->value -= input->u.mi.dx; + y->value -= input->u.mi.dy; + +- if (!input->u.mi.dx && !input->u.mi.dy) ++ if (!(input->u.mi.dwFlags & MOUSEEVENTF_ABSOLUTE) && !input->u.mi.dx && !input->u.mi.dy) + { + TRACE( "accumulating motion\n" ); + return FALSE; +-- +2.33.0 + diff --git a/patches/user32-rawinput-mouse-experimental/0006-winex11.drv-Send-relative-RawMotion-events-unprocess.patch b/patches/user32-rawinput-mouse-experimental/0006-winex11.drv-Send-relative-RawMotion-events-unprocess.patch new file mode 100644 index 00000000..357a99e0 --- /dev/null +++ b/patches/user32-rawinput-mouse-experimental/0006-winex11.drv-Send-relative-RawMotion-events-unprocess.patch @@ -0,0 +1,86 @@ +From b3d438135587b09803599f4df3b08bc7379546bc Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?R=C3=A9mi=20Bernon?= +Date: Mon, 25 Oct 2021 11:48:00 +0200 +Subject: [PATCH 6/6] winex11.drv: Send relative RawMotion events unprocessed. + +This makes relative raw input independent from cursor speed, as it is +the case on Windows. Absolute raw input is already translated to +virtual desktop space, and cursor speed is meaningless in this case. + +This does not support mixed relative/absolute X/Y axis. +--- + dlls/winex11.drv/mouse.c | 18 ++++++++++++------ + 1 file changed, 12 insertions(+), 6 deletions(-) + +diff --git a/dlls/winex11.drv/mouse.c b/dlls/winex11.drv/mouse.c +index e6a2266855a..62a80ea6300 100644 +--- a/dlls/winex11.drv/mouse.c ++++ b/dlls/winex11.drv/mouse.c +@@ -750,12 +750,12 @@ static void map_event_coords( HWND hwnd, Window window, Window event_root, int x + input->u.mi.dy = pt.y; + } + +-static BOOL map_raw_event_coords( XIRawEvent *event, INPUT *input ) ++static BOOL map_raw_event_coords( XIRawEvent *event, INPUT *input, RAWINPUT *rawinput ) + { + struct x11drv_thread_data *thread_data = x11drv_thread_data(); + XIValuatorClassInfo *x = &thread_data->x_valuator, *y = &thread_data->y_valuator; +- double x_value = 0, y_value = 0, x_scale, y_scale; +- const double *values = event->valuators.values; ++ const double *values = event->valuators.values, *raw_values = event->raw_values; ++ double x_raw = 0, y_raw = 0, x_value = 0, y_value = 0, x_scale, y_scale; + RECT virtual_rect; + int i; + +@@ -784,22 +784,30 @@ static BOOL map_raw_event_coords( XIRawEvent *event, INPUT *input ) + if (!XIMaskIsSet( event->valuators.mask, i )) continue; + if (i == x->number) + { ++ x_raw = *raw_values; + x_value = *values; + if (x->mode == XIModeRelative) x->value += x_value * x_scale; + else x->value = (x_value - x->min) * x_scale; + } + if (i == y->number) + { ++ y_raw = *raw_values; + y_value = *values; + if (y->mode == XIModeRelative) y->value += y_value * y_scale; + else y->value = (y_value - y->min) * y_scale; + } ++ raw_values++; + values++; + } + + input->u.mi.dx = round( x->value ); + input->u.mi.dy = round( y->value ); + ++ if (x->mode != XIModeAbsolute) rawinput->data.mouse.lLastX = x_raw; ++ else rawinput->data.mouse.lLastX = input->u.mi.dx; ++ if (y->mode != XIModeAbsolute) rawinput->data.mouse.lLastY = y_raw; ++ else rawinput->data.mouse.lLastY = input->u.mi.dy; ++ + TRACE( "event %f,%f value %f,%f input %d,%d\n", x_value, y_value, x->value, y->value, input->u.mi.dx, input->u.mi.dy ); + + x->value -= input->u.mi.dx; +@@ -2025,7 +2033,7 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) + input.u.mi.dwExtraInfo = 0; + input.u.mi.dx = 0; + input.u.mi.dy = 0; +- if (!map_raw_event_coords( event, &input )) return FALSE; ++ if (!map_raw_event_coords( event, &input, &rawinput )) return FALSE; + + if (!thread_data->xi2_rawinput_only) + __wine_send_input( 0, &input, NULL ); +@@ -2039,8 +2047,6 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) + rawinput.data.mouse.ulRawButtons = 0; + rawinput.data.mouse.u.usButtonData = 0; + rawinput.data.mouse.u.usButtonFlags = 0; +- rawinput.data.mouse.lLastX = input.u.mi.dx; +- rawinput.data.mouse.lLastY = input.u.mi.dy; + rawinput.data.mouse.ulExtraInformation = 0; + + input.type = INPUT_HARDWARE; +-- +2.33.0 + diff --git a/patches/user32-rawinput-mouse-experimental/definition b/patches/user32-rawinput-mouse-experimental/definition index 758f1b06..fe2d8d5e 100644 --- a/patches/user32-rawinput-mouse-experimental/definition +++ b/patches/user32-rawinput-mouse-experimental/definition @@ -1,4 +1,2 @@ Fixes: [45882] - Raw Input should use untransformed mouse values (affects Overwatch, several Source games). Depends: user32-rawinput-mouse -# Broken nontrivially by upstream commits... -Disabled: true diff --git a/patches/user32-rawinput-mouse/0001-winex11.drv-Split-XInput2-thread-initialization.patch b/patches/user32-rawinput-mouse/0001-winex11.drv-Split-XInput2-thread-initialization.patch index 6511463d..10c61d03 100644 --- a/patches/user32-rawinput-mouse/0001-winex11.drv-Split-XInput2-thread-initialization.patch +++ b/patches/user32-rawinput-mouse/0001-winex11.drv-Split-XInput2-thread-initialization.patch @@ -1,7 +1,7 @@ -From be00910ebbb1277a5e34e982450a20821757fa25 Mon Sep 17 00:00:00 2001 +From b4d1ea44dd7f2201ba7d02eb171ee2ddb4013fe5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Bernon?= Date: Fri, 17 Jan 2020 16:33:11 +0100 -Subject: [PATCH] winex11.drv: Split XInput2 thread initialization. +Subject: [PATCH 1/8] winex11.drv: Split XInput2 thread initialization. And rename the library and function loader to x11drv_xinput_load. --- @@ -11,10 +11,10 @@ And rename the library and function loader to x11drv_xinput_load. 3 files changed, 36 insertions(+), 17 deletions(-) diff --git a/dlls/winex11.drv/mouse.c b/dlls/winex11.drv/mouse.c -index 42bac332664..ce77c7e5985 100644 +index 8cc30f0736d..a299944613e 100644 --- a/dlls/winex11.drv/mouse.c +++ b/dlls/winex11.drv/mouse.c -@@ -286,6 +286,32 @@ static void update_relative_valuators(XIAnyClassInfo **valuators, int n_valuator +@@ -279,6 +279,32 @@ static void update_relative_valuators(XIAnyClassInfo **valuators, int n_valuator #endif @@ -47,7 +47,7 @@ index 42bac332664..ce77c7e5985 100644 /*********************************************************************** * enable_xinput2 */ -@@ -298,19 +324,9 @@ static void enable_xinput2(void) +@@ -291,19 +317,9 @@ static void enable_xinput2(void) unsigned char mask_bits[XIMaskLen(XI_LASTEVENT)]; int count; @@ -69,7 +69,7 @@ index 42bac332664..ce77c7e5985 100644 if (!pXIGetClientPointer( data->display, None, &data->xi2_core_pointer )) return; mask.mask = mask_bits; -@@ -350,9 +366,9 @@ static void disable_xinput2(void) +@@ -343,9 +359,9 @@ static void disable_xinput2(void) struct x11drv_thread_data *data = x11drv_thread_data(); XIEventMask mask; @@ -80,7 +80,7 @@ index 42bac332664..ce77c7e5985 100644 data->xi2_state = xi_disabled; mask.mask = NULL; -@@ -1908,9 +1924,9 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) +@@ -1919,9 +1935,9 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) /*********************************************************************** @@ -93,10 +93,10 @@ index 42bac332664..ce77c7e5985 100644 #if defined(SONAME_LIBXI) && defined(HAVE_X11_EXTENSIONS_XINPUT2_H) int event, error; diff --git a/dlls/winex11.drv/x11drv.h b/dlls/winex11.drv/x11drv.h -index c23cd512eb9..a46d9ef430c 100644 +index d384a8a68c0..2f14c3f7cea 100644 --- a/dlls/winex11.drv/x11drv.h +++ b/dlls/winex11.drv/x11drv.h -@@ -195,7 +195,8 @@ extern BOOL CDECL X11DRV_UnrealizePalette( HPALETTE hpal ) DECLSPEC_HIDDEN; +@@ -196,7 +196,8 @@ extern BOOL CDECL X11DRV_UnrealizePalette( HPALETTE hpal ) DECLSPEC_HIDDEN; /* X11 driver internal functions */ extern void X11DRV_Xcursor_Init(void) DECLSPEC_HIDDEN; @@ -107,10 +107,10 @@ index c23cd512eb9..a46d9ef430c 100644 extern DWORD copy_image_bits( BITMAPINFO *info, BOOL is_r8g8b8, XImage *image, const struct gdi_image_bits *src_bits, struct gdi_image_bits *dst_bits, diff --git a/dlls/winex11.drv/x11drv_main.c b/dlls/winex11.drv/x11drv_main.c -index 9ec4c7a98f6..43c30ab369c 100644 +index bd21afc8174..98f57383bc2 100644 --- a/dlls/winex11.drv/x11drv_main.c +++ b/dlls/winex11.drv/x11drv_main.c -@@ -610,7 +610,7 @@ static BOOL process_attach(void) +@@ -623,7 +623,7 @@ static BOOL process_attach(void) #ifdef SONAME_LIBXCOMPOSITE X11DRV_XComposite_Init(); #endif @@ -119,7 +119,7 @@ index 9ec4c7a98f6..43c30ab369c 100644 #ifdef HAVE_XKB if (use_xkb) use_xkb = XkbUseExtension( gdi_display, NULL, NULL ); -@@ -702,6 +702,8 @@ struct x11drv_thread_data *x11drv_init_thread_data(void) +@@ -716,6 +716,8 @@ struct x11drv_thread_data *x11drv_init_thread_data(void) if (use_xim) X11DRV_SetupXIM(); @@ -129,5 +129,5 @@ index 9ec4c7a98f6..43c30ab369c 100644 } -- -2.30.2 +2.33.0 diff --git a/patches/user32-rawinput-mouse/0002-winex11.drv-Support-XInput2-events-for-individual-wi.patch b/patches/user32-rawinput-mouse/0002-winex11.drv-Support-XInput2-events-for-individual-wi.patch index 956e8a33..d0bedbf7 100644 --- a/patches/user32-rawinput-mouse/0002-winex11.drv-Support-XInput2-events-for-individual-wi.patch +++ b/patches/user32-rawinput-mouse/0002-winex11.drv-Support-XInput2-events-for-individual-wi.patch @@ -1,7 +1,8 @@ -From 1632472dc5c87c67bdff91758c190925a910d985 Mon Sep 17 00:00:00 2001 +From ad9aab54712604c45c75262b7f7a984bc1a756cd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Bernon?= Date: Thu, 23 Jan 2020 11:00:19 +0100 -Subject: [PATCH] winex11.drv: Support XInput2 events for individual windows. +Subject: [PATCH 2/8] winex11.drv: Support XInput2 events for individual + windows. This will allow us to listen to the XInput version of several events, which can bring additional information. diff --git a/patches/user32-rawinput-mouse/0003-winex11.drv-Advertise-XInput2-version-2.1-support.patch b/patches/user32-rawinput-mouse/0003-winex11.drv-Advertise-XInput2-version-2.1-support.patch index f6135350..ed094f3c 100644 --- a/patches/user32-rawinput-mouse/0003-winex11.drv-Advertise-XInput2-version-2.1-support.patch +++ b/patches/user32-rawinput-mouse/0003-winex11.drv-Advertise-XInput2-version-2.1-support.patch @@ -1,7 +1,7 @@ -From fa0f68c400a4637a00ae4ef2c354a6fbdc92bc0d Mon Sep 17 00:00:00 2001 +From 7443945f500e43f507267dddd900356b8c06223e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Bernon?= -Date: Fri, 2 Aug 2019 02:24:32 -0400 -Subject: [PATCH] winex11.drv: Advertise XInput2 version 2.1 support. +Date: Sun, 24 Oct 2021 22:30:56 +0200 +Subject: [PATCH 3/8] winex11.drv: Advertise XInput2 version 2.1 support. Under XInput2 protocol version < 2.1, RawEvents are not supposed to be sent if a pointer grab is active. However slave device events are still diff --git a/patches/user32-rawinput-mouse/0004-winex11.drv-Keep-track-of-pointer-and-device-button-.patch b/patches/user32-rawinput-mouse/0004-winex11.drv-Keep-track-of-pointer-and-device-button-.patch index f2d32141..e672b1d7 100644 --- a/patches/user32-rawinput-mouse/0004-winex11.drv-Keep-track-of-pointer-and-device-button-.patch +++ b/patches/user32-rawinput-mouse/0004-winex11.drv-Keep-track-of-pointer-and-device-button-.patch @@ -1,7 +1,7 @@ -From 29097b205bc5d0861d14409988da04880626b879 Mon Sep 17 00:00:00 2001 +From 36e0b9f5b0b0ecb9de225dd3b1f092c99a1837f4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Bernon?= Date: Thu, 19 Dec 2019 22:34:44 +0100 -Subject: [PATCH] winex11.drv: Keep track of pointer and device button +Subject: [PATCH 4/8] winex11.drv: Keep track of pointer and device button mappings. We are going to receive raw button events and we will need to apply the @@ -16,7 +16,7 @@ Original patch by Andrew Eikum . 4 files changed, 106 insertions(+), 8 deletions(-) diff --git a/dlls/winex11.drv/keyboard.c b/dlls/winex11.drv/keyboard.c -index d86f418a64e..f905794b23a 100644 +index c6eab6f5cfa..1525dac8280 100644 --- a/dlls/winex11.drv/keyboard.c +++ b/dlls/winex11.drv/keyboard.c @@ -1882,13 +1882,24 @@ BOOL X11DRV_MappingNotify( HWND dummy, XEvent *event ) @@ -51,10 +51,10 @@ index d86f418a64e..f905794b23a 100644 } diff --git a/dlls/winex11.drv/mouse.c b/dlls/winex11.drv/mouse.c -index 0d41438c5c7..fc5fd29d7b6 100644 +index 9088aada596..6905d0827f8 100644 --- a/dlls/winex11.drv/mouse.c +++ b/dlls/winex11.drv/mouse.c -@@ -25,6 +25,9 @@ +@@ -27,6 +27,9 @@ #include #include #include @@ -64,7 +64,7 @@ index 0d41438c5c7..fc5fd29d7b6 100644 #ifdef HAVE_X11_EXTENSIONS_XINPUT2_H #include #endif -@@ -142,6 +145,14 @@ MAKE_FUNCPTR(XISelectEvents); +@@ -144,6 +147,14 @@ MAKE_FUNCPTR(XISelectEvents); #undef MAKE_FUNCPTR #endif @@ -79,7 +79,7 @@ index 0d41438c5c7..fc5fd29d7b6 100644 /*********************************************************************** * X11DRV_Xcursor_Init * -@@ -247,6 +258,70 @@ void sync_window_cursor( Window window ) +@@ -249,6 +260,70 @@ void sync_window_cursor( Window window ) set_window_cursor( window, cursor ); } @@ -150,7 +150,7 @@ index 0d41438c5c7..fc5fd29d7b6 100644 #ifdef HAVE_X11_EXTENSIONS_XINPUT2_H /*********************************************************************** * update_relative_valuators -@@ -1847,6 +1922,8 @@ static BOOL X11DRV_DeviceChanged( XGenericEventCookie *xev ) +@@ -1896,6 +1971,8 @@ static BOOL X11DRV_DeviceChanged( XGenericEventCookie *xev ) if (event->reason != XISlaveSwitch) return FALSE; update_relative_valuators( event->classes, event->num_classes ); @@ -159,7 +159,7 @@ index 0d41438c5c7..fc5fd29d7b6 100644 return TRUE; } -@@ -1916,13 +1993,12 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) +@@ -1928,13 +2005,12 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) #endif /* HAVE_X11_EXTENSIONS_XINPUT2_H */ @@ -174,7 +174,7 @@ index 0d41438c5c7..fc5fd29d7b6 100644 int event, error; void *libxi_handle = dlopen( SONAME_LIBXI, RTLD_NOW ); -@@ -1938,11 +2014,20 @@ void x11drv_xinput_load(void) +@@ -1950,11 +2026,20 @@ void x11drv_xinput_load(void) return; \ } @@ -196,10 +196,10 @@ index 0d41438c5c7..fc5fd29d7b6 100644 xinput2_available = XQueryExtension( gdi_display, "XInputExtension", &xinput2_opcode, &event, &error ); diff --git a/dlls/winex11.drv/x11drv.h b/dlls/winex11.drv/x11drv.h -index b7c876e35fe..7a89a010395 100644 +index 463c2027077..f7af7f346e5 100644 --- a/dlls/winex11.drv/x11drv.h +++ b/dlls/winex11.drv/x11drv.h -@@ -643,6 +643,7 @@ extern void retry_grab_clipping_window(void) DECLSPEC_HIDDEN; +@@ -642,6 +642,7 @@ extern void retry_grab_clipping_window(void) DECLSPEC_HIDDEN; extern BOOL clip_fullscreen_window( HWND hwnd, BOOL reset ) DECLSPEC_HIDDEN; extern void move_resize_window( HWND hwnd, int dir ) DECLSPEC_HIDDEN; extern void X11DRV_InitKeyboard( Display *display ) DECLSPEC_HIDDEN; @@ -208,10 +208,10 @@ index b7c876e35fe..7a89a010395 100644 DWORD mask, DWORD flags ) DECLSPEC_HIDDEN; diff --git a/dlls/winex11.drv/x11drv_main.c b/dlls/winex11.drv/x11drv_main.c -index 43c30ab369c..d8576949aea 100644 +index 98f57383bc2..2a35a6a8548 100644 --- a/dlls/winex11.drv/x11drv_main.c +++ b/dlls/winex11.drv/x11drv_main.c -@@ -616,6 +616,7 @@ static BOOL process_attach(void) +@@ -629,6 +629,7 @@ static BOOL process_attach(void) if (use_xkb) use_xkb = XkbUseExtension( gdi_display, NULL, NULL ); #endif X11DRV_InitKeyboard( gdi_display ); @@ -220,5 +220,5 @@ index 43c30ab369c..d8576949aea 100644 X11DRV_DisplayDevices_Init(FALSE); -- -2.30.2 +2.33.0 diff --git a/patches/user32-rawinput-mouse/0005-server-Add-send_hardware_message-flags-for-rawinput-.patch b/patches/user32-rawinput-mouse/0005-server-Add-send_hardware_message-flags-for-rawinput-.patch index c5a2d1f9..b63f5db6 100644 --- a/patches/user32-rawinput-mouse/0005-server-Add-send_hardware_message-flags-for-rawinput-.patch +++ b/patches/user32-rawinput-mouse/0005-server-Add-send_hardware_message-flags-for-rawinput-.patch @@ -1,7 +1,7 @@ -From 07d4dc9e66dc130f0b43225959120a5cf3c73fcf Mon Sep 17 00:00:00 2001 +From 265a4a77fa8b971040526ddfbdb4cf85e81b4dbd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Bernon?= Date: Mon, 26 Aug 2019 14:37:20 +0200 -Subject: [PATCH] server: Add send_hardware_message flags for rawinput +Subject: [PATCH 5/8] server: Add send_hardware_message flags for rawinput translation. --- @@ -11,7 +11,7 @@ Subject: [PATCH] server: Add send_hardware_message flags for rawinput 3 files changed, 9 insertions(+), 6 deletions(-) diff --git a/dlls/user32/message.c b/dlls/user32/message.c -index f53d417c22a..d2f91b28ac0 100644 +index e5ea0735ed2..c14c726273f 100644 --- a/dlls/user32/message.c +++ b/dlls/user32/message.c @@ -3279,6 +3279,7 @@ NTSTATUS send_hardware_message( HWND hwnd, const INPUT *input, const RAWINPUT *r @@ -31,10 +31,10 @@ index f53d417c22a..d2f91b28ac0 100644 case INPUT_HARDWARE: req->input.hw.msg = input->u.hi.uMsg; diff --git a/server/protocol.def b/server/protocol.def -index b5cc1dbae3a..3cff090335a 100644 +index 6a25db0326f..a61e4cca152 100644 --- a/server/protocol.def +++ b/server/protocol.def -@@ -2040,6 +2040,7 @@ enum message_type +@@ -2042,6 +2042,7 @@ enum message_type VARARG(keystate,bytes); /* global state array for all the keys */ @END #define SEND_HWMSG_INJECTED 0x01 @@ -43,10 +43,10 @@ index b5cc1dbae3a..3cff090335a 100644 /* Get a message from the current queue */ diff --git a/server/queue.c b/server/queue.c -index 71e3b69fe8c..d8428cdf13c 100644 +index fe5a3f2d5be..a4bea986b94 100644 --- a/server/queue.c +++ b/server/queue.c -@@ -1817,7 +1817,7 @@ done: +@@ -1736,7 +1736,7 @@ done: /* queue a hardware message for a mouse event */ static int queue_mouse_message( struct desktop *desktop, user_handle_t win, const hw_input_t *input, @@ -55,7 +55,7 @@ index 71e3b69fe8c..d8428cdf13c 100644 { const struct rawinput_device *device; struct hardware_msg_data *msg_data; -@@ -1872,7 +1872,7 @@ static int queue_mouse_message( struct desktop *desktop, user_handle_t win, cons +@@ -1791,7 +1791,7 @@ static int queue_mouse_message( struct desktop *desktop, user_handle_t win, cons y = desktop->cursor.y; } @@ -64,7 +64,7 @@ index 71e3b69fe8c..d8428cdf13c 100644 { memset( &raw_msg, 0, sizeof(raw_msg) ); raw_msg.foreground = foreground; -@@ -1931,7 +1931,7 @@ static int queue_mouse_message( struct desktop *desktop, user_handle_t win, cons +@@ -1850,7 +1850,7 @@ static int queue_mouse_message( struct desktop *desktop, user_handle_t win, cons /* queue a hardware message for a keyboard event */ static int queue_keyboard_message( struct desktop *desktop, user_handle_t win, const hw_input_t *input, @@ -73,7 +73,7 @@ index 71e3b69fe8c..d8428cdf13c 100644 { struct hw_msg_source source = { IMDT_KEYBOARD, origin }; const struct rawinput_device *device; -@@ -2009,7 +2009,7 @@ static int queue_keyboard_message( struct desktop *desktop, user_handle_t win, c +@@ -1928,7 +1928,7 @@ static int queue_keyboard_message( struct desktop *desktop, user_handle_t win, c break; } @@ -82,7 +82,7 @@ index 71e3b69fe8c..d8428cdf13c 100644 { memset( &raw_msg, 0, sizeof(raw_msg) ); raw_msg.foreground = foreground; -@@ -2632,10 +2632,10 @@ DECL_HANDLER(send_hardware_message) +@@ -2546,10 +2546,10 @@ DECL_HANDLER(send_hardware_message) switch (req->input.type) { case INPUT_MOUSE: diff --git a/patches/user32-rawinput-mouse/0006-user32-Set-SEND_HWMSG_RAWINPUT-flags-only-when-RAWIN.patch b/patches/user32-rawinput-mouse/0006-user32-Set-SEND_HWMSG_RAWINPUT-flags-only-when-RAWIN.patch index f9b77c97..68e0c498 100644 --- a/patches/user32-rawinput-mouse/0006-user32-Set-SEND_HWMSG_RAWINPUT-flags-only-when-RAWIN.patch +++ b/patches/user32-rawinput-mouse/0006-user32-Set-SEND_HWMSG_RAWINPUT-flags-only-when-RAWIN.patch @@ -1,8 +1,8 @@ -From 783d9dddfdce0b272e98b0d9da20f39e0f02576c Mon Sep 17 00:00:00 2001 +From 1026871222aa0c54a9ebd747c1b4bd7220815a45 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Bernon?= Date: Wed, 24 Mar 2021 23:29:28 +0100 -Subject: [PATCH] user32: Set SEND_HWMSG_RAWINPUT flags only when RAWINPUT is - set. +Subject: [PATCH 6/8] user32: Set SEND_HWMSG_RAWINPUT flags only when RAWINPUT + is set. So we can generate legacy messages only by calling __wine_send_input with NULL rawinput, and generate WM_INPUT messages only by calling diff --git a/patches/user32-rawinput-mouse/0007-user32-Support-sending-RIM_TYPEMOUSE-through-__wine_.patch b/patches/user32-rawinput-mouse/0007-user32-Support-sending-RIM_TYPEMOUSE-through-__wine_.patch index 91491f92..4ad8b1cb 100644 --- a/patches/user32-rawinput-mouse/0007-user32-Support-sending-RIM_TYPEMOUSE-through-__wine_.patch +++ b/patches/user32-rawinput-mouse/0007-user32-Support-sending-RIM_TYPEMOUSE-through-__wine_.patch @@ -1,7 +1,7 @@ -From bb3a28f74aa0ff79539e0deb74a09275bbfc8c73 Mon Sep 17 00:00:00 2001 +From 73870c715c6f7f8249e021d0b2feb833cb0b2fe9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Bernon?= Date: Thu, 25 Mar 2021 14:26:35 +0100 -Subject: [PATCH] user32: Support sending RIM_TYPEMOUSE through +Subject: [PATCH 7/8] user32: Support sending RIM_TYPEMOUSE through __wine_send_input. --- @@ -10,7 +10,7 @@ Subject: [PATCH] user32: Support sending RIM_TYPEMOUSE through 2 files changed, 9 insertions(+) diff --git a/dlls/user32/message.c b/dlls/user32/message.c -index abf892d1474..839b6d6bc14 100644 +index 05f00704906..a81690bc0d3 100644 --- a/dlls/user32/message.c +++ b/dlls/user32/message.c @@ -3299,6 +3299,12 @@ NTSTATUS send_hardware_message( HWND hwnd, const INPUT *input, const RAWINPUT *r @@ -27,10 +27,10 @@ index abf892d1474..839b6d6bc14 100644 req->input.hw.rawinput.hid.device = HandleToUlong( rawinput->header.hDevice ); req->input.hw.rawinput.hid.param = rawinput->header.wParam; diff --git a/server/queue.c b/server/queue.c -index d8428cdf13c..eef5bf56347 100644 +index a4bea986b94..6713b58c468 100644 --- a/server/queue.c +++ b/server/queue.c -@@ -2103,6 +2103,9 @@ static void queue_custom_hardware_message( struct desktop *desktop, user_handle_ +@@ -2022,6 +2022,9 @@ static void queue_custom_hardware_message( struct desktop *desktop, user_handle_ msg_data->size = sizeof(*msg_data) + report_size; msg_data->rawinput = input->hw.rawinput; diff --git a/patches/user32-rawinput-mouse/0008-winex11.drv-Listen-to-RawMotion-and-RawButton-events.patch b/patches/user32-rawinput-mouse/0008-winex11.drv-Listen-to-RawMotion-and-RawButton-events.patch index 3e81a440..c26f13e7 100644 --- a/patches/user32-rawinput-mouse/0008-winex11.drv-Listen-to-RawMotion-and-RawButton-events.patch +++ b/patches/user32-rawinput-mouse/0008-winex11.drv-Listen-to-RawMotion-and-RawButton-events.patch @@ -1,18 +1,18 @@ -From 53a1b02d4be9c6f30e1158ec987d5674d04dc158 Mon Sep 17 00:00:00 2001 +From b13e43a92335d20ff06dfbbeda37457b2c1edb3e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Bernon?= -Date: Thu, 25 Mar 2021 16:12:58 +0100 -Subject: [PATCH] winex11.drv: Listen to RawMotion and RawButton* events in the - desktop thread. +Date: Mon, 25 Oct 2021 11:45:47 +0200 +Subject: [PATCH 8/8] winex11.drv: Listen to RawMotion and RawButton* events in + the desktop thread. We still need to send "normal" input from the clipping window thread to trigger low-level hooks callbacks when clipping cursor. This is for instance used in our dinput implementation. --- - dlls/winex11.drv/event.c | 10 ++- - dlls/winex11.drv/mouse.c | 110 ++++++++++++++++++++++++++++++--- + dlls/winex11.drv/event.c | 10 +++- + dlls/winex11.drv/mouse.c | 106 ++++++++++++++++++++++++++++++--- dlls/winex11.drv/x11drv.h | 1 + dlls/winex11.drv/x11drv_main.c | 4 ++ - 4 files changed, 116 insertions(+), 9 deletions(-) + 4 files changed, 112 insertions(+), 9 deletions(-) diff --git a/dlls/winex11.drv/event.c b/dlls/winex11.drv/event.c index bc007bea1d6..bdfc133774a 100644 @@ -54,7 +54,7 @@ index bc007bea1d6..bdfc133774a 100644 #endif } diff --git a/dlls/winex11.drv/mouse.c b/dlls/winex11.drv/mouse.c -index c606f2755ae..01299392f7a 100644 +index c606f2755ae..0eaae753f87 100644 --- a/dlls/winex11.drv/mouse.c +++ b/dlls/winex11.drv/mouse.c @@ -415,7 +415,18 @@ void x11drv_xinput_enable( Display *display, Window window, long event_mask ) @@ -128,20 +128,15 @@ index c606f2755ae..01299392f7a 100644 XIRawEvent *event = xev->data; RAWINPUT rawinput; INPUT input; -@@ -2002,7 +2012,89 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) +@@ -2002,7 +2012,85 @@ static BOOL X11DRV_RawMotion( XGenericEventCookie *xev ) input.u.mi.dy = 0; if (!map_raw_event_coords( event, &input )) return FALSE; - __wine_send_input( 0, &input, &rawinput ); + if (!thread_data->xi2_rawinput_only) -+ { -+ TRACE( "pos %d,%d\n", input.u.mi.dx, input.u.mi.dy ); + __wine_send_input( 0, &input, NULL ); -+ } + else + { -+ TRACE( "raw pos %d,%d\n", input.u.mi.dx, input.u.mi.dy ); -+ + rawinput.header.dwType = RIM_TYPEMOUSE; + rawinput.header.dwSize = offsetof(RAWINPUT, data) + sizeof(RAWMOUSE); + rawinput.header.hDevice = ULongToHandle(1); /* WINE_MOUSE_HANDLE */ @@ -161,6 +156,7 @@ index c606f2755ae..01299392f7a 100644 + if (rawinput.data.mouse.lLastX || rawinput.data.mouse.lLastY) + __wine_send_input( 0, &input, &rawinput ); + } ++ + return TRUE; +} + @@ -219,7 +215,7 @@ index c606f2755ae..01299392f7a 100644 return TRUE; } -@@ -2078,6 +2170,10 @@ BOOL X11DRV_GenericEvent( HWND hwnd, XEvent *xev ) +@@ -2078,6 +2166,10 @@ BOOL X11DRV_GenericEvent( HWND hwnd, XEvent *xev ) case XI_RawMotion: ret = X11DRV_RawMotion( event ); break;