#include <errno.h>
#include <stdlib.h>
#include <string.h>
-#include <linux/input.h>
+#include "linux/input.h"
#include <unistd.h>
#include <fcntl.h>
#include <mtdev-plumbing.h>
#include "filter.h"
#include "libinput-private.h"
-#define DEFAULT_AXIS_STEP_DISTANCE li_fixed_from_int(10)
-
-#ifndef KEY_LIGHTS_TOGGLE
-#define KEY_LIGHTS_TOGGLE 0x21e
-#endif
+#define DEFAULT_AXIS_STEP_DISTANCE 10
void
evdev_device_led_update(struct evdev_device *device, enum libinput_led leds)
}
}
-li_fixed_t
+static inline double
+scale_axis(const struct input_absinfo *absinfo, double val, double to_range)
+{
+ return (val - absinfo->minimum) * to_range /
+ (absinfo->maximum - absinfo->minimum + 1);
+}
+
+double
evdev_device_transform_x(struct evdev_device *device,
- li_fixed_t x,
+ double x,
uint32_t width)
{
- return ((uint64_t)x - li_fixed_from_int(device->abs.min_x)) * width /
- (device->abs.max_x - device->abs.min_x + 1);
+ return scale_axis(device->abs.absinfo_x, x, width);
}
-li_fixed_t
+double
evdev_device_transform_y(struct evdev_device *device,
- li_fixed_t y,
+ double y,
uint32_t height)
{
- return ((uint64_t)y - li_fixed_from_int(device->abs.min_y)) * height /
- (device->abs.max_y - device->abs.min_y + 1);
+ return scale_axis(device->abs.absinfo_y, y, height);
}
static void
{
struct motion_params motion;
int32_t cx, cy;
- li_fixed_t x, y;
- li_fixed_t dx, dy;
+ double x, y;
int slot;
int seat_slot;
struct libinput_device *base = &device->base;
case EVDEV_NONE:
return;
case EVDEV_RELATIVE_MOTION:
- motion.dx = li_fixed_to_double(device->rel.dx);
- motion.dy = li_fixed_to_double(device->rel.dy);
+ motion.dx = device->rel.dx;
+ motion.dy = device->rel.dy;
device->rel.dx = 0;
device->rel.dy = 0;
/* Apply pointer acceleration. */
filter_dispatch(device->pointer.filter, &motion, device, time);
- dx = li_fixed_from_double(motion.dx);
- dy = li_fixed_from_double(motion.dy);
- if (dx == 0 && dy == 0)
+ if (motion.dx == 0.0 && motion.dy == 0.0)
break;
- pointer_notify_motion(base, time, dx, dy);
+ pointer_notify_motion(base, time, motion.dx, motion.dy);
break;
case EVDEV_ABSOLUTE_MT_DOWN:
if (!(device->seat_caps & EVDEV_DEVICE_TOUCH))
break;
seat->slot_map |= 1 << seat_slot;
- x = li_fixed_from_int(device->mt.slots[slot].x);
- y = li_fixed_from_int(device->mt.slots[slot].y);
+ x = device->mt.slots[slot].x;
+ y = device->mt.slots[slot].y;
touch_notify_touch_down(base, time, slot, seat_slot, x, y);
break;
break;
seat_slot = device->mt.slots[slot].seat_slot;
- x = li_fixed_from_int(device->mt.slots[slot].x);
- y = li_fixed_from_int(device->mt.slots[slot].y);
+ x = device->mt.slots[slot].x;
+ y = device->mt.slots[slot].y;
if (seat_slot == -1)
break;
seat->slot_map |= 1 << seat_slot;
transform_absolute(device, &cx, &cy);
- x = li_fixed_from_int(cx);
- y = li_fixed_from_int(cy);
- touch_notify_touch_down(base, time, -1, seat_slot, x, y);
+ touch_notify_touch_down(base, time, -1, seat_slot, cx, cy);
break;
case EVDEV_ABSOLUTE_MOTION:
transform_absolute(device, &cx, &cy);
- x = li_fixed_from_int(cx);
- y = li_fixed_from_int(cy);
+ x = cx;
+ y = cy;
if (device->seat_caps & EVDEV_DEVICE_TOUCH) {
seat_slot = device->abs.seat_slot;
}
static void
-evdev_process_touch_button(struct evdev_device *device, int time, int value)
+evdev_process_touch_button(struct evdev_device *device,
+ uint64_t time, int value)
{
if (device->pending_event != EVDEV_NONE &&
device->pending_event != EVDEV_ABSOLUTE_MOTION)
}
static inline void
-evdev_process_key(struct evdev_device *device, struct input_event *e, int time)
+evdev_process_key(struct evdev_device *device,
+ struct input_event *e, uint64_t time)
{
/* ignore kernel key repeat */
if (e->value == 2)
&device->base,
time,
e->code,
- e->value ? LIBINPUT_POINTER_BUTTON_STATE_PRESSED :
- LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
+ e->value ? LIBINPUT_BUTTON_STATE_PRESSED :
+ LIBINPUT_BUTTON_STATE_RELEASED);
break;
default:
&device->base,
time,
e->code,
- e->value ? LIBINPUT_KEYBOARD_KEY_STATE_PRESSED :
- LIBINPUT_KEYBOARD_KEY_STATE_RELEASED);
+ e->value ? LIBINPUT_KEY_STATE_PRESSED :
+ LIBINPUT_KEY_STATE_RELEASED);
break;
}
}
case REL_X:
if (device->pending_event != EVDEV_RELATIVE_MOTION)
evdev_flush_pending_event(device, time);
- device->rel.dx += li_fixed_from_int(e->value);
+ device->rel.dx += e->value;
device->pending_event = EVDEV_RELATIVE_MOTION;
break;
case REL_Y:
if (device->pending_event != EVDEV_RELATIVE_MOTION)
evdev_flush_pending_event(device, time);
- device->rel.dy += li_fixed_from_int(e->value);
+ device->rel.dy += e->value;
device->pending_event = EVDEV_RELATIVE_MOTION;
break;
case REL_WHEEL:
pointer_notify_axis(
base,
time,
- LIBINPUT_POINTER_AXIS_VERTICAL_SCROLL,
+ LIBINPUT_POINTER_AXIS_SCROLL_VERTICAL,
-1 * e->value * DEFAULT_AXIS_STEP_DISTANCE);
break;
case REL_HWHEEL:
pointer_notify_axis(
base,
time,
- LIBINPUT_POINTER_AXIS_HORIZONTAL_SCROLL,
+ LIBINPUT_POINTER_AXIS_SCROLL_HORIZONTAL,
e->value * DEFAULT_AXIS_STEP_DISTANCE);
break;
default:
{
struct libevdev *evdev = device->evdev;
const struct input_absinfo *absinfo;
+ struct input_absinfo fixed;
int has_abs, has_rel, has_mt;
int has_button, has_keyboard, has_touch;
struct mt_slot *slots;
if (libevdev_has_event_type(evdev, EV_ABS)) {
if ((absinfo = libevdev_get_abs_info(evdev, ABS_X))) {
- device->abs.min_x = absinfo->minimum;
- device->abs.max_x = absinfo->maximum;
+ if (absinfo->resolution == 0) {
+ fixed = *absinfo;
+ fixed.resolution = 1;
+ libevdev_set_abs_info(evdev, ABS_X, &fixed);
+ }
+ device->abs.absinfo_x = absinfo;
has_abs = 1;
}
if ((absinfo = libevdev_get_abs_info(evdev, ABS_Y))) {
- device->abs.min_y = absinfo->minimum;
- device->abs.max_y = absinfo->maximum;
+ if (absinfo->resolution == 0) {
+ fixed = *absinfo;
+ fixed.resolution = 1;
+ libevdev_set_abs_info(evdev, ABS_Y, &fixed);
+ }
+ device->abs.absinfo_y = absinfo;
has_abs = 1;
}
/* We only handle the slotted Protocol B in weston.
if (libevdev_has_event_code(evdev, EV_ABS, ABS_MT_POSITION_X) &&
libevdev_has_event_code(evdev, EV_ABS, ABS_MT_POSITION_Y)) {
absinfo = libevdev_get_abs_info(evdev, ABS_MT_POSITION_X);
- device->abs.min_x = absinfo->minimum;
- device->abs.max_x = absinfo->maximum;
+ if (absinfo->resolution == 0) {
+ fixed = *absinfo;
+ fixed.resolution = 1;
+ libevdev_set_abs_info(evdev,
+ ABS_MT_POSITION_X,
+ &fixed);
+ }
+ device->abs.absinfo_x = absinfo;
absinfo = libevdev_get_abs_info(evdev, ABS_MT_POSITION_Y);
- device->abs.min_y = absinfo->minimum;
- device->abs.max_y = absinfo->maximum;
+ if (absinfo->resolution == 0) {
+ fixed = *absinfo;
+ fixed.resolution = 1;
+ libevdev_set_abs_info(evdev,
+ ABS_MT_POSITION_Y,
+ &fixed);
+ }
+ device->abs.absinfo_y = absinfo;
device->is_mt = 1;
has_touch = 1;
has_mt = 1;
}
}
+int
+evdev_device_get_size(struct evdev_device *device,
+ double *width,
+ double *height)
+{
+ const struct input_absinfo *x, *y;
+
+ x = libevdev_get_abs_info(device->evdev, ABS_X);
+ y = libevdev_get_abs_info(device->evdev, ABS_Y);
+
+ if (!x || !y || !x->resolution || !y->resolution)
+ return -1;
+
+ *width = evdev_convert_to_mm(x, x->maximum);
+ *height = evdev_convert_to_mm(y, y->maximum);
+
+ return 0;
+}
+
void
evdev_device_remove(struct evdev_device *device)
{