diff --git a/demos/constraint-editor/constraint-editor-window.c b/demos/constraint-editor/constraint-editor-window.c index ca18e27cf8e9e771710eb8604fc05d9b617ecc16..fc4741318750bdb4ccb621e264ad65792c30fb46 100644 --- a/demos/constraint-editor/constraint-editor-window.c +++ b/demos/constraint-editor/constraint-editor-window.c @@ -361,11 +361,11 @@ save_cb (GtkWidget *button, } static void -constraint_editor_window_finalize (GObject *object) +constraint_editor_window_dispose (GObject *object) { - //ConstraintEditorWindow *self = (ConstraintEditorWindow *)object; + gtk_widget_dispose_template (GTK_WIDGET (object), CONSTRAINT_EDITOR_WINDOW_TYPE); - G_OBJECT_CLASS (constraint_editor_window_parent_class)->finalize (object); + G_OBJECT_CLASS (constraint_editor_window_parent_class)->dispose (object); } static int child_counter; @@ -497,7 +497,7 @@ constraint_editor_window_class_init (ConstraintEditorWindowClass *class) GObjectClass *object_class = G_OBJECT_CLASS (class); GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (class); - object_class->finalize = constraint_editor_window_finalize; + object_class->dispose = constraint_editor_window_dispose; gtk_widget_class_set_template_from_resource (widget_class, "/org/gtk/gtk4/constraint-editor/constraint-editor-window.ui"); diff --git a/demos/constraint-editor/constraint-editor.c b/demos/constraint-editor/constraint-editor.c index 6f897b2d8a031ee0a7e6fc851fd2662bb5a9f0b3..3e77eca1d4a6c773c61d4514b073622c91272044 100644 --- a/demos/constraint-editor/constraint-editor.c +++ b/demos/constraint-editor/constraint-editor.c @@ -607,10 +607,11 @@ constraint_editor_dispose (GObject *object) { ConstraintEditor *self = (ConstraintEditor *)object; - g_clear_pointer (&self->grid, gtk_widget_unparent); g_clear_object (&self->model); g_clear_object (&self->constraint); + gtk_widget_dispose_template (GTK_WIDGET (object), CONSTRAINT_EDITOR_TYPE); + G_OBJECT_CLASS (constraint_editor_parent_class)->dispose (object); } diff --git a/demos/constraint-editor/guide-editor.c b/demos/constraint-editor/guide-editor.c index 74dfe22f09614ff26aed92244421790b47082287..6e8e2ac5acc6a48ed7d69a02f4b92cfe219d2cc1 100644 --- a/demos/constraint-editor/guide-editor.c +++ b/demos/constraint-editor/guide-editor.c @@ -294,9 +294,10 @@ guide_editor_dispose (GObject *object) { GuideEditor *self = (GuideEditor *)object; - g_clear_pointer (&self->grid, gtk_widget_unparent); g_clear_object (&self->guide); + gtk_widget_dispose_template (GTK_WIDGET (self), GUIDE_EDITOR_TYPE); + G_OBJECT_CLASS (guide_editor_parent_class)->dispose (object); } diff --git a/demos/gtk-demo/application.c b/demos/gtk-demo/application.c index f1bca0523d509651bfb43f48f5281099ef597538..a3e29bfb1c14999b1173250c0cb4009575d753bc 100644 --- a/demos/gtk-demo/application.c +++ b/demos/gtk-demo/application.c @@ -504,6 +504,8 @@ demo_application_window_dispose (GObject *object) demo_application_window_store_state (window); + gtk_widget_dispose_template (GTK_WIDGET (window), demo_application_window_get_type ()); + G_OBJECT_CLASS (demo_application_window_parent_class)->dispose (object); } diff --git a/demos/gtk-demo/demo3widget.c b/demos/gtk-demo/demo3widget.c index 7a13f698c4987e326414c2e167dee68907927138..9f8d943d14f005437906803e462a6f8dcbf03a8b 100644 --- a/demos/gtk-demo/demo3widget.c +++ b/demos/gtk-demo/demo3widget.c @@ -37,7 +37,8 @@ demo3_widget_dispose (GObject *object) Demo3Widget *self = DEMO3_WIDGET (object); g_clear_object (&self->paintable); - g_clear_pointer (&self->menu, gtk_widget_unparent); + + gtk_widget_dispose_template (GTK_WIDGET (self), DEMO3_TYPE_WIDGET); G_OBJECT_CLASS (demo3_widget_parent_class)->dispose (object); } diff --git a/demos/gtk-demo/listbox.c b/demos/gtk-demo/listbox.c index 98a6a26611434f4500dab304e216a566a350d921..49bd2135ae0b42bf61e936df6a72715beef48ac7 100644 --- a/demos/gtk-demo/listbox.c +++ b/demos/gtk-demo/listbox.c @@ -260,12 +260,19 @@ gtk_message_row_state_flags_changed (GtkWidget *widget, GTK_WIDGET_CLASS (gtk_message_row_parent_class)->state_flags_changed (widget, previous_state_flags); } +static void +gtk_message_row_dispose (GObject *obj) +{ + gtk_widget_dispose_template (GTK_WIDGET (obj), GTK_TYPE_MESSAGE_ROW); + G_OBJECT_CLASS (gtk_message_row_parent_class)->dispose (obj); +} + static void gtk_message_row_finalize (GObject *obj) { GtkMessageRowPrivate *priv = GTK_MESSAGE_ROW (obj)->priv; g_object_unref (priv->message); - G_OBJECT_CLASS (gtk_message_row_parent_class)->finalize(obj); + G_OBJECT_CLASS (gtk_message_row_parent_class)->finalize (obj); } static void @@ -274,6 +281,7 @@ gtk_message_row_class_init (GtkMessageRowClass *klass) GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (klass); GObjectClass *object_class = G_OBJECT_CLASS (klass); + object_class->dispose = gtk_message_row_dispose; object_class->finalize = gtk_message_row_finalize; gtk_widget_class_set_template_from_resource (widget_class, "/listbox/listbox.ui"); diff --git a/demos/icon-browser/iconbrowserwin.c b/demos/icon-browser/iconbrowserwin.c index 4dbc0540578c40f93d086fddcc56cbd015ed8ebd..d0da5c464c5c320b0d8c17a47f5494e642a5cadd 100644 --- a/demos/icon-browser/iconbrowserwin.c +++ b/demos/icon-browser/iconbrowserwin.c @@ -409,6 +409,14 @@ icon_browser_window_init (IconBrowserWindow *win) g_signal_connect (win->context_model, "notify::selected", G_CALLBACK (selected_name_changed), win); } +static void +icon_browser_window_dispose (GObject *object) +{ + gtk_widget_dispose_template (GTK_WIDGET (object), ICON_BROWSER_WINDOW_TYPE); + + G_OBJECT_CLASS (icon_browser_window_parent_class)->dispose (object); +} + static void icon_browser_window_finalize (GObject *object) { @@ -424,6 +432,7 @@ icon_browser_window_class_init (IconBrowserWindowClass *class) { GObjectClass *object_class = G_OBJECT_CLASS (class); + object_class->dispose = icon_browser_window_dispose; object_class->finalize = icon_browser_window_finalize; g_type_ensure (IB_TYPE_ICON); diff --git a/demos/node-editor/node-editor-window.c b/demos/node-editor/node-editor-window.c index 68f261183ac320f23efab3a18e30a44bcb975ae5..25cf11b48d74079c73cdfbc90c00b02c5ab806d2 100644 --- a/demos/node-editor/node-editor-window.c +++ b/demos/node-editor/node-editor-window.c @@ -873,6 +873,14 @@ dark_mode_cb (GtkToggleButton *button, NULL); } +static void +node_editor_window_dispose (GObject *object) +{ + gtk_widget_dispose_template (GTK_WIDGET (object), NODE_EDITOR_WINDOW_TYPE); + + G_OBJECT_CLASS (node_editor_window_parent_class)->dispose (object); +} + static void node_editor_window_finalize (GObject *object) { @@ -967,6 +975,7 @@ node_editor_window_class_init (NodeEditorWindowClass *class) GObjectClass *object_class = G_OBJECT_CLASS (class); GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (class); + object_class->dispose = node_editor_window_dispose; object_class->finalize = node_editor_window_finalize; gtk_widget_class_set_template_from_resource (widget_class, diff --git a/gtk/gtkemojichooser.c b/gtk/gtkemojichooser.c index 810072c1460c38e03126af0cc0180570b597e94f..adeb485c6c66039fd7233d022eb193b79afaf550 100644 --- a/gtk/gtkemojichooser.c +++ b/gtk/gtkemojichooser.c @@ -249,6 +249,14 @@ gtk_emoji_chooser_finalize (GObject *object) G_OBJECT_CLASS (gtk_emoji_chooser_parent_class)->finalize (object); } +static void +gtk_emoji_chooser_dispose (GObject *object) +{ + gtk_widget_dispose_template (GTK_WIDGET (object), GTK_TYPE_EMOJI_CHOOSER); + + G_OBJECT_CLASS (gtk_emoji_chooser_parent_class)->dispose (object); +} + static void scroll_to_section (EmojiSection *section) { @@ -866,7 +874,7 @@ filter_func (GtkFlowBoxChild *child, goto out; term_tokens = g_str_tokenize_and_fold (text, "en", NULL); - + g_variant_get_child (emoji_data, 1, "&s", &name); name_tokens = g_str_tokenize_and_fold (name, "en", NULL); g_variant_get_child (emoji_data, 2, "^a&s", &keywords); @@ -1203,6 +1211,7 @@ gtk_emoji_chooser_class_init (GtkEmojiChooserClass *klass) GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (klass); object_class->finalize = gtk_emoji_chooser_finalize; + object_class->dispose = gtk_emoji_chooser_dispose; widget_class->show = gtk_emoji_chooser_show; widget_class->map = gtk_emoji_chooser_map; @@ -1278,7 +1287,7 @@ gtk_emoji_chooser_class_init (GtkEmojiChooserClass *klass) * @direction: 1 to scroll forward, -1 to scroll back * * Scrolls to the next or previous section. - */ + */ gtk_widget_class_install_action (widget_class, "scroll.section", "i", gtk_emoji_chooser_scroll_section); diff --git a/gtk/gtkfilechooserdialog.c b/gtk/gtkfilechooserdialog.c index 754aebc6503e2ab305296e76cf9b9049ec25886c..56b070a65a187c3b31c31a1d3f389e69641e9931 100644 --- a/gtk/gtkfilechooserdialog.c +++ b/gtk/gtkfilechooserdialog.c @@ -380,9 +380,7 @@ gtk_file_chooser_dialog_activate_response (GtkWidget *widget, static void gtk_file_chooser_dialog_dispose (GObject *object) { - GtkFileChooserDialogPrivate *priv = gtk_file_chooser_dialog_get_instance_private (GTK_FILE_CHOOSER_DIALOG (object)); - - g_clear_pointer ((GtkWidget **)&priv->widget, gtk_widget_unparent); + gtk_widget_dispose_template (GTK_WIDGET (object), GTK_TYPE_FILE_CHOOSER_DIALOG); G_OBJECT_CLASS (gtk_file_chooser_dialog_parent_class)->dispose (object); } diff --git a/gtk/gtkfilechooserwidget.c b/gtk/gtkfilechooserwidget.c index 6e212f5ab277ffcae23d0bc706f1b85e32ac09b3..da11ae735bf9cbebad6b0a251fa4b1161c1d29a9 100644 --- a/gtk/gtkfilechooserwidget.c +++ b/gtk/gtkfilechooserwidget.c @@ -515,7 +515,7 @@ static GSList *get_selected_infos (GtkFileChooserWidget *impl); static void search_setup_widgets (GtkFileChooserWidget *impl); static void search_stop_searching (GtkFileChooserWidget *impl, gboolean remove_query); -static void search_clear_model (GtkFileChooserWidget *impl, +static void search_clear_model (GtkFileChooserWidget *impl, gboolean remove_from_treeview); static void search_entry_activate_cb (GtkFileChooserWidget *impl); static void search_entry_stop_cb (GtkFileChooserWidget *impl); @@ -720,8 +720,8 @@ error_creating_folder_dialog (GtkFileChooserWidget *impl, GFile *file, GError *error) { - error_dialog (impl, - _("The folder could not be created"), + error_dialog (impl, + _("The folder could not be created"), error); } @@ -3122,10 +3122,11 @@ gtk_file_chooser_widget_dispose (GObject *object) GtkFileChooserWidget *impl = (GtkFileChooserWidget *) object; cancel_all_operations (impl); - g_clear_pointer (&impl->rename_file_popover, gtk_widget_unparent); + + /* browse_files_popover is not a template child */ g_clear_pointer (&impl->browse_files_popover, gtk_widget_unparent); - g_clear_object (&impl->extra_widget); g_clear_pointer (&impl->bookmarks_manager, _gtk_bookmarks_manager_free); + g_clear_object (&impl->extra_widget); if (impl->external_entry && impl->location_entry == impl->external_entry) { @@ -3133,9 +3134,10 @@ gtk_file_chooser_widget_dispose (GObject *object) location_entry_disconnect (impl); impl->external_entry = NULL; } + remove_settings_signal (impl); - g_clear_pointer (&impl->box, gtk_widget_unparent); + gtk_widget_dispose_template (GTK_WIDGET (impl), GTK_TYPE_FILE_CHOOSER_WIDGET); G_OBJECT_CLASS (gtk_file_chooser_widget_parent_class)->dispose (object); } @@ -6258,7 +6260,7 @@ gtk_file_chooser_widget_should_respond (GtkFileChooserWidget *impl) case SAVE_ENTRY: goto save_entry; - case NOT_REACHED: + case NOT_REACHED: default: g_assert_not_reached (); } diff --git a/gtk/gtkfontchooserdialog.c b/gtk/gtkfontchooserdialog.c index e731df8e45e4ccb4ebed99ed7e07f71740cdd640..5aeddd20c48538560fa8cc322b46ca0a9f1bd795 100644 --- a/gtk/gtkfontchooserdialog.c +++ b/gtk/gtkfontchooserdialog.c @@ -229,10 +229,10 @@ gtk_font_chooser_dialog_dispose (GObject *object) dialog); } - g_clear_pointer (&dialog->select_button, gtk_widget_unparent); - g_clear_pointer (&dialog->cancel_button, gtk_widget_unparent); + /* tweak_button is not a template child */ g_clear_pointer (&dialog->tweak_button, gtk_widget_unparent); - g_clear_pointer (&dialog->fontchooser, gtk_widget_unparent); + + gtk_widget_dispose_template (GTK_WIDGET (dialog), GTK_TYPE_FONT_CHOOSER_DIALOG); G_OBJECT_CLASS (gtk_font_chooser_dialog_parent_class)->dispose (object); } diff --git a/gtk/gtkmediacontrols.c b/gtk/gtkmediacontrols.c index 4c175737eb2978e785939fbf63e65b847a267cba..4dc8888e15f9233e49513416dec82fd8bccffd4f 100644 --- a/gtk/gtkmediacontrols.c +++ b/gtk/gtkmediacontrols.c @@ -138,7 +138,7 @@ time_adjustment_changed (GtkAdjustment *adjustment, if (gtk_adjustment_get_value (adjustment) == (double) gtk_media_stream_get_timestamp (controls->stream) / G_USEC_PER_SEC) return; - gtk_media_stream_seek (controls->stream, + gtk_media_stream_seek (controls->stream, gtk_adjustment_get_value (adjustment) * G_USEC_PER_SEC + 0.5); } @@ -208,7 +208,7 @@ gtk_media_controls_dispose (GObject *object) gtk_media_controls_set_media_stream (controls, NULL); - g_clear_pointer (&controls->box, gtk_widget_unparent); + gtk_widget_dispose_template (GTK_WIDGET (object), GTK_TYPE_MEDIA_CONTROLS); G_OBJECT_CLASS (gtk_media_controls_parent_class)->dispose (object); } diff --git a/gtk/gtkstatusbar.c b/gtk/gtkstatusbar.c index 02c0c1369db1fadf2716659007b3ef9e3c35b457..70afc1bdf4e72048f2b0db06fba2809d88368e12 100644 --- a/gtk/gtkstatusbar.c +++ b/gtk/gtkstatusbar.c @@ -143,7 +143,7 @@ gtk_statusbar_dispose (GObject *object) g_slist_free_full (self->keys, g_free); self->keys = NULL; - g_clear_pointer (&self->message_area, gtk_widget_unparent); + gtk_widget_dispose_template (GTK_WIDGET (self), GTK_TYPE_STATUSBAR); G_OBJECT_CLASS (gtk_statusbar_parent_class)->dispose (object); } @@ -225,7 +225,7 @@ gtk_statusbar_init (GtkStatusbar *statusbar) * * Returns: the new `GtkStatusbar` */ -GtkWidget* +GtkWidget* gtk_statusbar_new (void) { return g_object_new (GTK_TYPE_STATUSBAR, NULL); @@ -263,7 +263,7 @@ gtk_statusbar_get_context_id (GtkStatusbar *statusbar, { char *string; guint id; - + g_return_val_if_fail (GTK_IS_STATUSBAR (statusbar), 0); g_return_val_if_fail (context_description != NULL, 0); @@ -417,18 +417,18 @@ gtk_statusbar_remove (GtkStatusbar *statusbar, gtk_statusbar_pop (statusbar, context_id); return; } - + for (list = statusbar->messages; list; list = list->next) { msg = list->data; - + if (msg->context_id == context_id && msg->message_id == message_id) { statusbar->messages = g_slist_remove_link (statusbar->messages, list); gtk_statusbar_msg_free (msg); g_slist_free_1 (list); - + break; } } diff --git a/gtk/gtkwidget.c b/gtk/gtkwidget.c index 3d1a46897d81c6df867f43579a3c2d5277f1e8fa..360d8412a8cbc3691f96b1affcf5e708565909f7 100644 --- a/gtk/gtkwidget.c +++ b/gtk/gtkwidget.c @@ -386,11 +386,29 @@ * static void * foo_widget_init (FooWidget *self) * { - * // ... * gtk_widget_init_template (GTK_WIDGET (self)); + * + * // Initialize the rest of the widget... * } * ``` * + * as well as calling [method@Gtk.Widget.dispose_template] from the dispose + * function: + * + * ```c + * static void + * foo_widget_dispose (GObject *gobject) + * { + * FooWidget *self = FOO_WIDGET (gobject); + * + * // Dispose objects for which you have a reference... + * + * // Clear the template children for this widget type + * gtk_widget_dispose_template (GTK_WIDGET (self), FOO_TYPE_WIDGET); + * + * G_OBJECT_CLASS (foo_widget_parent_class)->dispose (gobject); + * } + * * You can access widgets defined in the template using the * [id@gtk_widget_get_template_child] function, but you will typically declare * a pointer in the instance private data structure of your type using the same @@ -408,9 +426,19 @@ * G_DEFINE_TYPE_WITH_PRIVATE (FooWidget, foo_widget, GTK_TYPE_BOX) * * static void + * foo_widget_dispose (GObject *gobject) + * { + * gtk_widget_dispose_template (GTK_WIDGET (gobject), FOO_TYPE_WIDGET); + * + * G_OBJECT_CLASS (foo_widget_parent_class)->dispose (gobject); + * } + * + * static void * foo_widget_class_init (FooWidgetClass *klass) * { * // ... + * G_OBJECT_CLASS (klass)->dispose = foo_widget_dispose; + * * gtk_widget_class_set_template_from_resource (GTK_WIDGET_CLASS (klass), * "/com/example/ui/foowidget.ui"); * gtk_widget_class_bind_template_child_private (GTK_WIDGET_CLASS (klass), @@ -422,7 +450,7 @@ * static void * foo_widget_init (FooWidget *widget) * { - * + * gtk_widget_init_template (GTK_WIDGET (widget)); * } * ``` * @@ -7437,16 +7465,7 @@ gtk_widget_real_destroy (GtkWidget *object) GObject *child_object = gtk_widget_get_template_child (widget, class_type, child_class->name); - - g_assert (child_object); - - if (!G_IS_OBJECT (child_object)) - { - g_critical ("Automated component '%s' of class '%s' seems to" - " have been prematurely finalized", - child_class->name, g_type_name (class_type)); - } - else + if (G_IS_OBJECT (child_object)) { FinalizeAssertion *assertion = g_slice_new0 (FinalizeAssertion); assertion->child_class = child_class; @@ -10978,6 +10997,81 @@ out: g_object_unref (builder); } +/** + * gtk_widget_dispose_template: + * @widget: the widget with a template + * @widget_type: the type of the widget to finalize the template for + * + * Clears the template children for the given widget. + * + * This function is the opposite of [method@Gtk.Widget.init_template], and + * it is used to clear all the template children from a widget instance. + * If you bound a template child to a field in the instance structure, or + * in the instance private data structure, the field will be set to `NULL` + * after this function returns. + * + * You should call this function inside the `GObjectClass.dispose()` + * implementation of any widget that called `gtk_widget_init_template()`. + * Typically, you will want to call this function last, right before + * chaining up to the parent type's dispose implementation, e.g. + * + * ```c + * static void + * some_widget_dispose (GObject *gobject) + * { + * SomeWidget *self = SOME_WIDGET (gobject); + * + * // Clear the template data for SomeWidget + * gtk_widget_dispose_template (GTK_WIDGET (self), SOME_TYPE_WIDGET); + * + * G_OBJECT_CLASS (some_widget_parent_class)->dispose (gobject); + * } + * ``` + * + * Since: 4.8 + */ +void +gtk_widget_dispose_template (GtkWidget *widget, + GType widget_type) +{ + g_return_if_fail (GTK_IS_WIDGET (widget)); + g_return_if_fail (g_type_name (widget_type) != NULL); + + GtkWidgetTemplate *template = GTK_WIDGET_GET_CLASS (widget)->priv->template; + g_return_if_fail (template != NULL); + + /* Tear down the automatic child data */ + GHashTable *auto_child_hash = get_auto_child_hash (widget, widget_type, FALSE); + + for (GSList *l = template->children; l != NULL; l = l->next) + { + AutomaticChildClass *child_class = l->data; + + /* This will drop the reference on the template children */ + if (auto_child_hash != NULL) + { + gpointer child = g_hash_table_lookup (auto_child_hash, child_class->name); + + g_assert (child != NULL); + + /* We have to explicitly unparent direct children of this widget */ + if (GTK_IS_WIDGET (child) && _gtk_widget_get_parent (child) == widget) + gtk_widget_unparent (child); + + g_hash_table_remove (auto_child_hash, child_class->name); + } + + /* Nullify the field last, to avoid re-entrancy issues */ + if (child_class->offset != 0) + { + gpointer field_p; + + field_p = G_STRUCT_MEMBER_P (widget, child_class->offset); + (* (gpointer *) field_p) = NULL; + } + } +} + /** * gtk_widget_class_set_template: * @widget_class: A `GtkWidgetClass` diff --git a/gtk/gtkwidget.h b/gtk/gtkwidget.h index 0788fcdd8179a9a78c3b599bee1eb9c481be5173..8720017baddbebbbe981b0116557a173aad6e65a 100644 --- a/gtk/gtkwidget.h +++ b/gtk/gtkwidget.h @@ -833,6 +833,9 @@ GDK_AVAILABLE_IN_ALL GObject *gtk_widget_get_template_child (GtkWidget *widget, GType widget_type, const char *name); +GDK_AVAILABLE_IN_4_8 +void gtk_widget_dispose_template (GtkWidget *widget, + GType widget_type); GDK_AVAILABLE_IN_ALL void gtk_widget_class_set_template (GtkWidgetClass *widget_class, GBytes *template_bytes); diff --git a/gtk/inspector/a11y.c b/gtk/inspector/a11y.c index f4b1bdafcae8e87b9325f6ac63968f3edf84cbe3..9a9140e183cf69dacf6260d4b758f91c594fae6e 100644 --- a/gtk/inspector/a11y.c +++ b/gtk/inspector/a11y.c @@ -462,7 +462,7 @@ dispose (GObject *o) g_clear_object (&sl->object); - g_clear_pointer (&sl->box, gtk_widget_unparent); + gtk_widget_dispose_template (GTK_WIDGET (o), GTK_TYPE_INSPECTOR_A11Y); G_OBJECT_CLASS (gtk_inspector_a11y_parent_class)->dispose (o); } diff --git a/gtk/inspector/actions.c b/gtk/inspector/actions.c index 1f8a46ca5ae5ef9cae91a976fd4649b8079c6420..24afc478567c018171a31ef17d9e89342e0482cd 100644 --- a/gtk/inspector/actions.c +++ b/gtk/inspector/actions.c @@ -420,14 +420,12 @@ static void dispose (GObject *object) { GtkInspectorActions *sl = GTK_INSPECTOR_ACTIONS (object); - GtkWidget *child; g_clear_object (&sl->sorted); g_clear_object (&sl->actions); g_clear_object (&sl->object); - while ((child = gtk_widget_get_first_child (GTK_WIDGET (sl)))) - gtk_widget_unparent (child); + gtk_widget_dispose_template (GTK_WIDGET (sl), GTK_TYPE_INSPECTOR_ACTIONS); G_OBJECT_CLASS (gtk_inspector_actions_parent_class)->dispose (object); } diff --git a/gtk/inspector/clipboard.c b/gtk/inspector/clipboard.c index 155862474f055dd81d5168399f5958bb3c8bc694..edfb8b6ca47790984cd25ff624b652c6ea991ed6 100644 --- a/gtk/inspector/clipboard.c +++ b/gtk/inspector/clipboard.c @@ -221,7 +221,7 @@ add_content_type_row (GtkInspectorClipboard *self, { GtkEventController *controller = gtk_drop_controller_motion_new (); g_signal_connect (controller, "enter", G_CALLBACK (on_drop_row_enter), viewer); - gtk_widget_add_controller (vbox, controller); + gtk_widget_add_controller (vbox, controller); gtk_widget_set_visible (viewer, FALSE); @@ -355,7 +355,7 @@ gtk_inspector_clipboard_dispose (GObject *object) gtk_inspector_clipboard_unset_display (self); - g_clear_pointer (&self->swin, gtk_widget_unparent); + gtk_widget_dispose_template (GTK_WIDGET (self), GTK_TYPE_INSPECTOR_CLIPBOARD); G_OBJECT_CLASS (gtk_inspector_clipboard_parent_class)->dispose (object); } diff --git a/gtk/inspector/general.c b/gtk/inspector/general.c index f456ea0da40551a381aa7554e190557b0e4cdebd..951ce98d1e0220c6aaa8d92f96137a0cc00e571b 100644 --- a/gtk/inspector/general.c +++ b/gtk/inspector/general.c @@ -1087,8 +1087,6 @@ gtk_inspector_general_dispose (GObject *object) GtkInspectorGeneral *gen = GTK_INSPECTOR_GENERAL (object); GList *list, *l; - g_clear_pointer (&gen->swin, gtk_widget_unparent); - g_signal_handlers_disconnect_by_func (gen->display, G_CALLBACK (seat_added), gen); g_signal_handlers_disconnect_by_func (gen->display, G_CALLBACK (seat_removed), gen); g_signal_handlers_disconnect_by_func (gen->display, G_CALLBACK (populate_display_notify_cb), gen); @@ -1099,6 +1097,8 @@ gtk_inspector_general_dispose (GObject *object) disconnect_seat (gen, GDK_SEAT (l->data)); g_list_free (list); + gtk_widget_dispose_template (GTK_WIDGET (gen), GTK_TYPE_INSPECTOR_GENERAL); + G_OBJECT_CLASS (gtk_inspector_general_parent_class)->dispose (object); } diff --git a/gtk/inspector/list-data.c b/gtk/inspector/list-data.c index fcf9807adb53522ac93c902224671c0b2307f654..c56defef951da858cff8d1a5a36c9d0d34be4350 100644 --- a/gtk/inspector/list-data.c +++ b/gtk/inspector/list-data.c @@ -190,10 +190,8 @@ static void dispose (GObject *object) { GtkInspectorListData *sl = GTK_INSPECTOR_LIST_DATA (object); - GtkWidget *child; - while ((child = gtk_widget_get_first_child (GTK_WIDGET (sl)))) - gtk_widget_unparent (child); + gtk_widget_dispose_template (GTK_WIDGET (sl), GTK_TYPE_INSPECTOR_LIST_DATA); G_OBJECT_CLASS (gtk_inspector_list_data_parent_class)->dispose (object); } diff --git a/gtk/inspector/logs.c b/gtk/inspector/logs.c index 79f0f7e904c9d0de346983dd1039abb2e4a95c01..97b5cf17c29e1347523d03b7afbb39a9b8c35278 100644 --- a/gtk/inspector/logs.c +++ b/gtk/inspector/logs.c @@ -99,10 +99,7 @@ gtk_inspector_logs_init (GtkInspectorLogs *logs) static void dispose (GObject *object) { - GtkWidget *child; - - while ((child = gtk_widget_get_first_child (GTK_WIDGET (object)))) - gtk_widget_unparent (child); + gtk_widget_dispose_template (GTK_WIDGET (object), GTK_TYPE_INSPECTOR_LOGS); G_OBJECT_CLASS (gtk_inspector_logs_parent_class)->dispose (object); } diff --git a/gtk/inspector/misc-info.c b/gtk/inspector/misc-info.c index 1bace8ae36b94f6c8b43bc1fc555606d1d3db71b..ff028d13d43525dffc3a657f732a03e1f1865668 100644 --- a/gtk/inspector/misc-info.c +++ b/gtk/inspector/misc-info.c @@ -120,7 +120,7 @@ format_state_flags (GtkStateFlags state) g_string_append (str, " | "); g_string_append (str, fclass->values[i].value_nick); } - } + } g_type_class_unref (fclass); } else @@ -603,7 +603,7 @@ dispose (GObject *o) { GtkInspectorMiscInfo *sl = GTK_INSPECTOR_MISC_INFO (o); - g_clear_pointer (&sl->swin, gtk_widget_unparent); + gtk_widget_dispose_template (GTK_WIDGET (sl), GTK_TYPE_INSPECTOR_MISC_INFO); G_OBJECT_CLASS (gtk_inspector_misc_info_parent_class)->dispose (o); } diff --git a/gtk/inspector/recorder.c b/gtk/inspector/recorder.c index 05078eb71b3cb6252e75367a65c300fea9d694dd..e5caf293fa6f04555249601604f3e4b301f03fb2 100644 --- a/gtk/inspector/recorder.c +++ b/gtk/inspector/recorder.c @@ -2039,11 +2039,12 @@ gtk_inspector_recorder_dispose (GObject *object) { GtkInspectorRecorder *recorder = GTK_INSPECTOR_RECORDER (object); - g_clear_pointer (&recorder->box, gtk_widget_unparent); g_clear_object (&recorder->render_node_model); g_clear_object (&recorder->render_node_root_model); g_clear_object (&recorder->render_node_selection); + gtk_widget_dispose_template (GTK_WIDGET (recorder), GTK_TYPE_INSPECTOR_RECORDER); + G_OBJECT_CLASS (gtk_inspector_recorder_parent_class)->dispose (object); } diff --git a/gtk/inspector/resource-list.c b/gtk/inspector/resource-list.c index ded5a1d3fb80bf7fbb0b68b2e3e45e7784b6dc13..3c0dc2a38eea2cd3e9943abfae95f065ebfa1d72 100644 --- a/gtk/inspector/resource-list.c +++ b/gtk/inspector/resource-list.c @@ -695,12 +695,12 @@ constructed (GObject *object) GListModel *sort_model; GtkSorter *column_sorter; GtkSorter *sorter; - + g_signal_connect (rl->open_details_button, "clicked", G_CALLBACK (open_details), rl); g_signal_connect (rl->close_details_button, "clicked", G_CALLBACK (close_details), rl); - + rl->tree_model = gtk_tree_list_model_new (load_resources (), FALSE, FALSE, @@ -745,7 +745,7 @@ set_property (GObject *object, GParamSpec *pspec) { GtkInspectorResourceList *rl = GTK_INSPECTOR_RESOURCE_LIST (object); - + switch (param_id) { case PROP_BUTTONS: @@ -765,10 +765,11 @@ dispose (GObject *object) { GtkInspectorResourceList *rl = GTK_INSPECTOR_RESOURCE_LIST (object); - g_clear_pointer (&rl->stack, gtk_widget_unparent); g_clear_object (&rl->selection); g_clear_object (&rl->tree_model); + gtk_widget_dispose_template (GTK_WIDGET (rl), GTK_TYPE_INSPECTOR_RESOURCE_LIST); + G_OBJECT_CLASS (gtk_inspector_resource_list_parent_class)->dispose (object); } diff --git a/gtk/inspector/tree-data.c b/gtk/inspector/tree-data.c index 08ca475b773498bc4eac50e861da07ebc6cdf993..b0e23c293323c34c08fc2f2ff4f7a65bbcd90258 100644 --- a/gtk/inspector/tree-data.c +++ b/gtk/inspector/tree-data.c @@ -100,7 +100,7 @@ add_columns (GtkInspectorTreeData *sl) gtk_tree_view_column_set_cell_data_func (col, cell, cell_data_func, sl, NULL); gtk_tree_view_append_column (sl->view, col); g_free (title); - } + } } static void @@ -175,10 +175,8 @@ static void dispose (GObject *object) { GtkInspectorTreeData *sl = GTK_INSPECTOR_TREE_DATA (object); - GtkWidget *child; - while ((child = gtk_widget_get_first_child (GTK_WIDGET (sl)))) - gtk_widget_unparent (child); + gtk_widget_dispose_template (GTK_WIDGET (sl), GTK_TYPE_INSPECTOR_TREE_DATA); G_OBJECT_CLASS (gtk_inspector_tree_data_parent_class)->dispose (object); } diff --git a/gtk/inspector/visual.c b/gtk/inspector/visual.c index c3b53bf56d587134a5907cdc7e796db269933632..19ac88b4ef118ba64392ff7c42eb4f84ab1d012a 100644 --- a/gtk/inspector/visual.c +++ b/gtk/inspector/visual.c @@ -1077,7 +1077,7 @@ inspect_inspector (GtkButton *button, inspector_window = gtk_inspector_window_get (gtk_widget_get_display (GTK_WIDGET (button))); gtk_window_present (GTK_WINDOW (inspector_window)); } - + static void gtk_inspector_visual_init (GtkInspectorVisual *vis) { @@ -1091,12 +1091,12 @@ gtk_inspector_visual_constructed (GObject *object) G_OBJECT_CLASS (gtk_inspector_visual_parent_class)->constructed (object); - g_signal_connect (vis->visual_box, "keynav-failed", G_CALLBACK (keynav_failed), vis); - g_signal_connect (vis->debug_box, "keynav-failed", G_CALLBACK (keynav_failed), vis); - g_signal_connect (vis->misc_box, "keynav-failed", G_CALLBACK (keynav_failed), vis); - g_signal_connect (vis->visual_box, "row-activated", G_CALLBACK (row_activated), vis); - g_signal_connect (vis->debug_box, "row-activated", G_CALLBACK (row_activated), vis); - g_signal_connect (vis->misc_box, "row-activated", G_CALLBACK (row_activated), vis); + g_signal_connect (vis->visual_box, "keynav-failed", G_CALLBACK (keynav_failed), vis); + g_signal_connect (vis->debug_box, "keynav-failed", G_CALLBACK (keynav_failed), vis); + g_signal_connect (vis->misc_box, "keynav-failed", G_CALLBACK (keynav_failed), vis); + g_signal_connect (vis->visual_box, "row-activated", G_CALLBACK (row_activated), vis); + g_signal_connect (vis->debug_box, "row-activated", G_CALLBACK (row_activated), vis); + g_signal_connect (vis->misc_box, "row-activated", G_CALLBACK (row_activated), vis); } static void @@ -1134,7 +1134,7 @@ gtk_inspector_visual_dispose (GObject *object) { GtkInspectorVisual *vis = GTK_INSPECTOR_VISUAL (object); - g_clear_pointer (&vis->swin, gtk_widget_unparent); + gtk_widget_dispose_template (GTK_WIDGET (vis), GTK_TYPE_INSPECTOR_VISUAL); G_OBJECT_CLASS (gtk_inspector_visual_parent_class)->dispose (object); } diff --git a/gtk/inspector/window.c b/gtk/inspector/window.c index 29d079e4c1fe4a53713a5a8090b8e66d49887b32..2bc45d82674b190ef186f15bd7bd21b81a1462d4 100644 --- a/gtk/inspector/window.c +++ b/gtk/inspector/window.c @@ -311,10 +311,11 @@ gtk_inspector_window_dispose (GObject *object) g_object_set_data (G_OBJECT (iw->inspected_display), "-gtk-inspector", NULL); - g_clear_pointer (&iw->top_stack, gtk_widget_unparent); g_clear_object (&iw->flash_overlay); g_clear_pointer (&iw->objects, g_array_unref); + gtk_widget_dispose_template (GTK_WIDGET (iw), GTK_TYPE_INSPECTOR_WINDOW); + G_OBJECT_CLASS (gtk_inspector_window_parent_class)->dispose (object); }