Compare commits

...

14 Commits

Author SHA1 Message Date
Tristan Van Berkom
0b0d41dc58 Fixed statement in gtkwindow.c when toplevelness changes.
Fixed a typo when checking if the heirarchy toplevel is a toplevel
before firing the hierarchy-changed signal.
2011-01-06 14:27:03 +09:00
Tristan Van Berkom
4d795437f1 Dont show the GtkWindow when removing it from a parent and becomming a toplevel
Showing the window causes it to try to grab focus, this causes problems
when embedded toplevels run through dispose cycles.
2011-01-04 00:55:04 +09:00
Tristan Van Berkom
e40b77b569 Fixed conflict while rebasing master. 2010-12-29 18:22:39 +09:00
Tristan Van Berkom
f0af03f951 Changes to testtoplevelembed
- Made notebook tabs smaller
  - No need to hide/show toplevels after removing from a parent,
    if it's visible it will be automatically shown after removing
    outside of it's previous parent.
2010-12-29 18:22:39 +09:00
Tristan Van Berkom
54f81cde17 Fixed GtkFileChooserDefault to handle cases of being in an embedded dialog.
This involves checking the toplevelness of new toplevels before connecting
but not the *old* ones for disconnecting signals. Also take care of handling
a row_reference that becomes invalid over the course of reparenting the
filechooser into another parent.
2010-12-29 18:22:39 +09:00
Tristan Van Berkom
460be460ec Fixed GtkWindow/GtkWidget to properly emit hierarchy changed for embedded toplevels
Now GtkWindow takes some measures when setting toplevelness:

  - When a window becomes toplevel after being embedded it saves
    the visibility state and reshow's itself so that the window
    re-realizes and presents itself again automatically

  - When emitting hierarchy-changed, synthetically mark the toplevel
    as not anchored, this allows the hierarchy changed propagation to
    recurse properly.

GtkWidget also takes care to unset the parent window *after* unparenting
the widget and after emitting the heirarhcy changed that leaves a NULL
toplevel.

That means there are now 2 cycles of "hierarchy-changed" when removing
an embedded toplevel from a parent, first one that makes the new toplevel
a NULL one (since the toplevel flag is not yet restored), the second cycle
makes the removed window toplevel again when setting the parent window
to NULL.
2010-12-29 18:22:39 +09:00
Tristan Van Berkom
96b954d242 Fixed focus handling on embedded windows.
Now GtkWindow chains up in focus vfuncs when non-toplevel, this
fixes focus in testtoplevelembed.
2010-12-29 18:22:39 +09:00
Tristan Van Berkom
acb71a2fa7 Added buttons to notebook tabs in testtoplevelembed
Now you can remove and reembed the toplevels (deleting the
toplevels put them back in the notebook).
2010-12-29 18:22:39 +09:00
Tristan Van Berkom
16f1253b77 Moved location of unsetting parent window inside gtk_widget_unparent().
Make sure to do this after the widget is unrealized.
2010-12-29 18:22:39 +09:00
Tristan Van Berkom
3630b63b9c Fixed issues with "hierarchy-changed" signal.
GtkFileChooserDefault watches the toplevel and montitors "set-focus"
signal on it... however the connection needs to be remade when the
GtkFileChooserDialog is in an embedded toplevel.

Measure's taken: GtkWindow propagates hierarchy changes when
_gtk_window_set_is_toplevel() is called, gtk_widget_unparent()
unsets the widget's parent window earlier in the function so that
the possible hierarchy change is still able to properly access the hierarchy.

