|
|
|
|
@@ -31,6 +31,7 @@
|
|
|
|
|
#include <time.h>
|
|
|
|
|
#include <unistd.h>
|
|
|
|
|
#include <xorg-server.h>
|
|
|
|
|
#include <list.h>
|
|
|
|
|
#include <exevents.h>
|
|
|
|
|
#include <xkbsrv.h>
|
|
|
|
|
#include <xf86Xinput.h>
|
|
|
|
|
@@ -40,6 +41,12 @@
|
|
|
|
|
|
|
|
|
|
#include <X11/Xatom.h>
|
|
|
|
|
|
|
|
|
|
#include "libinput-properties.h"
|
|
|
|
|
|
|
|
|
|
#ifndef XI86_SERVER_FD
|
|
|
|
|
#define XI86_SERVER_FD 0x20
|
|
|
|
|
#endif
|
|
|
|
|
|
|
|
|
|
#define TOUCHPAD_NUM_AXES 4 /* x, y, hscroll, vscroll */
|
|
|
|
|
#define TOUCH_MAX_SLOTS 15
|
|
|
|
|
#define XORG_KEYCODE_OFFSET 8
|
|
|
|
|
@@ -52,15 +59,10 @@
|
|
|
|
|
*/
|
|
|
|
|
#define TOUCH_AXIS_MAX 0xffff
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
|
libinput scales wheel events by DEFAULT_AXIS_STEP_DISTANCE, which is
|
|
|
|
|
currently 10.
|
|
|
|
|
*/
|
|
|
|
|
#define DEFAULT_LIBINPUT_AXIS_STEP_DISTANCE 10
|
|
|
|
|
|
|
|
|
|
struct xf86libinput_driver {
|
|
|
|
|
struct libinput *libinput;
|
|
|
|
|
int device_enabled_count;
|
|
|
|
|
struct xorg_list server_fds;
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
static struct xf86libinput_driver driver_context;
|
|
|
|
|
@@ -95,6 +97,80 @@ struct xf86libinput {
|
|
|
|
|
} options;
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
|
libinput provides a userdata for the context, but not per path device. so
|
|
|
|
|
the open_restricted call has the libinput context, but no reference to
|
|
|
|
|
the pInfo->fd that we actually need to return.
|
|
|
|
|
To avoid this, we store each path/fd combination during pre_init in the
|
|
|
|
|
context, then return that during open_restricted. If a device is added
|
|
|
|
|
twice with two different fds this may give us the wrong fd but why are
|
|
|
|
|
you doing that anyway.
|
|
|
|
|
*/
|
|
|
|
|
struct serverfd {
|
|
|
|
|
struct xorg_list node;
|
|
|
|
|
int fd;
|
|
|
|
|
char *path;
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
static inline int
|
|
|
|
|
use_server_fd(const InputInfoPtr pInfo) {
|
|
|
|
|
return pInfo->fd > -1 && (pInfo->flags & XI86_SERVER_FD);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static inline void
|
|
|
|
|
fd_push(struct xf86libinput_driver *context,
|
|
|
|
|
int fd,
|
|
|
|
|
const char *path)
|
|
|
|
|
{
|
|
|
|
|
struct serverfd *sfd = xnfcalloc(1, sizeof(*sfd));
|
|
|
|
|
|
|
|
|
|
sfd->fd = fd;
|
|
|
|
|
sfd->path = xnfstrdup(path);
|
|
|
|
|
xorg_list_add(&sfd->node, &context->server_fds);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static inline int
|
|
|
|
|
fd_get(struct xf86libinput_driver *context,
|
|
|
|
|
const char *path)
|
|
|
|
|
{
|
|
|
|
|
struct serverfd *sfd;
|
|
|
|
|
|
|
|
|
|
xorg_list_for_each_entry(sfd, &context->server_fds, node) {
|
|
|
|
|
if (strcmp(path, sfd->path) == 0)
|
|
|
|
|
return sfd->fd;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return -1;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static inline void
|
|
|
|
|
fd_pop(struct xf86libinput_driver *context, int fd)
|
|
|
|
|
{
|
|
|
|
|
struct serverfd *sfd;
|
|
|
|
|
|
|
|
|
|
xorg_list_for_each_entry(sfd, &context->server_fds, node) {
|
|
|
|
|
if (fd != sfd->fd)
|
|
|
|
|
continue;
|
|
|
|
|
|
|
|
|
|
xorg_list_del(&sfd->node);
|
|
|
|
|
free(sfd->path);
|
|
|
|
|
free(sfd);
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static inline int
|
|
|
|
|
fd_find(struct xf86libinput_driver *context, int fd)
|
|
|
|
|
{
|
|
|
|
|
struct serverfd *sfd;
|
|
|
|
|
|
|
|
|
|
xorg_list_for_each_entry(sfd, &context->server_fds, node) {
|
|
|
|
|
if (fd == sfd->fd)
|
|
|
|
|
return fd;
|
|
|
|
|
}
|
|
|
|
|
return -1;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static inline unsigned int
|
|
|
|
|
btn_linux2xorg(unsigned int b)
|
|
|
|
|
{
|
|
|
|
|
@@ -142,6 +218,7 @@ LibinputApplyConfig(DeviceIntPtr dev)
|
|
|
|
|
InputInfoPtr pInfo = dev->public.devicePrivate;
|
|
|
|
|
struct xf86libinput *driver_data = pInfo->private;
|
|
|
|
|
struct libinput_device *device = driver_data->device;
|
|
|
|
|
unsigned int scroll_button;
|
|
|
|
|
|
|
|
|
|
if (libinput_device_config_send_events_get_modes(device) != LIBINPUT_CONFIG_SEND_EVENTS_ENABLED &&
|
|
|
|
|
libinput_device_config_send_events_set_mode(device,
|
|
|
|
|
@@ -182,8 +259,9 @@ LibinputApplyConfig(DeviceIntPtr dev)
|
|
|
|
|
driver_data->options.matrix[6], driver_data->options.matrix[7],
|
|
|
|
|
driver_data->options.matrix[8]);
|
|
|
|
|
|
|
|
|
|
if (libinput_device_config_buttons_set_left_handed(device,
|
|
|
|
|
driver_data->options.left_handed) != LIBINPUT_CONFIG_STATUS_SUCCESS)
|
|
|
|
|
if (libinput_device_config_left_handed_is_available(device) &&
|
|
|
|
|
libinput_device_config_left_handed_set(device,
|
|
|
|
|
driver_data->options.left_handed) != LIBINPUT_CONFIG_STATUS_SUCCESS)
|
|
|
|
|
xf86IDrvMsg(pInfo, X_ERROR,
|
|
|
|
|
"Failed to set LeftHanded to %d\n",
|
|
|
|
|
driver_data->options.left_handed);
|
|
|
|
|
@@ -206,11 +284,13 @@ LibinputApplyConfig(DeviceIntPtr dev)
|
|
|
|
|
method);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (libinput_device_config_scroll_set_button(device,
|
|
|
|
|
btn_xorg2linux(driver_data->options.scroll_button)) != LIBINPUT_CONFIG_STATUS_SUCCESS)
|
|
|
|
|
xf86IDrvMsg(pInfo, X_ERROR,
|
|
|
|
|
"Failed to set ScrollButton to %d\n",
|
|
|
|
|
driver_data->options.scroll_button);
|
|
|
|
|
if (libinput_device_config_scroll_get_methods(device) & LIBINPUT_CONFIG_SCROLL_ON_BUTTON_DOWN) {
|
|
|
|
|
scroll_button = btn_xorg2linux(driver_data->options.scroll_button);
|
|
|
|
|
if (libinput_device_config_scroll_set_button(device, scroll_button) != LIBINPUT_CONFIG_STATUS_SUCCESS)
|
|
|
|
|
xf86IDrvMsg(pInfo, X_ERROR,
|
|
|
|
|
"Failed to set ScrollButton to %d\n",
|
|
|
|
|
driver_data->options.scroll_button);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static int
|
|
|
|
|
@@ -221,13 +301,24 @@ xf86libinput_on(DeviceIntPtr dev)
|
|
|
|
|
struct libinput *libinput = driver_context.libinput;
|
|
|
|
|
struct libinput_device *device = driver_data->device;
|
|
|
|
|
|
|
|
|
|
if (use_server_fd(pInfo)) {
|
|
|
|
|
char *path = xf86SetStrOption(pInfo->options, "Device", NULL);
|
|
|
|
|
fd_push(&driver_context, pInfo->fd, path);
|
|
|
|
|
free(path);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
device = libinput_path_add_device(libinput, driver_data->path);
|
|
|
|
|
if (!device)
|
|
|
|
|
return !Success;
|
|
|
|
|
|
|
|
|
|
libinput_device_ref(device);
|
|
|
|
|
libinput_device_set_user_data(device, pInfo);
|
|
|
|
|
driver_data->device = device;
|
|
|
|
|
|
|
|
|
|
/* if we use server fds, overwrite the fd with the one from
|
|
|
|
|
libinput nonetheless, otherwise the server won't call ReadInput
|
|
|
|
|
for our device. This must be swapped back to the real fd in
|
|
|
|
|
DEVICE_OFF so systemd-logind closes the right fd */
|
|
|
|
|
pInfo->fd = libinput_get_fd(libinput);
|
|
|
|
|
|
|
|
|
|
if (driver_context.device_enabled_count == 0) {
|
|
|
|
|
@@ -238,6 +329,8 @@ xf86libinput_on(DeviceIntPtr dev)
|
|
|
|
|
driver_context.device_enabled_count++;
|
|
|
|
|
dev->public.on = TRUE;
|
|
|
|
|
|
|
|
|
|
LibinputApplyConfig(dev);
|
|
|
|
|
|
|
|
|
|
return Success;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
@@ -251,7 +344,13 @@ xf86libinput_off(DeviceIntPtr dev)
|
|
|
|
|
RemoveEnabledDevice(pInfo->fd);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
pInfo->fd = -1;
|
|
|
|
|
if (use_server_fd(pInfo)) {
|
|
|
|
|
fd_pop(&driver_context, pInfo->fd);
|
|
|
|
|
pInfo->fd = xf86SetIntOption(pInfo->options, "fd", -1);
|
|
|
|
|
} else {
|
|
|
|
|
pInfo->fd = -1;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
dev->public.on = FALSE;
|
|
|
|
|
|
|
|
|
|
libinput_device_set_user_data(driver_data->device, NULL);
|
|
|
|
|
@@ -292,8 +391,8 @@ init_button_labels(Atom *labels, size_t size)
|
|
|
|
|
labels[6] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_HWHEEL_RIGHT);
|
|
|
|
|
labels[7] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_SIDE);
|
|
|
|
|
labels[8] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_EXTRA);
|
|
|
|
|
labels[9] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_BACK);
|
|
|
|
|
labels[10] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_FORWARD);
|
|
|
|
|
labels[9] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_FORWARD);
|
|
|
|
|
labels[10] = XIGetKnownProperty(BTN_LABEL_PROP_BTN_BACK);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static void
|
|
|
|
|
@@ -354,6 +453,53 @@ xf86libinput_init_pointer(InputInfoPtr pInfo)
|
|
|
|
|
return Success;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static int
|
|
|
|
|
xf86libinput_init_pointer_absolute(InputInfoPtr pInfo)
|
|
|
|
|
{
|
|
|
|
|
DeviceIntPtr dev= pInfo->dev;
|
|
|
|
|
struct xf86libinput *driver_data = pInfo->private;
|
|
|
|
|
int min, max, res;
|
|
|
|
|
int nbuttons = 7;
|
|
|
|
|
int i;
|
|
|
|
|
|
|
|
|
|
unsigned char btnmap[MAX_BUTTONS + 1];
|
|
|
|
|
Atom btnlabels[MAX_BUTTONS];
|
|
|
|
|
Atom axislabels[TOUCHPAD_NUM_AXES];
|
|
|
|
|
|
|
|
|
|
for (i = BTN_BACK; i >= BTN_SIDE; i--) {
|
|
|
|
|
if (libinput_device_has_button(driver_data->device, i)) {
|
|
|
|
|
nbuttons += i - BTN_SIDE + 1;
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
init_button_map(btnmap, ARRAY_SIZE(btnmap));
|
|
|
|
|
init_button_labels(btnlabels, ARRAY_SIZE(btnlabels));
|
|
|
|
|
init_axis_labels(axislabels, ARRAY_SIZE(axislabels));
|
|
|
|
|
|
|
|
|
|
InitPointerDeviceStruct((DevicePtr)dev, btnmap,
|
|
|
|
|
nbuttons,
|
|
|
|
|
btnlabels,
|
|
|
|
|
xf86libinput_ptr_ctl,
|
|
|
|
|
GetMotionHistorySize(),
|
|
|
|
|
TOUCHPAD_NUM_AXES,
|
|
|
|
|
axislabels);
|
|
|
|
|
min = 0;
|
|
|
|
|
max = TOUCH_AXIS_MAX;
|
|
|
|
|
res = 0;
|
|
|
|
|
|
|
|
|
|
xf86InitValuatorAxisStruct(dev, 0,
|
|
|
|
|
XIGetKnownProperty(AXIS_LABEL_PROP_ABS_X),
|
|
|
|
|
min, max, res * 1000, 0, res * 1000, Absolute);
|
|
|
|
|
xf86InitValuatorAxisStruct(dev, 1,
|
|
|
|
|
XIGetKnownProperty(AXIS_LABEL_PROP_ABS_Y),
|
|
|
|
|
min, max, res * 1000, 0, res * 1000, Absolute);
|
|
|
|
|
|
|
|
|
|
SetScrollValuator(dev, 2, SCROLL_TYPE_HORIZONTAL, driver_data->scroll_hdist, 0);
|
|
|
|
|
SetScrollValuator(dev, 3, SCROLL_TYPE_VERTICAL, driver_data->scroll_vdist, 0);
|
|
|
|
|
|
|
|
|
|
return Success;
|
|
|
|
|
}
|
|
|
|
|
static void
|
|
|
|
|
xf86libinput_kbd_ctrl(DeviceIntPtr device, KeybdCtrl *ctrl)
|
|
|
|
|
{
|
|
|
|
|
@@ -387,16 +533,30 @@ xf86libinput_init_keyboard(InputInfoPtr pInfo)
|
|
|
|
|
{
|
|
|
|
|
DeviceIntPtr dev= pInfo->dev;
|
|
|
|
|
XkbRMLVOSet rmlvo = {0};
|
|
|
|
|
XkbRMLVOSet defaults = {0};
|
|
|
|
|
|
|
|
|
|
rmlvo.rules = xf86SetStrOption(pInfo->options, "xkb_rules", "evdev");
|
|
|
|
|
rmlvo.model = xf86SetStrOption(pInfo->options, "xkb_model", "pc104");
|
|
|
|
|
rmlvo.layout = xf86SetStrOption(pInfo->options, "xkb_layout", "us");
|
|
|
|
|
rmlvo.variant = xf86SetStrOption(pInfo->options, "xkb_variant", NULL);
|
|
|
|
|
rmlvo.options = xf86SetStrOption(pInfo->options, "xkb_options", NULL);
|
|
|
|
|
XkbGetRulesDflts(&defaults);
|
|
|
|
|
|
|
|
|
|
rmlvo.rules = xf86SetStrOption(pInfo->options,
|
|
|
|
|
"xkb_rules",
|
|
|
|
|
defaults.rules);
|
|
|
|
|
rmlvo.model = xf86SetStrOption(pInfo->options,
|
|
|
|
|
"xkb_model",
|
|
|
|
|
defaults.model);
|
|
|
|
|
rmlvo.layout = xf86SetStrOption(pInfo->options,
|
|
|
|
|
"xkb_layout",
|
|
|
|
|
defaults.layout);
|
|
|
|
|
rmlvo.variant = xf86SetStrOption(pInfo->options,
|
|
|
|
|
"xkb_variant",
|
|
|
|
|
defaults.variant);
|
|
|
|
|
rmlvo.options = xf86SetStrOption(pInfo->options,
|
|
|
|
|
"xkb_options",
|
|
|
|
|
defaults.options);
|
|
|
|
|
|
|
|
|
|
InitKeyboardDeviceStruct(dev, &rmlvo, NULL,
|
|
|
|
|
xf86libinput_kbd_ctrl);
|
|
|
|
|
XkbFreeRMLVOSet(&rmlvo, FALSE);
|
|
|
|
|
XkbFreeRMLVOSet(&defaults, FALSE);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static void
|
|
|
|
|
@@ -445,8 +605,12 @@ xf86libinput_init(DeviceIntPtr dev)
|
|
|
|
|
|
|
|
|
|
if (libinput_device_has_capability(device, LIBINPUT_DEVICE_CAP_KEYBOARD))
|
|
|
|
|
xf86libinput_init_keyboard(pInfo);
|
|
|
|
|
if (libinput_device_has_capability(device, LIBINPUT_DEVICE_CAP_POINTER))
|
|
|
|
|
xf86libinput_init_pointer(pInfo);
|
|
|
|
|
if (libinput_device_has_capability(device, LIBINPUT_DEVICE_CAP_POINTER)) {
|
|
|
|
|
if (libinput_device_config_calibration_has_matrix(device))
|
|
|
|
|
xf86libinput_init_pointer_absolute(pInfo);
|
|
|
|
|
else
|
|
|
|
|
xf86libinput_init_pointer(pInfo);
|
|
|
|
|
}
|
|
|
|
|
if (libinput_device_has_capability(device, LIBINPUT_DEVICE_CAP_TOUCH))
|
|
|
|
|
xf86libinput_init_touch(pInfo);
|
|
|
|
|
|
|
|
|
|
@@ -506,6 +670,24 @@ xf86libinput_handle_motion(InputInfoPtr pInfo, struct libinput_event_pointer *ev
|
|
|
|
|
xf86PostMotionEventM(dev, Relative, mask);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static void
|
|
|
|
|
xf86libinput_handle_absmotion(InputInfoPtr pInfo, struct libinput_event_pointer *event)
|
|
|
|
|
{
|
|
|
|
|
DeviceIntPtr dev = pInfo->dev;
|
|
|
|
|
struct xf86libinput *driver_data = pInfo->private;
|
|
|
|
|
ValuatorMask *mask = driver_data->valuators;
|
|
|
|
|
double x, y;
|
|
|
|
|
|
|
|
|
|
x = libinput_event_pointer_get_absolute_x_transformed(event, TOUCH_AXIS_MAX);
|
|
|
|
|
y = libinput_event_pointer_get_absolute_y_transformed(event, TOUCH_AXIS_MAX);
|
|
|
|
|
|
|
|
|
|
valuator_mask_zero(mask);
|
|
|
|
|
valuator_mask_set_double(mask, 0, x);
|
|
|
|
|
valuator_mask_set_double(mask, 1, y);
|
|
|
|
|
|
|
|
|
|
xf86PostMotionEventM(dev, Absolute, mask);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static void
|
|
|
|
|
xf86libinput_handle_button(InputInfoPtr pInfo, struct libinput_event_pointer *event)
|
|
|
|
|
{
|
|
|
|
|
@@ -537,19 +719,38 @@ xf86libinput_handle_axis(InputInfoPtr pInfo, struct libinput_event_pointer *even
|
|
|
|
|
DeviceIntPtr dev = pInfo->dev;
|
|
|
|
|
struct xf86libinput *driver_data = pInfo->private;
|
|
|
|
|
ValuatorMask *mask = driver_data->valuators;
|
|
|
|
|
int axis;
|
|
|
|
|
double value;
|
|
|
|
|
|
|
|
|
|
if (libinput_event_pointer_get_axis(event) ==
|
|
|
|
|
LIBINPUT_POINTER_AXIS_SCROLL_VERTICAL)
|
|
|
|
|
axis = 3;
|
|
|
|
|
else
|
|
|
|
|
axis = 2;
|
|
|
|
|
|
|
|
|
|
value = libinput_event_pointer_get_axis_value(event) / DEFAULT_LIBINPUT_AXIS_STEP_DISTANCE;
|
|
|
|
|
enum libinput_pointer_axis axis;
|
|
|
|
|
enum libinput_pointer_axis_source source;
|
|
|
|
|
|
|
|
|
|
valuator_mask_zero(mask);
|
|
|
|
|
valuator_mask_set_double(mask, axis, value);
|
|
|
|
|
|
|
|
|
|
source = libinput_event_pointer_get_axis_source(event);
|
|
|
|
|
switch(source) {
|
|
|
|
|
case LIBINPUT_POINTER_AXIS_SOURCE_FINGER:
|
|
|
|
|
case LIBINPUT_POINTER_AXIS_SOURCE_WHEEL:
|
|
|
|
|
case LIBINPUT_POINTER_AXIS_SOURCE_CONTINUOUS:
|
|
|
|
|
break;
|
|
|
|
|
default:
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
axis = LIBINPUT_POINTER_AXIS_SCROLL_VERTICAL;
|
|
|
|
|
if (libinput_event_pointer_has_axis(event, axis)) {
|
|
|
|
|
if (source == LIBINPUT_POINTER_AXIS_SOURCE_WHEEL)
|
|
|
|
|
value = libinput_event_pointer_get_axis_value_discrete(event, axis);
|
|
|
|
|
else
|
|
|
|
|
value = libinput_event_pointer_get_axis_value(event, axis);
|
|
|
|
|
valuator_mask_set_double(mask, 3, value);
|
|
|
|
|
}
|
|
|
|
|
axis = LIBINPUT_POINTER_AXIS_SCROLL_HORIZONTAL;
|
|
|
|
|
if (libinput_event_pointer_has_axis(event, axis)) {
|
|
|
|
|
if (source == LIBINPUT_POINTER_AXIS_SOURCE_WHEEL)
|
|
|
|
|
value = libinput_event_pointer_get_axis_value_discrete(event, axis);
|
|
|
|
|
else
|
|
|
|
|
value = libinput_event_pointer_get_axis_value(event, axis);
|
|
|
|
|
valuator_mask_set_double(mask, 2, value);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
xf86PostMotionEventM(dev, Relative, mask);
|
|
|
|
|
}
|
|
|
|
|
@@ -568,8 +769,8 @@ xf86libinput_handle_touch(InputInfoPtr pInfo,
|
|
|
|
|
|
|
|
|
|
/* libinput doesn't give us hw touch ids which X expects, so
|
|
|
|
|
emulate them here */
|
|
|
|
|
static int next_touchid;
|
|
|
|
|
static int touchids[TOUCH_MAX_SLOTS] = {0};
|
|
|
|
|
static unsigned int next_touchid;
|
|
|
|
|
static unsigned int touchids[TOUCH_MAX_SLOTS] = {0};
|
|
|
|
|
|
|
|
|
|
slot = libinput_event_touch_get_slot(event);
|
|
|
|
|
|
|
|
|
|
@@ -619,7 +820,8 @@ xf86libinput_handle_event(struct libinput_event *event)
|
|
|
|
|
case LIBINPUT_EVENT_DEVICE_REMOVED:
|
|
|
|
|
break;
|
|
|
|
|
case LIBINPUT_EVENT_POINTER_MOTION_ABSOLUTE:
|
|
|
|
|
/* FIXME */
|
|
|
|
|
xf86libinput_handle_absmotion(pInfo,
|
|
|
|
|
libinput_event_get_pointer_event(event));
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case LIBINPUT_EVENT_POINTER_MOTION:
|
|
|
|
|
@@ -663,7 +865,9 @@ xf86libinput_read_input(InputInfoPtr pInfo)
|
|
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
if (rc < 0) {
|
|
|
|
|
ErrorFSigSafe("Error reading events: %d\n", -rc);
|
|
|
|
|
xf86IDrvMsg(pInfo, X_ERROR,
|
|
|
|
|
"Error reading events: %s\n",
|
|
|
|
|
strerror(-rc));
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
@@ -676,14 +880,22 @@ xf86libinput_read_input(InputInfoPtr pInfo)
|
|
|
|
|
static int
|
|
|
|
|
open_restricted(const char *path, int flags, void *data)
|
|
|
|
|
{
|
|
|
|
|
int fd = open(path, flags);
|
|
|
|
|
struct xf86libinput_driver *context = data;
|
|
|
|
|
int fd;
|
|
|
|
|
|
|
|
|
|
fd = fd_get(context, path);
|
|
|
|
|
if (fd == -1)
|
|
|
|
|
fd = open(path, flags);
|
|
|
|
|
return fd < 0 ? -errno : fd;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static void
|
|
|
|
|
close_restricted(int fd, void *data)
|
|
|
|
|
{
|
|
|
|
|
close(fd);
|
|
|
|
|
struct xf86libinput_driver *context = data;
|
|
|
|
|
|
|
|
|
|
if (fd_find(context, fd) == -1)
|
|
|
|
|
close(fd);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const struct libinput_interface interface = {
|
|
|
|
|
@@ -730,77 +942,13 @@ xf86libinput_log_handler(struct libinput *libinput,
|
|
|
|
|
LogVMessageVerb(type, verbosity, format, args);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static int xf86libinput_pre_init(InputDriverPtr drv,
|
|
|
|
|
InputInfoPtr pInfo,
|
|
|
|
|
int flags)
|
|
|
|
|
static void
|
|
|
|
|
xf86libinput_parse_options(InputInfoPtr pInfo,
|
|
|
|
|
struct xf86libinput *driver_data,
|
|
|
|
|
struct libinput_device *device)
|
|
|
|
|
{
|
|
|
|
|
struct xf86libinput *driver_data = NULL;
|
|
|
|
|
struct libinput *libinput = NULL;
|
|
|
|
|
struct libinput_device *device;
|
|
|
|
|
char *path;
|
|
|
|
|
uint32_t scroll_methods;
|
|
|
|
|
|
|
|
|
|
pInfo->fd = -1;
|
|
|
|
|
pInfo->type_name = 0;
|
|
|
|
|
pInfo->device_control = xf86libinput_device_control;
|
|
|
|
|
pInfo->read_input = xf86libinput_read_input;
|
|
|
|
|
pInfo->control_proc = NULL;
|
|
|
|
|
pInfo->switch_mode = NULL;
|
|
|
|
|
|
|
|
|
|
driver_data = calloc(1, sizeof(*driver_data));
|
|
|
|
|
if (!driver_data)
|
|
|
|
|
goto fail;
|
|
|
|
|
|
|
|
|
|
driver_data->valuators = valuator_mask_new(2);
|
|
|
|
|
if (!driver_data->valuators)
|
|
|
|
|
goto fail;
|
|
|
|
|
|
|
|
|
|
driver_data->scroll_vdist = 1;
|
|
|
|
|
driver_data->scroll_hdist = 1;
|
|
|
|
|
|
|
|
|
|
path = xf86SetStrOption(pInfo->options, "Device", NULL);
|
|
|
|
|
if (!path)
|
|
|
|
|
goto fail;
|
|
|
|
|
|
|
|
|
|
if (!driver_context.libinput) {
|
|
|
|
|
driver_context.libinput = libinput_path_create_context(&interface, &driver_context);
|
|
|
|
|
libinput_log_set_handler(driver_context.libinput,
|
|
|
|
|
xf86libinput_log_handler);
|
|
|
|
|
/* we want all msgs, let the server filter */
|
|
|
|
|
libinput_log_set_priority(driver_context.libinput,
|
|
|
|
|
LIBINPUT_LOG_PRIORITY_DEBUG);
|
|
|
|
|
} else {
|
|
|
|
|
libinput_ref(driver_context.libinput);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
libinput = driver_context.libinput;
|
|
|
|
|
|
|
|
|
|
if (libinput == NULL) {
|
|
|
|
|
xf86IDrvMsg(pInfo, X_ERROR, "Creating a device for %s failed\n", path);
|
|
|
|
|
goto fail;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
device = libinput_path_add_device(libinput, path);
|
|
|
|
|
if (!device) {
|
|
|
|
|
xf86IDrvMsg(pInfo, X_ERROR, "Failed to create a device for %s\n", path);
|
|
|
|
|
goto fail;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/* We ref the device but remove it afterwards. The hope is that
|
|
|
|
|
between now and DEVICE_INIT/DEVICE_ON, the device doesn't change.
|
|
|
|
|
*/
|
|
|
|
|
libinput_device_ref(device);
|
|
|
|
|
libinput_path_remove_device(device);
|
|
|
|
|
|
|
|
|
|
pInfo->fd = -1;
|
|
|
|
|
pInfo->private = driver_data;
|
|
|
|
|
driver_data->path = path;
|
|
|
|
|
driver_data->device = device;
|
|
|
|
|
|
|
|
|
|
/* Disable acceleration in the server, libinput does it for us */
|
|
|
|
|
pInfo->options = xf86ReplaceIntOption(pInfo->options, "AccelerationProfile", -1);
|
|
|
|
|
pInfo->options = xf86ReplaceStrOption(pInfo->options, "AccelerationScheme", "none");
|
|
|
|
|
|
|
|
|
|
if (libinput_device_config_tap_get_finger_count(device) > 0) {
|
|
|
|
|
BOOL tap = xf86SetBoolOption(pInfo->options,
|
|
|
|
|
"Tapping",
|
|
|
|
|
@@ -908,17 +1056,17 @@ static int xf86libinput_pre_init(InputDriverPtr drv,
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (libinput_device_config_buttons_has_left_handed(device)) {
|
|
|
|
|
if (libinput_device_config_left_handed_is_available(device)) {
|
|
|
|
|
BOOL left_handed = xf86SetBoolOption(pInfo->options,
|
|
|
|
|
"LeftHanded",
|
|
|
|
|
libinput_device_config_buttons_get_left_handed(device));
|
|
|
|
|
if (libinput_device_config_buttons_set_left_handed(device,
|
|
|
|
|
left_handed) !=
|
|
|
|
|
libinput_device_config_left_handed_get(device));
|
|
|
|
|
if (libinput_device_config_left_handed_set(device,
|
|
|
|
|
left_handed) !=
|
|
|
|
|
LIBINPUT_CONFIG_STATUS_SUCCESS) {
|
|
|
|
|
xf86IDrvMsg(pInfo, X_ERROR,
|
|
|
|
|
"Failed to set LeftHanded to %d\n",
|
|
|
|
|
left_handed);
|
|
|
|
|
left_handed = libinput_device_config_buttons_get_left_handed(device);
|
|
|
|
|
left_handed = libinput_device_config_left_handed_get(device);
|
|
|
|
|
}
|
|
|
|
|
driver_data->options.left_handed = left_handed;
|
|
|
|
|
}
|
|
|
|
|
@@ -970,6 +1118,85 @@ static int xf86libinput_pre_init(InputDriverPtr drv,
|
|
|
|
|
driver_data->options.scroll_button = scroll_button;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static int
|
|
|
|
|
xf86libinput_pre_init(InputDriverPtr drv,
|
|
|
|
|
InputInfoPtr pInfo,
|
|
|
|
|
int flags)
|
|
|
|
|
{
|
|
|
|
|
struct xf86libinput *driver_data = NULL;
|
|
|
|
|
struct libinput *libinput = NULL;
|
|
|
|
|
struct libinput_device *device;
|
|
|
|
|
char *path;
|
|
|
|
|
|
|
|
|
|
pInfo->type_name = 0;
|
|
|
|
|
pInfo->device_control = xf86libinput_device_control;
|
|
|
|
|
pInfo->read_input = xf86libinput_read_input;
|
|
|
|
|
pInfo->control_proc = NULL;
|
|
|
|
|
pInfo->switch_mode = NULL;
|
|
|
|
|
|
|
|
|
|
driver_data = calloc(1, sizeof(*driver_data));
|
|
|
|
|
if (!driver_data)
|
|
|
|
|
goto fail;
|
|
|
|
|
|
|
|
|
|
driver_data->valuators = valuator_mask_new(2);
|
|
|
|
|
if (!driver_data->valuators)
|
|
|
|
|
goto fail;
|
|
|
|
|
|
|
|
|
|
driver_data->scroll_vdist = 1;
|
|
|
|
|
driver_data->scroll_hdist = 1;
|
|
|
|
|
|
|
|
|
|
path = xf86SetStrOption(pInfo->options, "Device", NULL);
|
|
|
|
|
if (!path)
|
|
|
|
|
goto fail;
|
|
|
|
|
|
|
|
|
|
if (!driver_context.libinput) {
|
|
|
|
|
driver_context.libinput = libinput_path_create_context(&interface, &driver_context);
|
|
|
|
|
libinput_log_set_handler(driver_context.libinput,
|
|
|
|
|
xf86libinput_log_handler);
|
|
|
|
|
/* we want all msgs, let the server filter */
|
|
|
|
|
libinput_log_set_priority(driver_context.libinput,
|
|
|
|
|
LIBINPUT_LOG_PRIORITY_DEBUG);
|
|
|
|
|
xorg_list_init(&driver_context.server_fds);
|
|
|
|
|
} else {
|
|
|
|
|
libinput_ref(driver_context.libinput);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
libinput = driver_context.libinput;
|
|
|
|
|
|
|
|
|
|
if (libinput == NULL) {
|
|
|
|
|
xf86IDrvMsg(pInfo, X_ERROR, "Creating a device for %s failed\n", path);
|
|
|
|
|
goto fail;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (use_server_fd(pInfo))
|
|
|
|
|
fd_push(&driver_context, pInfo->fd, path);
|
|
|
|
|
|
|
|
|
|
device = libinput_path_add_device(libinput, path);
|
|
|
|
|
if (!device) {
|
|
|
|
|
xf86IDrvMsg(pInfo, X_ERROR, "Failed to create a device for %s\n", path);
|
|
|
|
|
goto fail;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/* We ref the device but remove it afterwards. The hope is that
|
|
|
|
|
between now and DEVICE_INIT/DEVICE_ON, the device doesn't change.
|
|
|
|
|
*/
|
|
|
|
|
libinput_device_ref(device);
|
|
|
|
|
libinput_path_remove_device(device);
|
|
|
|
|
if (use_server_fd(pInfo))
|
|
|
|
|
fd_pop(&driver_context, pInfo->fd);
|
|
|
|
|
|
|
|
|
|
pInfo->private = driver_data;
|
|
|
|
|
driver_data->path = path;
|
|
|
|
|
driver_data->device = device;
|
|
|
|
|
|
|
|
|
|
/* Disable acceleration in the server, libinput does it for us */
|
|
|
|
|
pInfo->options = xf86ReplaceIntOption(pInfo->options, "AccelerationProfile", -1);
|
|
|
|
|
pInfo->options = xf86ReplaceStrOption(pInfo->options, "AccelerationScheme", "none");
|
|
|
|
|
|
|
|
|
|
xf86libinput_parse_options(pInfo, driver_data, device);
|
|
|
|
|
|
|
|
|
|
/* now pick an actual type */
|
|
|
|
|
if (libinput_device_config_tap_get_finger_count(device) > 0)
|
|
|
|
|
pInfo->type_name = XI_TOUCHPAD;
|
|
|
|
|
@@ -984,6 +1211,8 @@ static int xf86libinput_pre_init(InputDriverPtr drv,
|
|
|
|
|
|
|
|
|
|
return Success;
|
|
|
|
|
fail:
|
|
|
|
|
if (use_server_fd(pInfo) && driver_context.libinput != NULL)
|
|
|
|
|
fd_pop(&driver_context, pInfo->fd);
|
|
|
|
|
if (driver_data->valuators)
|
|
|
|
|
valuator_mask_free(&driver_data->valuators);
|
|
|
|
|
free(path);
|
|
|
|
|
@@ -1012,6 +1241,11 @@ InputDriverRec xf86libinput_driver = {
|
|
|
|
|
.driverName = "libinput",
|
|
|
|
|
.PreInit = xf86libinput_pre_init,
|
|
|
|
|
.UnInit = xf86libinput_uninit,
|
|
|
|
|
.module = NULL,
|
|
|
|
|
.default_options= NULL,
|
|
|
|
|
#ifdef XI86_DRV_CAP_SERVER_FD
|
|
|
|
|
.capabilities = XI86_DRV_CAP_SERVER_FD
|
|
|
|
|
#endif
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
static XF86ModuleVersionInfo xf86libinput_version_info = {
|
|
|
|
|
@@ -1042,32 +1276,16 @@ _X_EXPORT XF86ModuleData libinputModuleData = {
|
|
|
|
|
|
|
|
|
|
/* Property support */
|
|
|
|
|
|
|
|
|
|
/* Tapping enabled/disabled: BOOL, 1 value */
|
|
|
|
|
#define PROP_TAP "libinput Tapping Enabled"
|
|
|
|
|
/* Calibration matrix: FLOAT, 9 values of a 3x3 matrix, in rows */
|
|
|
|
|
#define PROP_CALIBRATION "libinput Calibration Matrix"
|
|
|
|
|
/* Pointer accel speed: FLOAT, 1 value, 32 bit */
|
|
|
|
|
#define PROP_ACCEL "libinput Accel Speed"
|
|
|
|
|
/* Natural scrolling: BOOL, 1 value */
|
|
|
|
|
#define PROP_NATURAL_SCROLL "libinput Natural Scrolling Enabled"
|
|
|
|
|
/* Send-events mode: 32-bit int, 1 value */
|
|
|
|
|
#define PROP_SENDEVENTS "libinput Send Events Mode"
|
|
|
|
|
/* Left-handed enabled/disabled: BOOL, 1 value */
|
|
|
|
|
#define PROP_LEFT_HANDED "libinput Left Handed Enabled"
|
|
|
|
|
/* Scroll method: BOOL, 3 values in order 2fg, edge, button
|
|
|
|
|
only one is enabled at a time at max */
|
|
|
|
|
#define PROP_SCROLL_METHODS "libinput Scroll Methods"
|
|
|
|
|
/* Scroll button for button scrolling: 32-bit int, 1 value */
|
|
|
|
|
#define PROP_SCROLL_BUTTON "libinput Button Scrolling Button"
|
|
|
|
|
|
|
|
|
|
/* libinput-specific properties */
|
|
|
|
|
static Atom prop_tap;
|
|
|
|
|
static Atom prop_calibration;
|
|
|
|
|
static Atom prop_accel;
|
|
|
|
|
static Atom prop_natural_scroll;
|
|
|
|
|
static Atom prop_sendevents;
|
|
|
|
|
static Atom prop_sendevents_available;
|
|
|
|
|
static Atom prop_sendevents_enabled;
|
|
|
|
|
static Atom prop_left_handed;
|
|
|
|
|
static Atom prop_scroll_methods;
|
|
|
|
|
static Atom prop_scroll_methods_available;
|
|
|
|
|
static Atom prop_scroll_method_enabled;
|
|
|
|
|
static Atom prop_scroll_button;
|
|
|
|
|
|
|
|
|
|
/* general properties */
|
|
|
|
|
@@ -1203,25 +1421,28 @@ LibinputSetPropertySendEvents(DeviceIntPtr dev,
|
|
|
|
|
InputInfoPtr pInfo = dev->public.devicePrivate;
|
|
|
|
|
struct xf86libinput *driver_data = pInfo->private;
|
|
|
|
|
struct libinput_device *device = driver_data->device;
|
|
|
|
|
CARD32* data;
|
|
|
|
|
BOOL* data;
|
|
|
|
|
uint32_t modes = 0;
|
|
|
|
|
|
|
|
|
|
if (val->format != 32 || val->size != 1 || val->type != XA_CARDINAL)
|
|
|
|
|
if (val->format != 8 || val->size != 2 || val->type != XA_INTEGER)
|
|
|
|
|
return BadMatch;
|
|
|
|
|
|
|
|
|
|
data = (CARD32*)val->data;
|
|
|
|
|
data = (BOOL*)val->data;
|
|
|
|
|
|
|
|
|
|
if (data[0])
|
|
|
|
|
modes |= LIBINPUT_CONFIG_SEND_EVENTS_DISABLED;
|
|
|
|
|
if (data[1])
|
|
|
|
|
modes |= LIBINPUT_CONFIG_SEND_EVENTS_DISABLED_ON_EXTERNAL_MOUSE;
|
|
|
|
|
|
|
|
|
|
if (checkonly) {
|
|
|
|
|
uint32_t supported = libinput_device_config_send_events_get_modes(device);
|
|
|
|
|
uint32_t new_mode = *data;
|
|
|
|
|
uint32_t supported =
|
|
|
|
|
libinput_device_config_send_events_get_modes(device);
|
|
|
|
|
|
|
|
|
|
if ((new_mode | supported) != supported)
|
|
|
|
|
if ((modes | supported) != supported)
|
|
|
|
|
return BadValue;
|
|
|
|
|
|
|
|
|
|
/* Only one bit must be set */
|
|
|
|
|
if (new_mode && ((new_mode & (new_mode - 1)) != 0))
|
|
|
|
|
return BadValue;
|
|
|
|
|
} else {
|
|
|
|
|
driver_data->options.sendevents = *data;
|
|
|
|
|
driver_data->options.sendevents = modes;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return Success;
|
|
|
|
|
@@ -1244,7 +1465,7 @@ LibinputSetPropertyLeftHanded(DeviceIntPtr dev,
|
|
|
|
|
data = (BOOL*)val->data;
|
|
|
|
|
|
|
|
|
|
if (checkonly) {
|
|
|
|
|
int supported = libinput_device_config_buttons_has_left_handed(device);
|
|
|
|
|
int supported = libinput_device_config_left_handed_is_available(device);
|
|
|
|
|
int left_handed = *data;
|
|
|
|
|
|
|
|
|
|
if (!supported && left_handed)
|
|
|
|
|
@@ -1286,7 +1507,7 @@ LibinputSetPropertyScrollMethods(DeviceIntPtr dev,
|
|
|
|
|
if (__builtin_popcount(modes) > 1)
|
|
|
|
|
return BadValue;
|
|
|
|
|
|
|
|
|
|
if ((modes & supported) == 0)
|
|
|
|
|
if (modes && (modes & supported) == 0)
|
|
|
|
|
return BadValue;
|
|
|
|
|
} else {
|
|
|
|
|
driver_data->options.scroll_method = modes;
|
|
|
|
|
@@ -1340,11 +1561,15 @@ LibinputSetProperty(DeviceIntPtr dev, Atom atom, XIPropertyValuePtr val,
|
|
|
|
|
rc = LibinputSetPropertyAccel(dev, atom, val, checkonly);
|
|
|
|
|
else if (atom == prop_natural_scroll)
|
|
|
|
|
rc = LibinputSetPropertyNaturalScroll(dev, atom, val, checkonly);
|
|
|
|
|
else if (atom == prop_sendevents)
|
|
|
|
|
else if (atom == prop_sendevents_available)
|
|
|
|
|
return BadAccess; /* read-only */
|
|
|
|
|
else if (atom == prop_sendevents_enabled)
|
|
|
|
|
rc = LibinputSetPropertySendEvents(dev, atom, val, checkonly);
|
|
|
|
|
else if (atom == prop_left_handed)
|
|
|
|
|
rc = LibinputSetPropertyLeftHanded(dev, atom, val, checkonly);
|
|
|
|
|
else if (atom == prop_scroll_methods)
|
|
|
|
|
else if (atom == prop_scroll_methods_available)
|
|
|
|
|
return BadAccess; /* read-only */
|
|
|
|
|
else if (atom == prop_scroll_method_enabled)
|
|
|
|
|
rc = LibinputSetPropertyScrollMethods(dev, atom, val, checkonly);
|
|
|
|
|
else if (atom == prop_scroll_button)
|
|
|
|
|
rc = LibinputSetPropertyScrollButton(dev, atom, val, checkonly);
|
|
|
|
|
@@ -1368,6 +1593,7 @@ LibinputInitProperty(DeviceIntPtr dev)
|
|
|
|
|
const char *device_node;
|
|
|
|
|
CARD32 product[2];
|
|
|
|
|
uint32_t scroll_methods;
|
|
|
|
|
uint32_t sendevent_modes;
|
|
|
|
|
int rc;
|
|
|
|
|
|
|
|
|
|
prop_float = XIGetKnownProperty("FLOAT");
|
|
|
|
|
@@ -1375,7 +1601,7 @@ LibinputInitProperty(DeviceIntPtr dev)
|
|
|
|
|
if (libinput_device_config_tap_get_finger_count(device) > 0) {
|
|
|
|
|
BOOL tap = driver_data->options.tapping;
|
|
|
|
|
|
|
|
|
|
prop_tap = MakeAtom(PROP_TAP, strlen(PROP_TAP), TRUE);
|
|
|
|
|
prop_tap = MakeAtom(LIBINPUT_PROP_TAP, strlen(LIBINPUT_PROP_TAP), TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev, prop_tap, XA_INTEGER, 8,
|
|
|
|
|
PropModeReplace, 1, &tap, FALSE);
|
|
|
|
|
if (rc != Success)
|
|
|
|
|
@@ -1393,8 +1619,8 @@ LibinputInitProperty(DeviceIntPtr dev)
|
|
|
|
|
calibration[7] = 0;
|
|
|
|
|
calibration[8] = 1;
|
|
|
|
|
|
|
|
|
|
prop_calibration = MakeAtom(PROP_CALIBRATION,
|
|
|
|
|
strlen(PROP_CALIBRATION),
|
|
|
|
|
prop_calibration = MakeAtom(LIBINPUT_PROP_CALIBRATION,
|
|
|
|
|
strlen(LIBINPUT_PROP_CALIBRATION),
|
|
|
|
|
TRUE);
|
|
|
|
|
|
|
|
|
|
rc = XIChangeDeviceProperty(dev, prop_calibration, prop_float, 32,
|
|
|
|
|
@@ -1407,7 +1633,7 @@ LibinputInitProperty(DeviceIntPtr dev)
|
|
|
|
|
if (libinput_device_config_accel_is_available(device)) {
|
|
|
|
|
float speed = driver_data->options.speed;
|
|
|
|
|
|
|
|
|
|
prop_accel = MakeAtom(PROP_ACCEL, strlen(PROP_ACCEL), TRUE);
|
|
|
|
|
prop_accel = MakeAtom(LIBINPUT_PROP_ACCEL, strlen(LIBINPUT_PROP_ACCEL), TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev, prop_accel, prop_float, 32,
|
|
|
|
|
PropModeReplace, 1, &speed, FALSE);
|
|
|
|
|
if (rc != Success)
|
|
|
|
|
@@ -1418,8 +1644,8 @@ LibinputInitProperty(DeviceIntPtr dev)
|
|
|
|
|
if (libinput_device_config_scroll_has_natural_scroll(device)) {
|
|
|
|
|
BOOL natural_scroll = driver_data->options.natural_scrolling;
|
|
|
|
|
|
|
|
|
|
prop_natural_scroll = MakeAtom(PROP_NATURAL_SCROLL,
|
|
|
|
|
strlen(PROP_NATURAL_SCROLL),
|
|
|
|
|
prop_natural_scroll = MakeAtom(LIBINPUT_PROP_NATURAL_SCROLL,
|
|
|
|
|
strlen(LIBINPUT_PROP_NATURAL_SCROLL),
|
|
|
|
|
TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev, prop_natural_scroll, XA_INTEGER, 8,
|
|
|
|
|
PropModeReplace, 1, &natural_scroll, FALSE);
|
|
|
|
|
@@ -1428,27 +1654,55 @@ LibinputInitProperty(DeviceIntPtr dev)
|
|
|
|
|
XISetDevicePropertyDeletable(dev, prop_natural_scroll, FALSE);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (libinput_device_config_send_events_get_modes(device) !=
|
|
|
|
|
LIBINPUT_CONFIG_SEND_EVENTS_ENABLED) {
|
|
|
|
|
uint32_t sendevents = driver_data->options.sendevents;
|
|
|
|
|
sendevent_modes = libinput_device_config_send_events_get_modes(device);
|
|
|
|
|
if (sendevent_modes != LIBINPUT_CONFIG_SEND_EVENTS_ENABLED) {
|
|
|
|
|
uint32_t sendevents;
|
|
|
|
|
BOOL modes[2] = {FALSE};
|
|
|
|
|
|
|
|
|
|
prop_sendevents = MakeAtom(PROP_SENDEVENTS,
|
|
|
|
|
strlen(PROP_SENDEVENTS),
|
|
|
|
|
TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev, prop_sendevents,
|
|
|
|
|
XA_CARDINAL, 32,
|
|
|
|
|
PropModeReplace, 1, &sendevents, FALSE);
|
|
|
|
|
if (sendevent_modes & LIBINPUT_CONFIG_SEND_EVENTS_DISABLED)
|
|
|
|
|
modes[0] = TRUE;
|
|
|
|
|
if (sendevent_modes & LIBINPUT_CONFIG_SEND_EVENTS_DISABLED_ON_EXTERNAL_MOUSE)
|
|
|
|
|
modes[1] = TRUE;
|
|
|
|
|
|
|
|
|
|
prop_sendevents_available = MakeAtom(LIBINPUT_PROP_SENDEVENTS_AVAILABLE,
|
|
|
|
|
strlen(LIBINPUT_PROP_SENDEVENTS_AVAILABLE),
|
|
|
|
|
TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev, prop_sendevents_available,
|
|
|
|
|
XA_INTEGER, 8,
|
|
|
|
|
PropModeReplace, 2, modes, FALSE);
|
|
|
|
|
if (rc != Success)
|
|
|
|
|
return;
|
|
|
|
|
XISetDevicePropertyDeletable(dev, prop_sendevents, FALSE);
|
|
|
|
|
XISetDevicePropertyDeletable(dev, prop_sendevents_available, FALSE);
|
|
|
|
|
|
|
|
|
|
memset(modes, 0, sizeof(modes));
|
|
|
|
|
sendevents = driver_data->options.sendevents;
|
|
|
|
|
|
|
|
|
|
switch(sendevents) {
|
|
|
|
|
case LIBINPUT_CONFIG_SEND_EVENTS_DISABLED:
|
|
|
|
|
modes[0] = TRUE;
|
|
|
|
|
break;
|
|
|
|
|
case LIBINPUT_CONFIG_SEND_EVENTS_DISABLED_ON_EXTERNAL_MOUSE:
|
|
|
|
|
modes[1] = TRUE;
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
prop_sendevents_enabled = MakeAtom(LIBINPUT_PROP_SENDEVENTS_ENABLED,
|
|
|
|
|
strlen(LIBINPUT_PROP_SENDEVENTS_ENABLED),
|
|
|
|
|
TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev, prop_sendevents_enabled,
|
|
|
|
|
XA_INTEGER, 8,
|
|
|
|
|
PropModeReplace, 2, modes, FALSE);
|
|
|
|
|
if (rc != Success)
|
|
|
|
|
return;
|
|
|
|
|
XISetDevicePropertyDeletable(dev, prop_sendevents_enabled, FALSE);
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (libinput_device_config_buttons_has_left_handed(device)) {
|
|
|
|
|
if (libinput_device_config_left_handed_is_available(device)) {
|
|
|
|
|
BOOL left_handed = driver_data->options.left_handed;
|
|
|
|
|
|
|
|
|
|
prop_left_handed = MakeAtom(PROP_LEFT_HANDED,
|
|
|
|
|
strlen(PROP_LEFT_HANDED),
|
|
|
|
|
prop_left_handed = MakeAtom(LIBINPUT_PROP_LEFT_HANDED,
|
|
|
|
|
strlen(LIBINPUT_PROP_LEFT_HANDED),
|
|
|
|
|
TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev, prop_left_handed,
|
|
|
|
|
XA_INTEGER, 8,
|
|
|
|
|
@@ -1463,6 +1717,31 @@ LibinputInitProperty(DeviceIntPtr dev)
|
|
|
|
|
enum libinput_config_scroll_method method;
|
|
|
|
|
BOOL methods[3] = {FALSE};
|
|
|
|
|
|
|
|
|
|
if (scroll_methods & LIBINPUT_CONFIG_SCROLL_2FG)
|
|
|
|
|
methods[0] = TRUE;
|
|
|
|
|
if (scroll_methods & LIBINPUT_CONFIG_SCROLL_EDGE)
|
|
|
|
|
methods[1] = TRUE;
|
|
|
|
|
if (scroll_methods & LIBINPUT_CONFIG_SCROLL_ON_BUTTON_DOWN)
|
|
|
|
|
methods[2] = TRUE;
|
|
|
|
|
|
|
|
|
|
prop_scroll_methods_available =
|
|
|
|
|
MakeAtom(LIBINPUT_PROP_SCROLL_METHODS_AVAILABLE,
|
|
|
|
|
strlen(LIBINPUT_PROP_SCROLL_METHODS_AVAILABLE),
|
|
|
|
|
TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev,
|
|
|
|
|
prop_scroll_methods_available,
|
|
|
|
|
XA_INTEGER, 8,
|
|
|
|
|
PropModeReplace,
|
|
|
|
|
ARRAY_SIZE(methods),
|
|
|
|
|
&methods, FALSE);
|
|
|
|
|
if (rc != Success)
|
|
|
|
|
return;
|
|
|
|
|
XISetDevicePropertyDeletable(dev,
|
|
|
|
|
prop_scroll_methods_available,
|
|
|
|
|
FALSE);
|
|
|
|
|
|
|
|
|
|
memset(methods, 0, sizeof(methods));
|
|
|
|
|
|
|
|
|
|
method = libinput_device_config_scroll_get_method(device);
|
|
|
|
|
switch(method) {
|
|
|
|
|
case LIBINPUT_CONFIG_SCROLL_2FG:
|
|
|
|
|
@@ -1478,26 +1757,30 @@ LibinputInitProperty(DeviceIntPtr dev)
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
prop_scroll_methods = MakeAtom(PROP_SCROLL_METHODS,
|
|
|
|
|
strlen(PROP_SCROLL_METHODS),
|
|
|
|
|
TRUE);
|
|
|
|
|
prop_scroll_method_enabled =
|
|
|
|
|
MakeAtom(LIBINPUT_PROP_SCROLL_METHOD_ENABLED,
|
|
|
|
|
strlen(LIBINPUT_PROP_SCROLL_METHOD_ENABLED),
|
|
|
|
|
TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev,
|
|
|
|
|
prop_scroll_methods,
|
|
|
|
|
prop_scroll_method_enabled,
|
|
|
|
|
XA_INTEGER, 8,
|
|
|
|
|
PropModeReplace,
|
|
|
|
|
ARRAY_SIZE(methods),
|
|
|
|
|
&methods, FALSE);
|
|
|
|
|
if (rc != Success)
|
|
|
|
|
return;
|
|
|
|
|
XISetDevicePropertyDeletable(dev, prop_scroll_methods, FALSE);
|
|
|
|
|
|
|
|
|
|
XISetDevicePropertyDeletable(dev,
|
|
|
|
|
prop_scroll_method_enabled,
|
|
|
|
|
FALSE);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (libinput_device_config_scroll_get_methods(device) &
|
|
|
|
|
LIBINPUT_CONFIG_SCROLL_ON_BUTTON_DOWN) {
|
|
|
|
|
CARD32 scroll_button = driver_data->options.scroll_button;
|
|
|
|
|
|
|
|
|
|
prop_scroll_button = MakeAtom(PROP_SCROLL_BUTTON,
|
|
|
|
|
strlen(PROP_SCROLL_BUTTON),
|
|
|
|
|
prop_scroll_button = MakeAtom(LIBINPUT_PROP_SCROLL_BUTTON,
|
|
|
|
|
strlen(LIBINPUT_PROP_SCROLL_BUTTON),
|
|
|
|
|
TRUE);
|
|
|
|
|
rc = XIChangeDeviceProperty(dev, prop_scroll_button,
|
|
|
|
|
XA_CARDINAL, 32,
|
|
|
|
|
|