mirror of
https://github.com/labwc/labwc.git
synced 2025-10-29 05:40:24 -04:00
rcxml: rewrite <libinput> parser
This commit is contained in:
parent
7adbfe88aa
commit
a0d2e6a64b
1 changed files with 153 additions and 161 deletions
|
|
@ -700,112 +700,102 @@ err:
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
fill_libinput_category(char *nodename, char *content, struct parser_state *state)
|
fill_libinput_category(xmlNode *node)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
* Create a new profile (libinput-category) on `<libinput><device>`
|
* Create a new profile (libinput-category) on `<libinput><device>`
|
||||||
* so that the 'default' profile can be created without even providing a
|
* so that the 'default' profile can be created without even providing a
|
||||||
* category="" attribute (same as <device category="default">...)
|
* category="" attribute (same as <device category="default">...)
|
||||||
*/
|
*/
|
||||||
if (!strcmp(nodename, "device.libinput")) {
|
struct libinput_category *category = libinput_category_create();
|
||||||
state->current_libinput_category = libinput_category_create();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!content) {
|
xmlNode *child;
|
||||||
return;
|
char *key, *content;
|
||||||
}
|
LAB_XML_FOR_EACH(node, child, key, content) {
|
||||||
|
if (!strcmp(key, "category")) {
|
||||||
|
/*
|
||||||
|
* First we try to get a type based on a number of
|
||||||
|
* pre-defined terms, for example: 'default', 'touch',
|
||||||
|
* 'touchpad' and 'non-touch'
|
||||||
|
*/
|
||||||
|
category->type = get_device_type(content);
|
||||||
|
|
||||||
if (!state->current_libinput_category) {
|
/*
|
||||||
return;
|
* If we couldn't match against any of those terms, we
|
||||||
}
|
* use the provided value to define the device name
|
||||||
|
* that the settings should be applicable to.
|
||||||
string_truncate_at_pattern(nodename, ".device.libinput");
|
*/
|
||||||
|
if (category->type == LAB_LIBINPUT_DEVICE_NONE) {
|
||||||
if (!strcmp(nodename, "category")) {
|
xstrdup_replace(category->name, content);
|
||||||
/*
|
}
|
||||||
* First we try to get a type based on a number of pre-defined
|
} else if (!strcasecmp(key, "naturalScroll")) {
|
||||||
* terms, for example: 'default', 'touch', 'touchpad' and
|
set_bool_as_int(content, &category->natural_scroll);
|
||||||
* 'non-touch'
|
} else if (!strcasecmp(key, "leftHanded")) {
|
||||||
*/
|
set_bool_as_int(content, &category->left_handed);
|
||||||
state->current_libinput_category->type = get_device_type(content);
|
} else if (!strcasecmp(key, "pointerSpeed")) {
|
||||||
|
set_float(content, &category->pointer_speed);
|
||||||
/*
|
if (category->pointer_speed < -1) {
|
||||||
* If we couldn't match against any of those terms, we use the
|
category->pointer_speed = -1;
|
||||||
* provided value to define the device name that the settings
|
} else if (category->pointer_speed > 1) {
|
||||||
* should be applicable to.
|
category->pointer_speed = 1;
|
||||||
*/
|
}
|
||||||
if (state->current_libinput_category->type == LAB_LIBINPUT_DEVICE_NONE) {
|
} else if (!strcasecmp(key, "tap")) {
|
||||||
xstrdup_replace(state->current_libinput_category->name, content);
|
int ret = parse_bool(content, -1);
|
||||||
}
|
if (ret < 0) {
|
||||||
} else if (!strcasecmp(nodename, "naturalScroll")) {
|
continue;
|
||||||
set_bool_as_int(content, &state->current_libinput_category->natural_scroll);
|
}
|
||||||
} else if (!strcasecmp(nodename, "leftHanded")) {
|
category->tap = ret
|
||||||
set_bool_as_int(content, &state->current_libinput_category->left_handed);
|
? LIBINPUT_CONFIG_TAP_ENABLED
|
||||||
} else if (!strcasecmp(nodename, "pointerSpeed")) {
|
: LIBINPUT_CONFIG_TAP_DISABLED;
|
||||||
set_float(content, &state->current_libinput_category->pointer_speed);
|
} else if (!strcasecmp(key, "tapButtonMap")) {
|
||||||
if (state->current_libinput_category->pointer_speed < -1) {
|
if (!strcmp(content, "lrm")) {
|
||||||
state->current_libinput_category->pointer_speed = -1;
|
category->tap_button_map =
|
||||||
} else if (state->current_libinput_category->pointer_speed > 1) {
|
LIBINPUT_CONFIG_TAP_MAP_LRM;
|
||||||
state->current_libinput_category->pointer_speed = 1;
|
} else if (!strcmp(content, "lmr")) {
|
||||||
}
|
category->tap_button_map =
|
||||||
} else if (!strcasecmp(nodename, "tap")) {
|
LIBINPUT_CONFIG_TAP_MAP_LMR;
|
||||||
int ret = parse_bool(content, -1);
|
} else {
|
||||||
if (ret < 0) {
|
wlr_log(WLR_ERROR, "invalid tapButtonMap");
|
||||||
return;
|
}
|
||||||
}
|
} else if (!strcasecmp(key, "tapAndDrag")) {
|
||||||
state->current_libinput_category->tap = ret
|
int ret = parse_bool(content, -1);
|
||||||
? LIBINPUT_CONFIG_TAP_ENABLED
|
if (ret < 0) {
|
||||||
: LIBINPUT_CONFIG_TAP_DISABLED;
|
continue;
|
||||||
} else if (!strcasecmp(nodename, "tapButtonMap")) {
|
}
|
||||||
if (!strcmp(content, "lrm")) {
|
category->tap_and_drag = ret
|
||||||
state->current_libinput_category->tap_button_map =
|
? LIBINPUT_CONFIG_DRAG_ENABLED
|
||||||
LIBINPUT_CONFIG_TAP_MAP_LRM;
|
: LIBINPUT_CONFIG_DRAG_DISABLED;
|
||||||
} else if (!strcmp(content, "lmr")) {
|
} else if (!strcasecmp(key, "dragLock")) {
|
||||||
state->current_libinput_category->tap_button_map =
|
if (!strcasecmp(content, "timeout")) {
|
||||||
LIBINPUT_CONFIG_TAP_MAP_LMR;
|
/* "timeout" enables drag-lock with timeout */
|
||||||
} else {
|
category->drag_lock = LIBINPUT_CONFIG_DRAG_LOCK_ENABLED;
|
||||||
wlr_log(WLR_ERROR, "invalid tapButtonMap");
|
continue;
|
||||||
}
|
}
|
||||||
} else if (!strcasecmp(nodename, "tapAndDrag")) {
|
int ret = parse_bool(content, -1);
|
||||||
int ret = parse_bool(content, -1);
|
if (ret < 0) {
|
||||||
if (ret < 0) {
|
continue;
|
||||||
return;
|
}
|
||||||
}
|
/* "yes" enables drag-lock, without timeout if libinput >= 1.27 */
|
||||||
state->current_libinput_category->tap_and_drag = ret
|
int enabled = LIBINPUT_CONFIG_DRAG_LOCK_ENABLED;
|
||||||
? LIBINPUT_CONFIG_DRAG_ENABLED
|
|
||||||
: LIBINPUT_CONFIG_DRAG_DISABLED;
|
|
||||||
} else if (!strcasecmp(nodename, "dragLock")) {
|
|
||||||
if (!strcasecmp(content, "timeout")) {
|
|
||||||
/* "timeout" enables drag-lock with timeout */
|
|
||||||
state->current_libinput_category->drag_lock =
|
|
||||||
LIBINPUT_CONFIG_DRAG_LOCK_ENABLED;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
int ret = parse_bool(content, -1);
|
|
||||||
if (ret < 0) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
/* "yes" enables drag-lock, without timeout if libinput >= 1.27 */
|
|
||||||
int enabled = LIBINPUT_CONFIG_DRAG_LOCK_ENABLED;
|
|
||||||
#if HAVE_LIBINPUT_CONFIG_DRAG_LOCK_ENABLED_STICKY
|
#if HAVE_LIBINPUT_CONFIG_DRAG_LOCK_ENABLED_STICKY
|
||||||
enabled = LIBINPUT_CONFIG_DRAG_LOCK_ENABLED_STICKY;
|
enabled = LIBINPUT_CONFIG_DRAG_LOCK_ENABLED_STICKY;
|
||||||
#endif
|
#endif
|
||||||
state->current_libinput_category->drag_lock = ret ?
|
category->drag_lock = ret ?
|
||||||
enabled : LIBINPUT_CONFIG_DRAG_LOCK_DISABLED;
|
enabled : LIBINPUT_CONFIG_DRAG_LOCK_DISABLED;
|
||||||
} else if (!strcasecmp(nodename, "threeFingerDrag")) {
|
} else if (!strcasecmp(key, "threeFingerDrag")) {
|
||||||
#if HAVE_LIBINPUT_CONFIG_3FG_DRAG_ENABLED_3FG
|
#if HAVE_LIBINPUT_CONFIG_3FG_DRAG_ENABLED_3FG
|
||||||
if (!strcmp(content, "3")) {
|
if (!strcmp(content, "3")) {
|
||||||
state->current_libinput_category->three_finger_drag =
|
category->three_finger_drag =
|
||||||
LIBINPUT_CONFIG_3FG_DRAG_ENABLED_3FG;
|
LIBINPUT_CONFIG_3FG_DRAG_ENABLED_3FG;
|
||||||
} else if (!strcmp(content, "4")) {
|
} else if (!strcmp(content, "4")) {
|
||||||
state->current_libinput_category->three_finger_drag =
|
category->three_finger_drag =
|
||||||
LIBINPUT_CONFIG_3FG_DRAG_ENABLED_4FG;
|
LIBINPUT_CONFIG_3FG_DRAG_ENABLED_4FG;
|
||||||
} else {
|
} else {
|
||||||
int ret = parse_bool(content, -1);
|
int ret = parse_bool(content, -1);
|
||||||
if (ret < 0) {
|
if (ret < 0) {
|
||||||
return;
|
continue;
|
||||||
}
|
}
|
||||||
state->current_libinput_category->three_finger_drag = ret
|
category->three_finger_drag = ret
|
||||||
? LIBINPUT_CONFIG_3FG_DRAG_ENABLED_3FG
|
? LIBINPUT_CONFIG_3FG_DRAG_ENABLED_3FG
|
||||||
: LIBINPUT_CONFIG_3FG_DRAG_DISABLED;
|
: LIBINPUT_CONFIG_3FG_DRAG_DISABLED;
|
||||||
}
|
}
|
||||||
|
|
@ -813,80 +803,82 @@ fill_libinput_category(char *nodename, char *content, struct parser_state *state
|
||||||
wlr_log(WLR_ERROR, "<threeFingerDrag> is only"
|
wlr_log(WLR_ERROR, "<threeFingerDrag> is only"
|
||||||
" supported in libinput >= 1.28");
|
" supported in libinput >= 1.28");
|
||||||
#endif
|
#endif
|
||||||
} else if (!strcasecmp(nodename, "accelProfile")) {
|
} else if (!strcasecmp(key, "accelProfile")) {
|
||||||
state->current_libinput_category->accel_profile =
|
category->accel_profile =
|
||||||
get_accel_profile(content);
|
get_accel_profile(content);
|
||||||
} else if (!strcasecmp(nodename, "middleEmulation")) {
|
} else if (!strcasecmp(key, "middleEmulation")) {
|
||||||
int ret = parse_bool(content, -1);
|
int ret = parse_bool(content, -1);
|
||||||
if (ret < 0) {
|
if (ret < 0) {
|
||||||
return;
|
continue;
|
||||||
}
|
|
||||||
state->current_libinput_category->middle_emu = ret
|
|
||||||
? LIBINPUT_CONFIG_MIDDLE_EMULATION_ENABLED
|
|
||||||
: LIBINPUT_CONFIG_MIDDLE_EMULATION_DISABLED;
|
|
||||||
} else if (!strcasecmp(nodename, "disableWhileTyping")) {
|
|
||||||
int ret = parse_bool(content, -1);
|
|
||||||
if (ret < 0) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
state->current_libinput_category->dwt = ret
|
|
||||||
? LIBINPUT_CONFIG_DWT_ENABLED
|
|
||||||
: LIBINPUT_CONFIG_DWT_DISABLED;
|
|
||||||
} else if (!strcasecmp(nodename, "clickMethod")) {
|
|
||||||
if (!strcasecmp(content, "none")) {
|
|
||||||
state->current_libinput_category->click_method =
|
|
||||||
LIBINPUT_CONFIG_CLICK_METHOD_NONE;
|
|
||||||
} else if (!strcasecmp(content, "clickfinger")) {
|
|
||||||
state->current_libinput_category->click_method =
|
|
||||||
LIBINPUT_CONFIG_CLICK_METHOD_CLICKFINGER;
|
|
||||||
} else if (!strcasecmp(content, "buttonAreas")) {
|
|
||||||
state->current_libinput_category->click_method =
|
|
||||||
LIBINPUT_CONFIG_CLICK_METHOD_BUTTON_AREAS;
|
|
||||||
} else {
|
|
||||||
wlr_log(WLR_ERROR, "invalid clickMethod");
|
|
||||||
}
|
|
||||||
} else if (!strcasecmp(nodename, "scrollMethod")) {
|
|
||||||
if (!strcasecmp(content, "none")) {
|
|
||||||
state->current_libinput_category->scroll_method =
|
|
||||||
LIBINPUT_CONFIG_SCROLL_NO_SCROLL;
|
|
||||||
} else if (!strcasecmp(content, "edge")) {
|
|
||||||
state->current_libinput_category->scroll_method =
|
|
||||||
LIBINPUT_CONFIG_SCROLL_EDGE;
|
|
||||||
} else if (!strcasecmp(content, "twofinger")) {
|
|
||||||
state->current_libinput_category->scroll_method =
|
|
||||||
LIBINPUT_CONFIG_SCROLL_2FG;
|
|
||||||
} else {
|
|
||||||
wlr_log(WLR_ERROR, "invalid scrollMethod");
|
|
||||||
}
|
|
||||||
} else if (!strcasecmp(nodename, "sendEventsMode")) {
|
|
||||||
state->current_libinput_category->send_events_mode =
|
|
||||||
get_send_events_mode(content);
|
|
||||||
} else if (!strcasecmp(nodename, "calibrationMatrix")) {
|
|
||||||
errno = 0;
|
|
||||||
state->current_libinput_category->have_calibration_matrix = true;
|
|
||||||
float *mat = state->current_libinput_category->calibration_matrix;
|
|
||||||
gchar **elements = g_strsplit(content, " ", -1);
|
|
||||||
guint i = 0;
|
|
||||||
for (; elements[i]; ++i) {
|
|
||||||
char *end_str = NULL;
|
|
||||||
mat[i] = strtof(elements[i], &end_str);
|
|
||||||
if (errno == ERANGE || *end_str != '\0' || i == 6 || *elements[i] == '\0') {
|
|
||||||
wlr_log(WLR_ERROR, "invalid calibration matrix element"
|
|
||||||
" %s (index %d), expect six floats",
|
|
||||||
elements[i], i);
|
|
||||||
state->current_libinput_category->have_calibration_matrix = false;
|
|
||||||
errno = 0;
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
|
category->middle_emu = ret
|
||||||
|
? LIBINPUT_CONFIG_MIDDLE_EMULATION_ENABLED
|
||||||
|
: LIBINPUT_CONFIG_MIDDLE_EMULATION_DISABLED;
|
||||||
|
} else if (!strcasecmp(key, "disableWhileTyping")) {
|
||||||
|
int ret = parse_bool(content, -1);
|
||||||
|
if (ret < 0) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
category->dwt = ret
|
||||||
|
? LIBINPUT_CONFIG_DWT_ENABLED
|
||||||
|
: LIBINPUT_CONFIG_DWT_DISABLED;
|
||||||
|
} else if (!strcasecmp(key, "clickMethod")) {
|
||||||
|
if (!strcasecmp(content, "none")) {
|
||||||
|
category->click_method =
|
||||||
|
LIBINPUT_CONFIG_CLICK_METHOD_NONE;
|
||||||
|
} else if (!strcasecmp(content, "clickfinger")) {
|
||||||
|
category->click_method =
|
||||||
|
LIBINPUT_CONFIG_CLICK_METHOD_CLICKFINGER;
|
||||||
|
} else if (!strcasecmp(content, "buttonAreas")) {
|
||||||
|
category->click_method =
|
||||||
|
LIBINPUT_CONFIG_CLICK_METHOD_BUTTON_AREAS;
|
||||||
|
} else {
|
||||||
|
wlr_log(WLR_ERROR, "invalid clickMethod");
|
||||||
|
}
|
||||||
|
} else if (!strcasecmp(key, "scrollMethod")) {
|
||||||
|
if (!strcasecmp(content, "none")) {
|
||||||
|
category->scroll_method =
|
||||||
|
LIBINPUT_CONFIG_SCROLL_NO_SCROLL;
|
||||||
|
} else if (!strcasecmp(content, "edge")) {
|
||||||
|
category->scroll_method =
|
||||||
|
LIBINPUT_CONFIG_SCROLL_EDGE;
|
||||||
|
} else if (!strcasecmp(content, "twofinger")) {
|
||||||
|
category->scroll_method =
|
||||||
|
LIBINPUT_CONFIG_SCROLL_2FG;
|
||||||
|
} else {
|
||||||
|
wlr_log(WLR_ERROR, "invalid scrollMethod");
|
||||||
|
}
|
||||||
|
} else if (!strcasecmp(key, "sendEventsMode")) {
|
||||||
|
category->send_events_mode =
|
||||||
|
get_send_events_mode(content);
|
||||||
|
} else if (!strcasecmp(key, "calibrationMatrix")) {
|
||||||
|
errno = 0;
|
||||||
|
category->have_calibration_matrix = true;
|
||||||
|
float *mat = category->calibration_matrix;
|
||||||
|
gchar **elements = g_strsplit(content, " ", -1);
|
||||||
|
guint i = 0;
|
||||||
|
for (; elements[i]; ++i) {
|
||||||
|
char *end_str = NULL;
|
||||||
|
mat[i] = strtof(elements[i], &end_str);
|
||||||
|
if (errno == ERANGE || *end_str != '\0' || i == 6
|
||||||
|
|| *elements[i] == '\0') {
|
||||||
|
wlr_log(WLR_ERROR, "invalid calibration "
|
||||||
|
"matrix element %s (index %d), "
|
||||||
|
"expect six floats", elements[i], i);
|
||||||
|
category->have_calibration_matrix = false;
|
||||||
|
errno = 0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (i != 6 && category->have_calibration_matrix) {
|
||||||
|
wlr_log(WLR_ERROR, "wrong number of calibration "
|
||||||
|
"matrix elements, expected 6, got %d", i);
|
||||||
|
category->have_calibration_matrix = false;
|
||||||
|
}
|
||||||
|
g_strfreev(elements);
|
||||||
|
} else if (!strcasecmp(key, "scrollFactor")) {
|
||||||
|
set_double(content, &category->scroll_factor);
|
||||||
}
|
}
|
||||||
if (i != 6 && state->current_libinput_category->have_calibration_matrix) {
|
|
||||||
wlr_log(WLR_ERROR, "wrong number of calibration matrix elements,"
|
|
||||||
" expected 6, got %d", i);
|
|
||||||
state->current_libinput_category->have_calibration_matrix = false;
|
|
||||||
}
|
|
||||||
g_strfreev(elements);
|
|
||||||
} else if (!strcasecmp(nodename, "scrollFactor")) {
|
|
||||||
set_double(content, &state->current_libinput_category->scroll_factor);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1061,8 +1053,8 @@ entry(xmlNode *node, char *nodename, char *content, struct parser_state *state)
|
||||||
fill_touch(node);
|
fill_touch(node);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (state->in_libinput_category) {
|
if (!strcasecmp(nodename, "device.libinput")) {
|
||||||
fill_libinput_category(nodename, content, state);
|
fill_libinput_category(node);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (state->in_regions) {
|
if (state->in_regions) {
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue