From 25fa4a2929b66746dccab74b6880e750b93a6113 Mon Sep 17 00:00:00 2001 From: Matthias Clasen Date: Tue, 16 Nov 2004 05:30:37 +0000 Subject: [PATCH] Don't use one signal handler per instance to track changes to the * gtk/gtkbutton.c: * gtk/gtkimagemenuitem.c: Don't use one signal handler per instance to track changes to the gtk-menu-images and gtk-button-images settings. Instead use a single handler which iterates over the widget hierarchy. (#143668) --- ChangeLog | 8 ++++ ChangeLog.pre-2-10 | 8 ++++ ChangeLog.pre-2-6 | 8 ++++ ChangeLog.pre-2-8 | 8 ++++ gtk/gtkbutton.c | 73 ++++++++++++++++++++------------- gtk/gtkimagemenuitem.c | 92 ++++++++++++++++++++++++------------------ 6 files changed, 131 insertions(+), 66 deletions(-) diff --git a/ChangeLog b/ChangeLog index 5caca4b508..1be33dc6cd 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,11 @@ +2004-11-15 Matthias Clasen + + * gtk/gtkbutton.c: + * gtk/gtkimagemenuitem.c: Don't use one signal handler per + instance to track changes to the gtk-menu-images and + gtk-button-images settings. Instead use a single handler which + iterates over the widget hierarchy. (#143668) + Mon Nov 15 14:25:21 2004 Jonathan Blandford * gtk/gtktreeviewcolumn.c (_gtk_tree_view_column_cell_set_dirty): diff --git a/ChangeLog.pre-2-10 b/ChangeLog.pre-2-10 index 5caca4b508..1be33dc6cd 100644 --- a/ChangeLog.pre-2-10 +++ b/ChangeLog.pre-2-10 @@ -1,3 +1,11 @@ +2004-11-15 Matthias Clasen + + * gtk/gtkbutton.c: + * gtk/gtkimagemenuitem.c: Don't use one signal handler per + instance to track changes to the gtk-menu-images and + gtk-button-images settings. Instead use a single handler which + iterates over the widget hierarchy. (#143668) + Mon Nov 15 14:25:21 2004 Jonathan Blandford * gtk/gtktreeviewcolumn.c (_gtk_tree_view_column_cell_set_dirty): diff --git a/ChangeLog.pre-2-6 b/ChangeLog.pre-2-6 index 5caca4b508..1be33dc6cd 100644 --- a/ChangeLog.pre-2-6 +++ b/ChangeLog.pre-2-6 @@ -1,3 +1,11 @@ +2004-11-15 Matthias Clasen + + * gtk/gtkbutton.c: + * gtk/gtkimagemenuitem.c: Don't use one signal handler per + instance to track changes to the gtk-menu-images and + gtk-button-images settings. Instead use a single handler which + iterates over the widget hierarchy. (#143668) + Mon Nov 15 14:25:21 2004 Jonathan Blandford * gtk/gtktreeviewcolumn.c (_gtk_tree_view_column_cell_set_dirty): diff --git a/ChangeLog.pre-2-8 b/ChangeLog.pre-2-8 index 5caca4b508..1be33dc6cd 100644 --- a/ChangeLog.pre-2-8 +++ b/ChangeLog.pre-2-8 @@ -1,3 +1,11 @@ +2004-11-15 Matthias Clasen + + * gtk/gtkbutton.c: + * gtk/gtkimagemenuitem.c: Don't use one signal handler per + instance to track changes to the gtk-menu-images and + gtk-button-images settings. Instead use a single handler which + iterates over the widget hierarchy. (#143668) + Mon Nov 15 14:25:21 2004 Jonathan Blandford * gtk/gtktreeviewcolumn.c (_gtk_tree_view_column_cell_set_dirty): diff --git a/gtk/gtkbutton.c b/gtk/gtkbutton.c index da21b7dbec..5c65430d4f 100644 --- a/gtk/gtkbutton.c +++ b/gtk/gtkbutton.c @@ -75,8 +75,6 @@ struct _GtkButtonPrivate { gfloat xalign; gfloat yalign; - GtkSettings *settings; - guint show_image_connection; GtkWidget *image; guint align_set : 1; }; @@ -1578,43 +1576,64 @@ show_image_change_notify (GtkButton *button) GtkButtonPrivate *priv = GTK_BUTTON_GET_PRIVATE (button); if (priv->image) - g_object_set (priv->image, "visible", show_image (button), NULL); + { + if (show_image (button)) + gtk_widget_show (priv->image); + else + gtk_widget_hide (priv->image); + } } +static void +traverse_container (GtkWidget *widget, + gpointer data) +{ + if (GTK_IS_BUTTON (widget)) + show_image_change_notify (GTK_BUTTON (widget)); + else if (GTK_IS_CONTAINER (widget)) + gtk_container_forall (GTK_CONTAINER (widget), traverse_container, NULL); +} + +static void +gtk_button_setting_changed (GtkSettings *settings) +{ + GList *list, *l; + + list = gtk_window_list_toplevels (); + + for (l = list; l; l = l->next) + gtk_container_forall (GTK_CONTAINER (l->data), + traverse_container, NULL); + + g_list_free (list); +} + + static void gtk_button_screen_changed (GtkWidget *widget, GdkScreen *previous_screen) { - GtkButtonPrivate *priv = GTK_BUTTON_GET_PRIVATE (widget); GtkSettings *settings; + guint show_image_connection; - if (gtk_widget_has_screen (widget)) - settings = gtk_widget_get_settings (widget); - else - settings = NULL; - - if (settings == priv->settings) + if (!gtk_widget_has_screen (widget)) return; - if (priv->settings) - { - g_signal_handler_disconnect (priv->settings, priv->show_image_connection); - g_object_unref (priv->settings); - } + settings = gtk_widget_get_settings (widget); - if (settings) - { - priv->show_image_connection = - g_signal_connect_swapped (settings, - "notify::gtk-button-images", - G_CALLBACK (show_image_change_notify), - widget); + show_image_connection = + GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (settings), + "gtk-button-connection")); + + if (show_image_connection) + return; - g_object_ref (settings); - priv->settings = settings; - } - else - priv->settings = NULL; + show_image_connection = + g_signal_connect (settings, "notify::gtk-button-images", + G_CALLBACK (gtk_button_setting_changed), 0); + g_object_set_data (G_OBJECT (settings), + "gtk-button-connection", + GUINT_TO_POINTER (show_image_connection)); show_image_change_notify (GTK_BUTTON (widget)); } diff --git a/gtk/gtkimagemenuitem.c b/gtk/gtkimagemenuitem.c index f9b2710e6a..eee2c326a5 100644 --- a/gtk/gtkimagemenuitem.c +++ b/gtk/gtkimagemenuitem.c @@ -31,16 +31,8 @@ #include "gtkstock.h" #include "gtkiconfactory.h" #include "gtkimage.h" - -typedef struct _GtkImageMenuItemPrivate GtkImageMenuItemPrivate; - -struct _GtkImageMenuItemPrivate -{ - GtkSettings *settings; - guint show_image_connection; -}; - -#define GTK_IMAGE_MENU_ITEM_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), GTK_TYPE_IMAGE_MENU_ITEM, GtkImageMenuItemPrivate)) +#include "gtkcontainer.h" +#include "gtkwindow.h" static void gtk_image_menu_item_class_init (GtkImageMenuItemClass *klass); static void gtk_image_menu_item_init (GtkImageMenuItem *image_menu_item); @@ -145,8 +137,7 @@ gtk_image_menu_item_class_init (GtkImageMenuItemClass *klass) P_("Whether images should be shown in menus"), TRUE, G_PARAM_READWRITE)); - - g_type_class_add_private (gobject_class, sizeof (GtkImageMenuItemPrivate)); + } static void @@ -475,6 +466,8 @@ gtk_image_menu_item_new_from_stock (const gchar *stock_id, * @image: a widget to set as the image for the menu item. * * Sets the image of @image_menu_item to the given widget. + * Note that it depends on the show-menu-images setting whether + * the image will be displayed or not. **/ void gtk_image_menu_item_set_image (GtkImageMenuItem *image_menu_item, @@ -550,44 +543,65 @@ gtk_image_menu_item_remove (GtkContainer *container, static void show_image_change_notify (GtkImageMenuItem *image_menu_item) { - if (image_menu_item->image) - g_object_set (image_menu_item->image, "visible", show_image (image_menu_item), NULL); + if (image_menu_item->image) + { + if (show_image (image_menu_item)) + gtk_widget_show (image_menu_item->image); + else + gtk_widget_hide (image_menu_item->image); + } +} + +static void +traverse_container (GtkWidget *widget, + gpointer data) +{ + if (GTK_IS_IMAGE_MENU_ITEM (widget)) + show_image_change_notify (GTK_IMAGE_MENU_ITEM (widget)); + else if (GTK_IS_CONTAINER (widget)) + gtk_container_forall (GTK_CONTAINER (widget), traverse_container, NULL); +} + +static void +gtk_image_menu_item_setting_changed (GtkSettings *settings) +{ + GList *list, *l; + + list = gtk_window_list_toplevels (); + + for (l = list; l; l = l->next) + gtk_container_forall (GTK_CONTAINER (l->data), + traverse_container, NULL); + + g_list_free (list); } static void gtk_image_menu_item_screen_changed (GtkWidget *widget, GdkScreen *previous_screen) { - GtkImageMenuItemPrivate *priv = GTK_IMAGE_MENU_ITEM_GET_PRIVATE (widget); GtkSettings *settings; + guint show_image_connection; - if (gtk_widget_has_screen (widget)) - settings = gtk_widget_get_settings (widget); - else - settings = NULL; - - if (settings == priv->settings) + if (!gtk_widget_has_screen (widget)) return; - if (priv->settings) - { - g_signal_handler_disconnect (priv->settings, priv->show_image_connection); - g_object_unref (priv->settings); - } + settings = gtk_widget_get_settings (widget); + + show_image_connection = + GPOINTER_TO_UINT (g_object_get_data (G_OBJECT (settings), + "gtk-image-menu-item-connection")); + + if (show_image_connection) + return; - if (settings) - { - priv->show_image_connection = - g_signal_connect_swapped (settings, - "notify::gtk-menu-images", - G_CALLBACK (show_image_change_notify), - widget); - - g_object_ref (settings); - priv->settings = settings; - } - else - priv->settings = NULL; + show_image_connection = + g_signal_connect (settings, "notify::gtk-menu-images", + G_CALLBACK (gtk_image_menu_item_setting_changed), 0); + g_object_set_data (G_OBJECT (settings), + "gtk-image-menu-item-connection", + GUINT_TO_POINTER (show_image_connection)); show_image_change_notify (GTK_IMAGE_MENU_ITEM (widget)); } +