]> Pileus Git - ~andy/gtk/blobdiff - gtk/gtkwindow.c
Deprecate widget flag: GTK_WIDGET_MAPPED
[~andy/gtk] / gtk / gtkwindow.c
index 572565625b9b335f0ccc07c3afd489a611d84f1c..1695e1804139c55add4661d467869f3176a7d63c 100644 (file)
  * GTK+ at ftp://ftp.gtk.org/pub/gtk/. 
  */
 
-#include <config.h>
+#include "config.h"
 #include <string.h>
+#include <stdlib.h>
+#include <errno.h>
 #include <limits.h>
 #include "gdk/gdk.h"
 #include "gdk/gdkkeysyms.h"
 #include "gtkkeyhash.h"
 #include "gtkmain.h"
 #include "gtkmnemonichash.h"
+#include "gtkmenubar.h"
 #include "gtkiconfactory.h"
 #include "gtkicontheme.h"
 #include "gtkmarshalers.h"
 #include "gtkplug.h"
+#include "gtkbuildable.h"
 #include "gtkalias.h"
 
 #ifdef GDK_WINDOWING_X11
@@ -55,7 +59,6 @@ enum {
   FRAME_EVENT,
   ACTIVATE_FOCUS,
   ACTIVATE_DEFAULT,
-  MOVE_FOCUS,
   KEYS_CHANGED,
   LAST_SIGNAL
 };
@@ -89,11 +92,18 @@ enum {
   PROP_DECORATED,
   PROP_DELETABLE,
   PROP_GRAVITY,
+  PROP_TRANSIENT_FOR,
+  PROP_OPACITY,
   
   /* Readonly properties */
   PROP_IS_ACTIVE,
   PROP_HAS_TOPLEVEL_FOCUS,
   
+  /* Writeonly properties */
+  PROP_STARTUP_ID,
+  
+  PROP_MNEMONICS_VISIBLE,
+
   LAST_ARG
 };
 
@@ -172,10 +182,22 @@ struct _GtkWindowPrivate
   guint accept_focus : 1;
   guint focus_on_map : 1;
   guint deletable : 1;
+  guint transient_parent_group : 1;
+
+  guint reset_type_hint : 1;
+  guint opacity_set : 1;
+  guint builder_visible : 1;
+
+  guint mnemonics_visible : 1;
+  guint mnemonics_visible_set : 1;
+
+  GdkWindowTypeHint type_hint;
+
+  gdouble opacity;
+
+  gchar *startup_id;
 };
 
-static void gtk_window_class_init         (GtkWindowClass    *klass);
-static void gtk_window_init               (GtkWindow         *window);
 static void gtk_window_dispose            (GObject           *object);
 static void gtk_window_destroy            (GtkObject         *object);
 static void gtk_window_finalize           (GObject           *object);
@@ -191,6 +213,8 @@ static void gtk_window_size_allocate      (GtkWidget         *widget,
                                           GtkAllocation     *allocation);
 static gint gtk_window_event              (GtkWidget *widget,
                                           GdkEvent *event);
+static gboolean gtk_window_map_event      (GtkWidget         *widget,
+                                           GdkEventAny       *event);
 static gboolean gtk_window_frame_event    (GtkWindow *window,
                                           GdkEvent *event);
 static gint gtk_window_configure_event    (GtkWidget         *widget,
@@ -277,9 +301,10 @@ static void     gtk_window_unrealize_icon             (GtkWindow    *window);
 static void        gtk_window_notify_keys_changed (GtkWindow   *window);
 static GtkKeyHash *gtk_window_get_key_hash        (GtkWindow   *window);
 static void        gtk_window_free_key_hash       (GtkWindow   *window);
+static void       gtk_window_on_composited_changed (GdkScreen *screen,
+                                                    GtkWindow *window);
 
 static GSList      *toplevel_list = NULL;
-static GtkBinClass *parent_class = NULL;
 static guint        window_signals[LAST_SIGNAL] = { 0 };
 static GList       *default_icon_list = NULL;
 static gchar       *default_icon_name = NULL;
@@ -287,6 +312,14 @@ static guint        default_icon_serial = 0;
 static gboolean     disable_startup_notification = FALSE;
 static gboolean     sent_startup_notification = FALSE;
 
+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;
+
 static void gtk_window_set_property (GObject         *object,
                                     guint            prop_id,
                                     const GValue    *value,
@@ -296,33 +329,30 @@ static void gtk_window_get_property (GObject         *object,
                                     GValue          *value,
                                     GParamSpec      *pspec);
 
-
-GType
-gtk_window_get_type (void)
-{
-  static GType window_type = 0;
-
-  if (!window_type)
-    {
-      static const GTypeInfo window_info =
-      {
-       sizeof (GtkWindowClass),
-       NULL,           /* base_init */
-       NULL,           /* base_finalize */
-       (GClassInitFunc) gtk_window_class_init,
-       NULL,           /* class_finalize */
-       NULL,           /* class_data */
-       sizeof (GtkWindow),
-       0,              /* n_preallocs */
-       (GInstanceInitFunc) gtk_window_init,
-      };
-
-      window_type = g_type_register_static (GTK_TYPE_BIN, I_("GtkWindow"),
-                                           &window_info, 0);
-    }
-
-  return window_type;
-}
+/* GtkBuildable */
+static void gtk_window_buildable_interface_init  (GtkBuildableIface *iface);
+static void gtk_window_buildable_set_buildable_property (GtkBuildable        *buildable,
+                                                        GtkBuilder          *builder,
+                                                        const gchar         *name,
+                                                        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,
+                         G_IMPLEMENT_INTERFACE (GTK_TYPE_BUILDABLE,
+                                               gtk_window_buildable_interface_init))
 
 static void
 add_tab_bindings (GtkBindingSet    *binding_set,
@@ -330,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);
 }
 
@@ -345,19 +375,47 @@ 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);
 }
 
+static guint32
+extract_time_from_startup_id (const gchar* startup_id)
+{
+  gchar *timestr = g_strrstr (startup_id, "_TIME");
+  guint32 retval = GDK_CURRENT_TIME;
+
+  if (timestr)
+    {
+      gchar *end;
+      guint32 timestamp; 
+    
+      /* Skip past the "_TIME" part */
+      timestr += 5;
+
+      errno = 0;
+      timestamp = strtoul (timestr, &end, 0);
+      if (end != timestr && errno == 0)
+        retval = timestamp;
+    }
+
+  return retval;
+}
+
+static gboolean
+startup_id_is_fake (const gchar* startup_id)
+{
+  return strncmp (startup_id, "_TIME", 5) == 0;
+}
 
 static void
 gtk_window_class_init (GtkWindowClass *klass)
@@ -372,7 +430,11 @@ gtk_window_class_init (GtkWindowClass *klass)
   widget_class = (GtkWidgetClass*) klass;
   container_class = (GtkContainerClass*) klass;
   
-  parent_class = g_type_class_peek_parent (klass);
+  quark_gtk_embedded = g_quark_from_static_string ("gtk-embedded");
+  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;
@@ -385,6 +447,7 @@ gtk_window_class_init (GtkWindowClass *klass)
   widget_class->show = gtk_window_show;
   widget_class->hide = gtk_window_hide;
   widget_class->map = gtk_window_map;
+  widget_class->map_event = gtk_window_map_event;
   widget_class->unmap = gtk_window_unmap;
   widget_class->realize = gtk_window_realize;
   widget_class->unrealize = gtk_window_unrealize;
@@ -399,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;
@@ -440,6 +502,23 @@ gtk_window_class_init (GtkWindowClass *klass)
                                                        NULL,
                                                        GTK_PARAM_READWRITE));
 
+  /**
+   * GtkWindow:startup-id:
+   *
+   * The :startup-id is a write-only property for setting window's
+   * startup notification identifier. See gtk_window_set_startup_id()
+   * for more details.
+   *
+   * Since: 2.12
+   */
+  g_object_class_install_property (gobject_class,
+                                   PROP_STARTUP_ID,
+                                   g_param_spec_string ("startup-id",
+                                                       P_("Startup ID"),
+                                                       P_("Unique startup identifier for the window used by startup-notification"),
+                                                       NULL,
+                                                       GTK_PARAM_WRITABLE));
+
   g_object_class_install_property (gobject_class,
                                    PROP_ALLOW_SHRINK,
                                    g_param_spec_boolean ("allow-shrink",
@@ -517,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:
@@ -592,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.
    *
@@ -607,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.
    *
@@ -669,8 +755,43 @@ gtk_window_class_init (GtkWindowClass *klass)
                                                      GDK_GRAVITY_NORTH_WEST,
                                                      GTK_PARAM_READWRITE));
 
+
+  /**
+   * GtkWindow:transient-for:
+   *
+   * The transient parent of the window. See gtk_window_set_transient_for() for
+   * more details about transient windows.
+   *
+   * Since: 2.10
+   */
+  g_object_class_install_property (gobject_class,
+                                  PROP_TRANSIENT_FOR,
+                                  g_param_spec_object ("transient-for",
+                                                       P_("Transient for Window"),
+                                                       P_("The transient parent of the dialog"),
+                                                       GTK_TYPE_WINDOW,
+                                                       GTK_PARAM_READWRITE| G_PARAM_CONSTRUCT));
+
+  /**
+   * GtkWindow:opacity:
+   *
+   * The requested opacity of the window. See gtk_window_set_opacity() for
+   * more details about window opacity.
+   *
+   * Since: 2.12
+   */
+  g_object_class_install_property (gobject_class,
+                                  PROP_OPACITY,
+                                  g_param_spec_double ("opacity",
+                                                       P_("Opacity for Window"),
+                                                       P_("The opacity of the window, from 0 to 1"),
+                                                       0.0,
+                                                       1.0,
+                                                       1.0,
+                                                       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),
@@ -680,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),
@@ -689,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),
@@ -699,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),
@@ -709,19 +848,15 @@ gtk_window_class_init (GtkWindowClass *klass)
                   G_TYPE_NONE,
                   0);
 
