Index: gdk/win32/gdkevents-win32.c
===================================================================
--- gdk/win32/gdkevents-win32.c	(revision 18465)
+++ gdk/win32/gdkevents-win32.c	(working copy)
@@ -2888,24 +2888,59 @@
 
       append_event (event);
 
+      impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (window)->impl);
+
       if (event->any.type == GDK_UNMAP)
 	{
-	  impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (window)->impl);
+	  GSList *children = impl->transient_children;
 
+	  /* Iterate over our transient children and hide them */
+	  while (children != NULL)
+	    {
+	      GdkWindow *child = children->data;
+
+	      if (child)
+		{
+		  ShowWindow (GDK_WINDOW_HWND (child), SW_HIDE);
+		}
+
+	      children = g_slist_next (children);
+	    }
+
 	  if (impl->transient_owner && GetForegroundWindow () == GDK_WINDOW_HWND (window))
 	    {
 	      SetForegroundWindow (GDK_WINDOW_HWND (impl->transient_owner));
 	    }
+
+	  if (p_grab_window == window)
+	    {
+	      gdk_pointer_ungrab (msg->time);
+	    }
+
+	  if (k_grab_window == window)
+	    {
+	      gdk_keyboard_ungrab (msg->time);
+	    }
 	}
+      else if (event->any.type == GDK_MAP)
+	{
+	  /* Iterate over our transient children and show them */
+	  GSList *children = impl->transient_children;
 
-      if (event->any.type == GDK_UNMAP &&
-	  p_grab_window == window)
-	gdk_pointer_ungrab (msg->time);
+	  /* Iterate over our transient children and hide them */
+	  while (children != NULL)
+	    {
+	      GdkWindow *child = children->data;
 
-      if (event->any.type == GDK_UNMAP &&
-	  k_grab_window == window)
-	gdk_keyboard_ungrab (msg->time);
+	      if (child)
+		{
+		  ShowWindow (GDK_WINDOW_HWND (child), SW_RESTORE);
+		}
 
+	      children = g_slist_next (children);
+	    }
+	}
+
       return_val = TRUE;
       break;
 
Index: gdk/win32/gdkwindow-win32.c
===================================================================
--- gdk/win32/gdkwindow-win32.c	(revision 18465)
+++ gdk/win32/gdkwindow-win32.c	(working copy)
@@ -157,6 +157,8 @@
   impl->type_hint = GDK_WINDOW_TYPE_HINT_NORMAL;
   impl->extension_events_selected = FALSE;
   impl->transient_owner = NULL;
+  impl->transient_children = NULL;
+  impl->num_transients = 0;
 }
 
 static void
@@ -871,6 +873,7 @@
 {
   GdkWindowObject *private = (GdkWindowObject *)window;
   GdkWindowImplWin32 *window_impl = GDK_WINDOW_IMPL_WIN32 (private->impl);
+  GSList *tmp;
 
   g_return_if_fail (GDK_IS_WINDOW (window));
   
@@ -880,6 +883,19 @@
   if (private->extension_events != 0)
     _gdk_input_window_destroy (window);
 
+  /* Remove all our transient children */
+  tmp = window_impl->transient_children;
+  while (tmp != NULL)
+    {
+      GdkWindow *child = tmp->data;
+      GdkWindowImplWin32 *child_impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (child)->impl);
+
+      child_impl->transient_owner = NULL;
+      tmp = g_slist_next (tmp);
+    }
+  g_slist_free (window_impl->transient_children);
+  window_impl->transient_children = NULL;
+
   /* Remove ourself from our transient owner */
   if (window_impl->transient_owner != NULL)
     {
@@ -1977,6 +1993,8 @@
 {
   HWND window_id, parent_id;
   GdkWindowImplWin32 *window_impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (window)->impl);
+  GdkWindowImplWin32 *parent_impl = NULL;
+  GSList *item;
 
   g_return_if_fail (GDK_IS_WINDOW (window));
 
@@ -1999,8 +2017,32 @@
       return;
     }
 
-  window_impl->transient_owner = parent;
+  if (parent == NULL)
+    {
+      GdkWindowImplWin32 *trans_impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (window_impl->transient_owner)->impl);
+      if (trans_impl->transient_children != NULL)
+        {
+          item = g_slist_find (trans_impl->transient_children, window);
+          item->data = NULL;
+          trans_impl->transient_children = g_slist_delete_link (trans_impl->transient_children, item);
+          trans_impl->num_transients--;
+          if (!trans_impl->num_transients)
+            {
+              trans_impl->transient_children = NULL;
+            }
+        }
 
+      window_impl->transient_owner = NULL;
+    }
+  else
+    {
+      parent_impl = GDK_WINDOW_IMPL_WIN32 (GDK_WINDOW_OBJECT (parent)->impl);
+
+      parent_impl->transient_children = g_slist_append (parent_impl->transient_children, window);
+      parent_impl->num_transients++;
+      window_impl->transient_owner = parent;
+    }
+
   /* This changes the *owner* of the window, despite the misleading
    * name. (Owner and parent are unrelated concepts.) At least that's
    * what people who seem to know what they talk about say on
@@ -2964,7 +3006,7 @@
 	   gint  *nchildren)
 {
   guint i, n;
-  HWND child;
+  HWND child = NULL;
 
   n = 0;
   do {
Index: gdk/win32/gdkwindow-win32.h
===================================================================
--- gdk/win32/gdkwindow-win32.h	(revision 18465)
+++ gdk/win32/gdkwindow-win32.h	(working copy)
@@ -88,6 +88,8 @@
   gboolean extension_events_selected;
 
   GdkWindow *transient_owner;
+  GSList    *transient_children;
+  gint       num_transients;
 };
  
 struct _GdkWindowImplWin32Class 
