summaryrefslogtreecommitdiff
path: root/clutter
diff options
context:
space:
mode:
authorCarlos Garnacho <carlosg@gnome.org>2021-05-02 16:27:01 +0200
committerMarge Bot <marge-bot@gnome.org>2021-05-05 19:07:26 +0000
commit7ba1448e5bb6e0dcc1612d490dc048facaea5183 (patch)
treec1cc7e0760762732e03e1913d697829b42050444 /clutter
parentd4a042b88d24464c5d86a01bc9c5ebf6f8ace353 (diff)
downloadmutter-7ba1448e5bb6e0dcc1612d490dc048facaea5183.tar.gz
clutter: Move pointer a11y settings management from MetaInputSettings
All pointer a11y is a fabrication of Clutter backend-independent code, with the help of a ClutterVirtualInputDevice and with some UI on top. On the other hand, MetaInputSettings is a backend implementation detail, this has 2 gotchas: - In the native backend, the MetaInputSettings (and pointer a11y with it) are initialized early, before the ClutterSeat core pointer is set up. - Doing this from the MetaInputSettings also means another dubious access from the input thread into main thread territory. Move the pointer a11y into ClutterSettings, making this effectively backend-independent business, invariably done from the main thread and ensured to happen after seat initialization. Fixes: https://gitlab.gnome.org/GNOME/mutter/-/issues/1765 Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1849>
Diffstat (limited to 'clutter')
-rw-r--r--clutter/clutter/clutter-seat.c12
-rw-r--r--clutter/clutter/clutter-settings-private.h3
-rw-r--r--clutter/clutter/clutter-settings.c122
-rw-r--r--clutter/meson.build1
4 files changed, 138 insertions, 0 deletions
diff --git a/clutter/clutter/clutter-seat.c b/clutter/clutter/clutter-seat.c
index 24f36edbd..a62aeedc2 100644
--- a/clutter/clutter/clutter-seat.c
+++ b/clutter/clutter/clutter-seat.c
@@ -31,6 +31,7 @@
#include "clutter-private.h"
#include "clutter-seat.h"
#include "clutter-seat-private.h"
+#include "clutter-settings-private.h"
#include "clutter-virtual-input-device.h"
enum
@@ -115,12 +116,23 @@ clutter_seat_get_property (GObject *object,
}
static void
+clutter_seat_constructed (GObject *object)
+{
+ ClutterSettings *settings = clutter_settings_get_default ();
+
+ G_OBJECT_CLASS (clutter_seat_parent_class)->constructed (object);
+ clutter_settings_ensure_pointer_a11y_settings (settings,
+ CLUTTER_SEAT (object));
+}
+
+static void
clutter_seat_class_init (ClutterSeatClass *klass)
{
GObjectClass *object_class = G_OBJECT_CLASS (klass);
object_class->set_property = clutter_seat_set_property;
object_class->get_property = clutter_seat_get_property;
+ object_class->constructed = clutter_seat_constructed;
signals[DEVICE_ADDED] =
g_signal_new (I_("device-added"),
diff --git a/clutter/clutter/clutter-settings-private.h b/clutter/clutter/clutter-settings-private.h
index 7df4fccf1..a8a8e01e3 100644
--- a/clutter/clutter/clutter-settings-private.h
+++ b/clutter/clutter/clutter-settings-private.h
@@ -13,6 +13,9 @@ void clutter_settings_set_property_internal (ClutterSettings *settings,
const char *property,
GValue *value);
+void clutter_settings_ensure_pointer_a11y_settings (ClutterSettings *settings,
+ ClutterSeat *seat);
+
G_END_DECLS
#endif /* __CLUTTER_SETTINGS_PRIVATE_H__ */
diff --git a/clutter/clutter/clutter-settings.c b/clutter/clutter/clutter-settings.c
index e80dd2450..f3dffdbbb 100644
--- a/clutter/clutter/clutter-settings.c
+++ b/clutter/clutter/clutter-settings.c
@@ -32,6 +32,7 @@
#include "clutter-stage-private.h"
#include "clutter-private.h"
+#include <gdesktop-enums.h>
#include <stdlib.h>
#define DEFAULT_FONT_NAME "Sans 12"
@@ -67,6 +68,7 @@ struct _ClutterSettings
ClutterBackend *backend;
GSettings *font_settings;
GSettings *mouse_settings;
+ GSettings *mouse_a11y_settings;
gint double_click_time;
gint double_click_distance;
@@ -436,11 +438,110 @@ on_mouse_settings_change_event (GSettings *settings,
return FALSE;
}
+struct _pointer_a11y_settings_flags_pair {
+ const char *name;
+ ClutterPointerA11yFlags flag;
+} pointer_a11y_settings_flags_pair[] = {
+ { "secondary-click-enabled", CLUTTER_A11Y_SECONDARY_CLICK_ENABLED },
+ { "dwell-click-enabled", CLUTTER_A11Y_DWELL_ENABLED },
+};
+
+static ClutterPointerA11yDwellDirection
+pointer_a11y_dwell_direction_from_setting (ClutterSettings *self,
+ const char *key)
+{
+ GDesktopMouseDwellDirection dwell_gesture_direction;
+
+ dwell_gesture_direction = g_settings_get_enum (self->mouse_a11y_settings,
+ key);
+ switch (dwell_gesture_direction)
+ {
+ case G_DESKTOP_MOUSE_DWELL_DIRECTION_LEFT:
+ return CLUTTER_A11Y_DWELL_DIRECTION_LEFT;
+ break;
+ case G_DESKTOP_MOUSE_DWELL_DIRECTION_RIGHT:
+ return CLUTTER_A11Y_DWELL_DIRECTION_RIGHT;
+ break;
+ case G_DESKTOP_MOUSE_DWELL_DIRECTION_UP:
+ return CLUTTER_A11Y_DWELL_DIRECTION_UP;
+ break;
+ case G_DESKTOP_MOUSE_DWELL_DIRECTION_DOWN:
+ return CLUTTER_A11Y_DWELL_DIRECTION_DOWN;
+ break;
+ default:
+ break;
+ }
+ return CLUTTER_A11Y_DWELL_DIRECTION_NONE;
+}
+
+static void
+sync_pointer_a11y_settings (ClutterSettings *self,
+ ClutterSeat *seat)
+{
+ ClutterPointerA11ySettings pointer_a11y_settings;
+ GDesktopMouseDwellMode dwell_mode;
+ int i;
+
+ clutter_seat_get_pointer_a11y_settings (seat, &pointer_a11y_settings);
+ pointer_a11y_settings.controls = 0;
+ for (i = 0; i < G_N_ELEMENTS (pointer_a11y_settings_flags_pair); i++)
+ {
+ if (!g_settings_get_boolean (self->mouse_a11y_settings,
+ pointer_a11y_settings_flags_pair[i].name))
+ continue;
+
+ pointer_a11y_settings.controls |=
+ pointer_a11y_settings_flags_pair[i].flag;
+ }
+
+ /* "secondary-click-time" is expressed in seconds */
+ pointer_a11y_settings.secondary_click_delay =
+ (1000 * g_settings_get_double (self->mouse_a11y_settings,
+ "secondary-click-time"));
+ /* "dwell-time" is expressed in seconds */
+ pointer_a11y_settings.dwell_delay =
+ (1000 * g_settings_get_double (self->mouse_a11y_settings, "dwell-time"));
+ pointer_a11y_settings.dwell_threshold =
+ g_settings_get_int (self->mouse_a11y_settings, "dwell-threshold");
+
+ dwell_mode = g_settings_get_enum (self->mouse_a11y_settings, "dwell-mode");
+ if (dwell_mode == G_DESKTOP_MOUSE_DWELL_MODE_WINDOW)
+ pointer_a11y_settings.dwell_mode = CLUTTER_A11Y_DWELL_MODE_WINDOW;
+ else
+ pointer_a11y_settings.dwell_mode = CLUTTER_A11Y_DWELL_MODE_GESTURE;
+
+ pointer_a11y_settings.dwell_gesture_single =
+ pointer_a11y_dwell_direction_from_setting (self, "dwell-gesture-single");
+ pointer_a11y_settings.dwell_gesture_double =
+ pointer_a11y_dwell_direction_from_setting (self, "dwell-gesture-double");
+ pointer_a11y_settings.dwell_gesture_drag =
+ pointer_a11y_dwell_direction_from_setting (self, "dwell-gesture-drag");
+ pointer_a11y_settings.dwell_gesture_secondary =
+ pointer_a11y_dwell_direction_from_setting (self, "dwell-gesture-secondary");
+
+ clutter_seat_set_pointer_a11y_settings (seat, &pointer_a11y_settings);
+}
+
+static gboolean
+on_mouse_a11y_settings_change_event (GSettings *settings,
+ gpointer keys,
+ int n_keys,
+ gpointer user_data)
+{
+ ClutterSettings *self = CLUTTER_SETTINGS (user_data);
+ ClutterSeat *seat = clutter_backend_get_default_seat (self->backend);
+
+ sync_pointer_a11y_settings (self, seat);
+
+ return FALSE;
+}
+
static void
load_initial_settings (ClutterSettings *self)
{
static const gchar *font_settings_path = "org.gnome.desktop.interface";
static const gchar *mouse_settings_path = "org.gnome.desktop.peripherals.mouse";
+ static const char *mouse_a11y_settings_path = "org.gnome.desktop.a11y.mouse";
GSettingsSchemaSource *source = g_settings_schema_source_get_default ();
GSettingsSchema *schema;
@@ -477,6 +578,19 @@ load_initial_settings (ClutterSettings *self)
self);
}
}
+
+ schema = g_settings_schema_source_lookup (source, mouse_a11y_settings_path, TRUE);
+ if (!schema)
+ {
+ g_warning ("Failed to find schema: %s", mouse_settings_path);
+ }
+ else
+ {
+ self->mouse_a11y_settings = g_settings_new_full (schema, NULL, NULL);
+ g_signal_connect (self->mouse_a11y_settings, "change-event",
+ G_CALLBACK (on_mouse_a11y_settings_change_event),
+ self);
+ }
}
static void
@@ -490,6 +604,7 @@ clutter_settings_finalize (GObject *gobject)
g_clear_object (&self->font_settings);
g_clear_object (&self->mouse_settings);
+ g_clear_object (&self->mouse_a11y_settings);
G_OBJECT_CLASS (clutter_settings_parent_class)->finalize (gobject);
}
@@ -958,3 +1073,10 @@ _clutter_settings_set_backend (ClutterSettings *settings,
load_initial_settings (settings);
}
+
+void
+clutter_settings_ensure_pointer_a11y_settings (ClutterSettings *settings,
+ ClutterSeat *seat)
+{
+ sync_pointer_a11y_settings (settings, seat);
+}
diff --git a/clutter/meson.build b/clutter/meson.build
index defa73f1c..94f1eb0f1 100644
--- a/clutter/meson.build
+++ b/clutter/meson.build
@@ -81,6 +81,7 @@ endif
clutter_deps = [
clutter_pkg_deps,
clutter_pkg_private_deps,
+ gsettings_desktop_schemas_dep,
libmutter_cogl_dep,
m_dep
]