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 @@ -114,6 +115,16 @@ 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) { @@ -121,6 +132,7 @@ clutter_seat_class_init (ClutterSeatClass *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 #include #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 ] diff --git a/src/backends/meta-input-settings.c b/src/backends/meta-input-settings.c index 5a4ded964..6448e65a2 100644 --- a/src/backends/meta-input-settings.c +++ b/src/backends/meta-input-settings.c @@ -74,7 +74,6 @@ struct _MetaInputSettingsPrivate GSettings *trackball_settings; GSettings *keyboard_settings; GSettings *keyboard_a11y_settings; - GSettings *mouse_a11y_settings; GList *devices; GHashTable *mappable_devices; @@ -152,7 +151,6 @@ meta_input_settings_dispose (GObject *object) g_clear_object (&priv->trackball_settings); g_clear_object (&priv->keyboard_settings); g_clear_object (&priv->keyboard_a11y_settings); - g_clear_object (&priv->mouse_a11y_settings); g_clear_pointer (&priv->mappable_devices, g_hash_table_unref); g_clear_pointer (&priv->current_tools, g_hash_table_unref); @@ -1273,97 +1271,6 @@ meta_input_keyboard_a11y_settings_changed (GSettings *settings, load_keyboard_a11y_settings (input_settings); } -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 (MetaInputSettings *input_settings, - const char *key) -{ - MetaInputSettingsPrivate *priv = meta_input_settings_get_instance_private (input_settings); - GDesktopMouseDwellDirection dwell_gesture_direction; - - dwell_gesture_direction = g_settings_get_enum (priv->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 -load_pointer_a11y_settings (MetaInputSettings *input_settings) -{ - MetaInputSettingsPrivate *priv = meta_input_settings_get_instance_private (input_settings); - ClutterPointerA11ySettings pointer_a11y_settings; - GDesktopMouseDwellMode dwell_mode; - guint i; - - clutter_seat_get_pointer_a11y_settings (CLUTTER_SEAT (priv->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 (priv->mouse_a11y_settings, pointer_a11y_settings_flags_pair[i].name)) - 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 (priv->mouse_a11y_settings, "secondary-click-time")); - /* "dwell-time" is expressed in seconds */ - pointer_a11y_settings.dwell_delay = - (1000 * g_settings_get_double (priv->mouse_a11y_settings, "dwell-time")); - pointer_a11y_settings.dwell_threshold = g_settings_get_int (priv->mouse_a11y_settings, - "dwell-threshold"); - - dwell_mode = g_settings_get_enum (priv->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 (input_settings, "dwell-gesture-single"); - pointer_a11y_settings.dwell_gesture_double = - pointer_a11y_dwell_direction_from_setting (input_settings, "dwell-gesture-double"); - pointer_a11y_settings.dwell_gesture_drag = - pointer_a11y_dwell_direction_from_setting (input_settings, "dwell-gesture-drag"); - pointer_a11y_settings.dwell_gesture_secondary = - pointer_a11y_dwell_direction_from_setting (input_settings, "dwell-gesture-secondary"); - - clutter_seat_set_pointer_a11y_settings (CLUTTER_SEAT (priv->seat), - &pointer_a11y_settings); -} - -static void -meta_input_mouse_a11y_settings_changed (GSettings *settings, - const char *key, - gpointer user_data) -{ - MetaInputSettings *input_settings = META_INPUT_SETTINGS (user_data); - - load_pointer_a11y_settings (input_settings); -} - static GSettings * lookup_device_settings (ClutterInputDevice *device) { @@ -1750,7 +1657,6 @@ meta_input_settings_constructed (GObject *object) check_mappable_devices (input_settings); load_keyboard_a11y_settings (input_settings); - load_pointer_a11y_settings (input_settings); } static void @@ -1812,10 +1718,6 @@ meta_input_settings_init (MetaInputSettings *settings) g_signal_connect (priv->keyboard_a11y_settings, "changed", G_CALLBACK (meta_input_keyboard_a11y_settings_changed), settings); - priv->mouse_a11y_settings = g_settings_new ("org.gnome.desktop.a11y.mouse"); - g_signal_connect (priv->mouse_a11y_settings, "changed", - G_CALLBACK (meta_input_mouse_a11y_settings_changed), settings); - priv->mappable_devices = g_hash_table_new_full (NULL, NULL, NULL, (GDestroyNotify) device_mapping_info_free);