[PATCH weston 13/16] tablet: Remove tablet-specific tools on disconnect
Bastian Farkas
bfarkas at de.adit-jv.com
Wed Oct 25 11:16:46 UTC 2017
From: Lyude Paul <thatslyude at gmail.com>
Store all tablets that a tool was used on in a list. When the tablet
is removed, remove all tools only seen on this tablet.
Tools without a serial number are only ever bound to one tablet.
Co-authored-by: Peter Hutterer <peter.hutterer at who-t.net>
Signed-off-by: Lyude Paul <thatslyude at gmail.com>
Signed-off-by: Peter Hutterer <peter.hutterer at who-t.net>
Signed-off-by: Bastian Farkas <bfarkas at de.adit-jv.com>
---
libweston/compositor.h | 8 ++++++++
libweston/input.c | 33 +++++++++++++++++++++++++++++++--
libweston/libinput-device.c | 41 +++++++++++++++++++++++++++++++++++++----
3 files changed, 76 insertions(+), 6 deletions(-)
diff --git a/libweston/compositor.h b/libweston/compositor.h
index 90800a7..fb59615 100644
--- a/libweston/compositor.h
+++ b/libweston/compositor.h
@@ -477,6 +477,13 @@ struct weston_tablet_tool {
wl_fixed_t grab_x, grab_y;
};
+struct weston_tablet_tool_id {
+ struct wl_list link;
+
+ enum zwp_tablet_tool_v1_type type;
+ uint64_t serial;
+};
+
struct weston_tablet {
struct weston_seat *seat;
struct evdev_device *device;
@@ -484,6 +491,7 @@ struct weston_tablet {
struct wl_list resource_list;
struct wl_list link;
+ struct wl_list tool_id_list;
char *name;
uint32_t vid;
diff --git a/libweston/input.c b/libweston/input.c
index ecd4c58..d8251b1 100644
--- a/libweston/input.c
+++ b/libweston/input.c
@@ -1217,6 +1217,7 @@ weston_tablet_create(void)
return NULL;
wl_list_init(&tablet->resource_list);
+ wl_list_init(&tablet->tool_id_list);
return tablet;
}
@@ -1225,11 +1226,41 @@ WL_EXPORT void
weston_tablet_destroy(struct weston_tablet *tablet)
{
struct wl_resource *resource;
+ struct weston_tablet *t;
+ struct weston_tablet_tool *tool, *tmptool;
+ struct weston_tablet_tool_id *id, *tmpid;
wl_resource_for_each(resource, &tablet->resource_list)
zwp_tablet_v1_send_removed(resource);
+ /* First drop all tool ids from this tablet */
+ wl_list_for_each_safe(id, tmpid, &tablet->tool_id_list, link) {
+ wl_list_remove(&id->link);
+ free(id);
+ }
+
+ /* Remove the tablet from the list */
wl_list_remove(&tablet->link);
+
+ /* For each tool, check remaining tablets for the stored ID list. If we
+ * can't find this tool anywhere, we can drop it */
+ wl_list_for_each_safe(tool, tmptool,
+ &tablet->seat->tablet_tool_list, link) {
+ bool remove_tool = true;
+
+ wl_list_for_each(t, &tablet->seat->tablet_list, link) {
+ wl_list_for_each(id, &t->tool_id_list, link) {
+ if (tool->type == id->type &&
+ tool->serial == id->serial) {
+ remove_tool = false;
+ break;
+ }
+ }
+ }
+
+ if (remove_tool)
+ weston_seat_release_tablet_tool(tool);
+ }
}
WL_EXPORT void
@@ -3821,8 +3852,6 @@ weston_seat_release_pointer(struct weston_seat *seat)
WL_EXPORT void
weston_seat_release_tablet_tool(struct weston_tablet_tool *tool)
{
- /* FIXME: nothing is calling this function yet, tools are only
- released on shutdown when the seat goes away */
wl_signal_emit(&tool->removed_signal, tool);
weston_tablet_tool_destroy(tool);
diff --git a/libweston/libinput-device.c b/libweston/libinput-device.c
index 49ee444..82c528d 100644
--- a/libweston/libinput-device.c
+++ b/libweston/libinput-device.c
@@ -370,6 +370,7 @@ handle_tablet_proximity(struct libinput_device *libinput_device,
struct evdev_device *device;
struct weston_tablet *tablet;
struct weston_tablet_tool *tool;
+ struct weston_tablet_tool_id *id;
struct libinput_tablet_tool *libinput_tool;
enum libinput_tablet_tool_type libinput_tool_type;
uint32_t serial, type;
@@ -404,10 +405,12 @@ handle_tablet_proximity(struct libinput_device *libinput_device,
return;
}
- wl_list_for_each(tool, &device->seat->tablet_tool_list, link) {
- if (tool->serial == serial && tool->type == type) {
- create = false;
- break;
+ if (serial) {
+ wl_list_for_each(tool, &device->seat->tablet_tool_list, link) {
+ if (tool->serial == serial && tool->type == type) {
+ create = false;
+ break;
+ }
}
}
@@ -426,11 +429,41 @@ handle_tablet_proximity(struct libinput_device *libinput_device,
tool->capabilities |= 1 << ZWP_TABLET_TOOL_V1_CAPABILITY_TILT;
wl_list_insert(&device->seat->tablet_tool_list, &tool->link);
+
+ id = zalloc(sizeof *id);
+ if (id) {
+ id->type = tool->type;
+ id->serial = serial;
+ wl_list_insert(&tablet->tool_id_list, &id->link);
+ }
+
notify_tablet_tool_added(tool);
libinput_tablet_tool_set_user_data(libinput_tool, tool);
}
+ if (serial && !create) {
+ struct weston_tablet_tool_id *id;
+ bool add = true;
+
+ wl_list_for_each(id, &tablet->tool_id_list, link) {
+ if (id->type == tool->type &&
+ id->serial == tool->serial) {
+ add = false;
+ break;
+ }
+ }
+
+ if (add) {
+ id = zalloc(sizeof *id);
+ if (id) {
+ id->type = tool->type;
+ id->serial = tool->serial;
+ wl_list_insert(&tablet->tool_id_list, &id->link);
+ }
+ }
+ }
+
notify_tablet_tool_proximity_in(tool, time, tablet);
/* FIXME: we should send axis updates here */
notify_tablet_tool_frame(tool, time);
--
2.7.4
More information about the wayland-devel
mailing list