2 * Copyright © 2013 Red Hat, Inc.
4 * Permission to use, copy, modify, distribute, and sell this software
5 * and its documentation for any purpose is hereby granted without
6 * fee, provided that the above copyright notice appear in all copies
7 * and that both that copyright notice and this permission notice
8 * appear in supporting documentation, and that the name of Red Hat
9 * not be used in advertising or publicity pertaining to distribution
10 * of the software without specific, written prior permission. Red
11 * Hat makes no representations about the suitability of this software
12 * for any purpose. It is provided "as is" without express or implied
15 * THE AUTHORS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
16 * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN
17 * NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
18 * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
19 * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
20 * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
21 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
35 #include <sys/timerfd.h>
37 #include "evdev-mt-touchpad.h"
39 #define CASE_RETURN_STRING(a) case a: return #a;
41 #define DEFAULT_TAP_TIMEOUT_PERIOD 180
42 #define DEFAULT_TAP_MOVE_THRESHOLD 30
52 /*****************************************
53 * DO NOT EDIT THIS FILE!
55 * Look at the state diagram in doc/touchpad-tap-state-machine.svg, or
57 * https://drive.google.com/file/d/0B1NwWmji69noYTdMcU1kTUZuUVE/edit?usp=sharing
58 * (it's a http://draw.io diagram)
60 * Any changes in this file must be represented in the diagram.
63 static inline const char*
64 tap_state_to_str(enum tp_tap_state state) {
67 CASE_RETURN_STRING(TAP_STATE_IDLE);
68 CASE_RETURN_STRING(TAP_STATE_HOLD);
69 CASE_RETURN_STRING(TAP_STATE_TOUCH);
70 CASE_RETURN_STRING(TAP_STATE_TAPPED);
71 CASE_RETURN_STRING(TAP_STATE_TOUCH_2);
72 CASE_RETURN_STRING(TAP_STATE_TOUCH_2_HOLD);
73 CASE_RETURN_STRING(TAP_STATE_TOUCH_3);
74 CASE_RETURN_STRING(TAP_STATE_TOUCH_3_HOLD);
75 CASE_RETURN_STRING(TAP_STATE_DRAGGING);
76 CASE_RETURN_STRING(TAP_STATE_DRAGGING_WAIT);
77 CASE_RETURN_STRING(TAP_STATE_DRAGGING_OR_DOUBLETAP);
78 CASE_RETURN_STRING(TAP_STATE_DRAGGING_2);
79 CASE_RETURN_STRING(TAP_STATE_DEAD);
84 static inline const char*
85 tap_event_to_str(enum tap_event event) {
88 CASE_RETURN_STRING(TAP_EVENT_TOUCH);
89 CASE_RETURN_STRING(TAP_EVENT_MOTION);
90 CASE_RETURN_STRING(TAP_EVENT_RELEASE);
91 CASE_RETURN_STRING(TAP_EVENT_TIMEOUT);
92 CASE_RETURN_STRING(TAP_EVENT_BUTTON);
96 #undef CASE_RETURN_STRING
99 tp_tap_notify(struct tp_dispatch *tp,
102 enum libinput_pointer_button_state state)
107 case 1: button = BTN_LEFT; break;
108 case 2: button = BTN_RIGHT; break;
109 case 3: button = BTN_MIDDLE; break;
114 pointer_notify_button(&tp->device->base,
121 tp_tap_set_timer(struct tp_dispatch *tp, uint64_t time)
123 uint64_t timeout = time + DEFAULT_TAP_TIMEOUT_PERIOD;
124 struct itimerspec its;
126 its.it_interval.tv_sec = 0;
127 its.it_interval.tv_nsec = 0;
128 its.it_value.tv_sec = timeout / 1000;
129 its.it_value.tv_nsec = (timeout % 1000) * 1000 * 1000;
130 timerfd_settime(tp->tap.timer_fd, TFD_TIMER_ABSTIME, &its, NULL);
132 tp->tap.timeout = timeout;
136 tp_tap_clear_timer(struct tp_dispatch *tp)
142 tp_tap_idle_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
146 case TAP_EVENT_TOUCH:
147 tp->tap.state = TAP_STATE_TOUCH;
148 tp_tap_set_timer(tp, time);
150 case TAP_EVENT_RELEASE:
151 case TAP_EVENT_MOTION:
152 log_info("invalid event, no fingers are down\n");
154 case TAP_EVENT_TIMEOUT:
156 case TAP_EVENT_BUTTON:
157 tp->tap.state = TAP_STATE_DEAD;
163 tp_tap_touch_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
167 case TAP_EVENT_TOUCH:
168 tp->tap.state = TAP_STATE_TOUCH_2;
169 tp_tap_set_timer(tp, time);
171 case TAP_EVENT_RELEASE:
172 tp->tap.state = TAP_STATE_TAPPED;
173 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_PRESSED);
174 tp_tap_set_timer(tp, time);
176 case TAP_EVENT_TIMEOUT:
177 case TAP_EVENT_MOTION:
178 tp->tap.state = TAP_STATE_HOLD;
179 tp_tap_clear_timer(tp);
181 case TAP_EVENT_BUTTON:
182 tp->tap.state = TAP_STATE_DEAD;
188 tp_tap_hold_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
192 case TAP_EVENT_TOUCH:
193 tp->tap.state = TAP_STATE_TOUCH_2;
194 tp_tap_set_timer(tp, time);
196 case TAP_EVENT_RELEASE:
197 tp->tap.state = TAP_STATE_IDLE;
199 case TAP_EVENT_MOTION:
200 case TAP_EVENT_TIMEOUT:
202 case TAP_EVENT_BUTTON:
203 tp->tap.state = TAP_STATE_DEAD;
209 tp_tap_tapped_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
213 case TAP_EVENT_MOTION:
214 case TAP_EVENT_RELEASE:
215 log_info("invalid event when fingers are up\n");
217 case TAP_EVENT_TOUCH:
218 tp->tap.state = TAP_STATE_DRAGGING_OR_DOUBLETAP;
219 tp_tap_clear_timer(tp);
221 case TAP_EVENT_TIMEOUT:
222 tp->tap.state = TAP_STATE_IDLE;
223 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
225 case TAP_EVENT_BUTTON:
226 tp->tap.state = TAP_STATE_DEAD;
227 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
233 tp_tap_touch2_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
237 case TAP_EVENT_TOUCH:
238 tp->tap.state = TAP_STATE_TOUCH_3;
239 tp_tap_set_timer(tp, time);
241 case TAP_EVENT_RELEASE:
242 tp->tap.state = TAP_STATE_HOLD;
243 tp_tap_notify(tp, time, 2, LIBINPUT_POINTER_BUTTON_STATE_PRESSED);
244 tp_tap_notify(tp, time, 2, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
245 tp_tap_clear_timer(tp);
247 case TAP_EVENT_MOTION:
248 tp_tap_clear_timer(tp);
249 case TAP_EVENT_TIMEOUT:
250 tp->tap.state = TAP_STATE_TOUCH_2_HOLD;
252 case TAP_EVENT_BUTTON:
253 tp->tap.state = TAP_STATE_DEAD;
259 tp_tap_touch2_hold_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
263 case TAP_EVENT_TOUCH:
264 tp->tap.state = TAP_STATE_TOUCH_3;
265 tp_tap_set_timer(tp, time);
267 case TAP_EVENT_RELEASE:
268 tp->tap.state = TAP_STATE_HOLD;
270 case TAP_EVENT_MOTION:
271 case TAP_EVENT_TIMEOUT:
272 tp->tap.state = TAP_STATE_TOUCH_2_HOLD;
274 case TAP_EVENT_BUTTON:
275 tp->tap.state = TAP_STATE_DEAD;
281 tp_tap_touch3_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
285 case TAP_EVENT_TOUCH:
286 tp->tap.state = TAP_STATE_DEAD;
287 tp_tap_clear_timer(tp);
289 case TAP_EVENT_MOTION:
290 case TAP_EVENT_TIMEOUT:
291 tp->tap.state = TAP_STATE_TOUCH_3_HOLD;
292 tp_tap_clear_timer(tp);
294 case TAP_EVENT_RELEASE:
295 tp->tap.state = TAP_STATE_TOUCH_2_HOLD;
296 tp_tap_notify(tp, time, 3, LIBINPUT_POINTER_BUTTON_STATE_PRESSED);
297 tp_tap_notify(tp, time, 3, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
299 case TAP_EVENT_BUTTON:
300 tp->tap.state = TAP_STATE_DEAD;
306 tp_tap_touch3_hold_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
310 case TAP_EVENT_TOUCH:
311 tp->tap.state = TAP_STATE_DEAD;
312 tp_tap_set_timer(tp, time);
314 case TAP_EVENT_RELEASE:
315 tp->tap.state = TAP_STATE_TOUCH_2_HOLD;
317 case TAP_EVENT_MOTION:
318 case TAP_EVENT_TIMEOUT:
320 case TAP_EVENT_BUTTON:
321 tp->tap.state = TAP_STATE_DEAD;
327 tp_tap_dragging_or_doubletap_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
330 case TAP_EVENT_TOUCH:
331 tp->tap.state = TAP_STATE_DRAGGING_2;
333 case TAP_EVENT_RELEASE:
334 tp->tap.state = TAP_STATE_IDLE;
335 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
336 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_PRESSED);
337 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
338 tp_tap_clear_timer(tp);
340 case TAP_EVENT_MOTION:
341 case TAP_EVENT_TIMEOUT:
342 tp->tap.state = TAP_STATE_DRAGGING;
344 case TAP_EVENT_BUTTON:
345 tp->tap.state = TAP_STATE_DEAD;
346 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
352 tp_tap_dragging_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
356 case TAP_EVENT_TOUCH:
357 tp->tap.state = TAP_STATE_DRAGGING_2;
359 case TAP_EVENT_RELEASE:
360 tp->tap.state = TAP_STATE_DRAGGING_WAIT;
361 tp_tap_set_timer(tp, time);
363 case TAP_EVENT_MOTION:
364 case TAP_EVENT_TIMEOUT:
367 case TAP_EVENT_BUTTON:
368 tp->tap.state = TAP_STATE_DEAD;
369 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
375 tp_tap_dragging_wait_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
379 case TAP_EVENT_TOUCH:
380 tp->tap.state = TAP_STATE_DRAGGING;
381 tp_tap_clear_timer(tp);
383 case TAP_EVENT_RELEASE:
384 case TAP_EVENT_MOTION:
386 case TAP_EVENT_TIMEOUT:
387 tp->tap.state = TAP_STATE_IDLE;
388 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
390 case TAP_EVENT_BUTTON:
391 tp->tap.state = TAP_STATE_DEAD;
392 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
398 tp_tap_dragging2_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
402 case TAP_EVENT_RELEASE:
403 tp->tap.state = TAP_STATE_DRAGGING;
405 case TAP_EVENT_TOUCH:
406 tp->tap.state = TAP_STATE_DEAD;
407 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
409 case TAP_EVENT_MOTION:
410 case TAP_EVENT_TIMEOUT:
413 case TAP_EVENT_BUTTON:
414 tp->tap.state = TAP_STATE_DEAD;
415 tp_tap_notify(tp, time, 1, LIBINPUT_POINTER_BUTTON_STATE_RELEASED);
421 tp_tap_dead_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
425 case TAP_EVENT_RELEASE:
426 if (tp->nfingers_down == 0)
427 tp->tap.state = TAP_STATE_IDLE;
429 case TAP_EVENT_TOUCH:
430 case TAP_EVENT_MOTION:
431 case TAP_EVENT_TIMEOUT:
432 case TAP_EVENT_BUTTON:
438 tp_tap_handle_event(struct tp_dispatch *tp, enum tap_event event, uint64_t time)
440 enum tp_tap_state current;
441 if (!tp->tap.enabled)
444 current = tp->tap.state;
446 switch(tp->tap.state) {
448 tp_tap_idle_handle_event(tp, event, time);
450 case TAP_STATE_TOUCH:
451 tp_tap_touch_handle_event(tp, event, time);
454 tp_tap_hold_handle_event(tp, event, time);
456 case TAP_STATE_TAPPED:
457 tp_tap_tapped_handle_event(tp, event, time);
459 case TAP_STATE_TOUCH_2:
460 tp_tap_touch2_handle_event(tp, event, time);
462 case TAP_STATE_TOUCH_2_HOLD:
463 tp_tap_touch2_hold_handle_event(tp, event, time);
465 case TAP_STATE_TOUCH_3:
466 tp_tap_touch3_handle_event(tp, event, time);
468 case TAP_STATE_TOUCH_3_HOLD:
469 tp_tap_touch3_hold_handle_event(tp, event, time);
471 case TAP_STATE_DRAGGING_OR_DOUBLETAP:
472 tp_tap_dragging_or_doubletap_handle_event(tp, event, time);
474 case TAP_STATE_DRAGGING:
475 tp_tap_dragging_handle_event(tp, event, time);
477 case TAP_STATE_DRAGGING_WAIT:
478 tp_tap_dragging_wait_handle_event(tp, event, time);
480 case TAP_STATE_DRAGGING_2:
481 tp_tap_dragging2_handle_event(tp, event, time);
484 tp_tap_dead_handle_event(tp, event, time);
488 if (tp->tap.state == TAP_STATE_IDLE || tp->tap.state == TAP_STATE_DEAD)
489 tp_tap_clear_timer(tp);
491 log_debug("%s → %s → %s\n", tap_state_to_str(current), tap_event_to_str(event), tap_state_to_str(tp->tap.state));
495 tp_tap_exceeds_motion_threshold(struct tp_dispatch *tp, struct tp_touch *t)
497 int threshold = DEFAULT_TAP_MOVE_THRESHOLD;
500 tp_get_delta(t, &dx, &dy);
502 return dx * dx + dy * dy > threshold * threshold;
506 tp_tap_handle_state(struct tp_dispatch *tp, uint64_t time)
509 int filter_motion = 0;
511 if (tp->queued & TOUCHPAD_EVENT_BUTTON_PRESS)
512 tp_tap_handle_event(tp, TAP_EVENT_BUTTON, time);
514 tp_for_each_touch(tp, t) {
515 if (!t->dirty || t->state == TOUCH_NONE)
518 if (t->state == TOUCH_BEGIN)
519 tp_tap_handle_event(tp, TAP_EVENT_TOUCH, time);
520 else if (t->state == TOUCH_END)
521 tp_tap_handle_event(tp, TAP_EVENT_RELEASE, time);
522 else if (tp->tap.state != TAP_STATE_IDLE &&
523 tp_tap_exceeds_motion_threshold(tp, t))
524 tp_tap_handle_event(tp, TAP_EVENT_MOTION, time);
528 * In any state where motion exceeding the move threshold would
529 * move to the next state, filter that motion until we actually
530 * exceed it. This prevents small motion events while we're waiting
531 * on a decision if a tap is a tap.
533 switch (tp->tap.state) {
534 case TAP_STATE_TOUCH:
535 case TAP_STATE_TAPPED:
536 case TAP_STATE_DRAGGING_OR_DOUBLETAP:
537 case TAP_STATE_TOUCH_2:
538 case TAP_STATE_TOUCH_3:
547 return filter_motion;
551 tp_tap_timeout_handler(void *data)
553 struct tp_dispatch *touchpad = data;
559 len = read(touchpad->tap.timer_fd, &expires, sizeof expires);
560 if (len != sizeof expires)
561 /* This will only happen if the application made the fd
562 * non-blocking, but this function should only be called
563 * upon the timeout, so lets continue anyway. */
564 log_error("timerfd read error: %s\n", strerror(errno));
566 clock_gettime(CLOCK_MONOTONIC, &ts);
567 now = ts.tv_sec * 1000ULL + ts.tv_nsec / 1000000;
569 tp_tap_handle_timeout(touchpad, now);
573 tp_tap_handle_timeout(struct tp_dispatch *tp, uint64_t time)
575 if (!tp->tap.enabled)
578 if (tp->tap.timeout && tp->tap.timeout <= time) {
579 tp_tap_clear_timer(tp);
580 tp_tap_handle_event(tp, TAP_EVENT_TIMEOUT, time);
583 return tp->tap.timeout;
587 tp_init_tap(struct tp_dispatch *tp)
589 tp->tap.state = TAP_STATE_IDLE;
590 tp->tap.timer_fd = timerfd_create(CLOCK_MONOTONIC, TFD_CLOEXEC);
592 if (tp->tap.timer_fd == -1)
596 libinput_add_fd(tp->device->base.seat->libinput,
598 tp_tap_timeout_handler,
601 if (tp->tap.source == NULL) {
602 close(tp->tap.timer_fd);
606 tp->tap.enabled = 1; /* FIXME */
612 tp_destroy_tap(struct tp_dispatch *tp)
614 if (tp->tap.source) {
615 libinput_remove_source(tp->device->base.seat->libinput, tp->tap.source);
616 tp->tap.source = NULL;
618 if (tp->tap.timer_fd > -1) {
619 close(tp->tap.timer_fd);
620 tp->tap.timer_fd = -1;