[gnome-builder] libide/tweaks: port IdeTweaksCombo to using binding



commit 507297552aec96246842cc69c38640200599b3b9
Author: Christian Hergert <chergert redhat com>
Date:   Wed Aug 24 21:50:45 2022 -0700

    libide/tweaks: port IdeTweaksCombo to using binding
    
    This also improves the situation a bit by actually reacting to changes in
    the underlying binding (such as a setting changing) where as the existing
    code did not handle that at all.

 src/libide/tweaks/ide-tweaks-combo-row.c | 138 ++++++++++++++++++++++---------
 src/libide/tweaks/ide-tweaks-combo.c     | 114 ++++++-------------------
 src/libide/tweaks/ide-tweaks-combo.h     |  25 ++----
 3 files changed, 133 insertions(+), 144 deletions(-)
---
diff --git a/src/libide/tweaks/ide-tweaks-combo-row.c b/src/libide/tweaks/ide-tweaks-combo-row.c
index dfc015e7a..941ee805d 100644
--- a/src/libide/tweaks/ide-tweaks-combo-row.c
+++ b/src/libide/tweaks/ide-tweaks-combo-row.c
@@ -24,44 +24,115 @@
 
 #include <libide-core.h>
 
+#include "ide-tweaks-binding.h"
 #include "ide-tweaks-choice.h"
 #include "ide-tweaks-combo-row.h"
-#include "ide-tweaks-settings.h"
+#include "ide-tweaks-variant.h"
+
+#include "gsettings-mapping.h"
 
 struct _IdeTweaksComboRow
 {
-  AdwComboRow parent_instance;
-  IdeSettings *settings;
-  char *key;
+  AdwComboRow       parent_instance;
+  IdeTweaksBinding *binding;
+  guint             selecting_item : 1;
 };
 
 G_DEFINE_FINAL_TYPE (IdeTweaksComboRow, ide_tweaks_combo_row, ADW_TYPE_COMBO_ROW)
 
 enum {
   PROP_0,
-  PROP_KEY,
-  PROP_SETTINGS,
+  PROP_BINDING,
   N_PROPS
 };
 
 static GParamSpec *properties[N_PROPS];
 
 static void
-ide_tweaks_combo_row_notify_selected_item (IdeTweaksComboRow *self,
-                                           GParamSpec        *pspec)
+ide_tweaks_combo_row_notify_selected (IdeTweaksComboRow *self,
+                                      GParamSpec        *pspec)
 {
   IdeTweaksChoice *choice;
 
   g_assert (IDE_IS_TWEAKS_COMBO_ROW (self));
-  g_assert (self->settings != NULL);
-  g_assert (self->key != NULL);
+
+  if (self->binding == NULL || self->selecting_item)
+    return;
+
+  self->selecting_item = TRUE;
 
   if ((choice = adw_combo_row_get_selected_item (ADW_COMBO_ROW (self))))
     {
-      GVariant *action_target = ide_tweaks_choice_get_value (choice);
+      GVariant *variant = ide_tweaks_choice_get_value (choice);
+      GType type;
+
+      if (ide_tweaks_binding_get_expected_type (self->binding, &type))
+        {
+          g_auto(GValue) value = G_VALUE_INIT;
+
+          g_value_init (&value, type);
+
+          if (g_settings_get_mapping (&value, variant, NULL))
+            {
+              ide_tweaks_binding_set_value (self->binding, &value);
+              goto cleanup;
+            }
+        }
+    }
+
+  g_warning ("Failed to update choice!");
+
+cleanup:
+  self->selecting_item = FALSE;
+}
+
+static void
+ide_tweaks_combo_row_binding_changed_cb (IdeTweaksComboRow *self,
+                                         IdeTweaksBinding  *binding)
+{
+  g_autoptr(GVariant) variant = NULL;
+  g_auto(GValue) value = G_VALUE_INIT;
+  const GVariantType *expected_type;
+  GListModel *model;
+  GType type;
+  guint n_items;
+  int selected = -1;
+
+  g_assert (IDE_IS_TWEAKS_COMBO_ROW (self));
+  g_assert (IDE_IS_TWEAKS_BINDING (binding));
 
-      ide_settings_set_value (self->settings, self->key, action_target);
+  if (self->selecting_item)
+    return;
+
+  model = adw_combo_row_get_model (ADW_COMBO_ROW (self));
+  n_items = g_list_model_get_n_items (model);
+
+  if (n_items == 0)
+    return;
+
+  if (!ide_tweaks_binding_get_expected_type (binding, &type))
+    return;
+
+  expected_type = _ide_tweaks_gtype_to_variant_type (type);
+
+  g_value_init (&value, type);
+  if (ide_tweaks_binding_get_value (binding, &value))
+    variant = g_settings_set_mapping (&value, expected_type, NULL);
+
+  for (guint i = 0; i < n_items; i++)
+    {
+      g_autoptr(IdeTweaksChoice) choice = g_list_model_get_item (model, i);
+      GVariant *choice_variant = ide_tweaks_choice_get_value (choice);
+
+      if (variant && choice_variant && g_variant_equal (variant, choice_variant))
+        {
+          selected = i;
+          break;
+        }
     }
+
+  if (selected > -1)
+    adw_combo_row_set_selected (ADW_COMBO_ROW (self), selected);
 }
 
 static void
