[PATCH] touchpad: reset motion history when nfingers changes on semi-mt pads

Hans de Goede hdegoede at redhat.com
Mon Jul 21 06:25:47 PDT 2014


On semi-mt touchpads the reported position of the first finger down may
jump when the pad switches from st to mt mode. When this happens a large
delta gets seen on the first finger at the same time the second fingers
is first seen down, causing a spurious 2 finger scroll event.

Reset the motion history when nfingers changes on semi-mt pads to avoid this.

Signed-off-by: Hans de Goede <hdegoede at redhat.com>
---
 src/evdev-mt-touchpad.c | 8 ++++++++
 src/evdev-mt-touchpad.h | 2 ++
 2 files changed, 10 insertions(+)

diff --git a/src/evdev-mt-touchpad.c b/src/evdev-mt-touchpad.c
index b0520c7..315c531 100644
--- a/src/evdev-mt-touchpad.c
+++ b/src/evdev-mt-touchpad.c
@@ -406,6 +406,11 @@ tp_process_state(struct tp_dispatch *tp, uint64_t time)
 
 	for (i = 0; i < tp->ntouches; i++) {
 		t = tp_get_touch(tp, i);
+
+		/* semi-mt finger postions may "jump" when nfingers changes */
+		if (tp->semi_mt && tp->nfingers_down != tp->old_nfingers_down)
+			tp_motion_history_reset(t);
+
 		if (i >= tp->real_touches && t->state != TOUCH_NONE) {
 			t->x = first->x;
 			t->y = first->y;
@@ -454,6 +459,7 @@ tp_post_process_state(struct tp_dispatch *tp, uint64_t time)
 		t->dirty = false;
 	}
 
+	tp->old_nfingers_down = tp->nfingers_down;
 	tp->buttons.old_state = tp->buttons.state;
 
 	tp->queued = TOUCHPAD_EVENT_NONE;
@@ -668,6 +674,8 @@ tp_init_slots(struct tp_dispatch *tp,
 		tp->has_mt = false;
 	}
 
+	tp->semi_mt = libevdev_has_property(device->evdev, INPUT_PROP_SEMI_MT);
+
 	ARRAY_FOR_EACH(max_touches, m) {
 		if (libevdev_has_event_code(device->evdev,
 					    EV_KEY,
diff --git a/src/evdev-mt-touchpad.h b/src/evdev-mt-touchpad.h
index af6a3a3..83edf4f 100644
--- a/src/evdev-mt-touchpad.h
+++ b/src/evdev-mt-touchpad.h
@@ -152,8 +152,10 @@ struct tp_dispatch {
 	struct evdev_dispatch base;
 	struct evdev_device *device;
 	unsigned int nfingers_down;		/* number of fingers down */
+	unsigned int old_nfingers_down;		/* previous no fingers down */
 	unsigned int slot;			/* current slot */
 	bool has_mt;
+	bool semi_mt;
 
 	unsigned int real_touches;		/* number of slots */
 	unsigned int ntouches;			/* no slots inc. fakes */
-- 
2.0.1



More information about the wayland-devel mailing list