swc

Unnamed repository; edit this file 'description' to name the repository.
git clone git://git.nihaljere.xyz/swc
Log | Files | Refs | README | LICENSE

commit c617c3751ff65b7be847c70e8c01c1b6f26cce1f
parent 94322e53bbd2f827f5c3733812381ef698e0aeac
Author: Michael Forney <mforney@mforney.org>
Date:   Thu, 29 Dec 2016 20:34:34 -0800

Handle absolute pointer devices

Diffstat:
Mlibswc/evdev_device.c | 32+++++++++++++++++++++++++++++++-
Mlibswc/evdev_device.h | 3++-
Mlibswc/pointer.c | 8+++++++-
Mlibswc/pointer.h | 1+
Mlibswc/seat.c | 13+++++++++++++
5 files changed, 54 insertions(+), 3 deletions(-)

diff --git a/libswc/evdev_device.c b/libswc/evdev_device.c @@ -95,8 +95,18 @@ handle_rel_event(struct evdev_device *device, struct input_event *ev) } static void -handle_abs_event(struct evdev_device *device, struct input_event *input_event) +handle_abs_event(struct evdev_device *device, struct input_event *ev) { + switch (ev->code) { + case ABS_X: + device->abs.x = ev->value; + device->abs.pending = true; + break; + case ABS_Y: + device->abs.y = ev->value; + device->abs.pending = true; + break; + } } static void (*event_handlers[])(struct evdev_device *device, struct input_event *ev) = { @@ -115,6 +125,15 @@ is_motion_event(struct input_event *ev) static void handle_motion_events(struct evdev_device *device, uint32_t time) { + if (device->abs.pending) { + int32_t x = device->abs.x - device->abs.info.x->minimum; + int32_t max_x = device->abs.info.x->maximum - device->abs.info.x->minimum; + int32_t y = device->abs.y - device->abs.info.y->minimum; + int32_t max_y = device->abs.info.y->maximum - device->abs.info.y->minimum; + + device->handler->absolute_motion(time, x, max_x, y, max_y); + device->abs.pending = false; + } if (device->rel.pending) { wl_fixed_t dx = wl_fixed_from_int(device->rel.dx); wl_fixed_t dy = wl_fixed_from_int(device->rel.dy); @@ -221,6 +240,9 @@ evdev_device_new(const char *path, const struct evdev_device_handler *handler) device->needs_sync = false; device->handler = handler; device->capabilities = 0; + device->abs.info.x = libevdev_get_abs_info(device->dev, ABS_X); + device->abs.info.y = libevdev_get_abs_info(device->dev, ABS_Y); + device->abs.pending = false; memset(&device->rel, 0, sizeof(device->rel)); if (libevdev_has_event_code(device->dev, EV_KEY, KEY_ENTER)) { @@ -236,6 +258,14 @@ evdev_device_new(const char *path, const struct evdev_device_handler *handler) DEBUG("\tThis device is a pointer\n"); } + if (libevdev_has_event_code(device->dev, EV_ABS, ABS_X) + && libevdev_has_event_code(device->dev, EV_ABS, ABS_Y) + && libevdev_has_event_code(device->dev, EV_KEY, BTN_MOUSE) + && !libevdev_has_event_code(device->dev, EV_KEY, BTN_TOOL_FINGER)) + { + device->capabilities |= WL_SEAT_CAPABILITY_POINTER; + } + /* XXX: touch devices */ return device; diff --git a/libswc/evdev_device.h b/libswc/evdev_device.h @@ -40,6 +40,7 @@ struct evdev_device_handler { void (*button)(uint32_t time, uint32_t key, uint32_t state); void (*axis)(uint32_t time, uint32_t axis, wl_fixed_t amount); void (*relative_motion)(uint32_t time, wl_fixed_t dx, wl_fixed_t dy); + void (*absolute_motion)(uint32_t time, int32_t x, int32_t y, int32_t max_x, int32_t max_y); }; struct evdev_device { @@ -52,7 +53,7 @@ struct evdev_device { struct { struct { - struct input_absinfo x, y; + const struct input_absinfo *x, *y; } info; int32_t x, y; diff --git a/libswc/pointer.c b/libswc/pointer.c @@ -404,9 +404,15 @@ pointer_handle_axis(struct pointer *pointer, uint32_t time, uint32_t axis, wl_fi void pointer_handle_relative_motion(struct pointer *pointer, uint32_t time, wl_fixed_t dx, wl_fixed_t dy) { + pointer_handle_absolute_motion(pointer, time, pointer->x + dx, pointer->y + dy); +} + +void +pointer_handle_absolute_motion(struct pointer *pointer, uint32_t time, wl_fixed_t x, wl_fixed_t y) +{ struct pointer_handler *handler; - clip_position(pointer, pointer->x + dx, pointer->y + dy); + clip_position(pointer, x, y); wl_list_for_each (handler, &pointer->handlers, link) { if (handler->motion && handler->motion(handler, time, pointer->x, pointer->y)) diff --git a/libswc/pointer.h b/libswc/pointer.h @@ -81,5 +81,6 @@ struct wl_resource *pointer_bind(struct pointer *pointer, struct wl_client *clie void pointer_handle_button(struct pointer *pointer, uint32_t time, uint32_t button, uint32_t state); void pointer_handle_axis(struct pointer *pointer, uint32_t time, uint32_t axis, wl_fixed_t amount); void pointer_handle_relative_motion(struct pointer *pointer, uint32_t time, wl_fixed_t dx, wl_fixed_t dy); +void pointer_handle_absolute_motion(struct pointer *pointer, uint32_t time, wl_fixed_t x, wl_fixed_t y); #endif diff --git a/libswc/seat.c b/libswc/seat.c @@ -30,6 +30,7 @@ #include "keyboard.h" #include "launch.h" #include "pointer.h" +#include "screen.h" #include "surface.h" #include "util.h" @@ -97,6 +98,17 @@ handle_relative_motion(uint32_t time, wl_fixed_t dx, wl_fixed_t dy) } static void +handle_absolute_motion(uint32_t time, int32_t x, int32_t max_x, int32_t y, int32_t max_y) +{ + struct screen *screen = wl_container_of(swc.screens.next, screen, link); + struct swc_rectangle *rect = &screen->base.geometry; + wl_fixed_t fx = wl_fixed_from_int(x * rect->width / max_x + rect->x); + wl_fixed_t fy = wl_fixed_from_int(y * rect->height / max_y + rect->y); + + pointer_handle_absolute_motion(&seat.pointer, time, fx, fy); +} + +static void handle_keyboard_focus_event(struct wl_listener *listener, void *data) { struct event *ev = data; @@ -390,6 +402,7 @@ const static struct evdev_device_handler evdev_handler = { .button = handle_button, .axis = handle_axis, .relative_motion = handle_relative_motion, + .absolute_motion = handle_absolute_motion, }; static void