From 33439865de327c5bac1c9a531070514e63fe3a04 Mon Sep 17 00:00:00 2001 From: Derek Foreman Date: Fri, 28 Jul 2017 16:48:38 -0500 Subject: [PATCH] elput: Fix synthetic relative motion events based on abs events libinput won't actually give us this info, and logs an error instead. We can't synthesize based on pointer position due to pointer warping. So we must track abs reports and use previous abs reports to synthesize rel events. --- src/lib/elput/elput_evdev.c | 30 +++++++++++++++++++++++++++--- src/lib/elput/elput_private.h | 2 ++ 2 files changed, 29 insertions(+), 3 deletions(-) diff --git a/src/lib/elput/elput_evdev.c b/src/lib/elput/elput_evdev.c index 454b4a85de..1199a09798 100644 --- a/src/lib/elput/elput_evdev.c +++ b/src/lib/elput/elput_evdev.c @@ -880,6 +880,23 @@ _pointer_motion_send(Elput_Device *edev) ecore_event_add(ECORE_EVENT_MOUSE_MOVE, ev, _event_free, ev->dev); } +static void +_pointer_motion_relative_fake(struct libinput_event_pointer *event, double dx, double dy) +{ + Elput_Event_Pointer_Motion *ev; + + ev = calloc(1, sizeof(Elput_Event_Pointer_Motion)); + EINA_SAFETY_ON_NULL_RETURN(ev); + + ev->time_usec = libinput_event_pointer_get_time_usec(event); + ev->dx = dx; + ev->dy = dy; + ev->dx_unaccel = dx; + ev->dy_unaccel = dy; + + ecore_event_add(ELPUT_EVENT_POINTER_MOTION, ev, NULL, NULL); +} + static void _pointer_motion_relative(struct libinput_event_pointer *event) { @@ -937,6 +954,7 @@ _pointer_motion_abs(struct libinput_device *idev, struct libinput_event_pointer { Elput_Device *edev; Elput_Pointer *ptr; + double x, y; edev = libinput_device_get_user_data(idev); if (!edev) return EINA_FALSE; @@ -944,16 +962,22 @@ _pointer_motion_abs(struct libinput_device *idev, struct libinput_event_pointer ptr = _evdev_pointer_get(edev->seat); if (!ptr) return EINA_FALSE; - ptr->seat->pointer.x = + x = edev->absx; + edev->absx = libinput_event_pointer_get_absolute_x_transformed(event, edev->ow); - ptr->seat->pointer.y = + ptr->seat->pointer.x = edev->absx; + + y = edev->absy; + edev->absy = libinput_event_pointer_get_absolute_y_transformed(event, edev->oh); + ptr->seat->pointer.y = edev->absy; + ptr->timestamp = libinput_event_pointer_get_time(event); /* TODO: these needs to run a matrix transform based on output */ _pointer_motion_send(edev); - _pointer_motion_relative(event); + _pointer_motion_relative_fake(event, edev->absx - x, edev->absy - y); return EINA_TRUE; } diff --git a/src/lib/elput/elput_private.h b/src/lib/elput/elput_private.h index 709871c368..f5bc425182 100644 --- a/src/lib/elput/elput_private.h +++ b/src/lib/elput/elput_private.h @@ -231,6 +231,8 @@ struct _Elput_Device uint32_t ow, oh; + double absx, absy; + const char *path; const char *output_name; struct libinput_device *device;