summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/evdev-mt-touchpad.c44
-rw-r--r--src/libinput-util.c36
-rw-r--r--src/libinput-util.h1
3 files changed, 69 insertions, 12 deletions
diff --git a/src/evdev-mt-touchpad.c b/src/evdev-mt-touchpad.c
index eb950a2..99963e6 100644
--- a/src/evdev-mt-touchpad.c
+++ b/src/evdev-mt-touchpad.c
@@ -2372,8 +2372,9 @@ tp_init_pressure(struct tp_dispatch *tp,
struct evdev_device *device)
{
const struct input_absinfo *abs;
- unsigned int range;
unsigned int code = ABS_PRESSURE;
+ const char *prop;
+ int hi, lo;
if (tp->has_mt)
code = ABS_MT_PRESSURE;
@@ -2383,25 +2384,44 @@ tp_init_pressure(struct tp_dispatch *tp,
return;
}
- tp->pressure.use_pressure = true;
-
abs = libevdev_get_abs_info(device->evdev, code);
assert(abs);
- range = abs->maximum - abs->minimum;
+ prop = udev_device_get_property_value(device->udev_device,
+ "LIBINPUT_ATTR_PRESSURE_RANGE");
+ if (prop) {
+ if (!parse_pressure_range_property(prop, &hi, &lo)) {
+ evdev_log_bug_client(device,
+ "discarding invalid pressure range '%s'\n",
+ prop);
+ return;
+ }
- if (device->model_flags & EVDEV_MODEL_ELANTECH_TOUCHPAD) {
- tp->pressure.high = 24;
- tp->pressure.low = 10;
- } else if (device->model_flags & EVDEV_MODEL_CYAPA) {
- tp->pressure.high = 10;
- tp->pressure.low = 8;
+ if (hi == 0 && lo == 0) {
+ evdev_log_info(device,
+ "pressure-based touch detection disabled\n");
+ return;
+ }
} else {
+ unsigned int range = abs->maximum - abs->minimum;
+
/* Approximately the synaptics defaults */
- tp->pressure.high = abs->minimum + 0.12 * range;
- tp->pressure.low = abs->minimum + 0.10 * range;
+ hi = abs->minimum + 0.12 * range;
+ lo = abs->minimum + 0.10 * range;
+ }
+
+ if (hi > abs->maximum || hi < abs->minimum ||
+ lo > abs->maximum || lo < abs->minimum) {
+ evdev_log_bug_libinput(device,
+ "discarding out-of-bounds pressure range %d:%d\n",
+ hi, lo);
+ return;
}
+ tp->pressure.use_pressure = true;
+ tp->pressure.high = hi;
+ tp->pressure.low = lo;
+
evdev_log_debug(device,
"using pressure-based touch detection\n");
}
diff --git a/src/libinput-util.c b/src/libinput-util.c
index 351bbe4..38594fa 100644
--- a/src/libinput-util.c
+++ b/src/libinput-util.c
@@ -360,6 +360,42 @@ parse_tpkbcombo_layout_poperty(const char *prop,
}
/**
+ * Parses a string of the format "a:b" where both a and b must be integer
+ * numbers and a > b. Also allowed is the special string vaule "none" which
+ * amounts to unsetting the property.
+ *
+ * @param prop The value of the property
+ * @param hi Set to the first digit or 0 in case of 'none'
+ * @param lo Set to the second digit or 0 in case of 'none'
+ * @return true on success, false otherwise
+ */
+bool
+parse_pressure_range_property(const char *prop, int *hi, int *lo)
+{
+ int first, second;
+
+ if (!prop)
+ return false;
+
+ if (streq(prop, "none")) {
+ *hi = 0;
+ *lo = 0;
+ return true;
+ }
+
+ if (sscanf(prop, "%d:%d", &first, &second) != 2)
+ return false;
+
+ if (second >= first)
+ return false;
+
+ *hi = first;
+ *lo = second;
+
+ return true;
+}
+
+/**
* Return the next word in a string pointed to by state before the first
* separator character. Call repeatedly to tokenize a whole string.
*
diff --git a/src/libinput-util.h b/src/libinput-util.h
index 3fe0a02..4e97e01 100644
--- a/src/libinput-util.h
+++ b/src/libinput-util.h
@@ -393,6 +393,7 @@ int parse_mouse_wheel_click_count_property(const char *prop);
double parse_trackpoint_accel_property(const char *prop);
bool parse_dimension_property(const char *prop, size_t *width, size_t *height);
bool parse_calibration_property(const char *prop, float calibration[6]);
+bool parse_pressure_range_property(const char *prop, int *hi, int *lo);
enum tpkbcombo_layout {
TPKBCOMBO_LAYOUT_UNKNOWN,