]> Pileus Git - ~andy/gtk/blobdiff - gtk/gtkwindow.c
Deprecate flag macros for toplevel, state, no window and composite child
[~andy/gtk] / gtk / gtkwindow.c
index 7a19c5a263a8d64c6091acfd06e28c6aa4617cbf..004338972bd1679504347af9673cc16009ab8b30 100644 (file)
@@ -42,6 +42,7 @@
 #include "gtkkeyhash.h"
 #include "gtkmain.h"
 #include "gtkmnemonichash.h"
+#include "gtkmenubar.h"
 #include "gtkiconfactory.h"
 #include "gtkicontheme.h"
 #include "gtkmarshalers.h"
@@ -101,6 +102,8 @@ enum {
   /* Writeonly properties */
   PROP_STARTUP_ID,
   
+  PROP_MNEMONICS_VISIBLE,
+
   LAST_ARG
 };
 
@@ -185,6 +188,9 @@ struct _GtkWindowPrivate
   guint opacity_set : 1;
   guint builder_visible : 1;
 
+  guint mnemonics_visible : 1;
+  guint mnemonics_visible_set : 1;
+
   GdkWindowTypeHint type_hint;
 
   gdouble opacity;
@@ -310,6 +316,7 @@ static GQuark       quark_gtk_embedded = 0;
 static GQuark       quark_gtk_window_key_hash = 0;
 static GQuark       quark_gtk_window_default_icon_pixmap = 0;
 static GQuark       quark_gtk_window_icon_info = 0;
+static GQuark       quark_gtk_buildable_accels = 0;
 
 static GtkBuildableIface *parent_buildable_iface;
 
@@ -330,6 +337,17 @@ static void gtk_window_buildable_set_buildable_property (GtkBuildable        *bu
                                                         const GValue        *value);
 static void gtk_window_buildable_parser_finished (GtkBuildable     *buildable,
                                                  GtkBuilder       *builder);
+static gboolean gtk_window_buildable_custom_tag_start (GtkBuildable  *buildable,
+                                                      GtkBuilder    *builder,
+                                                      GObject       *child,
+                                                      const gchar   *tagname,
+                                                      GMarkupParser *parser,
+                                                      gpointer      *data);
+static void gtk_window_buildable_custom_finished (GtkBuildable  *buildable,
+                                                     GtkBuilder    *builder,
+                                                     GObject       *child,
+                                                     const gchar   *tagname,
+                                                     gpointer       user_data);
 
 
 G_DEFINE_TYPE_WITH_CODE (GtkWindow, gtk_window, GTK_TYPE_BIN,
@@ -342,10 +360,10 @@ add_tab_bindings (GtkBindingSet    *binding_set,
                  GtkDirectionType  direction)
 {
   gtk_binding_entry_add_signal (binding_set, GDK_Tab, modifiers,
-                                "move_focus", 1,
+                                "move-focus", 1,
                                 GTK_TYPE_DIRECTION_TYPE, direction);
   gtk_binding_entry_add_signal (binding_set, GDK_KP_Tab, modifiers,
-                                "move_focus", 1,
+                                "move-focus", 1,
                                 GTK_TYPE_DIRECTION_TYPE, direction);
 }
 
@@ -357,16 +375,16 @@ add_arrow_bindings (GtkBindingSet    *binding_set,
   guint keypad_keysym = keysym - GDK_Left + GDK_KP_Left;
   
   gtk_binding_entry_add_signal (binding_set, keysym, 0,
-                                "move_focus", 1,
+                                "move-focus", 1,
                                 GTK_TYPE_DIRECTION_TYPE, direction);
   gtk_binding_entry_add_signal (binding_set, keysym, GDK_CONTROL_MASK,
-                                "move_focus", 1,
+                                "move-focus", 1,
                                 GTK_TYPE_DIRECTION_TYPE, direction);
   gtk_binding_entry_add_signal (binding_set, keypad_keysym, 0,
-                                "move_focus", 1,
+                                "move-focus", 1,
                                 GTK_TYPE_DIRECTION_TYPE, direction);
   gtk_binding_entry_add_signal (binding_set, keypad_keysym, GDK_CONTROL_MASK,
-                                "move_focus", 1,
+                                "move-focus", 1,
                                 GTK_TYPE_DIRECTION_TYPE, direction);
 }
 
@@ -383,7 +401,8 @@ extract_time_from_startup_id (const gchar* startup_id)
     
       /* Skip past the "_TIME" part */
       timestr += 5;
-    
+
+      errno = 0;
       timestamp = strtoul (timestr, &end, 0);
       if (end != timestr && errno == 0)
         retval = timestamp;
@@ -415,6 +434,7 @@ gtk_window_class_init (GtkWindowClass *klass)
   quark_gtk_window_key_hash = g_quark_from_static_string ("gtk-window-key-hash");
   quark_gtk_window_default_icon_pixmap = g_quark_from_static_string ("gtk-window-default-icon-pixmap");
   quark_gtk_window_icon_info = g_quark_from_static_string ("gtk-window-icon-info");
+  quark_gtk_buildable_accels = g_quark_from_static_string ("gtk-window-buildable-accels");
 
   gobject_class->dispose = gtk_window_dispose;
   gobject_class->finalize = gtk_window_finalize;
@@ -442,9 +462,8 @@ gtk_window_class_init (GtkWindowClass *klass)
   widget_class->focus_out_event = gtk_window_focus_out_event;
   widget_class->client_event = gtk_window_client_event;
   widget_class->focus = gtk_window_focus;
-  
   widget_class->expose_event = gtk_window_expose;
-   
+
   container_class->check_resize = gtk_window_check_resize;
 
   klass->set_focus = gtk_window_real_set_focus;
@@ -482,7 +501,7 @@ gtk_window_class_init (GtkWindowClass *klass)
                                                        P_("Unique identifier for the window to be used when restoring a session"),
                                                        NULL,
                                                        GTK_PARAM_READWRITE));
