static void tp_tap_multitap_handle_event(struct tp_dispatch *tp, struct tp_touch *t, enum tap_event event, uint64_t time) { struct libinput *libinput = tp_libinput_context(tp); switch (event) { case TAP_EVENT_RELEASE: log_bug_libinput(libinput, "invalid tap event, no fingers are down\n"); break; case TAP_EVENT_TOUCH: tp->tap.state = TAP_STATE_MULTITAP_DOWN; tp->tap.multitap_last_time = time; tp_tap_notify(tp, time, 1, LIBINPUT_BUTTON_STATE_PRESSED); tp_tap_set_timer(tp, time); break; case TAP_EVENT_MOTION: log_bug_libinput(libinput, "invalid tap event, no fingers are down\n"); break; case TAP_EVENT_TIMEOUT: tp->tap.state = TAP_STATE_IDLE; tp_tap_notify(tp, time, 1, LIBINPUT_BUTTON_STATE_PRESSED); tp_tap_notify(tp, time, 1, LIBINPUT_BUTTON_STATE_RELEASED); break; case TAP_EVENT_BUTTON: tp->tap.state = TAP_STATE_IDLE; tp_tap_clear_timer(tp); break; case TAP_EVENT_THUMB: break; } }
static void tp_tap_idle_handle_event(struct tp_dispatch *tp, struct tp_touch *t, enum tap_event event, uint64_t time) { struct libinput *libinput = tp_libinput_context(tp); switch (event) { case TAP_EVENT_TOUCH: tp->tap.state = TAP_STATE_TOUCH; tp_tap_set_timer(tp, time); break; case TAP_EVENT_RELEASE: break; case TAP_EVENT_MOTION: log_bug_libinput(libinput, "invalid tap event, no fingers are down\n"); break; case TAP_EVENT_TIMEOUT: break; case TAP_EVENT_BUTTON: tp->tap.state = TAP_STATE_DEAD; break; case TAP_EVENT_THUMB: log_bug_libinput(libinput, "invalid tap event, no fingers down, no thumb\n"); break; } }
static void tp_edge_scroll_handle_edge(struct tp_dispatch *tp, struct tp_touch *t, enum scroll_event event) { struct libinput *libinput = tp_libinput_context(tp); switch (event) { case SCROLL_EVENT_TOUCH: case SCROLL_EVENT_TIMEOUT: log_bug_libinput(libinput, "unexpected scroll event %d in edge state\n", event); break; case SCROLL_EVENT_MOTION: /* If started at the bottom right, decide in which dir to scroll */ if (t->scroll.edge == (EDGE_RIGHT | EDGE_BOTTOM)) { t->scroll.edge &= tp_touch_get_edge(tp, t); if (!t->scroll.edge) tp_edge_scroll_set_state(tp, t, EDGE_SCROLL_TOUCH_STATE_AREA); } break; case SCROLL_EVENT_RELEASE: tp_edge_scroll_set_state(tp, t, EDGE_SCROLL_TOUCH_STATE_NONE); break; case SCROLL_EVENT_POSTED: break; } }
static void tp_edge_scroll_handle_edge_new(struct tp_dispatch *tp, struct tp_touch *t, enum scroll_event event) { struct libinput *libinput = tp_libinput_context(tp); switch (event) { case SCROLL_EVENT_TOUCH: log_bug_libinput(libinput, "unexpected scroll event %d in edge new state\n", event); break; case SCROLL_EVENT_MOTION: t->scroll.edge &= tp_touch_get_edge(tp, t); if (!t->scroll.edge) tp_edge_scroll_set_state(tp, t, EDGE_SCROLL_TOUCH_STATE_AREA); break; case SCROLL_EVENT_RELEASE: tp_edge_scroll_set_state(tp, t, EDGE_SCROLL_TOUCH_STATE_NONE); break; case SCROLL_EVENT_TIMEOUT: case SCROLL_EVENT_POSTED: tp_edge_scroll_set_state(tp, t, EDGE_SCROLL_TOUCH_STATE_EDGE); break; } }
static void tp_edge_scroll_handle_none(struct tp_dispatch *tp, struct tp_touch *t, enum scroll_event event) { struct libinput *libinput = tp_libinput_context(tp); switch (event) { case SCROLL_EVENT_TOUCH: if (tp_touch_get_edge(tp, t)) { tp_edge_scroll_set_state(tp, t, EDGE_SCROLL_TOUCH_STATE_EDGE_NEW); } else { tp_edge_scroll_set_state(tp, t, EDGE_SCROLL_TOUCH_STATE_AREA); } break; case SCROLL_EVENT_MOTION: case SCROLL_EVENT_RELEASE: case SCROLL_EVENT_TIMEOUT: case SCROLL_EVENT_POSTED: log_bug_libinput(libinput, "unexpected scroll event %d in none state\n", event); break; } }
static void tp_tap_tapped_handle_event(struct tp_dispatch *tp, struct tp_touch *t, enum tap_event event, uint64_t time) { struct libinput *libinput = tp_libinput_context(tp); switch (event) { case TAP_EVENT_MOTION: case TAP_EVENT_RELEASE: log_bug_libinput(libinput, "invalid tap event when fingers are up\n"); break; case TAP_EVENT_TOUCH: tp->tap.state = TAP_STATE_DRAGGING_OR_DOUBLETAP; tp_tap_set_timer(tp, time); break; case TAP_EVENT_TIMEOUT: tp->tap.state = TAP_STATE_IDLE; tp_tap_notify(tp, time, 1, LIBINPUT_BUTTON_STATE_RELEASED); break; case TAP_EVENT_BUTTON: tp->tap.state = TAP_STATE_DEAD; tp_tap_notify(tp, time, 1, LIBINPUT_BUTTON_STATE_RELEASED); break; case TAP_EVENT_THUMB: break; } }
static void middlebutton_state_error(struct evdev_device *device, enum evdev_middlebutton_event event) { log_bug_libinput(device->base.seat->libinput, "Invalid event %s in middle btn state %s\n", middlebutton_event_to_str(event), middlebutton_state_to_str(device->middlebutton.state)); }
static void tp_edge_scroll_handle_area(struct tp_dispatch *tp, struct tp_touch *t, enum scroll_event event) { struct libinput *libinput = tp_libinput_context(tp); switch (event) { case SCROLL_EVENT_TOUCH: case SCROLL_EVENT_TIMEOUT: case SCROLL_EVENT_POSTED: log_bug_libinput(libinput, "unexpected scroll event %d in area state\n", event); break; case SCROLL_EVENT_MOTION: break; case SCROLL_EVENT_RELEASE: tp_edge_scroll_set_state(tp, t, EDGE_SCROLL_TOUCH_STATE_NONE); break; } }
bool evdev_middlebutton_filter_button(struct evdev_device *device, uint64_t time, int button, enum libinput_button_state state) { enum evdev_middlebutton_event event; bool is_press = state == LIBINPUT_BUTTON_STATE_PRESSED; int rc; unsigned int bit = (button - BTN_LEFT); uint32_t old_mask = 0; if (!device->middlebutton.enabled) return false; switch (button) { case BTN_LEFT: if (is_press) event = MIDDLEBUTTON_EVENT_L_DOWN; else event = MIDDLEBUTTON_EVENT_L_UP; break; case BTN_RIGHT: if (is_press) event = MIDDLEBUTTON_EVENT_R_DOWN; else event = MIDDLEBUTTON_EVENT_R_UP; break; /* BTN_MIDDLE counts as "other" and resets middle button * emulation */ case BTN_MIDDLE: default: event = MIDDLEBUTTON_EVENT_OTHER; break; } if (button < BTN_LEFT || bit >= sizeof(device->middlebutton.button_mask) * 8) { log_bug_libinput(device->base.seat->libinput, "Button mask too small for %d\n", libevdev_event_code_get_name(EV_KEY, button)); return true; } rc = evdev_middlebutton_handle_event(device, time, event); old_mask = device->middlebutton.button_mask; if (is_press) device->middlebutton.button_mask |= 1 << bit; else device->middlebutton.button_mask &= ~(1 << bit); if (old_mask != device->middlebutton.button_mask && device->middlebutton.button_mask == 0) { evdev_middlebutton_handle_event(device, time, MIDDLEBUTTON_EVENT_ALL_UP); evdev_middlebutton_apply_config(device); } return rc; }