[gtk/fix-action-muxer-parent-chain] action muxer: Fix gtk_widget_get_action_group



commit 08f216e11f4098935caaf8f2ed80c6ac0de6bf2a
Author: Matthias Clasen <mclasen redhat com>
Date:   Wed Jun 19 20:59:00 2019 +0000

    action muxer: Fix gtk_widget_get_action_group
    
    The documentation for gtk_widget_get_action_group
    and gtk_widget_list_prefixes states that both of
    these operate on all the action groups that are
    'available' to the widget.
    
    Which means: they are meant to walk up the parent
    muxer chain. So do that.
    
    Add tests to verify the expected behavior.
    
    Closes: https://gitlab.gnome.org/GNOME/gtk/issues/1396

 gtk/gtkactionmuxer.c   |  33 +++++++++++--
 testsuite/gtk/action.c | 122 ++++++++++++++++++++++++++++++++++++++++++++++++-
 2 files changed, 150 insertions(+), 5 deletions(-)
---
diff --git a/gtk/gtkactionmuxer.c b/gtk/gtkactionmuxer.c
index 40fc0c14c9..ee97cd294f 100644
--- a/gtk/gtkactionmuxer.c
+++ b/gtk/gtkactionmuxer.c
@@ -742,10 +742,32 @@ gtk_action_muxer_remove (GtkActionMuxer *muxer,
     }
 }
 
+static void
+gtk_action_muxer_append_prefixes (gpointer key,
+                                  gpointer value,
+                                  gpointer user_data)
+{
+  const gchar *prefix = key;
+  GArray *prefixes= user_data;
+
+  g_array_append_val (prefixes, prefix);
+}
+
 const gchar **
 gtk_action_muxer_list_prefixes (GtkActionMuxer *muxer)
 {
-  return (const gchar **) g_hash_table_get_keys_as_array (muxer->groups, NULL);
+  GArray *prefixes;
+
+  prefixes = g_array_new (TRUE, FALSE, sizeof (gchar *));
+
+  for ( ; muxer != NULL; muxer = muxer->parent)
+    {
+      g_hash_table_foreach (muxer->groups,
+                            gtk_action_muxer_append_prefixes,
+                            prefixes);
+    }
+
+  return (const gchar **)(void *) g_array_free (prefixes, FALSE);
 }
 
 GActionGroup *