-                                                       
+
   /**
    * GtkWindow:startup-id:
    *
@@ -491,9 +510,9 @@ gtk_window_class_init (GtkWindowClass *klass)
    * for more details.
    *
    * Since: 2.12
-   */                                                  
+   */
   g_object_class_install_property (gobject_class,
-                                   PROP_ROLE,
+                                   PROP_STARTUP_ID,
                                    g_param_spec_string ("startup-id",
                                                        P_("Startup ID"),
                                                        P_("Unique startup identifier for the window used by startup-notification"),
@@ -577,6 +596,13 @@ gtk_window_class_init (GtkWindowClass *klass)
                                                         P_("Icon for this window"),
                                                         GDK_TYPE_PIXBUF,
                                                         GTK_PARAM_READWRITE));
+  g_object_class_install_property (gobject_class,
+                                   PROP_MNEMONICS_VISIBLE,
+                                   g_param_spec_boolean ("mnemonics-visible",
+                                                         P_("Mnemonics Visible"),
+                                                         P_("Whether mnemonics are currently visible in this window"),
+                                                         TRUE,
+                                                         GTK_PARAM_READWRITE));
   
   /**
    * GtkWindow:icon-name:
@@ -652,7 +678,7 @@ gtk_window_class_init (GtkWindowClass *klass)
                                                          GTK_PARAM_READWRITE));  
 
   /**
-   * GtkWindow:accept-focus-hint:
+   * GtkWindow:accept-focus:
    *
    * Whether the window should receive the input focus.
    *
@@ -667,7 +693,7 @@ gtk_window_class_init (GtkWindowClass *klass)
                                                          GTK_PARAM_READWRITE));  
 
   /**
-   * GtkWindow:focus-on-map-hint:
+   * GtkWindow:focus-on-map:
    *
    * Whether the window should receive the input focus when mapped.
    *
@@ -745,6 +771,7 @@ gtk_window_class_init (GtkWindowClass *klass)
                                                        P_("The transient parent of the dialog"),
                                                        GTK_TYPE_WINDOW,
                                                        GTK_PARAM_READWRITE| G_PARAM_CONSTRUCT));
+
   /**
    * GtkWindow:opacity:
    *
@@ -764,7 +791,7 @@ gtk_window_class_init (GtkWindowClass *klass)
                                                        GTK_PARAM_READWRITE));
 
   window_signals[SET_FOCUS] =
-    g_signal_new (I_("set_focus"),
+    g_signal_new (I_("set-focus"),
                   G_TYPE_FROM_CLASS (gobject_class),
                   G_SIGNAL_RUN_LAST,
                   G_STRUCT_OFFSET (GtkWindowClass, set_focus),
@@ -774,7 +801,7 @@ gtk_window_class_init (GtkWindowClass *klass)
                   GTK_TYPE_WIDGET);
   
   window_signals[FRAME_EVENT] =
-    g_signal_new (I_("frame_event"),
+    g_signal_new (I_("frame-event"),
                   G_TYPE_FROM_CLASS (gobject_class),
                   G_SIGNAL_RUN_LAST,
                   G_STRUCT_OFFSET(GtkWindowClass, frame_event),
@@ -783,8 +810,17 @@ gtk_window_class_init (GtkWindowClass *klass)
                   G_TYPE_BOOLEAN, 1,
                   GDK_TYPE_EVENT);
 
+  /**
+   * GtkWindow::activate-focus:
+   * @window: the window which received the signal
+   *
+   * The ::activate-default signal is a
+   * <link linkend="keybinding-signals">keybinding signal</link>
+   * which gets emitted when the user activates the currently
+   * focused widget of @window.
+   */
   window_signals[ACTIVATE_FOCUS] =
-    g_signal_new (I_("activate_focus"),
+    g_signal_new (I_("activate-focus"),
                   G_TYPE_FROM_CLASS (gobject_class),
                   G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
                   G_STRUCT_OFFSET (GtkWindowClass, activate_focus),
@@ -793,8 +829,17 @@ gtk_window_class_init (GtkWindowClass *klass)
                   G_TYPE_NONE,
                   0);
 
+  /**
+   * GtkWindow::activate-default:
+   * @window: the window which received the signal
+   *
+   * The ::activate-default signal is a
+   * <link linkend="keybinding-signals">keybinding signal</link>
+   * which gets emitted when the user activates the default widget
+   * of @window.
+   */
   window_signals[ACTIVATE_DEFAULT] =
-    g_signal_new (I_("activate_default"),
+    g_signal_new (I_("activate-default"),
                   G_TYPE_FROM_CLASS (gobject_class),
                   G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
                   G_STRUCT_OFFSET (GtkWindowClass, activate_default),
@@ -803,8 +848,15 @@ gtk_window_class_init (GtkWindowClass *klass)
                   G_TYPE_NONE,
                   0);
 
+  /**
+   * GtkWindow::keys-changed:
+   * @window: the window which received the signal
+   *
+   * The ::keys-changed signal gets emitted when the set of accelerators
+   * or mnemonics that are associated with @window changes.
+   */
   window_signals[KEYS_CHANGED] =
-    g_signal_new (I_("keys_changed"),
+    g_signal_new (I_("keys-changed"),
                   G_TYPE_FROM_CLASS (gobject_class),
                   G_SIGNAL_RUN_FIRST,
                   G_STRUCT_OFFSET (GtkWindowClass, keys_changed),
@@ -820,16 +872,16 @@ gtk_window_class_init (GtkWindowClass *klass)
   binding_set = gtk_binding_set_by_class (klass);
 
   gtk_binding_entry_add_signal (binding_set, GDK_space, 0,
-                                "activate_focus", 0);
+                                "activate-focus", 0);
   gtk_binding_entry_add_signal (binding_set, GDK_KP_Space, 0,
-                                "activate_focus", 0);
+                                "activate-focus", 0);
   
   gtk_binding_entry_add_signal (binding_set, GDK_Return, 0,
-                                "activate_default", 0);
+                                "activate-default", 0);
   gtk_binding_entry_add_signal (binding_set, GDK_ISO_Enter, 0,
-                                "activate_default", 0);
+                                "activate-default", 0);
   gtk_binding_entry_add_signal (binding_set, GDK_KP_Enter, 0,
-                                "activate_default", 0);
+                                "activate-default", 0);
 
   add_arrow_bindings (binding_set, GDK_Up, GTK_DIR_UP);
   add_arrow_bindings (binding_set, GDK_Down, GTK_DIR_DOWN);