GtkFileChooserDefault checks if the "new" toplevel is indeed
gtk_widget_is_toplevel() but not the old one, GtkRange has been
updated to use gtk_widget_is_toplevel() inside it's hierarhcy_changed
vfunc, other classes already do this properly.
2010-12-29 18:22:39 +09:00
Tristan Van Berkom
0435071747 Added tests/testtoplevelembed. 2010-12-29 18:22:39 +09:00
Tristan Van Berkom
70796f8475 Slightly less special casing in GtkWindow for gtk_widget_is_toplevel()
Also take care of setting the resize-mode at realize time depending
on toplevelness.
2010-12-29 18:22:39 +09:00
Tristan Van Berkom
1ce7cc6202 Added docs to gtk_widget_set_parent_window.
Also stop setting the resize mode of the window.
2010-12-29 18:22:39 +09:00
Tristan Van Berkom
6a7f0894df Allow GtkWindow to be parented if gtk_widget_set_parent_window() is called on one
This patch makes gtk_widget_set_parent_window() undo the toplevelness
of a GtkWindow, GtkWindow then realizes itself as a normal child widget
and behaves like a normal GtkBin by checking gtk_widget_is_toplevel() in
several places (show/hide/map/unmap/draw/size_allocate/check_resize/configure_event).
2010-12-29 18:22:38 +09:00
6 changed files with 310 additions and 42 deletions

View File