-  window_signals[MOVE_FOCUS] =
-    g_signal_new (I_("move_focus"),
-                  G_TYPE_FROM_CLASS (gobject_class),
-                  G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
-                  G_STRUCT_OFFSET (GtkWindowClass, move_focus),
-                  NULL, NULL,
-                  _gtk_marshal_VOID__ENUM,
-                  G_TYPE_NONE,
-                  1,
-                  GTK_TYPE_DIRECTION_TYPE);
-
+  /**
+   * 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),
@@ -737,15 +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);
   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);
@@ -802,22 +938,23 @@ gtk_window_init (GtkWindow *window)
   priv->accept_focus = TRUE;
   priv->focus_on_map = TRUE;
   priv->deletable = TRUE;
+  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)
     gtk_widget_set_colormap (GTK_WIDGET (window), colormap);
   
-  g_object_ref (window);
-  gtk_object_sink (GTK_OBJECT (window));
+  g_object_ref_sink (window);
   window->has_user_ref_count = TRUE;
   toplevel_list = g_slist_prepend (toplevel_list, window);
 
   gtk_decorated_window_init (window);
 
-  g_signal_connect (window,
-                   "event",
-                   G_CALLBACK (gtk_window_event),
-                   NULL);
+  g_signal_connect (window->screen, "composited-changed",
+                   G_CALLBACK (gtk_window_on_composited_changed), window);
 }
 
 static void
@@ -827,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:
@@ -841,6 +981,9 @@ gtk_window_set_property (GObject      *object,
     case PROP_ROLE:
       gtk_window_set_role (window, g_value_get_string (value));
       break;
+    case PROP_STARTUP_ID:
+      gtk_window_set_startup_id (window, g_value_get_string (value));
+      break; 
     case PROP_ALLOW_SHRINK:
       window->allow_shrink = g_value_get_boolean (value);
       gtk_widget_queue_resize (GTK_WIDGET (window));
@@ -917,7 +1060,17 @@ gtk_window_set_property (GObject      *object,
     case PROP_GRAVITY:
       gtk_window_set_gravity (window, g_value_get_enum (value));
       break;
+    case PROP_TRANSIENT_FOR:
+      gtk_window_set_transient_for (window, g_value_get_object (value));
+      break;
+    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;
     }
 }
@@ -929,9 +1082,11 @@ gtk_window_get_property (GObject      *object,
                         GParamSpec   *pspec)
 {
   GtkWindow  *window;
+  GtkWindowPrivate *priv;
 
   window = GTK_WINDOW (object);
-
+  priv = GTK_WINDOW_GET_PRIVATE (window);
+  
   switch (prop_id)
     {
       GtkWindowGeometryInfo *info;
@@ -992,8 +1147,7 @@ gtk_window_get_property (GObject      *object,
       g_value_set_boolean (value, window->has_toplevel_focus);
       break;
     case PROP_TYPE_HINT:
-      g_value_set_enum (value,
-                        window->type_hint);
+      g_value_set_enum (value, priv->type_hint);
       break;
     case PROP_SKIP_TASKBAR_HINT:
       g_value_set_boolean (value,
@@ -1024,12 +1178,164 @@ gtk_window_get_property (GObject      *object,
     case PROP_GRAVITY:
       g_value_set_enum (value, gtk_window_get_gravity (window));
       break;
+    case PROP_TRANSIENT_FOR:
+      g_value_set_object (value, gtk_window_get_transient_for (window));
+      break;
+    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;
     }
 }
 
+static void
+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
+gtk_window_buildable_set_buildable_property (GtkBuildable        *buildable,
+                                            GtkBuilder          *builder,
+                                            const gchar         *name,
+                                            const GValue        *value)
+{
+  GtkWindowPrivate *priv = GTK_WINDOW_GET_PRIVATE (buildable);
+
+  if (strcmp (name, "visible") == 0 && g_value_get_boolean (value))
+    priv->builder_visible = TRUE;
+  else
+    parent_buildable_iface->set_buildable_property (buildable, builder, name, value);
+}
+
+static void
+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));
+
+  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);
+}
+
 /**
  * gtk_window_new:
  * @type: type of window
@@ -1188,6 +1494,66 @@ gtk_window_set_role (GtkWindow   *window,
   g_object_notify (G_OBJECT (window), "role");
 }
 
+/**
+ * gtk_window_set_startup_id:
+ * @window: a #GtkWindow
+ * @startup_id: a string with startup-notification identifier
+ *
+ * Startup notification identifiers are used by desktop environment to 
+ * track application startup, to provide user feedback and other 
+ * features. This function changes the corresponding property on the
+ * underlying GdkWindow. Normally, startup identifier is managed 
+ * automatically and you should only use this function in special cases
+ * like transferring focus from other processes. You should use this
+ * function before calling gtk_window_present() or any equivalent
+ * function generating a window map event.
+ *
+ * This function is only useful on X11, not with other GTK+ targets.
+ * 
+ * Since: 2.12
+ **/
+void
+gtk_window_set_startup_id (GtkWindow   *window,
+                           const gchar *startup_id)
+{
+  GtkWindowPrivate *priv;
+
+  g_return_if_fail (GTK_IS_WINDOW (window));
+
+  priv = GTK_WINDOW_GET_PRIVATE (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))
+       gtk_window_present_with_time (window, timestamp);
+      else 
+        {
+          gdk_window_set_startup_id (GTK_WIDGET (window)->window,
+                                     priv->startup_id);
+          
+          /* If window is mapped, terminate the startup-notification too */
+          if (gtk_widget_get_mapped (GTK_WIDGET (window)) &&
+              !disable_startup_notification)
+            gdk_notify_startup_complete_with_id (priv->startup_id);
+        }
+    }
+
+  g_object_notify (G_OBJECT (window), "startup-id");
+}
+
 /**
  * gtk_window_get_role:
  * @window: a #GtkWindow
@@ -1210,7 +1576,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
@@ -1227,7 +1593,7 @@ gtk_window_set_focus (GtkWindow *window,
   if (focus)
     {
       g_return_if_fail (GTK_IS_WIDGET (focus));
-      g_return_if_fail (GTK_WIDGET_CAN_FOCUS (focus));
+      g_return_if_fail (gtk_widget_get_can_focus (focus));
     }
 
   if (focus)
@@ -1258,14 +1624,14 @@ _gtk_window_internal_set_focus (GtkWindow *window,
   g_return_if_fail (GTK_IS_WINDOW (window));
 
   if ((window->focus_widget != focus) ||
-      (focus && !GTK_WIDGET_HAS_FOCUS (focus)))
+      (focus && !gtk_widget_has_focus (focus)))
     g_signal_emit (window, window_signals[SET_FOCUS], 0, focus);
 }
 
 /**
  * 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
@@ -1283,7 +1649,7 @@ gtk_window_set_default (GtkWindow *window,
   g_return_if_fail (GTK_IS_WINDOW (window));
 
   if (default_widget)
-    g_return_if_fail (GTK_WIDGET_CAN_DEFAULT (default_widget));
+    g_return_if_fail (gtk_widget_get_can_default (default_widget));
   
   if (window->default_widget != default_widget)
     {
@@ -1297,7 +1663,7 @@ gtk_window_set_default (GtkWindow *window,
          old_default_widget = window->default_widget;
          
          if (window->focus_widget != window->default_widget ||
-             !GTK_WIDGET_RECEIVES_DEFAULT (window->default_widget))
+             !gtk_widget_get_receives_default (window->default_widget))
            GTK_WIDGET_UNSET_FLAGS (window->default_widget, GTK_HAS_DEFAULT);
          gtk_widget_queue_draw (window->default_widget);
        }
@@ -1307,7 +1673,7 @@ gtk_window_set_default (GtkWindow *window,
       if (window->default_widget)
        {
          if (window->focus_widget == NULL ||
-             !GTK_WIDGET_RECEIVES_DEFAULT (window->focus_widget))
+             !gtk_widget_get_receives_default (window->focus_widget))
            GTK_WIDGET_SET_FLAGS (window->default_widget, GTK_HAS_DEFAULT);
          gtk_widget_queue_draw (window->default_widget);
        }
@@ -1323,14 +1689,31 @@ gtk_window_set_default (GtkWindow *window,
     }
 }
 
-void
-gtk_window_set_policy (GtkWindow *window,
-                      gboolean   allow_shrink,
-                      gboolean   allow_grow,
-                      gboolean   auto_shrink)
+/**
+ * gtk_window_get_default_widget:
+ * @window: a #GtkWindow
+ *
+ * Returns the default widget for @window. See gtk_window_set_default()
+ * for more details.
+ *
+ * Returns: the default widget, or %NULL if there is none.
+ *
+ * Since: 2.14
+ **/
+GtkWidget *
+gtk_window_get_default_widget (GtkWindow *window)
 {
-  g_return_if_fail (GTK_IS_WINDOW (window));
+  g_return_val_if_fail (GTK_IS_WINDOW (window), NULL);
+
+  return window->default_widget;
+}
 