@@ -72,9 +143,16 @@ ide_tweaks_combo_row_constructed (GObject *object)
   G_OBJECT_CLASS (ide_tweaks_combo_row_parent_class)->constructed (object);
 
   g_signal_connect (self,
-                    "notify::selected-item",
-                    G_CALLBACK (ide_tweaks_combo_row_notify_selected_item),
+                    "notify::selected",
+                    G_CALLBACK (ide_tweaks_combo_row_notify_selected),
                     NULL);
+
+  if (self->binding)
+    g_signal_connect_object (self->binding,
+                             "changed",
+                             G_CALLBACK (ide_tweaks_combo_row_binding_changed_cb),
+                             self,
+                             G_CONNECT_SWAPPED);
 }
 
 static void
@@ -82,8 +160,7 @@ ide_tweaks_combo_row_dispose (GObject *object)
 {
   IdeTweaksComboRow *self = (IdeTweaksComboRow *)object;
 
-  g_clear_object (&self->settings);
-  g_clear_pointer (&self->key, g_free);
+  g_clear_object (&self->binding);
 
   G_OBJECT_CLASS (ide_tweaks_combo_row_parent_class)->dispose (object);
 }
@@ -98,12 +175,8 @@ ide_tweaks_combo_row_get_property (GObject    *object,
 
   switch (prop_id)
     {
-    case PROP_KEY:
-      g_value_set_string (value, self->key);
-      break;
-
-    case PROP_SETTINGS:
-      g_value_set_object (value, self->settings);
+    case PROP_BINDING:
+      g_value_set_object (value, self->binding);
       break;
 
     default:
@@ -121,14 +194,8 @@ ide_tweaks_combo_row_set_property (GObject      *object,
 
   switch (prop_id)
     {
-    case PROP_KEY:
-      if (ide_set_string (&self->key, g_value_get_string (value)))
-        g_object_notify_by_pspec (object, pspec);
-      break;
-
-    case PROP_SETTINGS:
-      if (g_set_object (&self->settings, g_value_get_object (value)))
-        g_object_notify_by_pspec (object, pspec);
+    case PROP_BINDING:
+      self->binding = g_value_dup_object (value);
       break;
 
     default:
@@ -147,14 +214,9 @@ ide_tweaks_combo_row_class_init (IdeTweaksComboRowClass *klass)
   object_class->get_property = ide_tweaks_combo_row_get_property;
   object_class->set_property = ide_tweaks_combo_row_set_property;
 
-  properties[PROP_KEY] =
-    g_param_spec_string ("key", NULL, NULL,
-                         NULL,
-                         (G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_STRINGS));
-
-  properties[PROP_SETTINGS] =
-    g_param_spec_object ("settings", NULL, NULL,
-                         IDE_TYPE_SETTINGS,
+  properties [PROP_BINDING] =
+    g_param_spec_object ("binding", NULL, NULL,
+                         IDE_TYPE_TWEAKS_BINDING,
                          (G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_STRINGS));
 
   g_object_class_install_properties (object_class, N_PROPS, properties);
diff --git a/src/libide/tweaks/ide-tweaks-combo.c b/src/libide/tweaks/ide-tweaks-combo.c
index 1ae1c315f..4c4ca5501 100644
--- a/src/libide/tweaks/ide-tweaks-combo.c
+++ b/src/libide/tweaks/ide-tweaks-combo.c
@@ -29,20 +29,19 @@
 #include "ide-tweaks-combo.h"
 #include "ide-tweaks-combo-row.h"
 #include "ide-tweaks-item-private.h"
+#include "ide-tweaks-variant.h"
+
+#include "gsettings-mapping.h"
 
 struct _IdeTweaksCombo
 {
   IdeTweaksWidget parent_instance;
-  IdeTweaksSettings *settings;
   char *title;
   char *subtitle;
-  char *key;
 };
 
 enum {
   PROP_0,
-  PROP_KEY,
-  PROP_SETTINGS,
   PROP_TITLE,
   PROP_SUBTITLE,
   N_PROPS
@@ -57,31 +56,43 @@ ide_tweaks_combo_create_for_item (IdeTweaksWidget *instance,
                                   IdeTweaksItem   *widget)
 {
   IdeTweaksCombo *self = (IdeTweaksCombo *)widget;
-  g_autoptr(IdeSettings) settings = NULL;
   g_autoptr(GListStore) store = NULL;
-  g_autoptr(GVariant) value = NULL;
+  g_autoptr(GVariant) variant = NULL;
+  IdeTweaksBinding *binding = NULL;
   IdeTweaksItem *root;
   AdwComboRow *row;
-  int selected = -1;
+  GType type;
   guint i = 0;
+  int selected = -1;
 
   g_assert (IDE_IS_TWEAKS_COMBO (self));
 
-  root = ide_tweaks_item_get_root (IDE_TWEAKS_ITEM (widget));
-  settings = IDE_SETTINGS (ide_tweaks_settings_create_action_group (self->settings, IDE_TWEAKS (root)));
+  if (!(binding = ide_tweaks_widget_get_binding (IDE_TWEAKS_WIDGET (widget))))
+    return NULL;
 
+  root = ide_tweaks_item_get_root (IDE_TWEAKS_ITEM (widget));
   store = g_list_store_new (IDE_TYPE_TWEAKS_CHOICE);
-  value = ide_settings_get_value (settings, self->key);
+
+  if (ide_tweaks_binding_get_expected_type (binding, &type))
+    {
+      const GVariantType *expected_type = _ide_tweaks_gtype_to_variant_type (type);
+      g_auto(GValue) value = G_VALUE_INIT;
+
+      g_value_init (&value, type);
+      if (ide_tweaks_binding_get_value (binding, &value))
+        variant = g_settings_set_mapping (&value, expected_type, NULL);
+    }
 
   for (IdeTweaksItem *child = ide_tweaks_item_get_first_child (IDE_TWEAKS_ITEM (self));
        child != NULL;
        child = ide_tweaks_item_get_next_sibling (child))
     {
-      if (!_ide_tweaks_item_is_hidden (child, root))
+      if (IDE_IS_TWEAKS_CHOICE (child) &&
+          !_ide_tweaks_item_is_hidden (child, root))
         {
-          GVariant *target = ide_tweaks_choice_get_value (IDE_TWEAKS_CHOICE (child));
+          GVariant *choice_variant = ide_tweaks_choice_get_value (IDE_TWEAKS_CHOICE (child));
 
-          if (g_variant_equal (value, target))
+          if (variant && choice_variant && g_variant_equal (variant, choice_variant))
             selected = i;
 
           g_list_store_append (store, child);
@@ -90,11 +101,10 @@ ide_tweaks_combo_create_for_item (IdeTweaksWidget *instance,
     }
 
   row = g_object_new (IDE_TYPE_TWEAKS_COMBO_ROW,
-                      "model", store,
-                      "settings", settings,
-                      "key", self->key,
                       "title", self->title,
                       "subtitle", self->subtitle,
+                      "binding", binding,
+                      "model", store,
                       "selected", selected > -1 ? selected : 0,
                       NULL);
 
@@ -113,7 +123,6 @@ ide_tweaks_combo_dispose (GObject *object)
 {
   IdeTweaksCombo *self = (IdeTweaksCombo *)object;
 
-  g_clear_object (&self->settings);
   g_clear_pointer (&self->title, g_free);
   g_clear_pointer (&self->subtitle, g_free);
 
@@ -130,10 +139,6 @@ ide_tweaks_combo_get_property (GObject    *object,
 
   switch (prop_id)
     {
-    case PROP_SETTINGS:
-      g_value_set_object (value, ide_tweaks_combo_get_settings (self));
-      break;
-
     case PROP_TITLE:
       g_value_set_string (value, ide_tweaks_combo_get_title (self));
       break;
@@ -142,10 +147,6 @@ ide_tweaks_combo_get_property (GObject    *object,
       g_value_set_string (value, ide_tweaks_combo_get_subtitle (self));
       break;
 
-    case PROP_KEY:
-      g_value_set_string (value, ide_tweaks_combo_get_key (self));
-      break;
-
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
     }
@@ -161,10 +162,6 @@ ide_tweaks_combo_set_property (GObject      *object,
 
   switch (prop_id)
     {
-    case PROP_SETTINGS:
-      ide_tweaks_combo_set_settings (self, g_value_get_object (value));
-      break;
-
     case PROP_TITLE:
       ide_tweaks_combo_set_title (self, g_value_get_string (value));
       break;
@@ -173,10 +170,6 @@ ide_tweaks_combo_set_property (GObject      *object,
       ide_tweaks_combo_set_subtitle (self, g_value_get_string (value));
       break;
 
-    case PROP_KEY:
-      ide_tweaks_combo_set_key (self, g_value_get_string (value));
-      break;
-
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
     }
@@ -197,16 +190,6 @@ ide_tweaks_combo_class_init (IdeTweaksComboClass *klass)
 
   widget_class->create_for_item = ide_tweaks_combo_create_for_item;
 
-  properties[PROP_SETTINGS] =
-    g_param_spec_object ("settings", NULL, NULL,
-                         IDE_TYPE_TWEAKS_SETTINGS,
-                         (G_PARAM_READWRITE | G_PARAM_EXPLICIT_NOTIFY | G_PARAM_STATIC_STRINGS));
-
-  properties[PROP_KEY] =
-    g_param_spec_string ("key", NULL, NULL,
-                         NULL,
-                         (G_PARAM_READWRITE | G_PARAM_EXPLICIT_NOTIFY | G_PARAM_STATIC_STRINGS));
-
   properties[PROP_TITLE] =
     g_param_spec_string ("title", NULL, NULL,
                          NULL,
@@ -266,48 +249,3 @@ ide_tweaks_combo_set_subtitle (IdeTweaksCombo *self,
   if (ide_set_string (&self->subtitle, subtitle))
     g_object_notify_by_pspec (G_OBJECT (self), properties [PROP_SUBTITLE]);
 }
-
-const char *
-ide_tweaks_combo_get_key (IdeTweaksCombo *self)
-{
-  g_return_val_if_fail (IDE_IS_TWEAKS_COMBO (self), NULL);
-
-  return self->key;
-}
-
-void
-ide_tweaks_combo_set_key (IdeTweaksCombo *self,
-                          const char     *key)
-{
-  g_return_if_fail (IDE_IS_TWEAKS_COMBO (self));
-
-  if (ide_set_string (&self->key, key))
-    g_object_notify_by_pspec (G_OBJECT (self), properties [PROP_KEY]);
-}
-
-/**
- * ide_tweaks_combo_get_settings:
- * @self: a #IdeTweaksCombo
- *
- * Gets the settings for the combo.
- *
- * Returns: (nullable) (transfer none): an #IdeTweaksSettings or %NULL
- */
-IdeTweaksSettings *
-ide_tweaks_combo_get_settings (IdeTweaksCombo *self)
-{
-  g_return_val_if_fail (IDE_IS_TWEAKS_COMBO (self), NULL);
-
-  return self->settings;
-}
-
-void
-ide_tweaks_combo_set_settings (IdeTweaksCombo    *self,
-                               IdeTweaksSettings *settings)
-{
-  g_return_if_fail (IDE_IS_TWEAKS_COMBO (self));
-  g_return_if_fail (!settings || IDE_IS_TWEAKS_SETTINGS (settings));
-
-  if (g_set_object (&self->settings, settings))
-    g_object_notify_by_pspec (G_OBJECT (self), properties [PROP_SETTINGS]);
-}
diff --git a/src/libide/tweaks/ide-tweaks-combo.h b/src/libide/tweaks/ide-tweaks-combo.h
index 925fcdea3..59faeac0d 100644
--- a/src/libide/tweaks/ide-tweaks-combo.h
+++ b/src/libide/tweaks/ide-tweaks-combo.h
@@ -24,7 +24,6 @@
 # error "Only <libide-tweaks.h> can be included directly."
 #endif
 
-#include "ide-tweaks-settings.h"
 #include "ide-tweaks-widget.h"
 
 G_BEGIN_DECLS
@@ -35,26 +34,16 @@ IDE_AVAILABLE_IN_ALL
 G_DECLARE_FINAL_TYPE (IdeTweaksCombo, ide_tweaks_combo, IDE, TWEAKS_COMBO, IdeTweaksWidget)
 
 IDE_AVAILABLE_IN_ALL
-IdeTweaksCombo    *ide_tweaks_combo_new          (void);
+IdeTweaksCombo *ide_tweaks_combo_new          (void);
 IDE_AVAILABLE_IN_ALL
-const char        *ide_tweaks_combo_get_title    (IdeTweaksCombo    *self);
+const char     *ide_tweaks_combo_get_title    (IdeTweaksCombo    *self);
 IDE_AVAILABLE_IN_ALL
-void               ide_tweaks_combo_set_title    (IdeTweaksCombo    *self,
-                                                  const char        *title);
+void            ide_tweaks_combo_set_title    (IdeTweaksCombo    *self,
+                                               const char        *title);
 IDE_AVAILABLE_IN_ALL
-const char        *ide_tweaks_combo_get_subtitle (IdeTweaksCombo    *self);
+const char     *ide_tweaks_combo_get_subtitle (IdeTweaksCombo    *self);
 IDE_AVAILABLE_IN_ALL
-void               ide_tweaks_combo_set_subtitle (IdeTweaksCombo    *self,
-                                                  const char        *subtitle);
-IDE_AVAILABLE_IN_ALL
-const char        *ide_tweaks_combo_get_key      (IdeTweaksCombo    *self);
-IDE_AVAILABLE_IN_ALL
-void               ide_tweaks_combo_set_key      (IdeTweaksCombo    *self,
-                                                  const char        *key);
-IDE_AVAILABLE_IN_ALL
-IdeTweaksSettings *ide_tweaks_combo_get_settings (IdeTweaksCombo    *self);
-IDE_AVAILABLE_IN_ALL
-void               ide_tweaks_combo_set_settings (IdeTweaksCombo    *self,
-                                                  IdeTweaksSettings *setings);
+void            ide_tweaks_combo_set_subtitle (IdeTweaksCombo    *self,
+                                               const char        *subtitle);
 
 G_END_DECLS


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]