diff --git a/ChangeLog b/ChangeLog index 3079647d8d..6b77fc5da8 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,25 @@ +Sat Mar 14 02:03:13 1998 Tim Janik + + * gtk/gtksignal.c: make use of *_by_id() functions for handler key. + + * gtk/gtkwidget.c: make use of *_by_id() functions for a bunch of keys. + (gtk_widget_shutdown): new function to perform pre-destruction shutdown + of the widget. + (gtk_widget_unparent): call gtk_widget_set_parent_window(widget,NULL) + + * gtk/gtkobject.h: + * gtk/gtkobject.c: GtkObject destruction is now split into an internally + used shutdown class method and the usual GtkObject::destroy signal + emission. this allowes for class based shutdown functionality prior + to actuall object destruction. + added *_by_id() counterparts for gtk_object_data_* functions, meant for + internal use only. + + * gtk/gtkmain.c (gtk_quit_add_destroy): new function which will destroy + a GtkObject once gtk_main() of a certain level finishes. it is save to + destroy the object prior to that, gtk_quit_add_destroy will only destroy + objects that are still existing. + 1998-03-13 Federico Mena Quintero * gtk/gtkclist.c (gtk_clist_row_is_visible): Now we return a diff --git a/ChangeLog.pre-2-0 b/ChangeLog.pre-2-0 index 3079647d8d..6b77fc5da8 100644 --- a/ChangeLog.pre-2-0 +++ b/ChangeLog.pre-2-0 @@ -1,3 +1,25 @@ +Sat Mar 14 02:03:13 1998 Tim Janik + + * gtk/gtksignal.c: make use of *_by_id() functions for handler key. + + * gtk/gtkwidget.c: make use of *_by_id() functions for a bunch of keys. + (gtk_widget_shutdown): new function to perform pre-destruction shutdown + of the widget. + (gtk_widget_unparent): call gtk_widget_set_parent_window(widget,NULL) + + * gtk/gtkobject.h: + * gtk/gtkobject.c: GtkObject destruction is now split into an internally + used shutdown class method and the usual GtkObject::destroy signal + emission. this allowes for class based shutdown functionality prior + to actuall object destruction. + added *_by_id() counterparts for gtk_object_data_* functions, meant for + internal use only. + + * gtk/gtkmain.c (gtk_quit_add_destroy): new function which will destroy + a GtkObject once gtk_main() of a certain level finishes. it is save to + destroy the object prior to that, gtk_quit_add_destroy will only destroy + objects that are still existing. + 1998-03-13 Federico Mena Quintero * gtk/gtkclist.c (gtk_clist_row_is_visible): Now we return a diff --git a/ChangeLog.pre-2-10 b/ChangeLog.pre-2-10 index 3079647d8d..6b77fc5da8 100644 --- a/ChangeLog.pre-2-10 +++ b/ChangeLog.pre-2-10 @@ -1,3 +1,25 @@ +Sat Mar 14 02:03:13 1998 Tim Janik + + * gtk/gtksignal.c: make use of *_by_id() functions for handler key. + + * gtk/gtkwidget.c: make use of *_by_id() functions for a bunch of keys. + (gtk_widget_shutdown): new function to perform pre-destruction shutdown + of the widget. + (gtk_widget_unparent): call gtk_widget_set_parent_window(widget,NULL) + + * gtk/gtkobject.h: + * gtk/gtkobject.c: GtkObject destruction is now split into an internally + used shutdown class method and the usual GtkObject::destroy signal + emission. this allowes for class based shutdown functionality prior + to actuall object destruction. + added *_by_id() counterparts for gtk_object_data_* functions, meant for + internal use only. + + * gtk/gtkmain.c (gtk_quit_add_destroy): new function which will destroy + a GtkObject once gtk_main() of a certain level finishes. it is save to + destroy the object prior to that, gtk_quit_add_destroy will only destroy + objects that are still existing. + 1998-03-13 Federico Mena Quintero * gtk/gtkclist.c (gtk_clist_row_is_visible): Now we return a diff --git a/ChangeLog.pre-2-2 b/ChangeLog.pre-2-2 index 3079647d8d..6b77fc5da8 100644 --- a/ChangeLog.pre-2-2 +++ b/ChangeLog.pre-2-2 @@ -1,3 +1,25 @@ +Sat Mar 14 02:03:13 1998 Tim Janik + + * gtk/gtksignal.c: make use of *_by_id() functions for handler key. + + * gtk/gtkwidget.c: make use of *_by_id() functions for a bunch of keys. + (gtk_widget_shutdown): new function to perform pre-destruction shutdown + of the widget. + (gtk_widget_unparent): call gtk_widget_set_parent_window(widget,NULL) + + * gtk/gtkobject.h: + * gtk/gtkobject.c: GtkObject destruction is now split into an internally + used shutdown class method and the usual GtkObject::destroy signal + emission. this allowes for class based shutdown functionality prior + to actuall object destruction. + added *_by_id() counterparts for gtk_object_data_* functions, meant for + internal use only. + + * gtk/gtkmain.c (gtk_quit_add_destroy): new function which will destroy + a GtkObject once gtk_main() of a certain level finishes. it is save to + destroy the object prior to that, gtk_quit_add_destroy will only destroy + objects that are still existing. + 1998-03-13 Federico Mena Quintero * gtk/gtkclist.c (gtk_clist_row_is_visible): Now we return a diff --git a/ChangeLog.pre-2-4 b/ChangeLog.pre-2-4 index 3079647d8d..6b77fc5da8 100644 --- a/ChangeLog.pre-2-4 +++ b/ChangeLog.pre-2-4 @@ -1,3 +1,25 @@ +Sat Mar 14 02:03:13 1998 Tim Janik + + * gtk/gtksignal.c: make use of *_by_id() functions for handler key. + + * gtk/gtkwidget.c: make use of *_by_id() functions for a bunch of keys. + (gtk_widget_shutdown): new function to perform pre-destruction shutdown + of the widget. + (gtk_widget_unparent): call gtk_widget_set_parent_window(widget,NULL) + + * gtk/gtkobject.h: + * gtk/gtkobject.c: GtkObject destruction is now split into an internally + used shutdown class method and the usual GtkObject::destroy signal + emission. this allowes for class based shutdown functionality prior + to actuall object destruction. + added *_by_id() counterparts for gtk_object_data_* functions, meant for + internal use only. + + * gtk/gtkmain.c (gtk_quit_add_destroy): new function which will destroy + a GtkObject once gtk_main() of a certain level finishes. it is save to + destroy the object prior to that, gtk_quit_add_destroy will only destroy + objects that are still existing. + 1998-03-13 Federico Mena Quintero * gtk/gtkclist.c (gtk_clist_row_is_visible): Now we return a diff --git a/ChangeLog.pre-2-6 b/ChangeLog.pre-2-6 index 3079647d8d..6b77fc5da8 100644 --- a/ChangeLog.pre-2-6 +++ b/ChangeLog.pre-2-6 @@ -1,3 +1,25 @@ +Sat Mar 14 02:03:13 1998 Tim Janik + + * gtk/gtksignal.c: make use of *_by_id() functions for handler key. + + * gtk/gtkwidget.c: make use of *_by_id() functions for a bunch of keys. + (gtk_widget_shutdown): new function to perform pre-destruction shutdown + of the widget. + (gtk_widget_unparent): call gtk_widget_set_parent_window(widget,NULL) + + * gtk/gtkobject.h: + * gtk/gtkobject.c: GtkObject destruction is now split into an internally + used shutdown class method and the usual GtkObject::destroy signal + emission. this allowes for class based shutdown functionality prior + to actuall object destruction. + added *_by_id() counterparts for gtk_object_data_* functions, meant for + internal use only. + + * gtk/gtkmain.c (gtk_quit_add_destroy): new function which will destroy + a GtkObject once gtk_main() of a certain level finishes. it is save to + destroy the object prior to that, gtk_quit_add_destroy will only destroy + objects that are still existing. + 1998-03-13 Federico Mena Quintero * gtk/gtkclist.c (gtk_clist_row_is_visible): Now we return a diff --git a/ChangeLog.pre-2-8 b/ChangeLog.pre-2-8 index 3079647d8d..6b77fc5da8 100644 --- a/ChangeLog.pre-2-8 +++ b/ChangeLog.pre-2-8 @@ -1,3 +1,25 @@ +Sat Mar 14 02:03:13 1998 Tim Janik + + * gtk/gtksignal.c: make use of *_by_id() functions for handler key. + + * gtk/gtkwidget.c: make use of *_by_id() functions for a bunch of keys. + (gtk_widget_shutdown): new function to perform pre-destruction shutdown + of the widget. + (gtk_widget_unparent): call gtk_widget_set_parent_window(widget,NULL) + + * gtk/gtkobject.h: + * gtk/gtkobject.c: GtkObject destruction is now split into an internally + used shutdown class method and the usual GtkObject::destroy signal + emission. this allowes for class based shutdown functionality prior + to actuall object destruction. + added *_by_id() counterparts for gtk_object_data_* functions, meant for + internal use only. + + * gtk/gtkmain.c (gtk_quit_add_destroy): new function which will destroy + a GtkObject once gtk_main() of a certain level finishes. it is save to + destroy the object prior to that, gtk_quit_add_destroy will only destroy + objects that are still existing. + 1998-03-13 Federico Mena Quintero * gtk/gtkclist.c (gtk_clist_row_is_visible): Now we return a diff --git a/gtk/gtkobject.c b/gtk/gtkobject.c index 52990edfe0..be39dfed54 100644 --- a/gtk/gtkobject.c +++ b/gtk/gtkobject.c @@ -68,11 +68,10 @@ static void gtk_object_set_arg (GtkObject *object, static void gtk_object_get_arg (GtkObject *object, GtkArg *arg, guint arg_id); +static void gtk_object_shutdown (GtkObject *object); static void gtk_object_real_destroy (GtkObject *object); static void gtk_object_finalize (GtkObject *object); static void gtk_object_notify_weaks (gpointer data); -static void gtk_object_data_init (void); -static GtkObjectData* gtk_object_data_new (void); static void gtk_object_data_destroy (GtkObjectData *odata); static guint* gtk_object_data_id_alloc (void); @@ -82,7 +81,6 @@ GtkArg* gtk_object_collect_args (guint *nargs, static guint object_signals[LAST_SIGNAL] = { 0 }; -static gint object_data_init = TRUE; static GHashTable *object_data_ht = NULL; static GMemChunk *object_data_mem_chunk = NULL; static GSList *object_data_id_list = NULL; @@ -91,6 +89,7 @@ static guint object_data_id_index = 0; static GHashTable *arg_info_ht = NULL; static const gchar *user_data_key = "user_data"; +static guint user_data_key_id = 0; #ifdef G_ENABLE_DEBUG @@ -127,13 +126,10 @@ gtk_object_pointer_hash (const gpointer v) } #endif /* G_ENABLE_DEBUG */ -/***************************************** - * gtk_object_init_type: +/**************************************************** + * GtkObject type, class and instance initialization * - * arguments: - * - * results: - *****************************************/ + ****************************************************/ void gtk_object_init_type () @@ -165,14 +161,6 @@ gtk_object_get_type () return GTK_TYPE_OBJECT; } -/***************************************** - * gtk_object_class_init: - * - * arguments: - * - * results: - *****************************************/ - static void gtk_object_class_init (GtkObjectClass *class) { @@ -203,35 +191,11 @@ gtk_object_class_init (GtkObjectClass *class) gtk_object_class_add_signals (class, object_signals, LAST_SIGNAL); + class->shutdown = gtk_object_shutdown; class->destroy = gtk_object_real_destroy; class->finalize = gtk_object_finalize; } -/***************************************** - * gtk_object_real_destroy: - * - * arguments: - * - * results: - *****************************************/ - -static void -gtk_object_real_destroy (GtkObject *object) -{ - g_return_if_fail (object != NULL); - g_return_if_fail (GTK_IS_OBJECT (object)); - - gtk_signal_handlers_destroy (object); -} - -/***************************************** - * gtk_object_init: - * - * arguments: - * - * results: - *****************************************/ - static void gtk_object_init (GtkObject *object) { @@ -253,12 +217,61 @@ gtk_object_init (GtkObject *object) #endif /* G_ENABLE_DEBUG */ } +/******************************************** + * Functions to end a GtkObject's life time + * + ********************************************/ + +void +gtk_object_destroy (GtkObject *object) +{ + g_return_if_fail (object != NULL); + g_return_if_fail (GTK_IS_OBJECT (object)); + + if (!GTK_OBJECT_DESTROYED (object)) + { + /* we will hold a reference on the object in this place, so + * to ease all classes shutdown and destroy implementations. + * i.e. they don't have to bother about referencing at all. + */ + gtk_object_ref (object); + object->klass->shutdown (object); + gtk_object_unref (object); + } +} + +static void +gtk_object_shutdown (GtkObject *object) +{ + GTK_OBJECT_SET_FLAGS (object, GTK_DESTROYED); + gtk_signal_emit (object, object_signals[DESTROY]); +} + +static void +gtk_object_real_destroy (GtkObject *object) +{ + gtk_signal_handlers_destroy (object); +} + +static void +gtk_object_finalize (GtkObject *object) +{ + GtkObjectData *odata, *next; + + odata = object->object_data; + while (odata) + { + next = odata->next; + gtk_object_data_destroy (odata); + odata = next; + } + + g_free (object); +} + /***************************************** - * gtk_object_set_arg: + * GtkObject argument handlers * - * arguments: - * - * results: *****************************************/ static void @@ -299,14 +312,6 @@ gtk_object_set_arg (GtkObject *object, } } -/***************************************** - * gtk_object_get_arg: - * - * arguments: - * - * results: - *****************************************/ - static void gtk_object_get_arg (GtkObject *object, GtkArg *arg, @@ -408,30 +413,6 @@ gtk_object_class_add_user_signal (GtkObjectClass *class, return signal_id; } -/***************************************** - * gtk_object_finalize: - * - * arguments: - * - * results: - *****************************************/ - -static void -gtk_object_finalize (GtkObject *object) -{ - GtkObjectData *odata, *next; - - odata = object->object_data; - while (odata) - { - next = odata->next; - gtk_object_data_destroy (odata); - odata = next; - } - - g_free (object); -} - /***************************************** * gtk_object_sink: * @@ -453,27 +434,6 @@ gtk_object_sink (GtkObject *object) } } -/***************************************** - * gtk_object_destroy: - * - * arguments: - * - * results: - *****************************************/ - -void -gtk_object_destroy (GtkObject *object) -{ - g_return_if_fail (object != NULL); - g_return_if_fail (GTK_IS_OBJECT (object)); - - if (!GTK_OBJECT_DESTROYED (object)) - { - GTK_OBJECT_SET_FLAGS (object, GTK_DESTROYED); - gtk_signal_emit (object, object_signals[DESTROY]); - } -} - /***************************************** * Weak references. * @@ -988,28 +948,97 @@ gtk_object_get_arg_type (const gchar *arg_name) } /***************************************** - * gtk_object_set_data: + * GtkObject object_data mechanism * - * arguments: - * - * results: *****************************************/ +void +gtk_object_set_data_by_id (GtkObject *object, + guint data_id, + gpointer data) +{ + g_return_if_fail (data_id > 0); + + gtk_object_set_data_by_id_full (object, data_id, data, NULL); +} + void gtk_object_set_data (GtkObject *object, const gchar *key, gpointer data) { - gtk_object_set_data_full (object, key, data, NULL); + g_return_if_fail (key != NULL); + + gtk_object_set_data_by_id_full (object, gtk_object_data_force_id (key), data, NULL); } -/***************************************** - * gtk_object_set_data_full: - * - * arguments: - * - * results: - *****************************************/ +void +gtk_object_set_data_by_id_full (GtkObject *object, + guint data_id, + gpointer data, + GtkDestroyNotify destroy) +{ + GtkObjectData *odata; + GtkObjectData *prev; + + g_return_if_fail (object != NULL); + g_return_if_fail (GTK_IS_OBJECT (object)); + g_return_if_fail (data_id > 0); + + if (!data) + { + prev = NULL; + odata = object->object_data; + + while (odata) + { + if (odata->id == data_id) + { + if (prev) + prev->next = odata->next; + if (odata == object->object_data) + object->object_data = odata->next; + + gtk_object_data_destroy (odata); + break; + } + + prev = odata; + odata = odata->next; + } + } + else + { + odata = object->object_data; + while (odata) + { + if (odata->id == data_id) + { + if (odata->destroy) + odata->destroy (odata->data); + + odata->data = data; + odata->destroy = destroy; + return; + } + + odata = odata->next; + } + + if (!object_data_mem_chunk) + object_data_mem_chunk = g_mem_chunk_new ("object data mem chunk", + sizeof (GtkObjectData), + 1024, G_ALLOC_AND_FREE); + + odata = g_chunk_new (GtkObjectData, object_data_mem_chunk); + odata->id = data_id; + odata->data = data; + odata->destroy = destroy; + odata->next = object->object_data; + + object->object_data = odata; + } +} void gtk_object_set_data_full (GtkObject *object, @@ -1017,129 +1046,138 @@ gtk_object_set_data_full (GtkObject *object, gpointer data, GtkDestroyNotify destroy) { - GtkObjectData *odata; - GtkObjectData *prev; - guint *id; - - g_return_if_fail (object != NULL); - g_return_if_fail (GTK_IS_OBJECT (object)); g_return_if_fail (key != NULL); - if (object_data_init) - gtk_object_data_init (); + gtk_object_set_data_by_id_full (object, gtk_object_data_force_id (key), data, destroy); +} + +guint +gtk_object_data_force_id (const gchar *key) +{ + guint *id; + + g_return_val_if_fail (key != NULL, 0); + + if (!object_data_ht) + object_data_ht = g_hash_table_new (g_str_hash, g_str_equal); id = g_hash_table_lookup (object_data_ht, (gpointer) key); - - if (!data) + if (!id) { - if (id) - { - prev = NULL; - odata = object->object_data; - - while (odata) - { - if (odata->id == *id) - { - if (prev) - prev->next = odata->next; - if (odata == object->object_data) - object->object_data = odata->next; - - gtk_object_data_destroy (odata); - break; - } - - prev = odata; - odata = odata->next; - } - } + id = gtk_object_data_id_alloc (); + g_hash_table_insert (object_data_ht, g_strdup (key), id); } - else - { - if (!id) - { - id = gtk_object_data_id_alloc (); - g_hash_table_insert (object_data_ht, (gpointer) g_strdup (key), id); - } + return *id; +} + +gpointer +gtk_object_get_data_by_id (GtkObject *object, + guint data_id) +{ + GtkObjectData *odata; + + g_return_val_if_fail (object != NULL, NULL); + g_return_val_if_fail (GTK_IS_OBJECT (object), NULL); + + if (data_id) + { odata = object->object_data; while (odata) { - if (odata->id == *id) - { - odata->data = data; - odata->destroy = destroy; - return; - } - + if (odata->id == data_id) + return odata->data; odata = odata->next; } - - odata = gtk_object_data_new (); - odata->id = *id; - odata->data = data; - odata->destroy = destroy; - - odata->next = object->object_data; - object->object_data = odata; } + + return NULL; } -/***************************************** - * gtk_object_get_data: - * - * arguments: - * - * results: - *****************************************/ - gpointer gtk_object_get_data (GtkObject *object, const gchar *key) { - GtkObjectData *odata; - guint *id; + guint id; - g_return_val_if_fail (object != NULL, NULL); - g_return_val_if_fail (GTK_IS_OBJECT (object), NULL); g_return_val_if_fail (key != NULL, NULL); - if (object_data_init) - gtk_object_data_init (); - - id = g_hash_table_lookup (object_data_ht, (gpointer) key); + id = gtk_object_data_try_key (key); if (id) - { - odata = object->object_data; - while (odata) - { - if (odata->id == *id) - return odata->data; - odata = odata->next; - } - } + return gtk_object_get_data_by_id (object, id); return NULL; } -/***************************************** - * gtk_object_remove_data: - * - * arguments: - * - * results: - *****************************************/ +guint +gtk_object_data_try_key (const gchar *key) +{ + g_return_val_if_fail (key != NULL, 0); + + if (object_data_ht) + { + guint *id; + + id = g_hash_table_lookup (object_data_ht, (gpointer) key); + if (id) + return *id; + } + + return 0; +} + +void +gtk_object_remove_data_by_id (GtkObject *object, + guint data_id) +{ + if (data_id) + gtk_object_set_data_by_id_full (object, data_id, NULL, NULL); +} void gtk_object_remove_data (GtkObject *object, const gchar *key) { - g_return_if_fail (object != NULL); - g_return_if_fail (GTK_IS_OBJECT (object)); + gint id; + g_return_if_fail (key != NULL); - gtk_object_set_data_full (object, key, NULL, NULL); + id = gtk_object_data_try_key (key); + if (id) + gtk_object_set_data_by_id_full (object, id, NULL, NULL); +} + +static void +gtk_object_data_destroy (GtkObjectData *odata) +{ + g_return_if_fail (odata != NULL); + + if (odata->destroy) + odata->destroy (odata->data); + + g_mem_chunk_free (object_data_mem_chunk, odata); +} + +static guint* +gtk_object_data_id_alloc () +{ + static guint next_id = 1; + guint *ids; + + if (!object_data_id_list || + (object_data_id_index == OBJECT_DATA_ID_CHUNK)) + { + ids = g_new (guint, OBJECT_DATA_ID_CHUNK); + object_data_id_index = 0; + object_data_id_list = g_slist_prepend (object_data_id_list, ids); + } + else + { + ids = object_data_id_list->data; + } + + ids[object_data_id_index] = next_id++; + return &ids[object_data_id_index++]; } /***************************************** @@ -1154,10 +1192,10 @@ void gtk_object_set_user_data (GtkObject *object, gpointer data) { - g_return_if_fail (object != NULL); - g_return_if_fail (GTK_IS_OBJECT (object)); + if (!user_data_key_id) + user_data_key_id = gtk_object_data_force_id (user_data_key); - gtk_object_set_data_full (object, user_data_key, data, NULL); + gtk_object_set_data_by_id_full (object, user_data_key_id, data, NULL); } /***************************************** @@ -1171,10 +1209,10 @@ gtk_object_set_user_data (GtkObject *object, gpointer gtk_object_get_user_data (GtkObject *object) { - g_return_val_if_fail (object != NULL, NULL); - g_return_val_if_fail (GTK_IS_OBJECT (object), NULL); + if (user_data_key_id) + gtk_object_get_data_by_id (object, user_data_key_id); - return gtk_object_get_data (object, user_data_key); + return NULL; } /***************************************** @@ -1267,102 +1305,6 @@ gtk_object_check_class_cast (GtkObjectClass *klass, return klass; } -/***************************************** - * gtk_object_data_init: - * - * arguments: - * - * results: - *****************************************/ - -static void -gtk_object_data_init () -{ - if (object_data_init) - { - object_data_init = FALSE; - - object_data_ht = g_hash_table_new (g_str_hash, g_str_equal); - } -} - -/***************************************** - * gtk_object_data_new: - * - * arguments: - * - * results: - *****************************************/ - -static GtkObjectData* -gtk_object_data_new () -{ - GtkObjectData *odata; - - if (!object_data_mem_chunk) - object_data_mem_chunk = g_mem_chunk_new ("object data mem chunk", - sizeof (GtkObjectData), - 1024, G_ALLOC_AND_FREE); - - odata = g_chunk_new (GtkObjectData, object_data_mem_chunk); - - odata->id = 0; - odata->data = NULL; - odata->destroy = NULL; - odata->next = NULL; - - return odata; -} - -/***************************************** - * gtk_object_data_destroy: - * - * arguments: - * - * results: - *****************************************/ - -static void -gtk_object_data_destroy (GtkObjectData *odata) -{ - g_return_if_fail (odata != NULL); - - if (odata->destroy) - odata->destroy (odata->data); - - g_mem_chunk_free (object_data_mem_chunk, odata); -} - -/***************************************** - * gtk_object_data_id_alloc: - * - * arguments: - * - * results: - *****************************************/ - -static guint* -gtk_object_data_id_alloc () -{ - static guint next_id = 1; - guint *ids; - - if (!object_data_id_list || - (object_data_id_index == OBJECT_DATA_ID_CHUNK)) - { - ids = g_new (guint, OBJECT_DATA_ID_CHUNK); - object_data_id_index = 0; - object_data_id_list = g_slist_prepend (object_data_id_list, ids); - } - else - { - ids = object_data_id_list->data; - } - - ids[object_data_id_index] = next_id++; - return &ids[object_data_id_index++]; -} - /***************************************** * gtk_object_collect_args: * diff --git a/gtk/gtkobject.h b/gtk/gtkobject.h index 44d218f84d..220c8316d2 100644 --- a/gtk/gtkobject.h +++ b/gtk/gtkobject.h @@ -67,15 +67,17 @@ extern "C" { #define GTK_OBJECT_NSIGNALS(obj) (GTK_OBJECT (obj)->klass->nsignals) /* GtkObject only uses the first 4 bits of the flags field. - * GtkWidget uses the remaining bits. Though this is a kinda nasty - * break up, it does make the size of GtkWidget smaller. + * Derived objects may use the remaining bits. Though this + * is a kinda nasty break up, it does make the size of + * derived objects smaller. */ enum { GTK_DESTROYED = 1 << 0, GTK_FLOATING = 1 << 1, GTK_RESERVED_1 = 1 << 2, - GTK_RESERVED_2 = 1 << 3 + GTK_RESERVED_2 = 1 << 3, + GTK_OBJECT_FLAG_LAST = GTK_RESERVED_2 }; /* GtkArg flag bits for gtk_object_add_arg_type @@ -161,13 +163,15 @@ struct _GtkObjectClass */ guint n_args; - /* The destroy function for objects. In one way ore another - * this is defined for all objects. If an object class overrides - * this method in order to perform class specific destruction - * then it should still call it after it is finished with its + /* The functions that will end an objects life time. In one way ore + * another all three of them are defined for all objects. If an + * object class overrides one of the methods in order to perform class + * specific destruction then it must still invoke its superclass' + * implementation of the method after it is finished with its * own cleanup. (See the destroy function for GtkWidget for * an example of how to do this). */ + void (* shutdown) (GtkObject *object); void (* destroy) (GtkObject *object); void (* finalize) (GtkObject *object); @@ -270,28 +274,45 @@ GtkType gtk_object_get_arg_type (const gchar *arg_name); * If 'data' is NULL then this call is equivalent to * 'gtk_object_remove_data'. */ -void gtk_object_set_data (GtkObject *object, - const gchar *key, - gpointer data); +void gtk_object_set_data (GtkObject *object, + const gchar *key, + gpointer data); /* Like gtk_object_set_data, but takes an additional argument - * which is a function to be called when the data is removed + * which is a function to be called when the data is removed. */ -void gtk_object_set_data_full (GtkObject *object, - const gchar *key, - gpointer data, - GtkDestroyNotify destroy); +void gtk_object_set_data_full (GtkObject *object, + const gchar *key, + gpointer data, + GtkDestroyNotify destroy); /* Get the data associated with "key". */ -gpointer gtk_object_get_data (GtkObject *object, - const gchar *key); +gpointer gtk_object_get_data (GtkObject *object, + const gchar *key); /* Remove the data associated with "key". This call is * equivalent to 'gtk_object_set_data' where 'data' is NULL. */ -void gtk_object_remove_data (GtkObject *object, - const gchar *key); +void gtk_object_remove_data (GtkObject *object, + const gchar *key); + +/* Object data functions that operate on key ids. + * These functions are meant for *internal* use only. + */ +void gtk_object_set_data_by_id (GtkObject *object, + guint data_id, + gpointer data); +void gtk_object_set_data_by_id_full (GtkObject *object, + guint data_id, + gpointer data, + GtkDestroyNotify destroy); +gpointer gtk_object_get_data_by_id (GtkObject *object, + guint data_id); +void gtk_object_remove_data_by_id (GtkObject *object, + guint data_id); +guint gtk_object_data_try_key (const gchar *key); +guint gtk_object_data_force_id (const gchar *key); /* Set the "user_data" object data field of "object". It should * be noted that this is no different than calling 'gtk_object_set_data' diff --git a/gtk/gtksignal.c b/gtk/gtksignal.c index be83a4ec04..c48c239d41 100644 --- a/gtk/gtksignal.c +++ b/gtk/gtksignal.c @@ -142,6 +142,7 @@ static guint next_signal = 1; static guint next_handler_id = 1; static const gchar *handler_key = "gtk-signal-handlers"; +static guint handler_key_id = 0; static GMemChunk *handler_mem_chunk = NULL; static GMemChunk *emission_mem_chunk = NULL; @@ -665,7 +666,7 @@ gtk_signal_disconnect (GtkObject *object, g_return_if_fail (object != NULL); g_return_if_fail (handler_id > 0); - handler = gtk_object_get_data (object, handler_key); + handler = gtk_object_get_data_by_id (object, handler_key_id); while (handler) { @@ -692,7 +693,7 @@ gtk_signal_disconnect_by_data (GtkObject *object, g_return_if_fail (object != NULL); found_one = FALSE; - handler = gtk_object_get_data (object, handler_key); + handler = gtk_object_get_data_by_id (object, handler_key_id); while (handler) { @@ -723,7 +724,7 @@ gtk_signal_handler_block (GtkObject *object, g_return_if_fail (object != NULL); g_return_if_fail (handler_id > 0); - tmp = gtk_object_get_data (object, handler_key); + tmp = gtk_object_get_data_by_id (object, handler_key_id); while (tmp) { @@ -752,7 +753,7 @@ gtk_signal_handler_block_by_data (GtkObject *object, gtk_signal_init (); found_one = FALSE; - handler = gtk_object_get_data (object, handler_key); + handler = gtk_object_get_data_by_id (object, handler_key_id); while (handler) { @@ -782,7 +783,7 @@ gtk_signal_handler_unblock (GtkObject *object, if (initialize) gtk_signal_init (); - handler = gtk_object_get_data (object, handler_key); + handler = gtk_object_get_data_by_id (object, handler_key_id); while (handler) { @@ -811,7 +812,7 @@ gtk_signal_handler_unblock_by_data (GtkObject *object, gtk_signal_init (); found_one = FALSE; - handler = gtk_object_get_data (object, handler_key); + handler = gtk_object_get_data_by_id (object, handler_key_id); while (handler) { @@ -839,7 +840,7 @@ gtk_signal_handlers_destroy (GtkObject *object) * handler_key data on each removal */ - handler = gtk_object_get_data (object, handler_key); + handler = gtk_object_get_data_by_id (object, handler_key_id); if (handler) { handler = handler->next; @@ -851,7 +852,7 @@ gtk_signal_handlers_destroy (GtkObject *object) gtk_signal_handler_unref (handler, object); handler = next; } - handler = gtk_object_get_data (object, handler_key); + handler = gtk_object_get_data_by_id (object, handler_key_id); gtk_signal_handler_unref (handler, object); } } @@ -974,7 +975,7 @@ gtk_signal_handler_unref (GtkHandler *handler, if (handler->prev) handler->prev->next = handler->next; else - gtk_object_set_data (object, handler_key, handler->next); + gtk_object_set_data_by_id (object, handler_key_id, handler->next); if (handler->next) handler->next->prev = handler->prev; @@ -991,9 +992,13 @@ gtk_signal_handler_insert (GtkObject *object, /* FIXME: remove */ g_assert (handler->next == NULL); /* FIXME: remove */ g_assert (handler->prev == NULL); - tmp = gtk_object_get_data (object, handler_key); + tmp = gtk_object_get_data_by_id (object, handler_key_id); if (!tmp) - gtk_object_set_data (object, handler_key, handler); + { + if (!handler_key_id) + handler_key_id = gtk_object_data_force_id (handler_key); + gtk_object_set_data_by_id (object, handler_key_id, handler); + } else while (tmp) { @@ -1005,7 +1010,7 @@ gtk_signal_handler_insert (GtkObject *object, handler->prev = tmp->prev; } else - gtk_object_set_data (object, handler_key, handler); + gtk_object_set_data_by_id (object, handler_key_id, handler); tmp->prev = handler; handler->next = tmp; break; @@ -1116,7 +1121,7 @@ gtk_signal_get_handlers (GtkObject *object, g_return_val_if_fail (object != NULL, NULL); g_return_val_if_fail (signal_type >= 1, NULL); - handlers = gtk_object_get_data (object, handler_key); + handlers = gtk_object_get_data_by_id (object, handler_key_id); while (handlers) { diff --git a/gtk/gtkwidget.c b/gtk/gtkwidget.c index b98f4e43dc..0be3b158d6 100644 --- a/gtk/gtkwidget.c +++ b/gtk/gtkwidget.c @@ -174,8 +174,9 @@ static void gtk_widget_set_arg (GtkWidget *widget, static void gtk_widget_get_arg (GtkWidget *widget, GtkArg *arg, guint arg_id); +static void gtk_widget_shutdown (GtkObject *object); static void gtk_widget_real_destroy (GtkObject *object); -static void gtk_widget_real_finalize (GtkObject *object); +static void gtk_widget_finalize (GtkObject *object); static void gtk_widget_real_show (GtkWidget *widget); static void gtk_widget_real_hide (GtkWidget *widget); static void gtk_widget_real_map (GtkWidget *widget); @@ -230,13 +231,18 @@ static GSList *gtk_widget_redraw_queue = NULL; static GSList *gtk_widget_resize_queue = NULL; static const gchar *aux_info_key = "gtk-aux-info"; +static guint aux_info_key_id = 0; +static const gchar *event_key = "gtk-event-mask"; +static guint event_key_id = 0; +static const gchar *extension_event_key = "gtk-extension-event-mode"; +static guint extension_event_key_id = 0; +static const gchar *parent_window_key = "gtk-parent-window"; +static guint parent_window_key_id = 0; +static const gchar *saved_default_style_key = "gtk-saved-default-style"; +static guint saved_default_style_key_id = 0; +static const gchar *shape_info_key = "gtk-shape-info"; static const gchar *colormap_key = "gtk-colormap"; static const gchar *visual_key = "gtk-visual"; -static const gchar *event_key = "gtk-event-mask"; -static const gchar *extension_event_key = "gtk-extension-event-mode"; -static const gchar *parent_window_key = "gtk-parent-window"; -static const gchar *shape_info_key = "gtk-shape-info"; -static const gchar *saved_default_style_key = "gtk-saved-default-style"; @@ -687,8 +693,9 @@ gtk_widget_class_init (GtkWidgetClass *klass) gtk_object_class_add_signals (object_class, widget_signals, LAST_SIGNAL); + object_class->shutdown = gtk_widget_shutdown; object_class->destroy = gtk_widget_real_destroy; - object_class->finalize = gtk_widget_real_finalize; + object_class->finalize = gtk_widget_finalize; klass->activate_signal = 0; klass->show = gtk_widget_real_show; @@ -837,28 +844,28 @@ gtk_widget_get_arg (GtkWidget *widget, switch (arg_id) { case ARG_X: - aux_info = gtk_object_get_data (GTK_OBJECT (widget), aux_info_key); + aux_info = gtk_object_get_data_by_id (GTK_OBJECT (widget), aux_info_key_id); if (!aux_info) GTK_VALUE_INT (*arg) = -2; else GTK_VALUE_INT (*arg) = aux_info->x; break; case ARG_Y: - aux_info = gtk_object_get_data (GTK_OBJECT (widget), aux_info_key); + aux_info = gtk_object_get_data_by_id (GTK_OBJECT (widget), aux_info_key_id); if (!aux_info) GTK_VALUE_INT (*arg) = -2; else GTK_VALUE_INT (*arg) = aux_info->y; break; case ARG_WIDTH: - aux_info = gtk_object_get_data (GTK_OBJECT (widget), aux_info_key); + aux_info = gtk_object_get_data_by_id (GTK_OBJECT (widget), aux_info_key_id); if (!aux_info) GTK_VALUE_INT (*arg) = -2; else GTK_VALUE_INT (*arg) = aux_info->width; break; case ARG_HEIGHT: - aux_info = gtk_object_get_data (GTK_OBJECT (widget), aux_info_key); + aux_info = gtk_object_get_data_by_id (GTK_OBJECT (widget), aux_info_key_id); if (!aux_info) GTK_VALUE_INT (*arg) = -2; else @@ -883,14 +890,14 @@ gtk_widget_get_arg (GtkWidget *widget, GTK_VALUE_BOOL (*arg) = GTK_WIDGET_HAS_DEFAULT (widget); break; case ARG_EVENTS: - eventp = gtk_object_get_data (GTK_OBJECT (widget), event_key); + eventp = gtk_object_get_data_by_id (GTK_OBJECT (widget), event_key_id); if (!eventp) GTK_VALUE_FLAGS (*arg) = 0; else GTK_VALUE_FLAGS (*arg) = *eventp; break; case ARG_EXTENSION_EVENTS: - modep = gtk_object_get_data (GTK_OBJECT (widget), extension_event_key); + modep = gtk_object_get_data_by_id (GTK_OBJECT (widget), extension_event_key_id); if (!modep) GTK_VALUE_FLAGS (*arg) = 0; else @@ -1162,6 +1169,7 @@ gtk_widget_unparent (GtkWidget *widget) old_parent = widget->parent; widget->parent = NULL; + gtk_widget_set_parent_window (widget, NULL); gtk_signal_emit (GTK_OBJECT (widget), widget_signals[PARENT_SET], old_parent); gtk_widget_unref (widget); @@ -1180,10 +1188,6 @@ gtk_widget_destroy (GtkWidget *widget) { g_return_if_fail (widget != NULL); g_return_if_fail (GTK_IS_WIDGET (widget)); - - GTK_WIDGET_UNSET_FLAGS (widget, GTK_VISIBLE); - if (GTK_WIDGET_REALIZED (widget)) - gtk_widget_unrealize (widget); gtk_object_destroy (GTK_OBJECT (widget)); } @@ -1300,8 +1304,6 @@ gtk_widget_show_all (GtkWidget *widget) void gtk_widget_hide_all (GtkWidget *widget) { - GtkWidgetClass *widget_class; - g_return_if_fail (widget != NULL); g_assert (widget->parent); @@ -1310,14 +1312,12 @@ gtk_widget_hide_all (GtkWidget *widget) GtkWidget *toplevel; toplevel = gtk_widget_get_toplevel (widget); - if (toplevel != widget) - GTK_CONTAINER (toplevel)->resize_widgets = - g_slist_remove (GTK_CONTAINER (toplevel)->resize_widgets, widget); + GTK_CONTAINER (toplevel)->resize_widgets = + g_slist_remove (GTK_CONTAINER (toplevel)->resize_widgets, widget); GTK_PRIVATE_UNSET_FLAG (widget, GTK_RESIZE_NEEDED); } - widget_class = GTK_WIDGET_CLASS(GTK_OBJECT(widget)->klass); - widget_class->hide_all (widget); + GTK_WIDGET_CLASS (GTK_OBJECT (widget)->klass)->hide_all (widget); } /***************************************** @@ -1426,6 +1426,15 @@ gtk_widget_unrealize (GtkWidget *widget) { g_return_if_fail (widget != NULL); + if (GTK_WIDGET_REDRAW_PENDING (widget)) + { + gtk_widget_redraw_queue = g_slist_remove (gtk_widget_redraw_queue, widget); + GTK_PRIVATE_UNSET_FLAG (widget, GTK_REDRAW_PENDING); + } + + if (GTK_WIDGET_HAS_SHAPE_MASK (widget)) + gtk_widget_shape_combine_mask (widget, NULL, -1, -1); + if (GTK_WIDGET_REALIZED (widget)) gtk_signal_emit (GTK_OBJECT (widget), widget_signals[UNREALIZE]); } @@ -1499,8 +1508,8 @@ gtk_widget_idle_sizer (void *data) free_slist = gtk_widget_resize_queue; gtk_widget_resize_queue = NULL; - slist = free_slist; - while (slist) + + for (slist = free_slist; slist; slist = slist->next) { GtkWidget *widget; @@ -1509,8 +1518,6 @@ gtk_widget_idle_sizer (void *data) GTK_PRIVATE_UNSET_FLAG (widget, GTK_RESIZE_PENDING); if (gtk_container_need_resize (GTK_CONTAINER (widget))) gtk_widget_queue_resize (widget); - - slist = slist->next; } g_slist_free (free_slist); @@ -1664,7 +1671,7 @@ gtk_widget_size_request (GtkWidget *widget, gtk_widget_ensure_style (widget); gtk_signal_emit (GTK_OBJECT (widget), widget_signals[SIZE_REQUEST], requisition); - aux_info = gtk_object_get_data (GTK_OBJECT (widget), aux_info_key); + aux_info = gtk_object_get_data_by_id (GTK_OBJECT (widget), aux_info_key_id); if (aux_info) { if (aux_info->width > 0) @@ -1693,7 +1700,7 @@ gtk_widget_size_allocate (GtkWidget *widget, g_return_if_fail (widget != NULL); real_allocation = *allocation; - aux_info = gtk_object_get_data (GTK_OBJECT (widget), aux_info_key); + aux_info = gtk_object_get_data_by_id (GTK_OBJECT (widget), aux_info_key_id); if (aux_info) { @@ -2370,11 +2377,13 @@ gtk_widget_set_style (GtkWidget *widget, GTK_WIDGET_UNSET_FLAGS (widget, GTK_RC_STYLE); GTK_PRIVATE_SET_FLAG (widget, GTK_USER_STYLE); - default_style = gtk_object_get_data (GTK_OBJECT (widget), saved_default_style_key); + default_style = gtk_object_get_data_by_id (GTK_OBJECT (widget), saved_default_style_key_id); if (!default_style) { gtk_style_ref (widget->style); - gtk_object_set_data (GTK_OBJECT (widget), saved_default_style_key, widget->style); + if (!saved_default_style_key_id) + saved_default_style_key_id = gtk_object_data_force_id (saved_default_style_key); + gtk_object_set_data_by_id (GTK_OBJECT (widget), saved_default_style_key_id, widget->style); } gtk_widget_set_style_internal (widget, style, initial_emission); @@ -2402,14 +2411,16 @@ gtk_widget_set_rc_style (GtkWidget *widget) GTK_PRIVATE_UNSET_FLAG (widget, GTK_USER_STYLE); GTK_WIDGET_SET_FLAGS (widget, GTK_RC_STYLE); - saved_style = gtk_object_get_data (GTK_OBJECT (widget), saved_default_style_key); + saved_style = gtk_object_get_data_by_id (GTK_OBJECT (widget), saved_default_style_key_id); new_style = gtk_rc_get_style (widget); if (new_style) { if (!saved_style) { gtk_style_ref (widget->style); - gtk_object_set_data (GTK_OBJECT (widget), saved_default_style_key, widget->style); + if (!saved_default_style_key_id) + saved_default_style_key_id = gtk_object_data_force_id (saved_default_style_key); + gtk_object_set_data_by_id (GTK_OBJECT (widget), saved_default_style_key_id, widget->style); } gtk_widget_set_style_internal (widget, new_style, initial_emission); } @@ -2419,7 +2430,7 @@ gtk_widget_set_rc_style (GtkWidget *widget) { g_assert (initial_emission == FALSE); /* FIXME: remove this line */ - gtk_object_remove_data (GTK_OBJECT (widget), saved_default_style_key); + gtk_object_remove_data_by_id (GTK_OBJECT (widget), saved_default_style_key_id); gtk_widget_set_style_internal (widget, saved_style, initial_emission); gtk_style_unref (saved_style); } @@ -2440,10 +2451,10 @@ gtk_widget_restore_default_style (GtkWidget *widget) GTK_PRIVATE_UNSET_FLAG (widget, GTK_USER_STYLE); - default_style = gtk_object_get_data (GTK_OBJECT (widget), saved_default_style_key); + default_style = gtk_object_get_data_by_id (GTK_OBJECT (widget), saved_default_style_key_id); if (default_style) { - gtk_object_remove_data (GTK_OBJECT (widget), saved_default_style_key); + gtk_object_remove_data_by_id (GTK_OBJECT (widget), saved_default_style_key_id); gtk_widget_set_style_internal (widget, default_style, FALSE); gtk_style_unref (default_style); } @@ -2630,13 +2641,15 @@ gtk_widget_set_parent_window (GtkWidget *widget, g_return_if_fail (widget != NULL); - old_parent_window = gtk_object_get_data (GTK_OBJECT (widget), - parent_window_key); + old_parent_window = gtk_object_get_data_by_id (GTK_OBJECT (widget), + parent_window_key_id); if (parent_window != old_parent_window) { - gtk_object_set_data (GTK_OBJECT (widget), parent_window_key, - parent_window); + if (!parent_window_key_id) + parent_window_key_id = gtk_object_data_force_id (parent_window_key); + gtk_object_set_data_by_id (GTK_OBJECT (widget), parent_window_key_id, + parent_window); if (old_parent_window) gdk_window_unref (old_parent_window); if (parent_window) @@ -2664,8 +2677,8 @@ gtk_widget_get_parent_window (GtkWidget *widget) g_return_val_if_fail (GTK_IS_WIDGET (widget), NULL); g_return_val_if_fail (widget->parent != NULL, NULL); - parent_window = gtk_object_get_data (GTK_OBJECT (widget), - parent_window_key); + parent_window = gtk_object_get_data_by_id (GTK_OBJECT (widget), + parent_window_key_id); return (parent_window != NULL) ? parent_window : widget->parent->window; } @@ -2687,11 +2700,13 @@ gtk_widget_set_uposition (GtkWidget *widget, g_return_if_fail (widget != NULL); - aux_info = gtk_object_get_data (GTK_OBJECT (widget), aux_info_key); + aux_info = gtk_object_get_data_by_id (GTK_OBJECT (widget), aux_info_key_id); if (!aux_info) { + if (!aux_info_key_id) + aux_info_key_id = gtk_object_data_force_id (aux_info_key); aux_info = gtk_widget_aux_info_new (); - gtk_object_set_data (GTK_OBJECT (widget), aux_info_key, aux_info); + gtk_object_set_data_by_id (GTK_OBJECT (widget), aux_info_key_id, aux_info); } if (x > -2) @@ -2727,11 +2742,13 @@ gtk_widget_set_usize (GtkWidget *widget, g_return_if_fail (widget != NULL); - aux_info = gtk_object_get_data (GTK_OBJECT (widget), aux_info_key); + aux_info = gtk_object_get_data_by_id (GTK_OBJECT (widget), aux_info_key_id); if (!aux_info) { + if (!aux_info_key_id) + aux_info_key_id = gtk_object_data_force_id (aux_info_key); aux_info = gtk_widget_aux_info_new (); - gtk_object_set_data (GTK_OBJECT (widget), aux_info_key, aux_info); + gtk_object_set_data_by_id (GTK_OBJECT (widget), aux_info_key_id, aux_info); } if (width > -1) @@ -2761,7 +2778,7 @@ gtk_widget_set_events (GtkWidget *widget, g_return_if_fail (!GTK_WIDGET_NO_WINDOW (widget)); g_return_if_fail (!GTK_WIDGET_REALIZED (widget)); - eventp = gtk_object_get_data (GTK_OBJECT (widget), event_key); + eventp = gtk_object_get_data_by_id (GTK_OBJECT (widget), event_key_id); if (events) { @@ -2769,14 +2786,14 @@ gtk_widget_set_events (GtkWidget *widget, eventp = g_new (gint, 1); *eventp = events; - gtk_object_set_data (GTK_OBJECT (widget), event_key, eventp); + if (!event_key_id) + event_key_id = gtk_object_data_force_id (event_key); + gtk_object_set_data_by_id (GTK_OBJECT (widget), event_key_id, eventp); } - else + else if (eventp) { - if (eventp) - g_free (eventp); - - gtk_object_remove_data (GTK_OBJECT (widget), event_key); + g_free (eventp); + gtk_object_remove_data_by_id (GTK_OBJECT (widget), event_key_id); } } @@ -2796,13 +2813,15 @@ gtk_widget_set_extension_events (GtkWidget *widget, g_return_if_fail (widget != NULL); - modep = gtk_object_get_data (GTK_OBJECT (widget), extension_event_key); + modep = gtk_object_get_data_by_id (GTK_OBJECT (widget), extension_event_key_id); if (!modep) modep = g_new (GdkExtensionMode, 1); *modep = mode; - gtk_object_set_data (GTK_OBJECT (widget), extension_event_key, modep); + if (!extension_event_key_id) + extension_event_key_id = gtk_object_data_force_id (extension_event_key); + gtk_object_set_data_by_id (GTK_OBJECT (widget), extension_event_key_id, modep); } @@ -2915,7 +2934,7 @@ gtk_widget_get_events (GtkWidget *widget) g_return_val_if_fail (widget != NULL, 0); - events = gtk_object_get_data (GTK_OBJECT (widget), event_key); + events = gtk_object_get_data_by_id (GTK_OBJECT (widget), event_key_id); if (events) return *events; @@ -2937,7 +2956,7 @@ gtk_widget_get_extension_events (GtkWidget *widget) g_return_val_if_fail (widget != NULL, 0); - mode = gtk_object_get_data (GTK_OBJECT (widget), extension_event_key); + mode = gtk_object_get_data_by_id (GTK_OBJECT (widget), extension_event_key_id); if (mode) return *mode; @@ -3331,89 +3350,81 @@ gtk_widget_marshal_signal_7 (GtkObject *object, func_data); } +static void +gtk_widget_shutdown (GtkObject *object) +{ + GtkWidget *widget; + + /* gtk_object_destroy() will already hold a refcount on object + */ + widget = GTK_WIDGET (object); + + if (widget->parent) + gtk_container_remove (GTK_CONTAINER (widget->parent), widget); + + GTK_WIDGET_UNSET_FLAGS (widget, GTK_VISIBLE); + if (GTK_WIDGET_REALIZED (widget)) + gtk_widget_unrealize (widget); + + parent_class->shutdown (object); +} + static void gtk_widget_real_destroy (GtkObject *object) { - GtkWidget *widget = GTK_WIDGET (object); + GtkWidget *widget; GtkStyle *saved_style; - gtk_widget_ref (widget); + /* gtk_object_destroy() will already hold a refcount on object + */ + widget = GTK_WIDGET (object); - if (GTK_WIDGET_REDRAW_PENDING (widget)) - { - gtk_widget_redraw_queue = g_slist_remove (gtk_widget_redraw_queue, widget); - GTK_PRIVATE_UNSET_FLAG (widget, GTK_REDRAW_PENDING); - } - if (GTK_CONTAINER_RESIZE_PENDING (widget)) { gtk_widget_resize_queue = g_slist_remove (gtk_widget_resize_queue, widget); GTK_PRIVATE_UNSET_FLAG (widget, GTK_RESIZE_PENDING); } - if (GTK_WIDGET_HAS_SHAPE_MASK (widget)) - gtk_widget_shape_combine_mask (widget, NULL, -1, -1); - gtk_grab_remove (widget); gtk_selection_remove_all (widget); - if (widget->parent) - gtk_container_remove (GTK_CONTAINER (widget->parent), widget); - - saved_style = gtk_object_get_data (GTK_OBJECT (widget), saved_default_style_key); + saved_style = gtk_object_get_data_by_id (GTK_OBJECT (widget), saved_default_style_key_id); if (saved_style) { gtk_style_unref (saved_style); - gtk_object_remove_data (GTK_OBJECT (widget), saved_default_style_key); + gtk_object_remove_data_by_id (GTK_OBJECT (widget), saved_default_style_key_id); } gtk_style_unref (widget->style); widget->style = NULL; parent_class->destroy (object); - - gtk_widget_unref (widget); } static void -gtk_widget_real_finalize (GtkObject *object) +gtk_widget_finalize (GtkObject *object) { GtkWidget *widget; GtkWidgetAuxInfo *aux_info; gint *events; GdkExtensionMode *mode; - g_return_if_fail (object != NULL); - g_return_if_fail (GTK_IS_WIDGET (object)); - widget = GTK_WIDGET (object); if (widget->name) - { - g_free (widget->name); - widget->name = NULL; - } + g_free (widget->name); - aux_info = gtk_object_get_data (GTK_OBJECT (widget), aux_info_key); + aux_info = gtk_object_get_data_by_id (GTK_OBJECT (widget), aux_info_key_id); if (aux_info) - { - gtk_widget_aux_info_destroy (aux_info); - gtk_object_remove_data (GTK_OBJECT (widget), aux_info_key); - } + gtk_widget_aux_info_destroy (aux_info); - events = gtk_object_get_data (GTK_OBJECT (widget), event_key); + events = gtk_object_get_data_by_id (GTK_OBJECT (widget), event_key_id); if (events) - { - g_free (events); - gtk_object_remove_data (GTK_OBJECT (widget), event_key); - } + g_free (events); - mode = gtk_object_get_data (GTK_OBJECT (widget), extension_event_key); + mode = gtk_object_get_data_by_id (GTK_OBJECT (widget), extension_event_key_id); if (mode) - { - g_free (mode); - gtk_object_remove_data (GTK_OBJECT (widget), extension_event_key); - } + g_free (mode); parent_class->finalize (object); }