[PATCH v2 9/9] server: Implement RegisterRawInputDevices RIDEV_INPUTSINK flag.
Rémi Bernon
rbernon at codeweavers.com
Mon Jun 15 05:05:48 CDT 2020
This flag allows applications to receive rawinput messages while in
background. They have to specify a target hwnd, which will receive them,
and the messages will carry a RIM_INPUTSINK wparam if the process wasn't
foreground.
Signed-off-by: Rémi Bernon <rbernon at codeweavers.com>
---
dlls/user32/rawinput.c | 9 ++++++++-
dlls/user32/tests/input.c | 8 +++-----
server/queue.c | 13 +++++++++----
3 files changed, 20 insertions(+), 10 deletions(-)
diff --git a/dlls/user32/rawinput.c b/dlls/user32/rawinput.c
index 7a9eb6ced17..103835e0e33 100644
--- a/dlls/user32/rawinput.c
+++ b/dlls/user32/rawinput.c
@@ -291,6 +291,13 @@ BOOL WINAPI DECLSPEC_HOTPATCH RegisterRawInputDevices(RAWINPUTDEVICE *devices, U
for (i = 0; i < device_count; ++i)
{
+ if ((devices[i].dwFlags & RIDEV_INPUTSINK) &&
+ (devices[i].hwndTarget == NULL))
+ {
+ SetLastError(ERROR_INVALID_PARAMETER);
+ return FALSE;
+ }
+
if ((devices[i].dwFlags & RIDEV_REMOVE) &&
(devices[i].hwndTarget != NULL))
{
@@ -306,7 +313,7 @@ BOOL WINAPI DECLSPEC_HOTPATCH RegisterRawInputDevices(RAWINPUTDEVICE *devices, U
TRACE("device %u: page %#x, usage %#x, flags %#x, target %p.\n",
i, devices[i].usUsagePage, devices[i].usUsage,
devices[i].dwFlags, devices[i].hwndTarget);
- if (devices[i].dwFlags & ~(RIDEV_REMOVE|RIDEV_NOLEGACY))
+ if (devices[i].dwFlags & ~(RIDEV_REMOVE|RIDEV_NOLEGACY|RIDEV_INPUTSINK))
FIXME("Unhandled flags %#x for device %u.\n", devices[i].dwFlags, i);
d[i].usage_page = devices[i].usUsagePage;
diff --git a/dlls/user32/tests/input.c b/dlls/user32/tests/input.c
index ecd44c44f16..7ab96360ad5 100644
--- a/dlls/user32/tests/input.c
+++ b/dlls/user32/tests/input.c
@@ -1804,9 +1804,7 @@ static void test_RegisterRawInputDevices(void)
SetLastError(0xdeadbeef);
res = RegisterRawInputDevices(raw_devices, ARRAY_SIZE(raw_devices), sizeof(RAWINPUTDEVICE));
- todo_wine
ok(res == FALSE, "RegisterRawInputDevices failed\n");
- todo_wine
ok(GetLastError() == ERROR_INVALID_PARAMETER, "RegisterRawInputDevices returned %08x\n", GetLastError());
raw_devices[0].hwndTarget = hwnd;
@@ -1881,13 +1879,13 @@ struct rawinput_test rawinput_tests[] =
/* cross-process foreground tests */
{ TRUE, TRUE, 0, FALSE, FALSE, FALSE, /* todos: */ FALSE, FALSE, FALSE },
- { TRUE, TRUE, RIDEV_INPUTSINK, FALSE, TRUE, FALSE, /* todos: */ FALSE, TRUE, FALSE },
+ { TRUE, TRUE, RIDEV_INPUTSINK, FALSE, TRUE, FALSE, /* todos: */ FALSE, FALSE, FALSE },
{ TRUE, TRUE, 0, FALSE, FALSE, FALSE, /* todos: */ FALSE, FALSE, FALSE },
/* multi-process rawinput tests */
{ TRUE, TRUE, 0, FALSE, FALSE, FALSE, /* todos: */ FALSE, FALSE, FALSE },
- { TRUE, TRUE, RIDEV_INPUTSINK, FALSE, TRUE, FALSE, /* todos: */ FALSE, TRUE, FALSE },
- { TRUE, TRUE, RIDEV_INPUTSINK, FALSE, TRUE, FALSE, /* todos: */ FALSE, TRUE, FALSE },
+ { TRUE, TRUE, RIDEV_INPUTSINK, FALSE, TRUE, FALSE, /* todos: */ FALSE, FALSE, FALSE },
+ { TRUE, TRUE, RIDEV_INPUTSINK, FALSE, TRUE, FALSE, /* todos: */ FALSE, FALSE, FALSE },
{ TRUE, TRUE, RIDEV_EXINPUTSINK, FALSE, FALSE, FALSE, /* todos: */ FALSE, FALSE, FALSE },
{ TRUE, TRUE, RIDEV_EXINPUTSINK, FALSE, TRUE, FALSE, /* todos: */ FALSE, TRUE, FALSE },
diff --git a/server/queue.c b/server/queue.c
index 14cffbd6a76..517d42d34dd 100644
--- a/server/queue.c
+++ b/server/queue.c
@@ -1648,6 +1648,7 @@ static int queue_rawinput_message( struct process* process, void* user )
struct desktop *desktop = NULL;
struct thread *thread = NULL, *foreground = NULL;
struct message *msg;
+ int wparam = RIM_INPUT;
if (raw_msg->data.rawinput.type == RIM_TYPEMOUSE)
device = process->rawinput_mouse;
@@ -1671,17 +1672,21 @@ static int queue_rawinput_message( struct process* process, void* user )
process != thread->process)
goto done;
- /* FIXME: Implement RIDEV_INPUTSINK */
- if (!desktop->foreground_input || !(foreground = get_window_thread( desktop->foreground_input->active )) ||
+ /* skip if target window is not in foreground process and RIDEV_INPUTSINK was not used */
+ if (!desktop->foreground_input ||
+ !(foreground = get_window_thread( desktop->foreground_input->active )) ||
thread->process != foreground->process)
- goto done;
+ {
+ if (!(device->flags & RIDEV_INPUTSINK)) goto done;
+ wparam = RIM_INPUTSINK;
+ }
if (!(msg = alloc_hardware_message( raw_msg->data.info, raw_msg->source, raw_msg->time )))
goto done;
msg->win = device->target;
msg->msg = WM_INPUT;
- msg->wparam = RIM_INPUT;
+ msg->wparam = wparam;
msg->lparam = 0;
memcpy( msg->data, &raw_msg->data, sizeof(raw_msg->data) );
--
2.27.0
More information about the wine-devel
mailing list