@@ -754,10 +776,13 @@ gtk_action_muxer_lookup (GtkActionMuxer *muxer,
 {
   Group *group;
 
-  group = g_hash_table_lookup (muxer->groups, prefix);
+  for ( ; muxer != NULL; muxer = muxer->parent)
+    {
+      group = g_hash_table_lookup (muxer->groups, prefix);
 
-  if (group != NULL)
-    return group->group;
+      if (group != NULL)
+        return group->group;
+    }
 
   return NULL;
 }
diff --git a/testsuite/gtk/action.c b/testsuite/gtk/action.c
index 92a1e08ffe..7ca703bf78 100644
--- a/testsuite/gtk/action.c
+++ b/testsuite/gtk/action.c
@@ -72,6 +72,125 @@ menu_item_label_notify_count (ActionTest    *fixture,
   g_object_unref (item);
 }
 
+static void
+g_test_action_muxer (void)
+{
+  GtkWidget *window;
+  GtkWidget *box;
+  GtkWidget *button;
+  const char **prefixes;
+  const char * const expected[] = { "win", NULL };
+  const char * const expected1[] = { "group1", "win", NULL };
+  const char * const expected2[] = { "group2", "win", NULL };
+  const char * const expected3[] = { "group1", "group2", "win", NULL };
+  GActionGroup *win;
+  GActionGroup *group1;
+  GActionGroup *group2;
+  GActionGroup *grp;
+
+  window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
+  box = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, 0);
+  button = gtk_button_new_with_label ("test");
+
+  gtk_container_add (GTK_CONTAINER (window), box);
+  gtk_container_add (GTK_CONTAINER (box), button);
+
+  win = G_ACTION_GROUP (g_simple_action_group_new ());
+  gtk_widget_insert_action_group (window, "win", win);
+
+  prefixes = gtk_widget_list_action_prefixes (window);
+  g_assert (g_strv_equal ((const char * const *)prefixes, expected));
+  g_free (prefixes);
+
+  prefixes = gtk_widget_list_action_prefixes (box);
+  g_assert (g_strv_equal ((const char * const *)prefixes, expected));
+  g_free (prefixes);
+
+  prefixes = gtk_widget_list_action_prefixes (button);
+  g_assert (g_strv_equal ((const char * const *)prefixes, expected));
+  g_free (prefixes);
+
+  grp = gtk_widget_get_action_group (window, "win");
+  g_assert (grp == win);
+  grp = gtk_widget_get_action_group (window, "bla");
+  g_assert (grp == NULL);
+
+  grp = gtk_widget_get_action_group (box, "win");
+  g_assert (grp == win);
+  grp = gtk_widget_get_action_group (box, "bla");
+  g_assert (grp == NULL);
+
+  grp = gtk_widget_get_action_group (button, "win");
+  g_assert (grp == win);
+  grp = gtk_widget_get_action_group (button, "bla");
+  g_assert (grp == NULL);
+
+  group1 = G_ACTION_GROUP (g_simple_action_group_new ());
+  gtk_widget_insert_action_group (button, "group1", group1);
+
+  prefixes = gtk_widget_list_action_prefixes (window);
+  g_assert (g_strv_equal ((const char * const *)prefixes, expected));
+  g_free (prefixes);
+
+  prefixes = gtk_widget_list_action_prefixes (box);
+  g_assert (g_strv_equal ((const char * const *)prefixes, expected));
+  g_free (prefixes);
+
+  prefixes = gtk_widget_list_action_prefixes (button);
+  g_assert (g_strv_equal ((const char * const *)prefixes, expected1));
+  g_free (prefixes);
+
+  grp = gtk_widget_get_action_group (window, "win");
+  g_assert (grp == win);
+  grp = gtk_widget_get_action_group (window, "group1");
+  g_assert (grp == NULL);
+
+  grp = gtk_widget_get_action_group (box, "win");
+  g_assert (grp == win);
+  grp = gtk_widget_get_action_group (box, "group1");
+  g_assert (grp == NULL);
+
+  grp = gtk_widget_get_action_group (button, "win");
+  g_assert (grp == win);
+  grp = gtk_widget_get_action_group (button, "group1");
+  g_assert (grp == group1);
+
+  group2 = G_ACTION_GROUP (g_simple_action_group_new ());
+  gtk_widget_insert_action_group (box, "group2", group2);
+
+  prefixes = gtk_widget_list_action_prefixes (window);
+  g_assert (g_strv_equal ((const char * const *)prefixes, expected));
+  g_free (prefixes);
+
+  prefixes = gtk_widget_list_action_prefixes (box);
+  g_assert (g_strv_equal ((const char * const *)prefixes, expected2));
+  g_free (prefixes);
+
+  prefixes = gtk_widget_list_action_prefixes (button);
+  g_assert (g_strv_equal ((const char * const *)prefixes, expected3));
+  g_free (prefixes);
+
+  grp = gtk_widget_get_action_group (window, "win");
+  g_assert (grp == win);
+  grp = gtk_widget_get_action_group (window, "group2");
+  g_assert (grp == NULL);
+
+  grp = gtk_widget_get_action_group (box, "win");
+  g_assert (grp == win);
+  grp = gtk_widget_get_action_group (box, "group2");
+  g_assert (grp == group2);
+
+  grp = gtk_widget_get_action_group (button, "win");
+  g_assert (grp == win);
+  grp = gtk_widget_get_action_group (button, "group2");
+  g_assert (grp == group2);
+
+  gtk_widget_destroy (window);
+  g_object_unref (win);
+  g_object_unref (group1);
+  g_object_unref (group2);
+}
+
 /* main */
 
 int
@@ -86,6 +205,7 @@ main (int    argc,
               menu_item_label_notify_count,
               action_test_teardown);
 
+  g_test_add_func ("/action/muxer/update-parent", g_test_action_muxer);
+
   return g_test_run ();
 }
-


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