+static void
+gtk_window_set_policy_internal (GtkWindow *window,
+                                gboolean   allow_shrink,
+                                gboolean   allow_grow,
+                                gboolean   auto_shrink)
+{
   window->allow_shrink = (allow_shrink != FALSE);
   window->allow_grow = (allow_grow != FALSE);
 
@@ -1339,8 +1722,19 @@ 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 (GTK_WIDGET (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
@@ -1348,7 +1742,6 @@ handle_keys_changed (gpointer data)
 {
   GtkWindow *window;
 
-  GDK_THREADS_ENTER ();
   window = GTK_WINDOW (data);
 
   if (window->keys_changed_handler)
@@ -1358,7 +1751,6 @@ handle_keys_changed (gpointer data)
     }
 
   g_signal_emit (window, window_signals[KEYS_CHANGED], 0);
-  GDK_THREADS_LEAVE ();
   
   return FALSE;
 }
@@ -1367,7 +1759,7 @@ static void
 gtk_window_notify_keys_changed (GtkWindow *window)
 {
   if (!window->keys_changed_handler)
-    window->keys_changed_handler = g_idle_add (handle_keys_changed, window);
+    window->keys_changed_handler = gdk_threads_add_idle (handle_keys_changed, window);
 }
 
 /**
@@ -1387,9 +1779,10 @@ 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);
 }
 
 /**
@@ -1410,6 +1803,7 @@ gtk_window_remove_accel_group (GtkWindow     *window,
                                        gtk_window_notify_keys_changed,
                                        window);
   _gtk_accel_group_detach (accel_group, G_OBJECT (window));
+  gtk_window_notify_keys_changed (window);
 }
 
 static GtkMnemonicHash *
@@ -1556,7 +1950,7 @@ gtk_window_set_position (GtkWindow         *window,
        */
       info->position_constraints_changed = TRUE;
 
-      gtk_widget_queue_resize (GTK_WIDGET (window));
+      gtk_widget_queue_resize_no_redraw (GTK_WIDGET (window));
     }
 
   window->position = position;
@@ -1577,7 +1971,7 @@ gtk_window_activate_focus (GtkWindow *window)
 {
   g_return_val_if_fail (GTK_IS_WINDOW (window), FALSE);
 
-  if (window->focus_widget && GTK_WIDGET_IS_SENSITIVE (window->focus_widget))
+  if (window->focus_widget && gtk_widget_is_sensitive (window->focus_widget))
     return gtk_widget_activate (window->focus_widget);
 
   return FALSE;
@@ -1590,10 +1984,10 @@ gtk_window_activate_focus (GtkWindow *window)
  * Retrieves the current focused widget within the 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.
+ * is not focused then  <literal>gtk_widget_has_focus (widget)</literal> will
+ * 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)
@@ -1609,7 +2003,7 @@ gtk_window_get_focus (GtkWindow *window)
  * 
  * Activates the default widget for the window, unless the current 
  * focused widget has been configured to receive the default action 
- * (see #GTK_RECEIVES_DEFAULT in #GtkWidgetFlags), in which case the
+ * (see gtk_widget_set_receives_default()), in which case the
  * focused widget is activated. 
  * 
  * Return value: %TRUE if a widget got activated.
@@ -1619,10 +2013,10 @@ gtk_window_activate_default (GtkWindow *window)
 {
   g_return_val_if_fail (GTK_IS_WINDOW (window), FALSE);
 
-  if (window->default_widget && GTK_WIDGET_IS_SENSITIVE (window->default_widget) &&
-      (!window->focus_widget || !GTK_WIDGET_RECEIVES_DEFAULT (window->focus_widget)))
+  if (window->default_widget && gtk_widget_is_sensitive (window->default_widget) &&
+      (!window->focus_widget || !gtk_widget_get_receives_default (window->focus_widget)))
     return gtk_widget_activate (window->default_widget);
-  else if (window->focus_widget && GTK_WIDGET_IS_SENSITIVE (window->focus_widget))
+  else if (window->focus_widget && gtk_widget_is_sensitive (window->focus_widget))
     return gtk_widget_activate (window->focus_widget);
 
   return FALSE;
@@ -1646,6 +2040,8 @@ void
 gtk_window_set_modal (GtkWindow *window,
                      gboolean   modal)
 {
+  GtkWidget *widget;
+
   g_return_if_fail (GTK_IS_WINDOW (window));
 
   modal = modal != FALSE;
@@ -1653,24 +2049,23 @@ gtk_window_set_modal (GtkWindow *window,
     return;
   
   window->modal = modal;
+  widget = GTK_WIDGET (window);
   
   /* adjust desired modality state */
   if (GTK_WIDGET_REALIZED (window))
     {
-      GtkWidget *widget = GTK_WIDGET (window);
-      
       if (window->modal)
        gdk_window_set_modal_hint (widget->window, TRUE);
       else
        gdk_window_set_modal_hint (widget->window, FALSE);
     }
 
-  if (GTK_WIDGET_VISIBLE (window))
+  if (gtk_widget_get_visible (widget))
     {
       if (window->modal)
-       gtk_grab_add (GTK_WIDGET (window));
+       gtk_grab_add (widget);
       else
-       gtk_grab_remove (GTK_WIDGET (window));
+       gtk_grab_remove (widget);
     }
 
   g_object_notify (G_OBJECT (window), "modal");
@@ -1702,8 +2097,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)
@@ -1718,37 +2113,35 @@ 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;
 
   g_return_if_fail (GTK_IS_WINDOW (window));
 
-  embedded_windows = g_object_get_data (G_OBJECT (window), "gtk-embedded");
+  embedded_windows = g_object_get_qdata (G_OBJECT (window), quark_gtk_embedded);
   if (embedded_windows)
-    g_object_steal_qdata (G_OBJECT (window), 
-                         g_quark_from_static_string ("gtk-embedded"));
+    g_object_steal_qdata (G_OBJECT (window), quark_gtk_embedded);
   embedded_windows = g_list_prepend (embedded_windows,
                                     GUINT_TO_POINTER (xid));
 
-  g_object_set_data_full (G_OBJECT (window), I_("gtk-embedded")
-                         embedded_windows,
-                         embedded_windows ?
-                           (GDestroyNotify) g_list_free : NULL);
+  g_object_set_qdata_full (G_OBJECT (window), quark_gtk_embedded
+                          embedded_windows,
+                          embedded_windows ?
+                          (GDestroyNotify) g_list_free : NULL);
 }
 
 void
-gtk_window_remove_embedded_xid (GtkWindow *window, guint xid)
+gtk_window_remove_embedded_xid (GtkWindow *window, GdkNativeWindow xid)
 {
   GList *embedded_windows;
   GList *node;
 
   g_return_if_fail (GTK_IS_WINDOW (window));
   
-  embedded_windows = g_object_get_data (G_OBJECT (window), "gtk-embedded");
+  embedded_windows = g_object_get_qdata (G_OBJECT (window), quark_gtk_embedded);
   if (embedded_windows)
-    g_object_steal_qdata (G_OBJECT (window), 
-                         g_quark_from_static_string ("gtk-embedded"));
+    g_object_steal_qdata (G_OBJECT (window), quark_gtk_embedded);
 
   node = g_list_find (embedded_windows, GUINT_TO_POINTER (xid));
   if (node)
@@ -1757,10 +2150,10 @@ gtk_window_remove_embedded_xid (GtkWindow *window, guint xid)
       g_list_free_1 (node);
     }
   
-  g_object_set_data_full (G_OBJECT (window), I_("gtk-embedded"),
-                         embedded_windows,
-                         embedded_windows ?
-                           (GDestroyNotify) g_list_free : NULL);
+  g_object_set_qdata_full (G_OBJECT (window), quark_gtk_embedded,
+                          embedded_windows,
+                          embedded_windows ?
+                          (GDestroyNotify) g_list_free : NULL);
 }
 
 void       
@@ -1781,7 +2174,7 @@ gtk_window_dispose (GObject *object)
   gtk_window_set_focus (window, NULL);
   gtk_window_set_default (window, NULL);
 
-  G_OBJECT_CLASS (parent_class)->dispose (object);
+  G_OBJECT_CLASS (gtk_window_parent_class)->dispose (object);
 }
 
 static void
@@ -1827,7 +2220,7 @@ gtk_window_transient_parent_unrealized (GtkWidget *parent,
 {
   if (GTK_WIDGET_REALIZED (window))
     gdk_property_delete (window->window, 
-                        gdk_atom_intern ("WM_TRANSIENT_FOR", FALSE));
+                        gdk_atom_intern_static_string ("WM_TRANSIENT_FOR"));
 }
 
 static void
@@ -1841,12 +2234,10 @@ gtk_window_transient_parent_screen_changed (GtkWindow   *parent,
 static void       
 gtk_window_unset_transient_for  (GtkWindow *window)
 {
+  GtkWindowPrivate *priv = GTK_WINDOW_GET_PRIVATE (window);
+  
   if (window->transient_parent)
     {
-      if (window->transient_parent->group)
-       gtk_window_group_remove_window (window->transient_parent->group,
-                                       window);
-
       g_signal_handlers_disconnect_by_func (window->transient_parent,
                                            gtk_window_transient_parent_realized,
                                            window);
@@ -1864,13 +2255,20 @@ gtk_window_unset_transient_for  (GtkWindow *window)
         disconnect_parent_destroyed (window);
       
       window->transient_parent = NULL;
+
+      if (priv->transient_parent_group)
+       {
+         priv->transient_parent_group = FALSE;
+         gtk_window_group_remove_window (window->group,
+                                         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
@@ -1880,20 +2278,20 @@ gtk_window_unset_transient_for  (GtkWindow *window)
  * functions in GTK+ will sometimes call
  * gtk_window_set_transient_for() on your behalf.
  *
- * On Windows, this function will and put the child window
- * on top of the parent, much as the window manager would have
- * done on X.
+ * On Windows, this function puts the child window on top of the parent, 
+ * much as the window manager would have done on X.
  * 
  **/
 void       
 gtk_window_set_transient_for  (GtkWindow *window, 
                               GtkWindow *parent)
 {
+  GtkWindowPrivate *priv = GTK_WINDOW_GET_PRIVATE (window);
+  
   g_return_if_fail (GTK_IS_WINDOW (window));
   g_return_if_fail (parent == NULL || GTK_IS_WINDOW (parent));
   g_return_if_fail (window != parent);
 
-    
   if (window->transient_parent)
     {
       if (GTK_WIDGET_REALIZED (window) && 
@@ -1906,7 +2304,7 @@ gtk_window_set_transient_for  (GtkWindow *window,
     }
 
   window->transient_parent = parent;
-
+  
   if (parent)
     {
       g_signal_connect (parent, "destroy",
@@ -1933,7 +2331,10 @@ gtk_window_set_transient_for  (GtkWindow *window,
                                              GTK_WIDGET (window));
 
       if (parent->group)
-       gtk_window_group_add_window (parent->group, window);
+       {
+         gtk_window_group_add_window (parent->group, window);
+         priv->transient_parent_group = TRUE;
+       }
     }
 }
 
@@ -1944,7 +2345,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 *
@@ -1955,6 +2356,68 @@ gtk_window_get_transient_for (GtkWindow *window)
   return window->transient_parent;
 }
 
+/**
+ * gtk_window_set_opacity:
+ * @window: a #GtkWindow
+ * @opacity: desired opacity, between 0 and 1
+ *
+ * Request the windowing system to make @window partially transparent,
+ * with opacity 0 being fully transparent and 1 fully opaque. (Values
+ * of the opacity parameter are clamped to the [0,1] range.) On X11
+ * this has any effect only on X screens with a compositing manager
+ * running. See gtk_widget_is_composited(). On Windows it should work
+ * always.
+ * 
+ * Note that setting a window's opacity after the window has been
+ * shown causes it to flicker once on Windows.
+ *
+ * Since: 2.12
+ **/
+void       
+gtk_window_set_opacity  (GtkWindow *window, 
+                        gdouble    opacity)
+{
+  GtkWindowPrivate *priv;
+  
+  g_return_if_fail (GTK_IS_WINDOW (window));
+
+  priv = GTK_WINDOW_GET_PRIVATE (window); 
+
+  if (opacity < 0.0)
+    opacity = 0.0;
+  else if (opacity > 1.0)
+    opacity = 1.0;
+
+  priv->opacity_set = TRUE;
+  priv->opacity = opacity;
+
+  if (GTK_WIDGET_REALIZED (window))
+    gdk_window_set_opacity (GTK_WIDGET (window)->window, priv->opacity);
+}
+
+/**
+ * gtk_window_get_opacity:
+ * @window: a #GtkWindow
+ *
+ * Fetches the requested opacity for this window. See
+ * gtk_window_set_opacity().
+ *
+ * Return value: the requested opacity for this window.
+ *
+ * Since: 2.12
+ **/
+gdouble
+gtk_window_get_opacity (GtkWindow *window)
+{
+  GtkWindowPrivate *priv;
+  
+  g_return_val_if_fail (GTK_IS_WINDOW (window), 0.0);
+
+  priv = GTK_WINDOW_GET_PRIVATE (window); 
+
+  return priv->opacity;
+}
+
 /**
  * gtk_window_set_type_hint:
  * @window: a #GtkWindow
@@ -1974,9 +2437,20 @@ void
 gtk_window_set_type_hint (GtkWindow           *window, 
                          GdkWindowTypeHint    hint)
 {
+  GtkWindowPrivate *priv;
+
   g_return_if_fail (GTK_IS_WINDOW (window));
-  g_return_if_fail (!GTK_WIDGET_VISIBLE (window));
-  window->type_hint = hint;
+  g_return_if_fail (!gtk_widget_get_mapped (GTK_WIDGET (window)));
+
+  priv = GTK_WINDOW_GET_PRIVATE (window);
+
+  if (hint < GDK_WINDOW_TYPE_HINT_DROPDOWN_MENU)
+    window->type_hint = hint;
+  else
+    window->type_hint = GDK_WINDOW_TYPE_HINT_NORMAL;
+
+  priv->reset_type_hint = TRUE;
+  priv->type_hint = hint;
 }
 
 /**
@@ -1990,9 +2464,13 @@ gtk_window_set_type_hint (GtkWindow           *window,
 GdkWindowTypeHint
 gtk_window_get_type_hint (GtkWindow *window)
 {
+  GtkWindowPrivate *priv;
+  
   g_return_val_if_fail (GTK_IS_WINDOW (window), GDK_WINDOW_TYPE_HINT_NORMAL);
 
-  return window->type_hint;
+  priv = GTK_WINDOW_GET_PRIVATE (window);
+  
+  return priv->type_hint;
 }
 
 /**
@@ -2400,7 +2878,7 @@ gtk_window_set_geometry_hints (GtkWindow       *window,
       gtk_window_set_gravity (window, geometry->win_gravity);
     }
   
-  gtk_widget_queue_resize (GTK_WIDGET (window));
+  gtk_widget_queue_resize_no_redraw (GTK_WIDGET (window));
 }
 
 /**
@@ -2465,6 +2943,7 @@ gtk_window_get_decorated (GtkWindow *window)
 }
 
 /**
+ * gtk_window_set_deletable:
  * @window: a #GtkWindow
  * @setting: %TRUE to decorate the window as deletable
  *
@@ -2519,6 +2998,8 @@ gtk_window_set_deletable (GtkWindow *window,
  * via gtk_window_set_deletable().
  *
  * Return value: %TRUE if the window has been set to have a close button
+ *
+ * Since: 2.10
  **/
 gboolean
 gtk_window_get_deletable (GtkWindow *window)
@@ -2535,15 +3016,14 @@ gtk_window_get_deletable (GtkWindow *window)
 static GtkWindowIconInfo*
 get_icon_info (GtkWindow *window)
 {
-  return g_object_get_data (G_OBJECT (window),
-                            "gtk-window-icon-info");
+  return g_object_get_qdata (G_OBJECT (window), quark_gtk_window_icon_info);
 }
      
 static void
 free_icon_info (GtkWindowIconInfo *info)
 {
   g_free (info->icon_name);
-  g_free (info);
+  g_slice_free (GtkWindowIconInfo, info);
 }
 
 
@@ -2556,9 +3036,9 @@ ensure_icon_info (GtkWindow *window)
   
   if (info == NULL)
     {
-      info = g_new0 (GtkWindowIconInfo, 1);
-      g_object_set_data_full (G_OBJECT (window),
-                              I_("gtk-window-icon-info"),
+      info = g_slice_new0 (GtkWindowIconInfo);
+      g_object_set_qdata_full (G_OBJECT (window),
+                              quark_gtk_window_icon_info,
                               info,
                               (GDestroyNotify)free_icon_info);
     }
@@ -2575,12 +3055,13 @@ typedef struct {
 static ScreenIconInfo *
 get_screen_icon_info (GdkScreen *screen)
 {
-  ScreenIconInfo *info = g_object_get_data (G_OBJECT (screen), 
-                                           "gtk-window-default-icon-pixmap");
+  ScreenIconInfo *info = g_object_get_qdata (G_OBJECT (screen), 
+                                            quark_gtk_window_default_icon_pixmap);
   if (!info)
     {
-      info = g_new0 (ScreenIconInfo, 1);
-      g_object_set_data (G_OBJECT (screen), I_("gtk-window-default-icon-pixmap"), info);
+      info = g_slice_new0 (ScreenIconInfo);
+      g_object_set_qdata (G_OBJECT (screen), 
+                         quark_gtk_window_default_icon_pixmap, info);
     }
 
   if (info->serial != default_icon_serial)
@@ -2854,10 +3335,7 @@ static void
 gtk_window_unrealize_icon (GtkWindow *window)
 {
   GtkWindowIconInfo *info;
-  GtkWidget *widget;
 
-  widget = GTK_WIDGET (window);
-  
   info = get_icon_info (window);
 
   if (info == NULL)
@@ -2962,8 +3440,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)
@@ -2983,8 +3461,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
@@ -3038,11 +3516,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.
  *
@@ -3059,6 +3537,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);
@@ -3084,7 +3565,7 @@ gtk_window_set_icon_name (GtkWindow   *window,
  *
  * Since: 2.6
  */
-G_CONST_RETURN gchar *
+const gchar *
 gtk_window_get_icon_name (GtkWindow *window)
 {
   GtkWindowIconInfo *info;
@@ -3103,8 +3584,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)
@@ -3150,7 +3631,7 @@ load_pixbuf_verbosely (const char *filename,
  * gtk_window_set_icon_from_file:
  * @window: a #GtkWindow
  * @filename: location of icon file
- * @err: location to store error, or %NULL.
+ * @err: (allow-none): location to store error, or %NULL.
  *
  * Sets the icon for @window.  
  * Warns on failure if @err is %NULL.
@@ -3259,7 +3740,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().
@@ -3306,10 +3787,29 @@ 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
- * @err: location to store error, or %NULL.
+ * @err: (allow-none): location to store error, or %NULL.
  *
  * Sets an icon to be used as fallback for windows that haven't
  * had gtk_window_set_icon_list() called on them from a file
@@ -3399,7 +3899,7 @@ gtk_window_set_default_size_internal (GtkWindow    *window,
   
   g_object_thaw_notify (G_OBJECT (window));
   
-  gtk_widget_queue_resize (GTK_WIDGET (window));
+  gtk_widget_queue_resize_no_redraw (GTK_WIDGET (window));
 }
 
 /**
@@ -3452,8 +3952,8 @@ gtk_window_set_default_size (GtkWindow   *window,
 /**
  * gtk_window_get_default_size:
  * @window: a #GtkWindow
- * @width: location to store the default width, or %NULL
- * @height: location to store the default height, or %NULL
+ * @width: (allow-none): location to store the default width, or %NULL
+ * @height: (allow-none): location to store the default height, or %NULL
  *
  * Gets the default size of the window. A value of -1 for the width or
  * height indicates that a default size has not been explicitly set
@@ -3514,14 +4014,14 @@ gtk_window_resize (GtkWindow *window,
   info->resize_width = width;
   info->resize_height = height;
 
-  gtk_widget_queue_resize (GTK_WIDGET (window));
+  gtk_widget_queue_resize_no_redraw (GTK_WIDGET (window));
 }
 
 /**
  * gtk_window_get_size:
  * @window: a #GtkWindow
- * @width: return location for width, or %NULL
- * @height: return location for height, or %NULL
+ * @width: (allow-none): (out): return location for width, or %NULL
+ * @height: (allow-none): (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
@@ -3541,7 +4041,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
@@ -3575,16 +4075,13 @@ gtk_window_get_size (GtkWindow *window,
                      gint      *height)
 {
   gint w, h;
-  GtkWidget *widget;
   
   g_return_if_fail (GTK_IS_WINDOW (window));
 
-  widget = GTK_WIDGET (window);
-  
   if (width == NULL && height == NULL)
     return;
 
-  if (GTK_WIDGET_MAPPED (window))
+  if (gtk_widget_get_mapped (GTK_WIDGET (window)))
     {
       gdk_drawable_get_size (GTK_WIDGET (window)->window,
                              &w, &h);
@@ -3639,7 +4136,8 @@ gtk_window_get_size (GtkWindow *window,
  * reference point. So, to place a window in the bottom right corner
  * you would first set gravity to south east, then write:
  * <literal>gtk_window_move (window, gdk_screen_width () - window_width,
- * gdk_screen_height () - window_height)</literal>.
+ * gdk_screen_height () - window_height)</literal> (note that this
+ * example does not take multi-head scenarios into account).
  *
  * The Extended Window Manager Hints specification at <ulink 
  * url="http://www.freedesktop.org/Standards/wm-spec">
@@ -3647,8 +4145,7 @@ gtk_window_get_size (GtkWindow *window,
  * nice table of gravities in the "implementation notes" section.
  *
  * The gtk_window_get_position() documentation may also be relevant.
- * 
- **/
+ */
 void
 gtk_window_move (GtkWindow *window,
                  gint       x,
@@ -3663,7 +4160,7 @@ gtk_window_move (GtkWindow *window,
 
   info = gtk_window_get_geometry_info (window, TRUE);  
   
-  if (GTK_WIDGET_MAPPED (window))
+  if (gtk_widget_get_mapped (widget))
     {
       /* we have now sent a request with this position
        * with currently-active constraints, so toggle flag.
@@ -3715,8 +4212,8 @@ gtk_window_move (GtkWindow *window,
 /**
  * gtk_window_get_position:
  * @window: a #GtkWindow
- * @root_x: return location for X coordinate of gravity-determined reference p\oint
- * @root_y: return location for Y coordinate of gravity-determined reference p\oint
+ * @root_x: return location for X coordinate of gravity-determined reference point
+ * @root_y: return location for Y coordinate of gravity-determined reference point
  *
  * This function returns the position you need to pass to
  * gtk_window_move() to keep @window in its current position.  This
@@ -3770,7 +4267,7 @@ gtk_window_get_position (GtkWindow *window,
   
   if (window->gravity == GDK_GRAVITY_STATIC)
     {
-      if (GTK_WIDGET_MAPPED (widget))
+      if (gtk_widget_get_mapped (widget))
         {
           /* This does a server round-trip, which is sort of wrong;
            * but a server round-trip is inevitable for
@@ -3800,7 +4297,7 @@ gtk_window_get_position (GtkWindow *window,
       gint x, y;
       gint w, h;
       
-      if (GTK_WIDGET_MAPPED (widget))
+      if (gtk_widget_get_mapped (widget))
         {
          if (window->frame)
            gdk_window_get_frame_extents (window->frame, &frame_extents);
@@ -3922,13 +4419,14 @@ gtk_window_destroy (GtkObject *object)
 
    gtk_window_free_key_hash (window);
 
-   GTK_OBJECT_CLASS (parent_class)->destroy (object);
+   GTK_OBJECT_CLASS (gtk_window_parent_class)->destroy (object);
 }
 
 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);
@@ -3955,7 +4453,13 @@ gtk_window_finalize (GObject *object)
       window->keys_changed_handler = 0;
     }
 
-  G_OBJECT_CLASS (parent_class)->finalize (object);
+  if (window->screen)
+    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);
 }
 
 static void
@@ -4059,12 +4563,13 @@ 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);
 
   if (window->bin.child &&
-      GTK_WIDGET_VISIBLE (window->bin.child) &&
-      !GTK_WIDGET_MAPPED (window->bin.child))
+      gtk_widget_get_visible (window->bin.child) &&
+      !gtk_widget_get_mapped (window->bin.child))
     gtk_widget_map (window->bin.child);
 
   if (window->frame)
@@ -4100,17 +4605,66 @@ gtk_window_map (GtkWidget *widget)
   window->need_default_size = FALSE;
   window->need_default_position = FALSE;
   
+  if (priv->reset_type_hint)
+    {
+      /* We should only reset the type hint when the application
+       * used gtk_window_set_type_hint() to change the hint.
+       * Some applications use X directly to change the properties;
+       * in that case, we shouldn't overwrite what they did.
+       */
+      gdk_window_set_type_hint (widget->window, priv->type_hint);
+      priv->reset_type_hint = FALSE;
+    }
+
   gdk_window_show (widget->window);
 
   if (window->frame)
     gdk_window_show (window->frame);
 
-  if (!disable_startup_notification &&
-      !sent_startup_notification)
+  if (!disable_startup_notification)
+    {
+      /* Do we have a custom startup-notification id? */
+      if (priv->startup_id != NULL)
+        {
+          /* 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)
+        {
+          sent_startup_notification = TRUE;
+          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
+gtk_window_map_event (GtkWidget   *widget,
+                      GdkEventAny *event)
+{
+  if (!gtk_widget_get_mapped (widget))
     {
-      sent_startup_notification = TRUE;
-      gdk_notify_startup_complete ();
+      /* we should be be unmapped, but are getting a MapEvent, this may happen
+       * to toplevel XWindows if mapping was intercepted by a window manager
+       * and an unmap request occoured while the MapRequestEvent was still
+       * being handled. we work around this situaiton here by re-requesting
+       * the window being unmapped. more details can be found in:
+       *   http://bugzilla.gnome.org/show_bug.cgi?id=316180
+       */
+      gdk_window_hide (widget->window);
     }
+  return FALSE;
 }
 
 static void
@@ -4144,11 +4698,11 @@ gtk_window_unmap (GtkWidget *widget)
     }
 
   state = gdk_window_get_state (widget->window);
-  window->iconify_initially = state & GDK_WINDOW_STATE_ICONIFIED;
-  window->maximize_initially = state & GDK_WINDOW_STATE_MAXIMIZED;
-  window->stick_initially = state & GDK_WINDOW_STATE_STICKY;
-  priv->above_initially = state & GDK_WINDOW_STATE_ABOVE;
-  priv->below_initially = state & GDK_WINDOW_STATE_BELOW;
+  window->iconify_initially = (state & GDK_WINDOW_STATE_ICONIFIED) != 0;
+  window->maximize_initially = (state & GDK_WINDOW_STATE_MAXIMIZED) != 0;
+  window->stick_initially = (state & GDK_WINDOW_STATE_STICKY) != 0;
+  priv->above_initially = (state & GDK_WINDOW_STATE_ABOVE) != 0;
+  priv->below_initially = (state & GDK_WINDOW_STATE_BELOW) != 0;
 }
 
 static void
@@ -4161,7 +4715,6 @@ gtk_window_realize (GtkWidget *widget)
   GtkWindowPrivate *priv;
   
   window = GTK_WINDOW (widget);
-
   priv = GTK_WINDOW_GET_PRIVATE (window);
 
   /* ensure widget tree is properly size allocated */
@@ -4229,6 +4782,9 @@ gtk_window_realize (GtkWidget *widget)
       window->frame = gdk_window_new (gtk_widget_get_root_window (widget),
                                      &attributes, attributes_mask);
                                                 
+      if (priv->opacity_set)
+       gdk_window_set_opacity (window->frame, priv->opacity);
+
       gdk_window_set_user_data (window->frame, widget);
       
       attributes.window_type = GDK_WINDOW_CHILD;
@@ -4238,6 +4794,11 @@ gtk_window_realize (GtkWidget *widget)
       attributes_mask = GDK_WA_X | GDK_WA_Y;
 
       parent_window = window->frame;
+
+      g_signal_connect (window,
+                       "event",
+                       G_CALLBACK (gtk_window_event),
+                       NULL);
     }
   else
     {
@@ -4255,13 +4816,17 @@ gtk_window_realize (GtkWidget *widget)
                            GDK_LEAVE_NOTIFY_MASK |
                            GDK_FOCUS_CHANGE_MASK |
                            GDK_STRUCTURE_MASK);
+  attributes.type_hint = priv->type_hint;
 
-  attributes_mask |= GDK_WA_VISUAL | GDK_WA_COLORMAP;
+  attributes_mask |= GDK_WA_VISUAL | GDK_WA_COLORMAP | GDK_WA_TYPE_HINT;
   attributes_mask |= (window->title ? GDK_WA_TITLE : 0);
   attributes_mask |= (window->wmclass_name ? GDK_WA_WMCLASS : 0);
   
   widget->window = gdk_window_new (parent_window, &attributes, attributes_mask);
 
+  if (!window->has_frame && priv->opacity_set)
+    gdk_window_set_opacity (widget->window, priv->opacity);
+
   gdk_window_enable_synchronized_configure (widget->window);
     
   gdk_window_set_user_data (widget->window, window);
@@ -4288,8 +4853,6 @@ gtk_window_realize (GtkWidget *widget)
   if (!priv->deletable)
     gdk_window_set_functions (widget->window, GDK_FUNC_ALL | GDK_FUNC_CLOSE);
 
-  gdk_window_set_type_hint (widget->window, window->type_hint);
-
   if (gtk_window_get_skip_pager_hint (window))
     gdk_window_set_skip_pager_hint (widget->window, TRUE);
 
@@ -4310,6 +4873,17 @@ gtk_window_realize (GtkWidget *widget)
     gdk_window_set_modal_hint (widget->window, TRUE);
   else
     gdk_window_set_modal_hint (widget->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 (widget->window, timestamp);
+#endif
+      if (!startup_id_is_fake (priv->startup_id)) 
+        gdk_window_set_startup_id (widget->window, priv->startup_id);
+    }
 
   /* Icons */
   gtk_window_realize_icon (window);
@@ -4352,8 +4926,8 @@ gtk_window_unrealize (GtkWidget *widget)
 
   /* Icons */
   gtk_window_unrealize_icon (window);
-  
-  (* GTK_WIDGET_CLASS (parent_class)->unrealize) (widget);
+
+  GTK_WIDGET_CLASS (gtk_window_parent_class)->unrealize (widget);
 }
 
 static void
@@ -4369,7 +4943,7 @@ gtk_window_size_request (GtkWidget      *widget,
   requisition->width = GTK_CONTAINER (window)->border_width * 2;
   requisition->height = GTK_CONTAINER (window)->border_width * 2;
 
-  if (bin->child && GTK_WIDGET_VISIBLE (bin->child))
+  if (bin->child && gtk_widget_get_visible (bin->child))
     {
       GtkRequisition child_requisition;
       
@@ -4390,7 +4964,7 @@ gtk_window_size_allocate (GtkWidget     *widget,
   window = GTK_WINDOW (widget);
   widget->allocation = *allocation;
 
-  if (window->bin.child && GTK_WIDGET_VISIBLE (window->bin.child))
+  if (window->bin.child && gtk_widget_get_visible (window->bin.child))
     {
       child_allocation.x = GTK_CONTAINER (window)->border_width;
       child_allocation.y = GTK_CONTAINER (window)->border_width;
@@ -4489,7 +5063,10 @@ gtk_window_configure_event (GtkWidget         *widget,
    */
 
   if (window->configure_request_count > 0)
-    window->configure_request_count -= 1;
+    {
+      window->configure_request_count -= 1;
+      gdk_window_thaw_toplevel_updates_libgtk_only (widget->window);
+    }
   
   /* As an optimization, we avoid a resize when possible.
    *
@@ -4543,7 +5120,7 @@ _gtk_window_query_nonaccels (GtkWindow      *window,
   if (!accel_mods)
     {
       static const guint bindings[] = {
-       GDK_space, GDK_KP_Space, GDK_Return, GDK_KP_Enter, GDK_Up, GDK_KP_Up, GDK_Down, GDK_KP_Down,
+       GDK_space, GDK_KP_Space, GDK_Return, GDK_ISO_Enter, GDK_KP_Enter, GDK_Up, GDK_KP_Up, GDK_Down, GDK_KP_Down,
        GDK_Left, GDK_KP_Left, GDK_Right, GDK_KP_Right, GDK_Tab, GDK_KP_Tab, GDK_ISO_Left_Tab,
       };
       guint i;
@@ -4577,7 +5154,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)
@@ -4598,7 +5177,7 @@ gtk_window_propagate_key_event (GtkWindow        *window,
     {
       GtkWidget *parent;
       
-      if (GTK_WIDGET_IS_SENSITIVE (focus))
+      if (gtk_widget_is_sensitive (focus))
         handled = gtk_widget_event (focus, (GdkEvent*) event);
       
       parent = focus->parent;
@@ -4633,7 +5212,7 @@ gtk_window_key_press_event (GtkWidget   *widget,
 
   /* Chain up, invokes binding set */
   if (!handled)
-    handled = GTK_WIDGET_CLASS (parent_class)->key_press_event (widget, event);
+    handled = GTK_WIDGET_CLASS (gtk_window_parent_class)->key_press_event (widget, event);
 
   return handled;
 }
@@ -4651,7 +5230,7 @@ gtk_window_key_release_event (GtkWidget   *widget,
 
   /* Chain up, invokes binding set */
   if (!handled)
-    handled = GTK_WIDGET_CLASS (parent_class)->key_press_event (widget, event);
+    handled = GTK_WIDGET_CLASS (gtk_window_parent_class)->key_release_event (widget, event);
 
   return handled;
 }
@@ -4730,7 +5309,7 @@ gtk_window_focus_in_event (GtkWidget     *widget,
    *  the window is visible before actually handling the
    *  event
    */
-  if (GTK_WIDGET_VISIBLE (widget))
+  if (gtk_widget_get_visible (widget))
     {
       _gtk_window_set_has_toplevel_focus (window, TRUE);
       _gtk_window_set_is_active (window, TRUE);
@@ -4744,10 +5323,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;
 }
 
@@ -4760,7 +5346,7 @@ send_client_message_to_embedded_windows (GtkWidget *widget,
 {
   GList *embedded_windows;
 
-  embedded_windows = g_object_get_data (G_OBJECT (widget), "gtk-embedded");
+  embedded_windows = g_object_get_qdata (G_OBJECT (widget), quark_gtk_embedded);
   if (embedded_windows)
     {
       GdkEvent *send_event = gdk_event_new (GDK_CLIENT_EVENT);
@@ -4773,7 +5359,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;
        }
@@ -4788,8 +5374,8 @@ gtk_window_client_event (GtkWidget        *widget,
 {
   if (!atom_rcfiles)
     {
-      atom_rcfiles = gdk_atom_intern ("_GTK_READ_RCFILES", FALSE);
-      atom_iconthemes = gdk_atom_intern ("_GTK_LOAD_ICONTHEMES", FALSE);
+      atom_rcfiles = gdk_atom_intern_static_string ("_GTK_READ_RCFILES");
+      atom_iconthemes = gdk_atom_intern_static_string ("_GTK_LOAD_ICONTHEMES");
     }
 
   if (event->message_type == atom_rcfiles) 
@@ -4810,10 +5396,8 @@ gtk_window_client_event (GtkWidget       *widget,
 static void
 gtk_window_check_resize (GtkContainer *container)
 {
-  GtkWindow *window = GTK_WINDOW (container);
-
-  if (GTK_WIDGET_VISIBLE (container))
-    gtk_window_move_resize (window);
+  if (gtk_widget_get_visible (GTK_WIDGET (container)))
+    gtk_window_move_resize (GTK_WINDOW (container));
 }
 
 static gboolean
@@ -4886,21 +5470,21 @@ gtk_window_real_set_focus (GtkWindow *window,
     {
       g_object_ref (old_focus);
       g_object_freeze_notify (G_OBJECT (old_focus));
-      old_focus_had_default = GTK_WIDGET_HAS_DEFAULT (old_focus);
+      old_focus_had_default = gtk_widget_has_default (old_focus);
     }
   if (focus)
     {
       g_object_ref (focus);
       g_object_freeze_notify (G_OBJECT (focus));
-      focus_had_default = GTK_WIDGET_HAS_DEFAULT (focus);
+      focus_had_default = gtk_widget_has_default (focus);
     }
   
   if (window->default_widget)
-    had_default = GTK_WIDGET_HAS_DEFAULT (window->default_widget);
+    had_default = gtk_widget_has_default (window->default_widget);
   
   if (window->focus_widget)
     {
-      if (GTK_WIDGET_RECEIVES_DEFAULT (window->focus_widget) &&
+      if (gtk_widget_get_receives_default (window->focus_widget) &&
          (window->focus_widget != window->default_widget))
         {
          GTK_WIDGET_UNSET_FLAGS (window->focus_widget, GTK_HAS_DEFAULT);
@@ -4925,10 +5509,10 @@ gtk_window_real_set_focus (GtkWindow *window,
     {
       window->focus_widget = focus;
   
-      if (GTK_WIDGET_RECEIVES_DEFAULT (window->focus_widget) &&
+      if (gtk_widget_get_receives_default (window->focus_widget) &&
          (window->focus_widget != window->default_widget))
        {
-         if (GTK_WIDGET_CAN_DEFAULT (window->focus_widget))
+         if (gtk_widget_get_can_default (window->focus_widget))
            GTK_WIDGET_SET_FLAGS (window->focus_widget, GTK_HAS_DEFAULT);
 
          if (window->default_widget)
@@ -4948,12 +5532,12 @@ gtk_window_real_set_focus (GtkWindow *window,
    * is harmless.
    */
   if (window->default_widget &&
-      (had_default != GTK_WIDGET_HAS_DEFAULT (window->default_widget)))
+      (had_default != gtk_widget_has_default (window->default_widget)))
     gtk_widget_queue_draw (window->default_widget);
   
   if (old_focus)
     {
-      if (old_focus_had_default != GTK_WIDGET_HAS_DEFAULT (old_focus))
+      if (old_focus_had_default != gtk_widget_has_default (old_focus))
        gtk_widget_queue_draw (old_focus);
        
       g_object_thaw_notify (G_OBJECT (old_focus));
@@ -4961,7 +5545,7 @@ gtk_window_real_set_focus (GtkWindow *window,
     }
   if (focus)
     {
-      if (focus_had_default != GTK_WIDGET_HAS_DEFAULT (focus))
+      if (focus_had_default != gtk_widget_has_default (focus))
        gtk_widget_queue_draw (focus);
 
       g_object_thaw_notify (G_OBJECT (focus));
@@ -5053,6 +5637,8 @@ gtk_window_compute_configure_request_size (GtkWindow *window,
          {
           gint base_width = 0;
           gint base_height = 0;
+          gint min_width = 0;
+          gint min_height = 0;
           gint width_inc = 1;
           gint height_inc = 1;
           
@@ -5069,10 +5655,10 @@ gtk_window_compute_configure_request_size (GtkWindow *window,
                   base_width = geometry.base_width;
                   base_height = geometry.base_height;
                 }
-              else if (flags & GDK_HINT_MIN_SIZE)
+              if (flags & GDK_HINT_MIN_SIZE)
                 {
-                  base_width = geometry.min_width;
-                  base_height = geometry.min_height;
+                  min_width = geometry.min_width;
+                  min_height = geometry.min_height;
                 }
               if (flags & GDK_HINT_RESIZE_INC)
                 {
@@ -5082,10 +5668,10 @@ gtk_window_compute_configure_request_size (GtkWindow *window,
             }
             
           if (info->default_width > 0)
-            *width = info->default_width * width_inc + base_width;
+            *width = MAX (info->default_width * width_inc + base_width, min_width);
           
           if (info->default_height > 0)
-            *height = info->default_height * height_inc + base_height;
+            *height = MAX (info->default_height * height_inc + base_height, min_height);
          }
     }
   else
@@ -5104,15 +5690,23 @@ 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
 get_effective_position (GtkWindow *window)
 {
   GtkWindowPosition pos = window->position;
+
   if (pos == GTK_WIN_POS_CENTER_ON_PARENT &&
       (window->transient_parent == NULL ||
-       !GTK_WIDGET_MAPPED (window->transient_parent)))
+       !gtk_widget_get_mapped (GTK_WIDGET (window->transient_parent))))
     pos = GTK_WIN_POS_NONE;
 
   return pos;
@@ -5179,6 +5773,21 @@ center_window_on_monitor (GtkWindow *window,
     *y = monitor.y;
 }
 
+static void
+clamp (gint *base,
+       gint  extent,
+       gint  clamp_base,
+       gint  clamp_extent)
+{
+  if (extent > clamp_extent)
+    /* Center */
+    *base = clamp_base + clamp_extent/2 - extent/2;
+  else if (*base < clamp_base)
+    *base = clamp_base;
+  else if (*base + extent > clamp_base + clamp_extent)
+    *base = clamp_base + clamp_extent - extent;
+}
+
 static void
 clamp_window_to_rectangle (gint               *x,
                            gint               *y,
@@ -5186,21 +5795,19 @@ clamp_window_to_rectangle (gint               *x,
                            gint                h,
                            const GdkRectangle *rect)
 {
-  gint outside_w, outside_h;
-  
-  outside_w = (*x + w) - (rect->x + rect->width);
-  if (outside_w > 0)
-    *x -= outside_w;
-
-  outside_h = (*y + h) - (rect->y + rect->height);
-  if (outside_h > 0)
-    *y -= outside_h; 
+#ifdef DEBUGGING_OUTPUT
+  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 larger than the screen, center on the screen. */
-  if (*x < rect->x)
-    *x += (rect->x - *x) / 2;
-  if (*y < rect->y)
-    *y += (rect->y - *y) / 2;
+  /* If it is too large, center it. If it fits on the monitor but is
+   * partially outside, move it to the closest edge. Do this
+   * separately in x and y directions.
+   */
+  clamp (x, w, rect->x, rect->width);
+  clamp (y, h, rect->y, rect->height);
+#ifdef DEBUGGING_OUTPUT
+  g_print (" ==> %+d%+d: %dx%d\n", *x, *y, w, h);
+#endif
 }
 
 
@@ -5225,7 +5832,7 @@ gtk_window_compute_configure_request (GtkWindow    *window,
   screen = gtk_window_check_screen (window);
   
   gtk_widget_size_request (widget, NULL);
-  gtk_window_compute_configure_request_size (window, &w, &h);
+  gtk_window_compute_configure_request_size (window, (guint *)&w, (guint *)&h);
   
   gtk_window_compute_hints (window, &new_geometry, &new_flags);
   gtk_window_constrain_size (window,
@@ -5236,12 +5843,21 @@ gtk_window_compute_configure_request (GtkWindow    *window,
   parent_widget = (GtkWidget*) window->transient_parent;
   
   pos = get_effective_position (window);
-  info = gtk_window_get_geometry_info (window, TRUE);
-
-  /* by default, don't change position requested */
-  x = info->last.configure_request.x;
-  y = info->last.configure_request.y;
+  info = gtk_window_get_geometry_info (window, FALSE);
   
+  /* by default, don't change position requested */
+  if (info)
+    {
+      x = info->last.configure_request.x;
+      y = info->last.configure_request.y;
+    }
+  else
+    {
+      x = 0;
+      y = 0;
+    }
+
+
   if (window->need_default_position)
     {
 
@@ -5268,7 +5884,7 @@ gtk_window_compute_configure_request (GtkWindow    *window,
             GdkRectangle monitor;
             gint ox, oy;
             
-            g_assert (GTK_WIDGET_MAPPED (parent_widget)); /* established earlier */
+            g_assert (gtk_widget_get_mapped (parent_widget)); /* established earlier */
 
             if (parent_widget->window != NULL)
               monitor_num = gdk_screen_get_monitor_at_window (screen,
@@ -5334,7 +5950,7 @@ gtk_window_compute_configure_request (GtkWindow    *window,
         }
     } /* if (window->need_default_position) */
 
-  if (window->need_default_position &&
+  if (window->need_default_position && info &&
       info->initial_pos_set)
     {
       x = info->initial_x;
@@ -5619,7 +6235,7 @@ gtk_window_move_resize (GtkWindow *window)
       allocation = widget->allocation;
       gtk_widget_size_allocate (widget, &allocation);
 
-      gdk_window_process_all_updates ();
+      gdk_window_process_updates (widget->window, TRUE);
       
       gdk_window_configure_finished (widget->window);
 
@@ -5659,7 +6275,7 @@ gtk_window_move_resize (GtkWindow *window)
            */
          info->last = saved_last_info;
           
-         gtk_widget_queue_resize (widget); /* migth recurse for GTK_RESIZE_IMMEDIATE */
+         gtk_widget_queue_resize_no_redraw (widget); /* migth recurse for GTK_RESIZE_IMMEDIATE */
        }
 
       return;                  /* Bail out, we didn't really process the move/resize */
@@ -5712,28 +6328,49 @@ gtk_window_move_resize (GtkWindow *window)
                             new_request.width, new_request.height);
        }
       
-      /* Increment the number of have-not-yet-received-notify requests */
-      window->configure_request_count += 1;
-
-      /* for GTK_RESIZE_QUEUE toplevels, we are now awaiting a new
-       * configure event in response to our resizing request.
-       * the configure event will cause a new resize with
-       * ->configure_notify_received=TRUE.
-       * until then, we want to
-       * - discard expose events
-       * - coalesce resizes for our children
-       * - defer any window resizes until the configure event arrived
-       * to achieve this, we queue a resize for the window, but remove its
-       * resizing handler, so resizing will not be handled from the next
-       * idle handler but when the configure event arrives.
-       *
-       * FIXME: we should also dequeue the pending redraws here, since
-       * we handle those ourselves upon ->configure_notify_received==TRUE.
-       */
-      if (container->resize_mode == GTK_RESIZE_QUEUE)
-       {
-         gtk_widget_queue_resize (widget);
-         _gtk_container_dequeue_resize_handler (container);
+      if (window->type == GTK_WINDOW_POPUP)
+        {
+         GtkAllocation allocation;
+
+         /* Directly size allocate for override redirect (popup) windows. */
+          allocation.x = 0;
+         allocation.y = 0;
+         allocation.width = new_request.width;
+         allocation.height = new_request.height;
+
+         gtk_widget_size_allocate (widget, &allocation);
+
+         gdk_window_process_updates (widget->window, TRUE);
+
+         if (container->resize_mode == GTK_RESIZE_QUEUE)
+           gtk_widget_queue_draw (widget);
+       }
+      else
+        {
+         /* Increment the number of have-not-yet-received-notify requests */
+         window->configure_request_count += 1;
+         gdk_window_freeze_toplevel_updates_libgtk_only (widget->window);
+
+         /* for GTK_RESIZE_QUEUE toplevels, we are now awaiting a new
+          * configure event in response to our resizing request.
+          * the configure event will cause a new resize with
+          * ->configure_notify_received=TRUE.
+          * until then, we want to
+          * - discard expose events
+          * - coalesce resizes for our children
+          * - defer any window resizes until the configure event arrived
+          * to achieve this, we queue a resize for the window, but remove its
+          * resizing handler, so resizing will not be handled from the next
+          * idle handler but when the configure event arrives.
+          *
+          * FIXME: we should also dequeue the pending redraws here, since
+          * we handle those ourselves upon ->configure_notify_received==TRUE.
+          */
+         if (container->resize_mode == GTK_RESIZE_QUEUE)
+           {
+             gtk_widget_queue_resize_no_redraw (widget);
+             _gtk_container_dequeue_resize_handler (container);
+           }
        }
     }
   else
@@ -5985,11 +6622,11 @@ static gint
 gtk_window_expose (GtkWidget      *widget,
                   GdkEventExpose *event)
 {
-  if (!GTK_WIDGET_APP_PAINTABLE (widget))
+  if (!gtk_widget_get_app_paintable (widget))
     gtk_window_paint (widget, &event->area);
   
-  if (GTK_WIDGET_CLASS (parent_class)->expose_event)
-    return GTK_WIDGET_CLASS (parent_class)->expose_event (widget, event);
+  if (GTK_WIDGET_CLASS (gtk_window_parent_class)->expose_event)
+    return GTK_WIDGET_CLASS (gtk_window_parent_class)->expose_event (widget, event);
 
   return FALSE;
 }
@@ -6010,7 +6647,7 @@ gtk_window_expose (GtkWidget      *widget,
  * frame_event you can receive all events targeted at the frame.
  * 
  * This function is used by the linux-fb port to implement managed
- * windows, but it could concievably be used by X-programs that
+ * windows, but it could conceivably be used by X-programs that
  * want to do their own window decorations.
  *
  **/
@@ -6113,7 +6750,7 @@ gtk_window_set_frame_dimensions (GtkWindow *window,
  * where the user can see it.
  *
  * If you are calling this function in response to a user interaction,
- * it is preferable to use gdk_window_present_with_time().
+ * it is preferable to use gtk_window_present_with_time().
  * 
  **/
 void
@@ -6144,7 +6781,7 @@ gtk_window_present_with_time (GtkWindow *window,
 
   widget = GTK_WIDGET (window);
 
-  if (GTK_WIDGET_VISIBLE (window))
+  if (gtk_widget_get_visible (widget))
     {
       g_assert (widget->window != NULL);
       
@@ -6187,7 +6824,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.
  * 
  **/
@@ -6222,7 +6859,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
@@ -6260,7 +6897,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.
  * 
  **/
@@ -6296,7 +6933,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.
  * 
  **/
@@ -6337,7 +6974,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.
  * 
  **/
@@ -6373,7 +7010,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.
  * 
  **/
@@ -6410,7 +7047,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
@@ -6450,7 +7087,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
@@ -6495,7 +7132,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 
@@ -6519,7 +7156,7 @@ gtk_window_set_keep_above (GtkWindow *window,
   widget = GTK_WIDGET (window);
   priv = GTK_WINDOW_GET_PRIVATE (window);
 
-  priv->above_initially = setting;
+  priv->above_initially = setting != FALSE;
   if (setting)
     priv->below_initially = FALSE;
 
@@ -6549,7 +7186,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 
@@ -6573,7 +7210,7 @@ gtk_window_set_keep_below (GtkWindow *window,
   widget = GTK_WIDGET (window);
   priv = GTK_WINDOW_GET_PRIVATE (window);
 
-  priv->below_initially = setting;
+  priv->below_initially = setting != FALSE;
   if (setting)
     priv->above_initially = FALSE;
 
@@ -6600,7 +7237,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);
 }
 
 /**
@@ -6648,7 +7285,7 @@ gtk_window_set_gravity (GtkWindow *window,
 
       /* gtk_window_move_resize() will adapt gravity
        */
-      gtk_widget_queue_resize (GTK_WIDGET (window));
+      gtk_widget_queue_resize_no_redraw (GTK_WIDGET (window));
 
       g_object_notify (G_OBJECT (window), "gravity");
     }
@@ -6660,7 +7297,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)
@@ -6699,9 +7336,8 @@ gtk_window_begin_resize_drag  (GtkWindow    *window,
   GdkWindow *toplevel;
   
   g_return_if_fail (GTK_IS_WINDOW (window));
-  g_return_if_fail (GTK_WIDGET_VISIBLE (window));
-  
   widget = GTK_WIDGET (window);
+  g_return_if_fail (gtk_widget_get_visible (widget));
   
   if (window->frame)
     toplevel = window->frame;
@@ -6717,10 +7353,10 @@ gtk_window_begin_resize_drag  (GtkWindow    *window,
 /**
  * gtk_window_get_frame_dimensions:
  * @window: a #GtkWindow
- * @left: location to store the width of the frame at the left, or %NULL
- * @top: location to store the height of the frame at the top, or %NULL
- * @right: location to store the width of the frame at the returns, or %NULL
- * @bottom: location to store the height of the frame at the bottom, or %NULL
+ * @left: (allow-none): location to store the width of the frame at the left, or %NULL
+ * @top: (allow-none): location to store the height of the frame at the top, or %NULL
+ * @right: (allow-none): location to store the width of the frame at the returns, or %NULL
+ * @bottom: (allow-none): location to store the height of the frame at the bottom, or %NULL
  *
  * (Note: this is a special-purpose function intended for the
  *  framebuffer port; see gtk_window_set_has_frame(). It will not
@@ -6779,9 +7415,8 @@ gtk_window_begin_move_drag  (GtkWindow *window,
   GdkWindow *toplevel;
   
   g_return_if_fail (GTK_IS_WINDOW (window));
-  g_return_if_fail (GTK_WIDGET_VISIBLE (window));
-  
   widget = GTK_WIDGET (window);
+  g_return_if_fail (gtk_widget_get_visible (widget));
   
   if (window->frame)
     toplevel = window->frame;
@@ -6822,7 +7457,7 @@ gtk_window_set_screen (GtkWindow *window,
   widget = GTK_WIDGET (window);
 
   previous_screen = window->screen;
-  was_mapped = GTK_WIDGET_MAPPED (widget);
+  was_mapped = gtk_widget_get_mapped (widget);
 
   if (was_mapped)
     gtk_widget_unmap (widget);
@@ -6833,13 +7468,30 @@ gtk_window_set_screen (GtkWindow *window,
   window->screen = screen;
   gtk_widget_reset_rc_styles (widget);
   if (screen != previous_screen)
-    _gtk_widget_propagate_screen_changed (widget, previous_screen);
+    {
+      g_signal_handlers_disconnect_by_func (previous_screen,
+                                           gtk_window_on_composited_changed, window);
+      g_signal_connect (screen, "composited-changed", 
+                       G_CALLBACK (gtk_window_on_composited_changed), window);
+      
+      _gtk_widget_propagate_screen_changed (widget, previous_screen);
+      _gtk_widget_propagate_composited_changed (widget);
+    }
   g_object_notify (G_OBJECT (window), "screen");
 
   if (was_mapped)
     gtk_widget_map (widget);
 }
 
+static void
+gtk_window_on_composited_changed (GdkScreen *screen,
+                                 GtkWindow *window)
+{
+  gtk_widget_queue_draw (GTK_WIDGET (window));
+  
+  _gtk_widget_propagate_composited_changed (GTK_WIDGET (window));
+}
+
 static GdkScreen *
 gtk_window_check_screen (GtkWindow *window)
 {
@@ -6859,7 +7511,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
  */
@@ -6927,7 +7579,7 @@ gtk_window_group_get_type (void)
 
   if (!window_group_type)
     {
-      static const GTypeInfo window_group_info =
+      const GTypeInfo window_group_info =
       {
        sizeof (GtkWindowGroupClass),
        NULL,           /* base_init */
@@ -6936,7 +7588,7 @@ gtk_window_group_get_type (void)
        NULL,           /* class_finalize */
        NULL,           /* class_data */
        sizeof (GtkWindowGroup),
-       16,             /* n_preallocs */
+       0,              /* n_preallocs */
        (GInstanceInitFunc) NULL,
       };
 
@@ -7006,7 +7658,7 @@ gtk_window_group_add_window (GtkWindowGroup *window_group,
       if (window->group)
        gtk_window_group_remove_window (window->group, window);
       else
-       window_group_cleanup_grabs (_gtk_window_get_group (NULL), window);
+       window_group_cleanup_grabs (gtk_window_get_group (NULL), window);
 
       window->group = window_group;
 
@@ -7026,7 +7678,7 @@ gtk_window_group_remove_window (GtkWindowGroup *window_group,
                                GtkWindow      *window)
 {
   g_return_if_fail (GTK_IS_WINDOW_GROUP (window_group));
-  g_return_if_fail (GTK_IS_WIDGET (window));
+  g_return_if_fail (GTK_IS_WINDOW (window));
   g_return_if_fail (window->group == window_group);
 
   g_object_ref (window);
@@ -7038,10 +7690,52 @@ gtk_window_group_remove_window (GtkWindowGroup *window_group,
   g_object_unref (window);
 }
 
-/* Return the group for the window or the default group
+/**
+ * gtk_window_group_list_windows:
+ * @window_group: a #GtkWindowGroup
+ *
+ * Returns a list of the #GtkWindows that belong to @window_group.
+ *
+ * Returns: (element-type GtkWidget) (transfer container): A newly-allocated list of
+ *   windows inside the group.
+ *
+ * Since: 2.14
+ **/
+GList *
+gtk_window_group_list_windows (GtkWindowGroup *window_group)
+{
+  GList *toplevels, *toplevel, *group_windows;
+
+  g_return_val_if_fail (GTK_IS_WINDOW_GROUP (window_group), NULL);
+
+  group_windows = NULL;
+  toplevels = gtk_window_list_toplevels ();
+
+  for (toplevel = toplevels; toplevel; toplevel = toplevel->next)
+    {
+      GtkWindow *window = toplevel->data;
+
+      if (window_group == window->group)
+       group_windows = g_list_prepend (group_windows, window);
+    }
+
+  return g_list_reverse (group_windows);
+}
+
+/**
+ * gtk_window_get_group:
+ * @window: (allow-none): a #GtkWindow, or %NULL
+ *
+ * Returns the group for @window or the default group, if
+ * @window is %NULL or if @window does not have an explicit
+ * window group.
+ *
+ * Returns: (transfer none): the #GtkWindowGroup for a window or the default group
+ *
+ * Since: 2.10
  */
 GtkWindowGroup *
-_gtk_window_get_group (GtkWindow *window)
+gtk_window_get_group (GtkWindow *window)
 {
   if (window && window->group)
     return window->group;
@@ -7273,14 +7967,13 @@ gtk_XParseGeometry (const char   *string,
  * to be called when the window has its "final" size, i.e. after calling
  * gtk_widget_show_all() on the contents and gtk_window_set_geometry_hints()
  * on the window.
- * 
- * <informalexample><programlisting>
- * #include &lt;gtk/gtk.h&gt;
+ * |[
+ * #include <gtk/gtk.h>
  *    
  * static void
  * fill_with_content (GtkWidget *vbox)
  * {
- *   /<!-- -->* fill with content... *<!-- -->/
+ *   /&ast; fill with content... &ast;/
  * }
  *    
  * int
@@ -7291,7 +7984,7 @@ gtk_XParseGeometry (const char   *string,
  *     100, 50, 0, 0, 100, 50, 10, 10, 0.0, 0.0, GDK_GRAVITY_NORTH_WEST  
  *   };
  *    
- *   gtk_init (&amp;argc, &amp;argv);
+ *   gtk_init (&argc, &argv);
  *   
  *   window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
  *   vbox = gtk_vbox_new (FALSE, 0);
@@ -7302,7 +7995,7 @@ gtk_XParseGeometry (const char   *string,
  *   
  *   gtk_window_set_geometry_hints (GTK_WINDOW (window),
  *                                 window,
- *                                 &amp;size_hints,
+ *                                 &size_hints,
  *                                 GDK_HINT_MIN_SIZE | 
  *                                 GDK_HINT_BASE_SIZE | 
  *                                 GDK_HINT_RESIZE_INC);
@@ -7310,7 +8003,7 @@ gtk_XParseGeometry (const char   *string,
  *   if (argc &gt; 1)
  *     {
  *       if (!gtk_window_parse_geometry (GTK_WINDOW (window), argv[1]))
- *         fprintf (stderr, "Failed to parse '&percnt;s'\n", argv[1]);
+ *         fprintf (stderr, "Failed to parse '%s'\n", argv[1]);
  *     }
  *    
  *   gtk_widget_show_all (window);
@@ -7318,7 +8011,7 @@ gtk_XParseGeometry (const char   *string,
  *    
  *   return 0;
  * }
- * </programlisting></informalexample>
+ * ]|
  *
  * Return value: %TRUE if string was parsed successfully
  **/
@@ -7326,7 +8019,7 @@ gboolean
 gtk_window_parse_geometry (GtkWindow   *window,
                            const gchar *geometry)
 {
-  gint result, x, y;
+  gint result, x = 0, y = 0;
   guint w, h;
   GdkGravity grav;
   gboolean size_set, pos_set;
@@ -7349,7 +8042,7 @@ gtk_window_parse_geometry (GtkWindow   *window,
       size_set = TRUE;
     }
 
-  gtk_window_get_size (window, &w, &h);
+  gtk_window_get_size (window, (gint *)&w, (gint *)&h);
   
   grav = GDK_GRAVITY_NORTH_WEST;
 
@@ -7475,9 +8168,15 @@ struct _GtkWindowKeyEntry
 {
   guint keyval;
   guint modifiers;
-  gboolean is_mnemonic;
+  guint is_mnemonic : 1;
 };
 
+static void 
+window_key_entry_destroy (gpointer data)
+{
+  g_slice_free (GtkWindowKeyEntry, data);
+}
+
 static void
 add_to_key_hash (GtkWindow      *window,
                 guint           keyval,
@@ -7487,7 +8186,7 @@ add_to_key_hash (GtkWindow      *window,
 {
   GtkKeyHash *key_hash = data;
 
-  GtkWindowKeyEntry *entry = g_new (GtkWindowKeyEntry, 1);
+  GtkWindowKeyEntry *entry = g_slice_new (GtkWindowKeyEntry);
 
   entry->keyval = keyval;
   entry->modifiers = modifiers;
@@ -7511,15 +8210,15 @@ static GtkKeyHash *
 gtk_window_get_key_hash (GtkWindow *window)
 {
   GdkScreen *screen = gtk_window_check_screen (window);
-  GtkKeyHash *key_hash = g_object_get_data (G_OBJECT (window), "gtk-window-key-hash");
+  GtkKeyHash *key_hash = g_object_get_qdata (G_OBJECT (window), quark_gtk_window_key_hash);
   
   if (key_hash)
     return key_hash;
   
   key_hash = _gtk_key_hash_new (gdk_keymap_get_for_display (gdk_screen_get_display (screen)),
-                               (GDestroyNotify)g_free);
+                               (GDestroyNotify)window_key_entry_destroy);
   _gtk_window_keys_foreach (window, add_to_key_hash, key_hash);
-  g_object_set_data (G_OBJECT (window), I_("gtk-window-key-hash"), key_hash);
+  g_object_set_qdata (G_OBJECT (window), quark_gtk_window_key_hash, key_hash);
 
   return key_hash;
 }
@@ -7527,11 +8226,11 @@ gtk_window_get_key_hash (GtkWindow *window)
 static void
 gtk_window_free_key_hash (GtkWindow *window)
 {
-  GtkKeyHash *key_hash = g_object_get_data (G_OBJECT (window), "gtk-window-key-hash");
+  GtkKeyHash *key_hash = g_object_get_qdata (G_OBJECT (window), quark_gtk_window_key_hash);
   if (key_hash)
     {
       _gtk_key_hash_free (key_hash);
-      g_object_set_data (G_OBJECT (window), "gtk-window-key-hash", NULL);
+      g_object_set_qdata (G_OBJECT (window), quark_gtk_window_key_hash, NULL);
     }
 }
 
@@ -7544,43 +8243,58 @@ gtk_window_free_key_hash (GtkWindow *window)
  * called by the default ::key_press_event handler for toplevel windows,
  * however in some cases it may be useful to call this directly when
  * 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 = g_object_get_data (G_OBJECT (window), "gtk-window-key-hash");
+  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);
+
+  key_hash = gtk_window_get_key_hash (window);
 
-  if (!key_hash)
-    {
-      gtk_window_keys_changed (window);
-      key_hash = g_object_get_data (G_OBJECT (window), "gtk-window-key-hash");
-    }
-  
   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);
     }
@@ -7588,12 +8302,20 @@ gtk_window_activate_key (GtkWindow   *window,
   if (found_entry)
     {
       if (found_entry->is_mnemonic)
-       return gtk_window_mnemonic_activate (window, found_entry->keyval, found_entry->modifiers);
+        {
+          if (enable_mnemonics)
+            return gtk_window_mnemonic_activate (window, found_entry->keyval,
+                                                 found_entry->modifiers);
+        }
       else
-       return gtk_accel_groups_activate (G_OBJECT (window), found_entry->keyval, found_entry->modifiers);
+        {
+          if (enable_accels)
+            return gtk_accel_groups_activate (G_OBJECT (window), found_entry->keyval,
+                                              found_entry->modifiers);
+        }
     }
-  else
-    return FALSE;
+
+  return FALSE;
 }
 
 static void
@@ -7610,14 +8332,14 @@ window_update_has_focus (GtkWindow *window)
        {
          if (window->focus_widget &&
              window->focus_widget != widget &&
-             !GTK_WIDGET_HAS_FOCUS (window->focus_widget))
+             !gtk_widget_has_focus (window->focus_widget))
            do_focus_change (window->focus_widget, TRUE);       
        }
       else
        {
          if (window->focus_widget &&
              window->focus_widget != widget &&
-             GTK_WIDGET_HAS_FOCUS (window->focus_widget))
+             gtk_widget_has_focus (window->focus_widget))
            do_focus_change (window->focus_widget, FALSE);
        }
     }
@@ -7649,6 +8371,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
@@ -7678,12 +8435,11 @@ _gtk_window_set_has_toplevel_focus (GtkWindow *window,
  * gtk_window_set_auto_startup_notification:
  * @setting: %TRUE to automatically do startup notification
  *
- * By default, after showing the first #GtkWindow for each #GdkScreen,
- * GTK+ calls gdk_screen_notify_startup_complete().  Call this
- * function to disable the automatic startup notification. You might
- * do this if your first window is a splash screen, and you want to
- * delay notification until after your real main window has been
- * shown, for example.
+ * By default, after showing the first #GtkWindow, GTK+ calls 
+ * gdk_notify_startup_complete().  Call this function to disable 
+ * the automatic startup notification. You might do this if your 
+ * first window is a splash screen, and you want to delay notification 
+ * until after your real main window has been shown, for example.
  *
  * In that example, you would disable startup notification
  * temporarily, show your splash screen, then re-enable it so that
@@ -7697,7 +8453,77 @@ 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;
+}
+
+/* gtk_window_get_mnemonics_visible:
+ * @window: a #GtkWindow
+ *
+ * Gets the value of the #GtkWindow:mnemonics-visible property.
+ *
+ * Returns: %TRUE if mnemonics are supposed to be visible
+ * in this window.
+ *
+ * Since: 2.20
+ */
+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;
+}
+
+/**
+ * gtk_window_set_mnemonics_visible:
+ * @window: a #GtkWindow
+ * @setting: the new value
+ *
+ * Sets the #GtkWindow:mnemonics-visible property.
+ *
+ * Since: 2.20
+ */
+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