@@ -889,6 +941,7 @@ gtk_window_init (GtkWindow *window)
   priv->type_hint = GDK_WINDOW_TYPE_HINT_NORMAL;
   priv->opacity = 1.0;
   priv->startup_id = NULL;
+  priv->mnemonics_visible = TRUE;
 
   colormap = _gtk_widget_peek_colormap ();
   if (colormap)
@@ -900,7 +953,7 @@ gtk_window_init (GtkWindow *window)
 
   gtk_decorated_window_init (window);
 
-  g_signal_connect (window->screen, "composited_changed",
+  g_signal_connect (window->screen, "composited-changed",
                    G_CALLBACK (gtk_window_on_composited_changed), window);
 }
 
@@ -911,9 +964,12 @@ gtk_window_set_property (GObject      *object,
                         GParamSpec   *pspec)
 {
   GtkWindow  *window;
+  GtkWindowPrivate *priv;
   
   window = GTK_WINDOW (object);
 
+  priv = GTK_WINDOW_GET_PRIVATE (window);
+
   switch (prop_id)
     {
     case PROP_TYPE:
@@ -1010,6 +1066,9 @@ gtk_window_set_property (GObject      *object,
     case PROP_OPACITY:
       gtk_window_set_opacity (window, g_value_get_double (value));
       break;
+    case PROP_MNEMONICS_VISIBLE:
+      gtk_window_set_mnemonics_visible (window, g_value_get_boolean (value));
+      break;
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       break;
@@ -1125,6 +1184,9 @@ gtk_window_get_property (GObject      *object,
     case PROP_OPACITY:
       g_value_set_double (value, gtk_window_get_opacity (window));
       break;
+    case PROP_MNEMONICS_VISIBLE:
+      g_value_set_boolean (value, priv->mnemonics_visible);
+      break;
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       break;
@@ -1137,7 +1199,8 @@ gtk_window_buildable_interface_init (GtkBuildableIface *iface)
   parent_buildable_iface = g_type_interface_peek_parent (iface);
   iface->set_buildable_property = gtk_window_buildable_set_buildable_property;
   iface->parser_finished = gtk_window_buildable_parser_finished;
-
+  iface->custom_tag_start = gtk_window_buildable_custom_tag_start;
+  iface->custom_finished = gtk_window_buildable_custom_finished;
 }
 
 static void
@@ -1159,11 +1222,118 @@ gtk_window_buildable_parser_finished (GtkBuildable *buildable,
                                      GtkBuilder   *builder)
 {
   GtkWindowPrivate *priv = GTK_WINDOW_GET_PRIVATE (buildable);
+  GObject *object;
+  GSList *accels, *l;
 
   if (priv->builder_visible)
     gtk_widget_show (GTK_WIDGET (buildable));
 
-    parent_buildable_iface->parser_finished (buildable, builder);
+  accels = g_object_get_qdata (G_OBJECT (buildable), quark_gtk_buildable_accels);
+  for (l = accels; l; l = l->next)
+    {
+      object = gtk_builder_get_object (builder, l->data);
+      if (!object)
+       {
+         g_warning ("Unknown accel group %s specified in window %s",
+                    (const gchar*)l->data, gtk_buildable_get_name (buildable));
+         continue;
+       }
+      gtk_window_add_accel_group (GTK_WINDOW (buildable),
+                                 GTK_ACCEL_GROUP (object));
+      g_free (l->data);
+    }
+
+  g_object_set_qdata (G_OBJECT (buildable), quark_gtk_buildable_accels, NULL);
+
+  parent_buildable_iface->parser_finished (buildable, builder);
+}
+
+typedef struct {
+  GObject *object;
+  GSList *items;
+} GSListSubParserData;
+
+static void
+window_start_element (GMarkupParseContext *context,
+                         const gchar         *element_name,
+                         const gchar        **names,
+                         const gchar        **values,
+                         gpointer            user_data,
+                         GError            **error)
+{
+  guint i;
+  GSListSubParserData *data = (GSListSubParserData*)user_data;
+
+  if (strcmp (element_name, "group") == 0)
+    {
+      for (i = 0; names[i]; i++)
+       {
+         if (strcmp (names[i], "name") == 0)
+           data->items = g_slist_prepend (data->items, g_strdup (values[i]));
+       }
+    }
+  else if (strcmp (element_name, "accel-groups") == 0)
+    return;
+  else
+    g_warning ("Unsupported tag type for GtkWindow: %s\n",
+              element_name);
+
+}
+
+static const GMarkupParser window_parser =
+  {
+    window_start_element
+  };
+
+static gboolean
+gtk_window_buildable_custom_tag_start (GtkBuildable  *buildable,
+                                      GtkBuilder    *builder,
+                                      GObject       *child,
+                                      const gchar   *tagname,
+                                      GMarkupParser *parser,
+                                      gpointer      *data)
+{
+  GSListSubParserData *parser_data;
+
+  if (parent_buildable_iface->custom_tag_start (buildable, builder, child, 
+                                               tagname, parser, data))
+    return TRUE;
+
+  if (strcmp (tagname, "accel-groups") == 0)
+    {
+      parser_data = g_slice_new0 (GSListSubParserData);
+      parser_data->items = NULL;
+      parser_data->object = G_OBJECT (buildable);
+
+      *parser = window_parser;
+      *data = parser_data;
+      return TRUE;
+    }
+
+  return FALSE;
+}
+
+static void
+gtk_window_buildable_custom_finished (GtkBuildable  *buildable,
+                                         GtkBuilder    *builder,
+                                         GObject       *child,
+                                         const gchar   *tagname,
+                                         gpointer       user_data)
+{
+  GSListSubParserData *data;
+
+  parent_buildable_iface->custom_finished (buildable, builder, child, 
+                                          tagname, user_data);
+
+  if (strcmp (tagname, "accel-groups") != 0)
+    return;
+  
+  data = (GSListSubParserData*)user_data;
+
+  g_object_set_qdata_full (G_OBJECT (buildable), quark_gtk_buildable_accels, 
+                          data->items, (GDestroyNotify) g_slist_free);
+
+  g_slice_free (GSListSubParserData, data);
 }
 
 /**
@@ -1352,18 +1522,21 @@ gtk_window_set_startup_id (GtkWindow   *window,
   
   g_free (priv->startup_id);
   priv->startup_id = g_strdup (startup_id);
-  
+
   if (GTK_WIDGET_REALIZED (window))
     {
+      guint32 timestamp = extract_time_from_startup_id (priv->startup_id);
+
+#ifdef GDK_WINDOWING_X11
+      if (timestamp != GDK_CURRENT_TIME)
+       gdk_x11_window_set_user_time (GTK_WIDGET (window)->window, timestamp);
+#endif
+
       /* Here we differentiate real and "fake" startup notification IDs,
        * constructed on purpose just to pass interaction timestamp
-       */  
+       */
       if (startup_id_is_fake (priv->startup_id))
-        {
-          guint32 timestamp = extract_time_from_startup_id (priv->startup_id);
-
-          gtk_window_present_with_time (window, timestamp);
-        }
+       gtk_window_present_with_time (window, timestamp);
       else 
         {
           gdk_window_set_startup_id (GTK_WIDGET (window)->window,
@@ -1400,7 +1573,7 @@ gtk_window_get_role (GtkWindow *window)
 /**
  * gtk_window_set_focus:
  * @window: a #GtkWindow
- * @focus: widget to be the new focus widget, or %NULL to unset
+ * @focus: (allow-none): widget to be the new focus widget, or %NULL to unset
  *   any focus widget for the toplevel window.
  *
  * If @focus is not the current focus widget, and is focusable, sets
@@ -1455,7 +1628,7 @@ _gtk_window_internal_set_focus (GtkWindow *window,
 /**
  * gtk_window_set_default:
  * @window: a #GtkWindow
- * @default_widget: widget to be the default, or %NULL to unset the
+ * @default_widget: (allow-none): widget to be the default, or %NULL to unset the
  *                  default widget for the toplevel.
  *
  * The default widget is the widget that's activated when the user
@@ -1532,14 +1705,12 @@ gtk_window_get_default_widget (GtkWindow *window)
   return window->default_widget;
 }
 
-void
-gtk_window_set_policy (GtkWindow *window,
-                      gboolean   allow_shrink,
-                      gboolean   allow_grow,
-                      gboolean   auto_shrink)
+static void
+gtk_window_set_policy_internal (GtkWindow *window,
+                                gboolean   allow_shrink,
+                                gboolean   allow_grow,
+                                gboolean   auto_shrink)
 {
-  g_return_if_fail (GTK_IS_WINDOW (window));
-
   window->allow_shrink = (allow_shrink != FALSE);
   window->allow_grow = (allow_grow != FALSE);
 
@@ -1548,10 +1719,21 @@ gtk_window_set_policy (GtkWindow *window,
   g_object_notify (G_OBJECT (window), "allow-grow");
   g_object_notify (G_OBJECT (window), "resizable");
   g_object_thaw_notify (G_OBJECT (window));
-  
+
   gtk_widget_queue_resize_no_redraw (GTK_WIDGET (window));
 }
 
+void
+gtk_window_set_policy (GtkWindow *window,
+                      gboolean   allow_shrink,
+                      gboolean   allow_grow,
+                      gboolean   auto_shrink)
+{
+  g_return_if_fail (GTK_IS_WINDOW (window));
+
+  gtk_window_set_policy_internal (window, allow_shrink, allow_grow, auto_shrink);
+}
+
 static gboolean
 handle_keys_changed (gpointer data)
 {
@@ -1594,7 +1776,7 @@ gtk_window_add_accel_group (GtkWindow     *window,
   g_return_if_fail (GTK_IS_ACCEL_GROUP (accel_group));
 
   _gtk_accel_group_attach (accel_group, G_OBJECT (window));
-  g_signal_connect_object (accel_group, "accel_changed",
+  g_signal_connect_object (accel_group, "accel-changed",
                           G_CALLBACK (gtk_window_notify_keys_changed),
                           window, G_CONNECT_SWAPPED);
   gtk_window_notify_keys_changed (window);
@@ -1800,9 +1982,9 @@ gtk_window_activate_focus (GtkWindow *window)
  * Note that this is the widget that would have the focus
  * if the toplevel window focused; if the toplevel window
  * is not focused then  <literal>GTK_WIDGET_HAS_FOCUS (widget)</literal> will
- * not be %TRUE for the widget. 
- * 
- * Return value: the currently focused widget, or %NULL if there is none.
+ * not be %TRUE for the widget.
+ *
+ * Return value: (transfer none): the currently focused widget, or %NULL if there is none.
  **/
 GtkWidget *
 gtk_window_get_focus (GtkWindow *window)
@@ -1911,8 +2093,8 @@ gtk_window_get_modal (GtkWindow *window)
  * callbacks that might destroy the widgets, you <emphasis>must</emphasis> call
  * <literal>g_list_foreach (result, (GFunc)g_object_ref, NULL)</literal> first, and
  * then unref all the widgets afterwards.
- * 
- * Return value: list of toplevel widgets
+ *
+ * Return value: (element-type GtkWidget) (transfer container): list of toplevel widgets
  **/
 GList*
 gtk_window_list_toplevels (void)
@@ -1927,7 +2109,7 @@ gtk_window_list_toplevels (void)
 }
 
 void
-gtk_window_add_embedded_xid (GtkWindow *window, guint xid)
+gtk_window_add_embedded_xid (GtkWindow *window, GdkNativeWindow xid)
 {
   GList *embedded_windows;
 
@@ -1946,7 +2128,7 @@ gtk_window_add_embedded_xid (GtkWindow *window, guint xid)
 }
 
 void
-gtk_window_remove_embedded_xid (GtkWindow *window, guint xid)
+gtk_window_remove_embedded_xid (GtkWindow *window, GdkNativeWindow xid)
 {
   GList *embedded_windows;
   GList *node;
@@ -2082,7 +2264,7 @@ gtk_window_unset_transient_for  (GtkWindow *window)
 /**
  * gtk_window_set_transient_for:
  * @window: a #GtkWindow
- * @parent: parent window
+ * @parent: (allow-none): parent window
  *
  * Dialog windows should be set transient for the main application
  * window they were spawned from. This allows <link
@@ -2159,7 +2341,7 @@ gtk_window_set_transient_for  (GtkWindow *window,
  * Fetches the transient parent for this window. See
  * gtk_window_set_transient_for().
  *
- * Return value: the transient parent for this window, or %NULL
+ * Return value: (transfer none): the transient parent for this window, or %NULL
  *    if no transient parent has been set.
  **/
 GtkWindow *
@@ -2254,7 +2436,7 @@ gtk_window_set_type_hint (GtkWindow           *window,
   GtkWindowPrivate *priv;
 
   g_return_if_fail (GTK_IS_WINDOW (window));
-  g_return_if_fail (!GTK_WIDGET_VISIBLE (window));
+  g_return_if_fail (!GTK_WIDGET_MAPPED (window));
 
   priv = GTK_WINDOW_GET_PRIVATE (window);
 
@@ -3254,8 +3436,8 @@ gtk_window_set_icon_list (GtkWindow  *window,
  * Retrieves the list of icons set by gtk_window_set_icon_list().
  * The list is copied, but the reference count on each
  * member won't be incremented.
- * 
- * Return value: copy of window's icon list
+ *
+ * Return value: (element-type GdkPixbuf) (transfer container): copy of window's icon list
  **/
 GList*
 gtk_window_get_icon_list (GtkWindow  *window)
@@ -3275,8 +3457,8 @@ gtk_window_get_icon_list (GtkWindow  *window)
 /**
  * gtk_window_set_icon:
  * @window: a #GtkWindow
- * @icon: icon image, or %NULL
- * 
+ * @icon: (allow-none): icon image, or %NULL
+ *
  * Sets up the icon representing a #GtkWindow. This icon is used when
  * the window is minimized (also known as iconified).  Some window
  * managers or desktop environments may also place it in the window
@@ -3330,11 +3512,11 @@ update_themed_icon (GtkIconTheme *icon_theme,
 /**
  * gtk_window_set_icon_name:
  * @window: a #GtkWindow
- * @name: the name of the themed icon
+ * @name: (allow-none): the name of the themed icon
  *
  * Sets the icon for the window from a named themed icon. See
- * the docs for #GtkIconTheme for more details. 
- * 
+ * the docs for #GtkIconTheme for more details.
+ *
  * Note that this has nothing to do with the WM_ICON_NAME 
  * property which is mentioned in the ICCCM.
  *
@@ -3351,6 +3533,9 @@ gtk_window_set_icon_name (GtkWindow   *window,
 
   info = ensure_icon_info (window);
 
+  if (g_strcmp0 (info->icon_name, name) == 0)
+    return;
+
   tmp = info->icon_name;
   info->icon_name = g_strdup (name);
   g_free (tmp);
@@ -3395,8 +3580,8 @@ gtk_window_get_icon_name (GtkWindow *window)
  * Gets the value set by gtk_window_set_icon() (or if you've
  * called gtk_window_set_icon_list(), gets the first icon in
  * the icon list).
- * 
- * Return value: icon for window
+ *
+ * Return value: (transfer none): icon for window
  **/
 GdkPixbuf*
 gtk_window_get_icon (GtkWindow  *window)
@@ -3551,7 +3736,7 @@ gtk_window_set_default_icon (GdkPixbuf *icon)
 /**
  * gtk_window_set_default_icon_name:
  * @name: the name of the themed icon
- * 
+ *
  * Sets an icon to be used as fallback for windows that haven't
  * had gtk_window_set_icon_list() called on them from a named
  * themed icon, see gtk_window_set_icon_name().
@@ -3598,6 +3783,25 @@ gtk_window_set_default_icon_name (const gchar *name)
   g_list_free (toplevels);
 }
 
+/**
+ * gtk_window_get_default_icon_name:
+ *
+ * Returns the fallback icon name for windows that has been set
+ * with gtk_window_set_default_icon_name(). The returned
+ * string is owned by GTK+ and should not be modified. It
+ * is only valid until the next call to
+ * gtk_window_set_default_icon_name().
+ *
+ * Returns: the fallback icon name for windows
+ *
+ * Since: 2.16
+ */
+const gchar *
+gtk_window_get_default_icon_name (void)
+{
+  return default_icon_name;
+}
+
 /**
  * gtk_window_set_default_icon_from_file:
  * @filename: location of icon file
@@ -3812,8 +4016,8 @@ gtk_window_resize (GtkWindow *window,
 /**
  * gtk_window_get_size:
  * @window: a #GtkWindow
- * @width: return location for width, or %NULL
- * @height: return location for height, or %NULL
+ * @width: (out): return location for width, or %NULL
+ * @height: (out): return location for height, or %NULL
  *
  * Obtains the current size of @window. If @window is not onscreen,
  * it returns the size GTK+ will suggest to the <link
@@ -3833,7 +4037,7 @@ gtk_window_resize (GtkWindow *window,
  * because the size of the window may change between the time that you
  * get the size and the time that you perform some action assuming
  * that size is the current size. To avoid race conditions, connect to
- * "configure_event" on the window and adjust your size-dependent
+ * "configure-event" on the window and adjust your size-dependent
  * state to match the size delivered in the #GdkEventConfigure.
  *
  * Note 2: The returned size does <emphasis>not</emphasis> include the
@@ -4218,6 +4422,7 @@ static void
 gtk_window_finalize (GObject *object)
 {
   GtkWindow *window = GTK_WINDOW (object);
+  GtkWindowPrivate *priv = GTK_WINDOW_GET_PRIVATE (window);
   GtkMnemonicHash *mnemonic_hash;
 
   g_free (window->title);
@@ -4245,11 +4450,11 @@ gtk_window_finalize (GObject *object)
     }
 
   if (window->screen)
-    {
-      g_signal_handlers_disconnect_by_func (window->screen,
-                                           gtk_window_on_composited_changed, window);
-    }
-      
+    g_signal_handlers_disconnect_by_func (window->screen,
+                                          gtk_window_on_composited_changed, window);
+
+  g_free (priv->startup_id);
+
   G_OBJECT_CLASS (gtk_window_parent_class)->finalize (object);
 }
 
@@ -4354,6 +4559,7 @@ gtk_window_map (GtkWidget *widget)
   GtkWindow *window = GTK_WINDOW (widget);
   GtkWindowPrivate *priv = GTK_WINDOW_GET_PRIVATE (window);
   GdkWindow *toplevel;
+  gboolean auto_mnemonics;
 
   GTK_WIDGET_SET_FLAGS (widget, GTK_MAPPED);
 
@@ -4419,7 +4625,8 @@ gtk_window_map (GtkWidget *widget)
           /* Make sure we have a "real" id */
           if (!startup_id_is_fake (priv->startup_id)) 
             gdk_notify_startup_complete_with_id (priv->startup_id);
-            
+
+          g_free (priv->startup_id);
           priv->startup_id = NULL;
         }
       else if (!sent_startup_notification)
@@ -4428,6 +4635,14 @@ gtk_window_map (GtkWidget *widget)
           gdk_notify_startup_complete ();
         }
     }
+
+  /* if auto-mnemonics is enabled and mnemonics visible is not already set
+   * (as in the case of popup menus), then hide mnemonics initially
+   */
+  g_object_get (gtk_widget_get_settings (widget), "gtk-auto-mnemonics",
+                &auto_mnemonics, NULL);
+  if (auto_mnemonics && !priv->mnemonics_visible_set)
+    gtk_window_set_mnemonics_visible (window, FALSE);
 }
 
 static gboolean
@@ -4707,8 +4922,8 @@ gtk_window_unrealize (GtkWidget *widget)
 
   /* Icons */
   gtk_window_unrealize_icon (window);
-  
-  (* GTK_WIDGET_CLASS (gtk_window_parent_class)->unrealize) (widget);
+
+  GTK_WIDGET_CLASS (gtk_window_parent_class)->unrealize (widget);
 }
 
 static void
@@ -4935,7 +5150,9 @@ _gtk_window_query_nonaccels (GtkWindow      *window,
  * overriding the standard key handling for a toplevel window.
  *
  * Return value: %TRUE if a widget in the focus chain handled the event.
- **/
+ *
+ * Since: 2.4
+ */
 gboolean
 gtk_window_propagate_key_event (GtkWindow        *window,
                                 GdkEventKey      *event)
@@ -5102,10 +5319,17 @@ gtk_window_focus_out_event (GtkWidget     *widget,
                            GdkEventFocus *event)
 {
   GtkWindow *window = GTK_WINDOW (widget);
+  gboolean auto_mnemonics;
 
   _gtk_window_set_has_toplevel_focus (window, FALSE);
   _gtk_window_set_is_active (window, FALSE);
 
+  /* set the mnemonic-visible property to false */
+  g_object_get (gtk_widget_get_settings (widget),
+                "gtk-auto-mnemonics", &auto_mnemonics, NULL);
+  if (auto_mnemonics)
+    gtk_window_set_mnemonics_visible (window, FALSE);
+
   return FALSE;
 }
 
@@ -5131,7 +5355,7 @@ send_client_message_to_embedded_windows (GtkWidget *widget,
       
       while (embedded_windows)
        {
-         guint xid = GPOINTER_TO_UINT (embedded_windows->data);
+         GdkNativeWindow xid = GDK_GPOINTER_TO_NATIVE_WINDOW(embedded_windows->data);
          gdk_event_send_client_message_for_display (gtk_widget_get_display (widget), send_event, xid);
          embedded_windows = embedded_windows->next;
        }
@@ -5464,6 +5688,13 @@ gtk_window_compute_configure_request_size (GtkWindow *window,
       if (info->resize_height > 0)
         *height = info->resize_height;
     }
+
+  /* Don't ever request zero width or height, its not supported by
+     gdk. The size allocation code will round it to 1 anyway but if
+     we do it then the value returned from this function will is
+     not comparable to the size allocation read from the GtkWindow. */
+  *width = MAX (*width, 1);
+  *height = MAX (*height, 1);
 }
 
 static GtkWindowPosition
@@ -5562,7 +5793,7 @@ clamp_window_to_rectangle (gint               *x,
                            const GdkRectangle *rect)
 {
 #ifdef DEBUGGING_OUTPUT
-  g_print ("%s: %+d%+d %dx%d: %+d%+d: %dx%d", __FUNCTION__, rect->x, rect->y, rect->width, rect->height, *x, *y, w, h);
+  g_print ("%s: %+d%+d %dx%d: %+d%+d: %dx%d", G_STRFUNC, rect->x, rect->y, rect->width, rect->height, *x, *y, w, h);
 #endif
 
   /* If it is too large, center it. If it fits on the monitor but is
@@ -6590,7 +6821,7 @@ gtk_window_present_with_time (GtkWindow *window,
  * in which case the window will be iconified before it ever appears
  * onscreen.
  *
- * You can track iconification via the "window_state_event" signal
+ * You can track iconification via the "window-state-event" signal
  * on #GtkWidget.
  * 
  **/
@@ -6625,7 +6856,7 @@ gtk_window_iconify (GtkWindow *window)
  * linkend="gtk-X11-arch">window manager</link>) could iconify it
  * again before your code which assumes deiconification gets to run.
  *
- * You can track iconification via the "window_state_event" signal
+ * You can track iconification via the "window-state-event" signal
  * on #GtkWidget.
  **/
 void
@@ -6663,7 +6894,7 @@ gtk_window_deiconify (GtkWindow *window)
  *
  * It's permitted to call this function before showing a window.
  *
- * You can track stickiness via the "window_state_event" signal
+ * You can track stickiness via the "window-state-event" signal
  * on #GtkWidget.
  * 
  **/
@@ -6699,7 +6930,7 @@ gtk_window_stick (GtkWindow *window)
  * manager</link>) could stick it again. But normally the window will
  * end up stuck. Just don't write code that crashes if not.
  *
- * You can track stickiness via the "window_state_event" signal
+ * You can track stickiness via the "window-state-event" signal
  * on #GtkWidget.
  * 
  **/
@@ -6740,7 +6971,7 @@ gtk_window_unstick (GtkWindow *window)
  * in which case the window will be maximized when it appears onscreen
  * initially.
  *
- * You can track maximization via the "window_state_event" signal
+ * You can track maximization via the "window-state-event" signal
  * on #GtkWidget.
  * 
  **/
@@ -6776,7 +7007,7 @@ gtk_window_maximize (GtkWindow *window)
  * managers honor requests to unmaximize. But normally the window will
  * end up unmaximized. Just don't write code that crashes if not.
  *
- * You can track maximization via the "window_state_event" signal
+ * You can track maximization via the "window-state-event" signal
  * on #GtkWidget.
  * 
  **/
@@ -6813,7 +7044,7 @@ gtk_window_unmaximize (GtkWindow *window)
  * windows. But normally the window will end up fullscreen. Just
  * don't write code that crashes if not.
  *
- * You can track the fullscreen state via the "window_state_event" signal
+ * You can track the fullscreen state via the "window-state-event" signal
  * on #GtkWidget.
  * 
  * Since: 2.2
@@ -6853,7 +7084,7 @@ gtk_window_fullscreen (GtkWindow *window)
  * windows. But normally the window will end up restored to its normal
  * state. Just don't write code that crashes if not.
  *
- * You can track the fullscreen state via the "window_state_event" signal
+ * You can track the fullscreen state via the "window-state-event" signal
  * on #GtkWidget.
  * 
  * Since: 2.2
@@ -6898,7 +7129,7 @@ gtk_window_unfullscreen (GtkWindow *window)
  * in which case the window will be kept above when it appears onscreen
  * initially.
  *
- * You can track the above state via the "window_state_event" signal
+ * You can track the above state via the "window-state-event" signal
  * on #GtkWidget.
  *
  * Note that, according to the <ulink 
@@ -6952,7 +7183,7 @@ gtk_window_set_keep_above (GtkWindow *window,
  * in which case the window will be kept below when it appears onscreen
  * initially.
  *
- * You can track the below state via the "window_state_event" signal
+ * You can track the below state via the "window-state-event" signal
  * on #GtkWidget.
  *
  * Note that, according to the <ulink 
@@ -7003,7 +7234,7 @@ gtk_window_set_resizable (GtkWindow *window,
 {
   g_return_if_fail (GTK_IS_WINDOW (window));
 
-  gtk_window_set_policy (window, FALSE, resizable, FALSE);
+  gtk_window_set_policy_internal (window, FALSE, resizable, FALSE);
 }
 
 /**
@@ -7063,7 +7294,7 @@ gtk_window_set_gravity (GtkWindow *window,
  *
  * Gets the value set by gtk_window_set_gravity().
  *
- * Return value: window gravity
+ * Return value: (transfer none): window gravity
  **/
 GdkGravity
 gtk_window_get_gravity (GtkWindow *window)
@@ -7239,7 +7470,7 @@ gtk_window_set_screen (GtkWindow *window,
     {
       g_signal_handlers_disconnect_by_func (previous_screen,
                                            gtk_window_on_composited_changed, window);
-      g_signal_connect (screen, "composited_changed", 
+      g_signal_connect (screen, "composited-changed", 
                        G_CALLBACK (gtk_window_on_composited_changed), window);
       
       _gtk_widget_propagate_screen_changed (widget, previous_screen);
@@ -7279,7 +7510,7 @@ gtk_window_check_screen (GtkWindow *window)
  *
  * Returns the #GdkScreen associated with @window.
  *
- * Return value: a #GdkScreen.
+ * Return value: (transfer none): a #GdkScreen.
  *
  * Since: 2.2
  */
@@ -7464,7 +7695,8 @@ gtk_window_group_remove_window (GtkWindowGroup *window_group,
  *
  * Returns a list of the #GtkWindows that belong to @window_group.
  *
- * Returns: A newly-allocated list of windows inside the group.
+ * Returns: (element-type GtkWidget) (transfer container): A newly-allocated list of
+ *   windows inside the group.
  *
  * Since: 2.14
  **/
@@ -7495,9 +7727,9 @@ gtk_window_group_list_windows (GtkWindowGroup *window_group)
  *
  * Returns the group for @window or the default group, if
  * @window is %NULL or if @window does not have an explicit
- * window group. 
+ * window group.
  *
- * Returns: the #GtkWindowGroup for a window or the default group
+ * Returns: (transfer none): the #GtkWindowGroup for a window or the default group
  *
  * Since: 2.10
  */
@@ -8012,13 +8244,17 @@ gtk_window_free_key_hash (GtkWindow *window)
  * overriding the standard key handling for a toplevel window.
  *
  * Return value: %TRUE if a mnemonic or accelerator was found and activated.
- **/
+ *
+ * Since: 2.4
+ */
 gboolean
 gtk_window_activate_key (GtkWindow   *window,
                         GdkEventKey *event)
 {
   GtkKeyHash *key_hash;
   GtkWindowKeyEntry *found_entry = NULL;
+  gboolean enable_mnemonics;
+  gboolean enable_accels;
 
   g_return_val_if_fail (GTK_IS_WINDOW (window), FALSE);
   g_return_val_if_fail (event != NULL, FALSE);
@@ -8027,39 +8263,43 @@ gtk_window_activate_key (GtkWindow   *window,
 
   if (key_hash)
     {
+      GSList *tmp_list;
       GSList *entries = _gtk_key_hash_lookup (key_hash,
                                              event->hardware_keycode,
                                              event->state,
                                              gtk_accelerator_get_default_mod_mask (),
                                              event->group);
-      GSList *tmp_list;
+
+      g_object_get (gtk_widget_get_settings (GTK_WIDGET (window)),
+                    "gtk-enable-mnemonics", &enable_mnemonics,
+                    "gtk-enable-accels", &enable_accels,
+                    NULL);
 
       for (tmp_list = entries; tmp_list; tmp_list = tmp_list->next)
        {
          GtkWindowKeyEntry *entry = tmp_list->data;
          if (entry->is_mnemonic)
-           {
-             found_entry = entry;
-             break;
-           }
+            {
+              if (enable_mnemonics)
+               {
+                 found_entry = entry;
+                 break;
+               }
+            }
+          else 
+            {
+              if (enable_accels && !found_entry)
+                {
+                 found_entry = entry;
+                }
+            }
        }
-      
-      if (!found_entry && entries)
-       found_entry = entries->data;
 
       g_slist_free (entries);
     }
 
   if (found_entry)
     {
-      gboolean enable_mnemonics;
-      gboolean enable_accels;
-
-      g_object_get (gtk_widget_get_settings (GTK_WIDGET (window)),
-                    "gtk-enable-mnemonics", &enable_mnemonics,
-                    "gtk-enable-accels", &enable_accels,
-                    NULL);
-
       if (found_entry->is_mnemonic)
         {
           if (enable_mnemonics)
@@ -8130,6 +8370,41 @@ _gtk_window_set_is_active (GtkWindow *window,
     }
 }
 
+/**
+ * _gtk_window_set_is_toplevel:
+ * @window: a #GtkWindow
+ * @is_toplevel: %TRUE if the window is still a real toplevel (nominally a
+ * parent of the root window); %FALSE if it is not (for example, for an
+ * in-process, parented GtkPlug)
+ *
+ * Internal function used by #GtkPlug when it gets parented/unparented by a
+ * #GtkSocket.  This keeps the @window's #GTK_TOPLEVEL flag in sync with the
+ * global list of toplevel windows.
+ */
+void
+_gtk_window_set_is_toplevel (GtkWindow *window,
+                            gboolean   is_toplevel)
+{
+  if (gtk_widget_is_toplevel (GTK_WIDGET (window)))
+    g_assert (g_slist_find (toplevel_list, window) != NULL);
+  else
+    g_assert (g_slist_find (toplevel_list, window) == NULL);
+
+  if (is_toplevel == gtk_widget_is_toplevel (GTK_WIDGET (window)))
+    return;
+
+  if (is_toplevel)
+    {
+      GTK_WIDGET_SET_FLAGS (window, GTK_TOPLEVEL);
+      toplevel_list = g_slist_prepend (toplevel_list, window);
+    }
+  else
+    {
+      GTK_WIDGET_UNSET_FLAGS (window, GTK_TOPLEVEL);
+      toplevel_list = g_slist_remove (toplevel_list, window);
+    }
+}
+
 /**
  * _gtk_window_set_has_toplevel_focus:
  * @window: a #GtkWindow
@@ -8177,7 +8452,58 @@ gtk_window_set_auto_startup_notification (gboolean setting)
   disable_startup_notification = !setting;
 }
 
-#ifdef G_OS_WIN32
+/**
+ * gtk_window_get_window_type:
+ * @window: a #GtkWindow
+ *
+ * Gets the type of the window. See #GtkWindowType.
+ *
+ * Return value: the type of the window
+ *
+ * Since: 2.20
+ **/
+GtkWindowType
+gtk_window_get_window_type (GtkWindow *window)
+{
+  g_return_val_if_fail (GTK_IS_WINDOW (window), GTK_WINDOW_TOPLEVEL);
+
+  return window->type;
+}
+
+gboolean
+gtk_window_get_mnemonics_visible (GtkWindow *window)
+{
+  GtkWindowPrivate *priv;
+
+  g_return_val_if_fail (GTK_IS_WINDOW (window), FALSE);
+
+  priv = GTK_WINDOW_GET_PRIVATE (window);
+
+  return priv->mnemonics_visible;
+}
+
+void
+gtk_window_set_mnemonics_visible (GtkWindow *window,
+                                  gboolean   setting)
+{
+  GtkWindowPrivate *priv;
+
+  g_return_if_fail (GTK_IS_WINDOW (window));
+
+  priv = GTK_WINDOW_GET_PRIVATE (window);
+
+  setting = setting != FALSE;
+
+  if (priv->mnemonics_visible != setting)
+    {
+      priv->mnemonics_visible = setting;
+      g_object_notify (G_OBJECT (window), "mnemonics-visible");
+    }
+
+  priv->mnemonics_visible_set = TRUE;
+}
+
+#if defined (G_OS_WIN32) && !defined (_WIN64)
 
 #undef gtk_window_set_icon_from_file