@@ -1180,11 +1180,14 @@ shortcuts_reload_icons_get_info_cb (GCancellable *cancellable,
pixbuf = _gtk_file_info_render_icon (info, GTK_WIDGET (data->impl), data->impl->icon_size);
path = gtk_tree_row_reference_get_path (data->row_ref);
gtk_tree_model_get_iter (GTK_TREE_MODEL (data->impl->shortcuts_model), &iter, path);
gtk_list_store_set (data->impl->shortcuts_model, &iter,
SHORTCUTS_COL_PIXBUF, pixbuf,
-1);
gtk_tree_path_free (path);
if (path)
{
gtk_tree_model_get_iter (GTK_TREE_MODEL (data->impl->shortcuts_model), &iter, path);
gtk_list_store_set (data->impl->shortcuts_model, &iter,
SHORTCUTS_COL_PIXBUF, pixbuf,
-1);
gtk_tree_path_free (path);
}
if (pixbuf)
g_object_unref (pixbuf);
@@ -5588,21 +5591,20 @@ gtk_file_chooser_default_hierarchy_changed (GtkWidget *widget,
GtkWidget *toplevel;
impl = GTK_FILE_CHOOSER_DEFAULT (widget);
toplevel = gtk_widget_get_toplevel (widget);
if (previous_toplevel)
if (previous_toplevel &&
impl->toplevel_set_focus_id != 0)
{
g_assert (impl->toplevel_set_focus_id != 0);
g_signal_handler_disconnect (previous_toplevel,
impl->toplevel_set_focus_id);
impl->toplevel_set_focus_id = 0;
impl->toplevel_last_focus_widget = NULL;
}
else
g_assert (impl->toplevel_set_focus_id == 0);
toplevel = gtk_widget_get_toplevel (widget);
if (GTK_IS_WINDOW (toplevel))
if (gtk_widget_is_toplevel (toplevel))
{
g_assert (impl->toplevel_set_focus_id == 0);
impl->toplevel_set_focus_id = g_signal_connect (toplevel, "set-focus",
G_CALLBACK (toplevel_set_focus_cb), impl);
impl->toplevel_last_focus_widget = gtk_window_get_focus (GTK_WINDOW (toplevel));

View File

@@ -1725,7 +1725,7 @@ gtk_range_hierarchy_changed (GtkWidget *widget,
G_CALLBACK (resize_grip_visible_changed),
widget);
window = gtk_widget_get_toplevel (widget);
if (GTK_IS_WINDOW (window))
if (gtk_widget_is_toplevel (window))
g_signal_connect (window, "notify::resize-grip-visible",
G_CALLBACK (resize_grip_visible_changed), widget);
}

View File

@@ -3719,14 +3719,6 @@ gtk_widget_unparent (GtkWidget *widget)
if (gtk_container_get_focus_child (GTK_CONTAINER (priv->parent)) == widget)
gtk_container_set_focus_child (GTK_CONTAINER (priv->parent), NULL);
/* If we are unanchoring the child, we save around the toplevel
* to emit hierarchy changed
*/
if (priv->parent->priv->anchored)
g_object_ref (toplevel);
else
toplevel = NULL;
gtk_widget_queue_draw_child (widget);
/* Reset the width and height here, to force reallocation if we
@@ -3745,6 +3737,14 @@ gtk_widget_unparent (GtkWidget *widget)
gtk_widget_unrealize (widget);
}
/* If we are unanchoring the child, we save around the toplevel
* to emit hierarchy changed
*/
if (priv->parent->priv->anchored)
g_object_ref (toplevel);
else
toplevel = NULL;
/* Removing a widget from a container restores the child visible
* flag to the default state, so it doesn't affect the child
* in the next parent.
@@ -3753,7 +3753,6 @@ gtk_widget_unparent (GtkWidget *widget)
old_parent = priv->parent;
priv->parent = NULL;
gtk_widget_set_parent_window (widget, NULL);
/* parent may no longer expand if the removed
* child was expand=TRUE and could therefore
@@ -3774,6 +3773,13 @@ gtk_widget_unparent (GtkWidget *widget)
g_object_unref (toplevel);
}
/* Now that the parent pointer is nullified and the hierarchy-changed
* already passed, go ahead and unset the parent window, if we are unparenting
* an embeded GtkWindow the window will become toplevel again and hierarchy-changed
* will fire again for the new subhierarchy.
*/
gtk_widget_set_parent_window (widget, NULL);
g_object_notify (G_OBJECT (widget), "parent");
g_object_thaw_notify (G_OBJECT (widget));
if (!priv->parent)
@@ -8633,6 +8639,7 @@ gtk_widget_get_default_style (void)
}
#ifdef G_ENABLE_DEBUG
/* Verify invariants, see docs/widget_system.txt for notes on much of
* this. Invariants may be temporarily broken while we're in the
* process of updating state, of course, so you can only
@@ -9063,6 +9070,16 @@ gtk_widget_render_icon (GtkWidget *widget,
* @parent_window: the new parent window.
*
* Sets a non default parent window for @widget.
*
* For GtkWindow classes, setting a @parent_window effects whether
* the window is a toplevel window or can be embedded into other
* widgets.
*
* <note><para>
* For GtkWindow classes, this needs to be called before the
* window is realized.
* </para></note>
*
**/
void
gtk_widget_set_parent_window (GtkWidget *widget,
@@ -9083,6 +9100,13 @@ gtk_widget_set_parent_window (GtkWidget *widget,
g_object_unref (old_parent_window);
if (parent_window)
g_object_ref (parent_window);
/* Unset toplevel flag when adding a parent window to a widget,
* this is the primary entry point to allow toplevels to be
* embeddable.
*/
if (GTK_IS_WINDOW (widget) && !GTK_IS_PLUG (widget))
_gtk_window_set_is_toplevel (GTK_WINDOW (widget), parent_window == NULL);
}
}

View File

@@ -4584,6 +4584,12 @@ gtk_window_show (GtkWidget *widget)
GtkContainer *container = GTK_CONTAINER (window);
gboolean need_resize;
if (!gtk_widget_is_toplevel (GTK_WIDGET (widget)))
{
GTK_WIDGET_CLASS (gtk_window_parent_class)->show (widget);
return;
}
_gtk_widget_set_visible_flag (widget, TRUE);
need_resize = _gtk_container_get_need_resize (container) || !gtk_widget_get_realized (widget);
@@ -4661,6 +4667,12 @@ gtk_window_hide (GtkWidget *widget)
GtkWindow *window = GTK_WINDOW (widget);
GtkWindowPrivate *priv = window->priv;
if (!gtk_widget_is_toplevel (GTK_WIDGET (widget)))
{
GTK_WIDGET_CLASS (gtk_window_parent_class)->hide (widget);
return;
}
_gtk_widget_set_visible_flag (widget, FALSE);
gtk_widget_unmap (widget);
@@ -4680,6 +4692,12 @@ gtk_window_map (GtkWidget *widget)
gdk_window = gtk_widget_get_window (widget);
if (!gtk_widget_is_toplevel (GTK_WIDGET (widget)))
{
GTK_WIDGET_CLASS (gtk_window_parent_class)->map (widget);
return;
}
gtk_widget_set_mapped (widget, TRUE);
child = gtk_bin_get_child (&(window->bin));
@@ -4790,6 +4808,12 @@ gtk_window_unmap (GtkWidget *widget)
GdkWindow *gdk_window;
GdkWindowState state;
if (!gtk_widget_is_toplevel (GTK_WIDGET (widget)))
{
GTK_WIDGET_CLASS (gtk_window_parent_class)->unmap (widget);
return;
}
gdk_window = gtk_widget_get_window (widget);
gtk_widget_set_mapped (widget, FALSE);
@@ -4840,6 +4864,39 @@ gtk_window_realize (GtkWidget *widget)
gtk_widget_get_allocation (widget, &allocation);
if (gtk_widget_get_parent_window (widget))
{
gtk_container_set_resize_mode (GTK_CONTAINER (widget), GTK_RESIZE_PARENT);
gtk_widget_set_realized (widget, TRUE);
attributes.x = allocation.x;
attributes.y = allocation.y;
attributes.width = allocation.width;
attributes.height = allocation.height;
attributes.window_type = GDK_WINDOW_CHILD;
attributes.event_mask = gtk_widget_get_events (widget) | GDK_EXPOSURE_MASK | GDK_STRUCTURE_MASK;
attributes.visual = gtk_widget_get_visual (widget);
attributes.wclass = GDK_INPUT_OUTPUT;
attributes_mask = GDK_WA_X | GDK_WA_Y | GDK_WA_VISUAL;
gdk_window = gdk_window_new (gtk_widget_get_parent_window (widget),
&attributes, attributes_mask);
gtk_widget_set_window (widget, gdk_window);
gdk_window_set_user_data (gdk_window, widget);
gtk_widget_style_attach (widget);
gtk_style_set_background (gtk_widget_get_style (widget), gdk_window, GTK_STATE_NORMAL);
gdk_window_enable_synchronized_configure (gdk_window);
return;
}
gtk_container_set_resize_mode (GTK_CONTAINER (window), GTK_RESIZE_QUEUE);
/* ensure widget tree is properly size allocated */
if (allocation.x == -1 &&
allocation.y == -1 &&
@@ -4923,6 +4980,7 @@ gtk_window_realize (GtkWidget *widget)
gtk_style_context_set_background (context, gdk_window);
if (priv->transient_parent &&
gtk_widget_get_realized (GTK_WIDGET (priv->transient_parent)))
gdk_window_set_transient_for (gdk_window,
@@ -4930,48 +4988,48 @@ gtk_window_realize (GtkWidget *widget)
if (priv->wm_role)
gdk_window_set_role (gdk_window, priv->wm_role);
if (!priv->decorated)
gdk_window_set_decorations (gdk_window, 0);
if (!priv->deletable)
gdk_window_set_functions (gdk_window, GDK_FUNC_ALL | GDK_FUNC_CLOSE);
if (gtk_window_get_skip_pager_hint (window))
gdk_window_set_skip_pager_hint (gdk_window, TRUE);
if (gtk_window_get_skip_taskbar_hint (window))
gdk_window_set_skip_taskbar_hint (gdk_window, TRUE);
if (gtk_window_get_accept_focus (window))
gdk_window_set_accept_focus (gdk_window, TRUE);
else
gdk_window_set_accept_focus (gdk_window, FALSE);
if (gtk_window_get_focus_on_map (window))
gdk_window_set_focus_on_map (gdk_window, TRUE);
else
gdk_window_set_focus_on_map (gdk_window, FALSE);
if (priv->modal)
gdk_window_set_modal_hint (gdk_window, TRUE);
else
gdk_window_set_modal_hint (gdk_window, FALSE);
if (priv->startup_id)
{
#ifdef GDK_WINDOWING_X11
guint32 timestamp = extract_time_from_startup_id (priv->startup_id);
if (timestamp != GDK_CURRENT_TIME)
gdk_x11_window_set_user_time (gdk_window, timestamp);
gdk_x11_window_set_user_time (gdk_window, timestamp);
#endif
if (!startup_id_is_fake (priv->startup_id))
gdk_window_set_startup_id (gdk_window, priv->startup_id);
gdk_window_set_startup_id (gdk_window, priv->startup_id);
}
/* Icons */
gtk_window_realize_icon (window);
if (priv->has_resize_grip)
resize_grip_create_window (window);
}
@@ -5180,6 +5238,24 @@ gtk_window_size_allocate (GtkWidget *widget,
gtk_widget_set_allocation (widget, allocation);
if (gtk_widget_get_realized (widget))
{
/* If it's not a toplevel we're embedded, we need to resize the window's
* window and skip the grip.
*/
if (!gtk_widget_is_toplevel (widget))
{
gdk_window_move_resize (gtk_widget_get_window (widget),
allocation->x, allocation->y,
allocation->width, allocation->height);
}
else
{
update_grip_visibility (window);
set_grip_position (window);
}
}
child = gtk_bin_get_child (&(window->bin));
if (child && gtk_widget_get_visible (child))
{
@@ -5193,12 +5269,6 @@ gtk_window_size_allocate (GtkWidget *widget,
gtk_widget_size_allocate (child, &child_allocation);
}
if (gtk_widget_get_realized (widget))
{
update_grip_visibility (window);
set_grip_position (window);
}
}
static gint
@@ -5210,6 +5280,15 @@ gtk_window_configure_event (GtkWidget *widget,
GtkWindowPrivate *priv = window->priv;
gboolean expected_reply = priv->configure_request_count > 0;
if (!gtk_widget_is_toplevel (GTK_WIDGET (widget)))
{
if (GTK_WIDGET_CLASS (gtk_window_parent_class)->configure_event)
return GTK_WIDGET_CLASS (gtk_window_parent_class)->configure_event (widget, event);
gdk_window_configure_finished (gtk_widget_get_window (widget));
return FALSE;
}
/* priv->configure_request_count incremented for each
* configure request, and decremented to a min of 0 for
* each configure notify.
@@ -5394,7 +5473,8 @@ gtk_window_set_has_resize_grip (GtkWindow *window,
priv->has_resize_grip = value;
gtk_widget_queue_draw (widget);
if (gtk_widget_get_realized (widget))
if (gtk_widget_get_realized (widget) &&
gtk_widget_is_toplevel (GTK_WIDGET (widget)))
{
if (priv->has_resize_grip && priv->grip_window == NULL)
resize_grip_create_window (window);
@@ -5463,6 +5543,9 @@ gtk_window_resize_grip_is_visible (GtkWindow *window)
if (!priv->resizable)
return FALSE;
if (!gtk_widget_is_toplevel (GTK_WIDGET (widget)))
return FALSE;
if (gtk_widget_get_realized (widget))
{
GdkWindowState state;
@@ -5883,7 +5966,11 @@ gtk_window_client_event (GtkWidget *widget,
static void
gtk_window_check_resize (GtkContainer *container)
{
if (gtk_widget_get_visible (GTK_WIDGET (container)))
/* If the window is not toplevel anymore than it's embedded somewhere,
* so handle it like a normal window */
if (!gtk_widget_is_toplevel (GTK_WIDGET (container)))
GTK_CONTAINER_CLASS (gtk_window_parent_class)->check_resize (container);
else if (gtk_widget_get_visible (GTK_WIDGET (container)))
gtk_window_move_resize (GTK_WINDOW (container));
}
@@ -5899,6 +5986,9 @@ gtk_window_focus (GtkWidget *widget,
GtkWidget *old_focus_child;
GtkWidget *parent;
if (!gtk_widget_is_toplevel (GTK_WIDGET (widget)))
return GTK_WIDGET_CLASS (gtk_window_parent_class)->focus (widget, direction);
container = GTK_CONTAINER (widget);
window = GTK_WINDOW (widget);
priv = window->priv;
@@ -5952,6 +6042,12 @@ static void
gtk_window_move_focus (GtkWidget *widget,
GtkDirectionType dir)
{
if (!gtk_widget_is_toplevel (GTK_WIDGET (widget)))
{
GTK_WIDGET_CLASS (gtk_window_parent_class)->move_focus (widget, dir);
return;
}
gtk_widget_child_focus (widget, dir);
if (! gtk_container_get_focus_child (GTK_CONTAINER (widget)))
@@ -6641,6 +6737,7 @@ gtk_window_move_resize (GtkWindow *window)
GtkWindowLastGeometryInfo saved_last_info;
widget = GTK_WIDGET (window);
gdk_window = gtk_widget_get_window (widget);
container = GTK_CONTAINER (widget);
info = gtk_window_get_geometry_info (window, TRUE);
@@ -9123,6 +9220,8 @@ _gtk_window_set_is_toplevel (GtkWindow *window,
gboolean is_toplevel)
{
GtkWidget *widget;
GtkWidget *toplevel;
gboolean was_anchored;
widget = GTK_WIDGET (window);
@@ -9134,15 +9233,49 @@ _gtk_window_set_is_toplevel (GtkWindow *window,
if (is_toplevel == gtk_widget_is_toplevel (widget))
return;
was_anchored = _gtk_widget_get_anchored (widget);
if (is_toplevel)
{
/* Pass through regular pathways of an embedded toplevel
* to go through unmapping and hiding the widget before
* becomming a toplevel again.
*
* We remain hidden after becomming toplevel in order to
* avoid problems during an embedded toplevel's dispose cycle
* (When a toplevel window is shown it tries to grab focus again,
* this causes problems while disposing).
*/
gtk_widget_hide (widget);
/* Save the toplevel this widget was previously anchored into before
* propagating a hierarchy-changed.
*
* Usually this happens by way of gtk_widget_unparent() and we are
* already unanchored at this point, just adding this clause incase
* things happen differently.
*/
toplevel = gtk_widget_get_toplevel (widget);
if (!gtk_widget_is_toplevel (toplevel))
toplevel = NULL;
_gtk_widget_set_is_toplevel (widget, TRUE);
/* When a window becomes toplevel after being embedded and anchored
* into another window we need to unset it's anchored flag so that
* the hierarchy changed signal kicks in properly.
*/
_gtk_widget_set_anchored (widget, FALSE);
_gtk_widget_propagate_hierarchy_changed (widget, toplevel);
toplevel_list = g_slist_prepend (toplevel_list, window);
}
else
{
_gtk_widget_set_is_toplevel (widget, FALSE);
toplevel_list = g_slist_remove (toplevel_list, window);
_gtk_widget_propagate_hierarchy_changed (widget, widget);
}
}

View File

@@ -100,7 +100,8 @@ noinst_PROGRAMS = $(TEST_PROGS) \
testscrolledwindow \
testcellarea \
testswitch \
styleexamples
styleexamples \
testtoplevelembed
if USE_X11
noinst_PROGRAMS += testerrors
@@ -194,6 +195,7 @@ testexpand_DEPENDENCIES = $(TEST_DEPS)
testexpander_DEPENDENCIES = $(TEST_DEPS)
testswitch_DEPENDENCIES = $(TEST_DEPS)
styleexamples_DEPENDENCIES = $(TEST_DEPS)
testtoplevelembed_DEPENDENCIES = $(TEST_DEPS)
flicker_LDADD = $(LDADDS)
simple_LDADD = $(LDADDS)
@@ -273,6 +275,7 @@ testexpand_LDADD = $(LDADDS)
testexpander_LDADD = $(LDADDS)
testswitch_LDADD = $(LDADDS)
styleexamples_LDADD = $(LDADDS)
testtoplevelembed_LDADD = $(LDADDS)
testentrycompletion_SOURCES = \
prop-editor.c \
@@ -405,8 +408,11 @@ testexpand_SOURCES = testexpand.c
testexpander_SOURCES = testexpander.c
testswitch_SOURCES = testswitch.c
styleexamples_SOURCES = styleexamples.c
testtoplevelembed_SOURCES = testtoplevelembed.c
EXTRA_DIST += \
prop-editor.h \
testgtk.1 \

103
tests/testtoplevelembed.c Normal file
View File

@@ -0,0 +1,103 @@
#include "config.h"
#include <gtk/gtk.h>
GtkWidget *notebook;
static void
remove_notebook_page (GtkWidget *button,
GtkWidget *toplevel)
{
gtk_container_remove (GTK_CONTAINER (notebook), toplevel);
gtk_widget_show (toplevel);
}
GtkWidget *
create_tab_label (GtkWidget *toplevel)
{
GtkWidget *box = gtk_hbox_new (FALSE, 2);
GtkWidget *label = gtk_label_new (G_OBJECT_TYPE_NAME (toplevel));
GtkWidget *button = gtk_button_new ();
GtkWidget *image = gtk_image_new_from_stock (GTK_STOCK_CLOSE, GTK_ICON_SIZE_MENU);
gtk_container_add (GTK_CONTAINER (button), image);
gtk_box_pack_start (GTK_BOX (box), label, TRUE, TRUE, 0);
gtk_box_pack_start (GTK_BOX (box), button, FALSE, TRUE, 0);
g_signal_connect (button, "clicked",
G_CALLBACK (remove_notebook_page), toplevel);
gtk_widget_show_all (box);
return box;
}
static void
toplevel_delete_event (GtkWidget *toplevel,
GdkEvent *event,
gpointer none)
{
GdkWindow *gdk_win;
GtkWidget *label = create_tab_label (toplevel);
gdk_win = gtk_widget_get_window (notebook);
g_assert (gdk_win);
gtk_widget_hide (toplevel);
gtk_widget_unrealize (toplevel);
gtk_widget_set_parent_window (toplevel, gdk_win);
gtk_notebook_append_page (GTK_NOTEBOOK (notebook), toplevel, label);
gtk_widget_show (toplevel);
}
gint
main (gint argc, gchar **argv)
{
GtkWidget *window;
GtkWidget *widget;
gtk_init (&argc, &argv);
window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
gtk_window_set_title (GTK_WINDOW (window), "Toplevel widget embedding example");
g_signal_connect (window, "destroy", gtk_main_quit, NULL);
notebook = gtk_notebook_new ();
gtk_notebook_set_scrollable (GTK_NOTEBOOK (notebook), TRUE);
gtk_container_add (GTK_CONTAINER (window), notebook);
gtk_widget_realize (notebook);
widget = gtk_about_dialog_new ();
toplevel_delete_event (widget, NULL, NULL);
g_signal_connect (widget, "delete-event", G_CALLBACK (toplevel_delete_event), NULL);
widget = gtk_file_chooser_dialog_new ("the chooser", NULL, GTK_FILE_CHOOSER_ACTION_OPEN, NULL, NULL);
toplevel_delete_event (widget, NULL, NULL);
g_signal_connect (widget, "delete-event", G_CALLBACK (toplevel_delete_event), NULL);
widget = gtk_color_selection_dialog_new ("the colorsel");
toplevel_delete_event (widget, NULL, NULL);
g_signal_connect (widget, "delete-event", G_CALLBACK (toplevel_delete_event), NULL);
widget = gtk_font_selection_dialog_new ("the fontsel");
toplevel_delete_event (widget, NULL, NULL);
g_signal_connect (widget, "delete-event", G_CALLBACK (toplevel_delete_event), NULL);
widget = gtk_recent_chooser_dialog_new ("the recent chooser", NULL,
GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT,
NULL);
toplevel_delete_event (widget, NULL, NULL);
g_signal_connect (widget, "delete-event", G_CALLBACK (toplevel_delete_event), NULL);
widget = gtk_message_dialog_new (NULL, GTK_DIALOG_MODAL,
GTK_MESSAGE_QUESTION, GTK_BUTTONS_YES_NO,
"Do you have any questions ?");
toplevel_delete_event (widget, NULL, NULL);
g_signal_connect (widget, "delete-event", G_CALLBACK (toplevel_delete_event), NULL);
gtk_widget_show_all (window);
gtk_main ();
}