]> git.saurik.com Git - wxWidgets.git/blobdiff - src/gtk/window.cpp
compilation fix
[wxWidgets.git] / src / gtk / window.cpp
index 17b690e47b3022c88b31def749885f8ef031a0ad..ee398f439a8c5c03e6e6ee44a0f0609f0faa57a1 100644 (file)
@@ -44,6 +44,8 @@
 #include "gdk/gdkkeysyms.h"
 #include "wx/gtk/win_gtk.h"
 
+#include "gdk/gdkx.h"
+
 //-----------------------------------------------------------------------------
 // documentation on internals
 //-----------------------------------------------------------------------------
 extern wxList     wxPendingDelete;
 extern bool       g_blockEventsOnDrag;
 extern bool       g_blockEventsOnScroll;
-static bool       g_capturing = FALSE;
+extern wxCursor   g_globalCursor;
+static wxWindow  *g_captureWindow = (wxWindow*) NULL;
 static wxWindow  *g_focusWindow = (wxWindow*) NULL;
 
 /* hack: we need something to pass to gtk_menu_popup, so we store the time of
@@ -145,16 +148,15 @@ static gint gtk_debug_focus_in_callback( GtkWidget *WXUNUSED(widget),
                                          GdkEvent *WXUNUSED(event),
                                          const wxChar *name )
 {
-    // to enable logging of the focus events replace 0 with 1
-#if 0
+/*
     static bool s_done = FALSE;
     if ( !s_done )
     {
         wxLog::AddTraceMask("focus");
         s_done = TRUE;
     }
-#endif
     wxLogTrace(_T("FOCUS NOW AT: %s"), name);
+*/
 
     return FALSE;
 }
@@ -176,25 +178,401 @@ void debug_focus_in( GtkWidget* widget, const wxChar* name, const wxChar *window
 #endif // Debug
 
 //-----------------------------------------------------------------------------
-// local code (see below)
+// missing gdk functions
+//-----------------------------------------------------------------------------
+
+void
+gdk_window_warp_pointer (GdkWindow      *window,
+                         gint            x,
+                         gint            y)
+{
+  GdkWindowPrivate *priv;
+
+  if (!window)
+    window = (GdkWindow*) &gdk_root_parent;
+
+  priv = (GdkWindowPrivate*) window;
+
+  if (!priv->destroyed)
+  {
+      XWarpPointer (priv->xdisplay,
+                    None,              /* not source window -> move from anywhere */
+                    priv->xwindow,  /* dest window */
+                    0, 0, 0, 0,        /* not source window -> move from anywhere */
+                    x, y );
+  }
+}
+
+//-----------------------------------------------------------------------------
+// idle system
+//-----------------------------------------------------------------------------
+
+extern void wxapp_install_idle_handler();
+extern bool g_isIdle;
+
 //-----------------------------------------------------------------------------
+// key event conversion routines
+//-----------------------------------------------------------------------------
+
+#if (GTK_MINOR_VERSION == 0)
+/* these functions are copied verbatim from GTK 1.2 */
+static void
+gdkx_XConvertCase (KeySym symbol,
+                   KeySym *lower,
+                   KeySym *upper)
+{
+  register KeySym sym = symbol;
+
+  g_return_if_fail (lower != NULL);
+  g_return_if_fail (upper != NULL);
+
+  *lower = sym;
+  *upper = sym;
+
+  switch (sym >> 8)
+    {
+#if        defined (GDK_A) && defined (GDK_Ooblique)
+    case 0: /* Latin 1 */
+      if ((sym >= GDK_A) && (sym <= GDK_Z))
+        *lower += (GDK_a - GDK_A);
+      else if ((sym >= GDK_a) && (sym <= GDK_z))
+        *upper -= (GDK_a - GDK_A);
+      else if ((sym >= GDK_Agrave) && (sym <= GDK_Odiaeresis))
+        *lower += (GDK_agrave - GDK_Agrave);
+      else if ((sym >= GDK_agrave) && (sym <= GDK_odiaeresis))
+        *upper -= (GDK_agrave - GDK_Agrave);
+      else if ((sym >= GDK_Ooblique) && (sym <= GDK_Thorn))
+        *lower += (GDK_oslash - GDK_Ooblique);
+      else if ((sym >= GDK_oslash) && (sym <= GDK_thorn))
+        *upper -= (GDK_oslash - GDK_Ooblique);
+      break;
+#endif        /* LATIN1 */
+
+#if        defined (GDK_Aogonek) && defined (GDK_tcedilla)
+    case 1: /* Latin 2 */
+      /* Assume the KeySym is a legal value (ignore discontinuities) */
+      if (sym == GDK_Aogonek)
+        *lower = GDK_aogonek;
+      else if (sym >= GDK_Lstroke && sym <= GDK_Sacute)
+        *lower += (GDK_lstroke - GDK_Lstroke);
+      else if (sym >= GDK_Scaron && sym <= GDK_Zacute)
+        *lower += (GDK_scaron - GDK_Scaron);
+      else if (sym >= GDK_Zcaron && sym <= GDK_Zabovedot)
+        *lower += (GDK_zcaron - GDK_Zcaron);
+      else if (sym == GDK_aogonek)
+        *upper = GDK_Aogonek;
+      else if (sym >= GDK_lstroke && sym <= GDK_sacute)
+        *upper -= (GDK_lstroke - GDK_Lstroke);
+      else if (sym >= GDK_scaron && sym <= GDK_zacute)
+        *upper -= (GDK_scaron - GDK_Scaron);
+      else if (sym >= GDK_zcaron && sym <= GDK_zabovedot)
+        *upper -= (GDK_zcaron - GDK_Zcaron);
+      else if (sym >= GDK_Racute && sym <= GDK_Tcedilla)
+        *lower += (GDK_racute - GDK_Racute);
+      else if (sym >= GDK_racute && sym <= GDK_tcedilla)
+        *upper -= (GDK_racute - GDK_Racute);
+      break;
+#endif        /* LATIN2 */
+
+#if        defined (GDK_Hstroke) && defined (GDK_Cabovedot)
+    case 2: /* Latin 3 */
+      /* Assume the KeySym is a legal value (ignore discontinuities) */
+      if (sym >= GDK_Hstroke && sym <= GDK_Hcircumflex)
+        *lower += (GDK_hstroke - GDK_Hstroke);
+      else if (sym >= GDK_Gbreve && sym <= GDK_Jcircumflex)
+        *lower += (GDK_gbreve - GDK_Gbreve);
+      else if (sym >= GDK_hstroke && sym <= GDK_hcircumflex)
+        *upper -= (GDK_hstroke - GDK_Hstroke);
+      else if (sym >= GDK_gbreve && sym <= GDK_jcircumflex)
+        *upper -= (GDK_gbreve - GDK_Gbreve);
+      else if (sym >= GDK_Cabovedot && sym <= GDK_Scircumflex)
+        *lower += (GDK_cabovedot - GDK_Cabovedot);
+      else if (sym >= GDK_cabovedot && sym <= GDK_scircumflex)
+        *upper -= (GDK_cabovedot - GDK_Cabovedot);
+      break;
+#endif        /* LATIN3 */
+
+#if        defined (GDK_Rcedilla) && defined (GDK_Amacron)
+    case 3: /* Latin 4 */
+      /* Assume the KeySym is a legal value (ignore discontinuities) */
+      if (sym >= GDK_Rcedilla && sym <= GDK_Tslash)
+        *lower += (GDK_rcedilla - GDK_Rcedilla);
+      else if (sym >= GDK_rcedilla && sym <= GDK_tslash)
+        *upper -= (GDK_rcedilla - GDK_Rcedilla);
+      else if (sym == GDK_ENG)
+        *lower = GDK_eng;
+      else if (sym == GDK_eng)
+        *upper = GDK_ENG;
+      else if (sym >= GDK_Amacron && sym <= GDK_Umacron)
+        *lower += (GDK_amacron - GDK_Amacron);
+      else if (sym >= GDK_amacron && sym <= GDK_umacron)
+        *upper -= (GDK_amacron - GDK_Amacron);
+      break;
+#endif        /* LATIN4 */
+
+#if        defined (GDK_Serbian_DJE) && defined (GDK_Cyrillic_yu)
+    case 6: /* Cyrillic */
+      /* Assume the KeySym is a legal value (ignore discontinuities) */
+      if (sym >= GDK_Serbian_DJE && sym <= GDK_Serbian_DZE)
+        *lower -= (GDK_Serbian_DJE - GDK_Serbian_dje);
+      else if (sym >= GDK_Serbian_dje && sym <= GDK_Serbian_dze)
+        *upper += (GDK_Serbian_DJE - GDK_Serbian_dje);
+      else if (sym >= GDK_Cyrillic_YU && sym <= GDK_Cyrillic_HARDSIGN)
+        *lower -= (GDK_Cyrillic_YU - GDK_Cyrillic_yu);
+      else if (sym >= GDK_Cyrillic_yu && sym <= GDK_Cyrillic_hardsign)
+        *upper += (GDK_Cyrillic_YU - GDK_Cyrillic_yu);
+      break;
+#endif        /* CYRILLIC */
+
+#if        defined (GDK_Greek_ALPHAaccent) && defined (GDK_Greek_finalsmallsigma)
+    case 7: /* Greek */
+      /* Assume the KeySym is a legal value (ignore discontinuities) */
+      if (sym >= GDK_Greek_ALPHAaccent && sym <= GDK_Greek_OMEGAaccent)
+        *lower += (GDK_Greek_alphaaccent - GDK_Greek_ALPHAaccent);
+      else if (sym >= GDK_Greek_alphaaccent && sym <= GDK_Greek_omegaaccent &&
+               sym != GDK_Greek_iotaaccentdieresis &&
+               sym != GDK_Greek_upsilonaccentdieresis)
+        *upper -= (GDK_Greek_alphaaccent - GDK_Greek_ALPHAaccent);
+      else if (sym >= GDK_Greek_ALPHA && sym <= GDK_Greek_OMEGA)
+        *lower += (GDK_Greek_alpha - GDK_Greek_ALPHA);
+      else if (sym >= GDK_Greek_alpha && sym <= GDK_Greek_omega &&
+               sym != GDK_Greek_finalsmallsigma)
+        *upper -= (GDK_Greek_alpha - GDK_Greek_ALPHA);
+      break;
+#endif        /* GREEK */
+    }
+}
+
+static guint
+gdk_keyval_to_upper (guint          keyval)
+{
+  if (keyval)
+    {
+      KeySym lower_val = 0;
+      KeySym upper_val = 0;
+
+      gdkx_XConvertCase (keyval, &lower_val, &upper_val);
+      return upper_val;
+    }
+  return 0;
+}
+#endif
 
-static void InitAdjustment(GtkAdjustment *adjust)
+static long map_to_unmodified_wx_keysym( KeySym keysym )
 {
-    adjust->lower = 0.0;
-    adjust->upper = 1.0;
-    adjust->value = 0.0;
-    adjust->step_increment = 1.0;
-    adjust->page_increment = 1.0;
-    adjust->page_size = 5.0;
-    gtk_signal_emit_by_name( GTK_OBJECT(adjust), "changed" );
+    guint key_code = 0;
+
+    switch (keysym)
+    {
+        case GDK_Shift_L:
+        case GDK_Shift_R:       key_code = WXK_SHIFT;       break;
+        case GDK_Control_L:
+        case GDK_Control_R:     key_code = WXK_CONTROL;     break;
+        case GDK_Meta_L:
+        case GDK_Meta_R:
+        case GDK_Alt_L:
+        case GDK_Alt_R:
+        case GDK_Super_L:
+        case GDK_Super_R:       key_code = WXK_ALT;         break;
+        case GDK_Menu:          key_code = WXK_MENU;        break;
+        case GDK_Help:          key_code = WXK_HELP;        break;
+        case GDK_BackSpace:     key_code = WXK_BACK;        break;
+        case GDK_ISO_Left_Tab:
+        case GDK_Tab:           key_code = WXK_TAB;         break;
+        case GDK_Linefeed:      key_code = WXK_RETURN;      break;
+        case GDK_Clear:         key_code = WXK_CLEAR;       break;
+        case GDK_Return:        key_code = WXK_RETURN;      break;
+        case GDK_Pause:         key_code = WXK_PAUSE;       break;
+        case GDK_Scroll_Lock:   key_code = WXK_SCROLL;      break;
+        case GDK_Escape:        key_code = WXK_ESCAPE;      break;
+        case GDK_Delete:        key_code = WXK_DELETE;      break;
+        case GDK_Home:          key_code = WXK_HOME;        break;
+        case GDK_Left:          key_code = WXK_LEFT;        break;
+        case GDK_Up:            key_code = WXK_UP;          break;
+        case GDK_Right:         key_code = WXK_RIGHT;       break;
+        case GDK_Down:          key_code = WXK_DOWN;        break;
+        case GDK_Prior:         key_code = WXK_PRIOR;       break;
+//      case GDK_Page_Up:       key_code = WXK_PAGEUP;      break;
+        case GDK_Next:          key_code = WXK_NEXT;        break;
+//      case GDK_Page_Down:     key_code = WXK_PAGEDOWN;    break;
+        case GDK_End:           key_code = WXK_END;         break;
+        case GDK_Begin:         key_code = WXK_HOME;        break;
+        case GDK_Select:        key_code = WXK_SELECT;      break;
+        case GDK_Print:         key_code = WXK_PRINT;       break;
+        case GDK_Execute:       key_code = WXK_EXECUTE;     break;
+        case GDK_Insert:        key_code = WXK_INSERT;      break;
+        case GDK_Num_Lock:      key_code = WXK_NUMLOCK;     break;
+
+        case GDK_KP_0:         key_code = WXK_NUMPAD0;      break;
+        case GDK_KP_1:         key_code = WXK_NUMPAD1;      break;
+        case GDK_KP_2:         key_code = WXK_NUMPAD2;      break;
+        case GDK_KP_3:         key_code = WXK_NUMPAD3;      break;
+        case GDK_KP_4:         key_code = WXK_NUMPAD4;      break;
+        case GDK_KP_5:         key_code = WXK_NUMPAD5;      break;
+        case GDK_KP_6:         key_code = WXK_NUMPAD6;      break;
+        case GDK_KP_7:         key_code = WXK_NUMPAD7;      break;
+        case GDK_KP_8:         key_code = WXK_NUMPAD8;      break;
+        case GDK_KP_9:         key_code = WXK_NUMPAD9;      break;
+        case GDK_KP_Space:     key_code = WXK_NUMPAD_SPACE; break;
+        case GDK_KP_Tab:       key_code = WXK_NUMPAD_TAB;   break;
+        case GDK_KP_Enter:     key_code = WXK_NUMPAD_ENTER; break;
+        case GDK_KP_F1:        key_code = WXK_NUMPAD_F1;    break;
+        case GDK_KP_F2:        key_code = WXK_NUMPAD_F2;    break;
+        case GDK_KP_F3:        key_code = WXK_NUMPAD_F3;    break;
+        case GDK_KP_F4:        key_code = WXK_NUMPAD_F4;    break;
+        case GDK_KP_Home:      key_code = WXK_NUMPAD_HOME;  break;
+        case GDK_KP_Left:      key_code = WXK_NUMPAD_LEFT;  break;
+        case GDK_KP_Up:        key_code = WXK_NUMPAD_UP;    break;
+        case GDK_KP_Right:     key_code = WXK_NUMPAD_RIGHT; break;
+        case GDK_KP_Down:      key_code = WXK_NUMPAD_DOWN;  break;
+        case GDK_KP_Prior:     key_code = WXK_NUMPAD_PRIOR; break;
+//      case GDK_KP_Page_Up:   key_code = WXK_NUMPAD_PAGEUP;   break;
+        case GDK_KP_Next:      key_code = WXK_NUMPAD_NEXT;  break;
+//      case GDK_KP_Page_Down: key_code = WXK_NUMPAD_PAGEDOWN; break;
+        case GDK_KP_End:       key_code = WXK_NUMPAD_END;   break;
+        case GDK_KP_Begin:     key_code = WXK_NUMPAD_BEGIN; break;
+        case GDK_KP_Insert:    key_code = WXK_NUMPAD_INSERT; break;
+        case GDK_KP_Delete:    key_code = WXK_NUMPAD_DELETE; break;
+        case GDK_KP_Equal:     key_code = WXK_NUMPAD_EQUAL;  break;
+        case GDK_KP_Multiply:  key_code = WXK_NUMPAD_MULTIPLY; break;
+        case GDK_KP_Add:       key_code = WXK_NUMPAD_ADD;    break;
+        case GDK_KP_Separator: key_code = WXK_NUMPAD_SEPARATOR; break;
+        case GDK_KP_Subtract:  key_code = WXK_NUMPAD_SUBTRACT;  break;
+        case GDK_KP_Decimal:   key_code = WXK_NUMPAD_DECIMAL;   break;
+        case GDK_KP_Divide:    key_code = WXK_NUMPAD_DIVIDE;    break;
+
+        case GDK_F1:            key_code = WXK_F1;          break;
+        case GDK_F2:            key_code = WXK_F2;          break;
+        case GDK_F3:            key_code = WXK_F3;          break;
+        case GDK_F4:            key_code = WXK_F4;          break;
+        case GDK_F5:            key_code = WXK_F5;          break;
+        case GDK_F6:            key_code = WXK_F6;          break;
+        case GDK_F7:            key_code = WXK_F7;          break;
+        case GDK_F8:            key_code = WXK_F8;          break;
+        case GDK_F9:            key_code = WXK_F9;          break;
+        case GDK_F10:           key_code = WXK_F10;         break;
+        case GDK_F11:           key_code = WXK_F11;         break;
+        case GDK_F12:           key_code = WXK_F12;         break;
+        default:
+        {
+            if (keysym <= 0xFF)
+            {
+                guint upper = gdk_keyval_to_upper( keysym );
+                keysym = (upper != 0 ? upper : keysym ); /* to be MSW compatible */
+                key_code = keysym;
+            }
+        }
+    }
+
+    return (key_code);
+}
+
+static long map_to_wx_keysym( KeySym keysym )
+{
+    guint key_code = 0;
+
+    switch (keysym)
+    {
+        case GDK_Menu:          key_code = WXK_MENU;        break;
+        case GDK_Help:          key_code = WXK_HELP;        break;
+        case GDK_BackSpace:     key_code = WXK_BACK;        break;
+        case GDK_ISO_Left_Tab:
+        case GDK_Tab:           key_code = WXK_TAB;         break;
+        case GDK_Linefeed:      key_code = WXK_RETURN;      break;
+        case GDK_Clear:         key_code = WXK_CLEAR;       break;
+        case GDK_Return:        key_code = WXK_RETURN;      break;
+        case GDK_Pause:         key_code = WXK_PAUSE;       break;
+        case GDK_Scroll_Lock:   key_code = WXK_SCROLL;      break;
+        case GDK_Escape:        key_code = WXK_ESCAPE;      break;
+        case GDK_Delete:        key_code = WXK_DELETE;      break;
+        case GDK_Home:          key_code = WXK_HOME;        break;
+        case GDK_Left:          key_code = WXK_LEFT;        break;
+        case GDK_Up:            key_code = WXK_UP;          break;
+        case GDK_Right:         key_code = WXK_RIGHT;       break;
+        case GDK_Down:          key_code = WXK_DOWN;        break;
+        case GDK_Prior:         key_code = WXK_PRIOR;       break;
+//      case GDK_Page_Up:       key_code = WXK_PAGEUP;      break;
+        case GDK_Next:          key_code = WXK_NEXT;        break;
+//      case GDK_Page_Down:     key_code = WXK_PAGEDOWN;    break;
+        case GDK_End:           key_code = WXK_END;         break;
+        case GDK_Begin:         key_code = WXK_HOME;        break;
+        case GDK_Select:        key_code = WXK_SELECT;      break;
+        case GDK_Print:         key_code = WXK_PRINT;       break;
+        case GDK_Execute:       key_code = WXK_EXECUTE;     break;
+        case GDK_Insert:        key_code = WXK_INSERT;      break;
+        case GDK_Num_Lock:      key_code = WXK_NUMLOCK;     break;
+
+        case GDK_KP_0:         key_code = '0';      break;
+        case GDK_KP_1:         key_code = '1';      break;
+        case GDK_KP_2:         key_code = '2';      break;
+        case GDK_KP_3:         key_code = '3';      break;
+        case GDK_KP_4:         key_code = '4';      break;
+        case GDK_KP_5:         key_code = '5';      break;
+        case GDK_KP_6:         key_code = '6';      break;
+        case GDK_KP_7:         key_code = '7';      break;
+        case GDK_KP_8:         key_code = '8';      break;
+        case GDK_KP_9:         key_code = '9';      break;
+        case GDK_KP_Space:     key_code = ' ';      break;
+        case GDK_KP_Tab:       key_code = WXK_TAB;    break;        /* or '\t' ??? */
+        case GDK_KP_Enter:     key_code = WXK_RETURN; break;        /* or '\r' ??? */
+        case GDK_KP_F1:        key_code = WXK_NUMPAD_F1;    break;
+        case GDK_KP_F2:        key_code = WXK_NUMPAD_F2;    break;
+        case GDK_KP_F3:        key_code = WXK_NUMPAD_F3;    break;
+        case GDK_KP_F4:        key_code = WXK_NUMPAD_F4;    break;
+        case GDK_KP_Home:      key_code = WXK_HOME;  break;
+        case GDK_KP_Left:      key_code = WXK_LEFT;  break;
+        case GDK_KP_Up:        key_code = WXK_UP;    break;
+        case GDK_KP_Right:     key_code = WXK_RIGHT; break;
+        case GDK_KP_Down:      key_code = WXK_DOWN;  break;
+        case GDK_KP_Prior:     key_code = WXK_PRIOR; break;
+//      case GDK_KP_Page_Up:   key_code = WXK_PAGEUP; break;
+        case GDK_KP_Next:      key_code = WXK_NEXT;  break;
+//      case GDK_KP_Page_Down: key_code = WXK_PAGEDOWN; break;
+        case GDK_KP_End:       key_code = WXK_END;    break;
+        case GDK_KP_Begin:     key_code = WXK_HOME;   break;
+        case GDK_KP_Insert:    key_code = WXK_INSERT; break;
+        case GDK_KP_Delete:    key_code = WXK_DELETE; break;
+        case GDK_KP_Equal:     key_code = '=';   break;
+        case GDK_KP_Multiply:  key_code = '*';   break;
+        case GDK_KP_Add:       key_code = '+';   break;
+        case GDK_KP_Separator: key_code = ',';   break;
+        case GDK_KP_Subtract:  key_code = '-';   break;
+        case GDK_KP_Decimal:   key_code = '.';   break;
+        case GDK_KP_Divide:    key_code = '/';   break;
+
+        case GDK_F1:            key_code = WXK_F1;          break;
+        case GDK_F2:            key_code = WXK_F2;          break;
+        case GDK_F3:            key_code = WXK_F3;          break;
+        case GDK_F4:            key_code = WXK_F4;          break;
+        case GDK_F5:            key_code = WXK_F5;          break;
+        case GDK_F6:            key_code = WXK_F6;          break;
+        case GDK_F7:            key_code = WXK_F7;          break;
+        case GDK_F8:            key_code = WXK_F8;          break;
+        case GDK_F9:            key_code = WXK_F9;          break;
+        case GDK_F10:           key_code = WXK_F10;         break;
+        case GDK_F11:           key_code = WXK_F11;         break;
+        case GDK_F12:           key_code = WXK_F12;         break;
+        default:
+        {
+            if (keysym <= 0xFF)
+            {
+                key_code = keysym;
+            }
+        }
+    }
+
+    return (key_code);
 }
 
+//-----------------------------------------------------------------------------
+// local code (see below)
+//-----------------------------------------------------------------------------
+
 #if (GTK_MINOR_VERSION > 0)
 
 static void draw_frame( GtkWidget *widget, wxWindow *win )
 {
-    if (!win->HasVMT())
+    if (!win->m_hasVMT)
         return;
 
     int dw = 0;
@@ -221,7 +599,7 @@ static void draw_frame( GtkWidget *widget, wxWindow *win )
         if (scroll_window->hscrollbar_visible)
         {
             dh += 15;   /* dh += hscrollbar->allocation.height; */
-            dw += scroll_class->scrollbar_spacing;
+            dh += scroll_class->scrollbar_spacing;
         }
     }
 
@@ -240,7 +618,7 @@ static void draw_frame( GtkWidget *widget, wxWindow *win )
                          GTK_STATE_NORMAL,
                          GTK_SHADOW_OUT,
                          dx, dy,
-                         win->GetWidth()-dw, win->GetHeight()-dh );
+                         win->m_width-dw, win->m_height-dh );
         return;
     }
 
@@ -251,7 +629,7 @@ static void draw_frame( GtkWidget *widget, wxWindow *win )
                          GTK_STATE_NORMAL,
                          GTK_SHADOW_IN,
                          dx, dy,
-                         win->GetWidth()-dw, win->GetHeight()-dh );
+                         win->m_width-dw, win->m_height-dh );
         return;
     }
 }
@@ -283,7 +661,7 @@ static void gtk_window_own_draw_callback( GtkWidget *widget, GdkRectangle *WXUNU
 
 static void gtk_window_expose_callback( GtkWidget *WXUNUSED(widget), GdkEventExpose *gdk_event, wxWindow *win )
 {
-    if ( !win->HasVMT() )
+    if ( !win->m_hasVMT )
         return;
 
     win->GetUpdateRegion().Union( gdk_event->area.x,
@@ -314,7 +692,10 @@ static void gtk_window_expose_callback( GtkWidget *WXUNUSED(widget), GdkEventExp
 
 static void gtk_window_draw_callback( GtkWidget *WXUNUSED(widget), GdkRectangle *rect, wxWindow *win )
 {
-    if ( !win->HasVMT() )
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
+    if (!win->m_hasVMT)
         return;
 
     win->GetUpdateRegion().Union( rect->x, rect->y,
@@ -333,109 +714,52 @@ static void gtk_window_draw_callback( GtkWidget *WXUNUSED(widget), GdkRectangle
 
 static gint gtk_window_key_press_callback( GtkWidget *widget, GdkEventKey *gdk_event, wxWindow *win )
 {
-    if (!win->HasVMT()) return FALSE;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
+    if (!win->m_hasVMT) return FALSE;
     if (g_blockEventsOnDrag) return FALSE;
 
 /*
-    printf( "OnKeyPress from " );
-    if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-        printf( win->GetClassInfo()->GetClassName() );
-    printf( ".\n" );
+    printf( "KeyDown-ScanCode is: %d.\n", gdk_event->keyval );
+    if (gdk_event->state & GDK_SHIFT_MASK)
+      printf( "ShiftDown.\n" );
+    else
+      printf( "ShiftUp.\n" );
+    if (gdk_event->state & GDK_CONTROL_MASK)
+      printf( "ControlDown.\n" );
+    else
+      printf( "ControlUp.\n" );
+    printf( "\n" );
 */
+    int x = 0;
+    int y = 0;
+    GdkModifierType state;
+    if (gdk_event->window) gdk_window_get_pointer(gdk_event->window, &x, &y, &state);
 
-    long key_code = 0;
-    switch (gdk_event->keyval)
-    {
-        case GDK_BackSpace:     key_code = WXK_BACK;        break;
-        case GDK_ISO_Left_Tab:
-        case GDK_KP_Tab:
-        case GDK_Tab:           key_code = WXK_TAB;         break;
-        case GDK_Linefeed:      key_code = WXK_RETURN;      break;
-        case GDK_Clear:         key_code = WXK_CLEAR;       break;
-        case GDK_Return:        key_code = WXK_RETURN;      break;
-        case GDK_Pause:         key_code = WXK_PAUSE;       break;
-        case GDK_Scroll_Lock:   key_code = WXK_SCROLL;      break;
-        case GDK_Escape:        key_code = WXK_ESCAPE;      break;
-        case GDK_Delete:        key_code = WXK_DELETE;      break;
-        case GDK_Home:          key_code = WXK_HOME;        break;
-        case GDK_Left:          key_code = WXK_LEFT;        break;
-        case GDK_Up:            key_code = WXK_UP;          break;
-        case GDK_Right:         key_code = WXK_RIGHT;       break;
-        case GDK_Down:          key_code = WXK_DOWN;        break;
-        case GDK_Prior:         key_code = WXK_PRIOR;       break;
-//      case GDK_Page_Up:       key_code = WXK_PAGEUP;      break;
-        case GDK_Next:          key_code = WXK_NEXT;        break;
-//      case GDK_Page_Down:     key_code = WXK_PAGEDOWN;    break;
-        case GDK_End:           key_code = WXK_END;         break;
-        case GDK_Begin:         key_code = WXK_HOME;        break;
-        case GDK_Select:        key_code = WXK_SELECT;      break;
-        case GDK_Print:         key_code = WXK_PRINT;       break;
-        case GDK_Execute:       key_code = WXK_EXECUTE;     break;
-        case GDK_Insert:        key_code = WXK_INSERT;      break;
-        case GDK_Num_Lock:      key_code = WXK_NUMLOCK;     break;
-        case GDK_KP_Enter:      key_code = WXK_RETURN;      break;
-        case GDK_KP_Home:       key_code = WXK_HOME;        break;
-        case GDK_KP_Left:       key_code = WXK_LEFT;        break;
-        case GDK_KP_Up:         key_code = WXK_UP;          break;
-        case GDK_KP_Right:      key_code = WXK_RIGHT;       break;
-        case GDK_KP_Down:       key_code = WXK_DOWN;        break;
-        case GDK_KP_Prior:      key_code = WXK_PRIOR;       break;
-//      case GDK_KP_Page_Up:    key_code = WXK_PAGEUP;      break;
-        case GDK_KP_Next:       key_code = WXK_NEXT;        break;
-//      case GDK_KP_Page_Down:  key_code = WXK_PAGEDOWN;    break;
-        case GDK_KP_End:        key_code = WXK_END;         break;
-        case GDK_KP_Begin:      key_code = WXK_HOME;        break;
-        case GDK_KP_Insert:     key_code = WXK_INSERT;      break;
-        case GDK_KP_Delete:     key_code = WXK_DELETE;      break;
-        case GDK_KP_Multiply:   key_code = WXK_MULTIPLY;    break;
-        case GDK_KP_Add:        key_code = WXK_ADD;         break;
-        case GDK_KP_Separator:  key_code = WXK_SEPARATOR;   break;
-        case GDK_KP_Subtract:   key_code = WXK_SUBTRACT;    break;
-        case GDK_KP_Decimal:    key_code = WXK_DECIMAL;     break;
-        case GDK_KP_Divide:     key_code = WXK_DIVIDE;      break;
-        case GDK_KP_0:          key_code = WXK_NUMPAD0;     break;
-        case GDK_KP_1:          key_code = WXK_NUMPAD1;     break;
-        case GDK_KP_2:          key_code = WXK_NUMPAD2;     break;
-        case GDK_KP_3:          key_code = WXK_NUMPAD3;     break;
-        case GDK_KP_4:          key_code = WXK_NUMPAD4;     break;
-        case GDK_KP_5:          key_code = WXK_NUMPAD5;     break;
-        case GDK_KP_6:          key_code = WXK_NUMPAD6;     break;
-        case GDK_KP_7:          key_code = WXK_NUMPAD7;     break;
-        case GDK_KP_8:          key_code = WXK_NUMPAD7;     break;
-        case GDK_KP_9:          key_code = WXK_NUMPAD9;     break;
-        case GDK_F1:            key_code = WXK_F1;          break;
-        case GDK_F2:            key_code = WXK_F2;          break;
-        case GDK_F3:            key_code = WXK_F3;          break;
-        case GDK_F4:            key_code = WXK_F4;          break;
-        case GDK_F5:            key_code = WXK_F5;          break;
-        case GDK_F6:            key_code = WXK_F6;          break;
-        case GDK_F7:            key_code = WXK_F7;          break;
-        case GDK_F8:            key_code = WXK_F8;          break;
-        case GDK_F9:            key_code = WXK_F9;          break;
-        case GDK_F10:           key_code = WXK_F10;         break;
-        case GDK_F11:           key_code = WXK_F11;         break;
-        case GDK_F12:           key_code = WXK_F12;         break;
-        default:
-        {
-            if ((gdk_event->keyval >= 0x20) && (gdk_event->keyval <= 0xFF))
-                key_code = gdk_event->keyval;
-        }
-    }
+    long key_code = map_to_unmodified_wx_keysym( gdk_event->keyval );
+
+    /* sending unknown key events doesn't really make sense */
+    if (key_code == 0) return FALSE;
 
-    if (!key_code) return FALSE;
+    bool ret = FALSE;
 
     wxKeyEvent event( wxEVT_KEY_DOWN );
+    event.SetTimestamp( gdk_event->time );
     event.m_shiftDown = (gdk_event->state & GDK_SHIFT_MASK);
     event.m_controlDown = (gdk_event->state & GDK_CONTROL_MASK);
     event.m_altDown = (gdk_event->state & GDK_MOD1_MASK);
     event.m_metaDown = (gdk_event->state & GDK_MOD2_MASK);
     event.m_keyCode = key_code;
-    event.m_x = 0;
-    event.m_y = 0;
+    event.m_scanCode = gdk_event->keyval;
+    event.m_x = x;
+    event.m_y = y;
     event.SetEventObject( win );
+    ret = win->GetEventHandler()->ProcessEvent( event );
 
-    bool ret = win->GetEventHandler()->ProcessEvent( event );
+    key_code = map_to_wx_keysym( gdk_event->keyval );
 
+#if wxUSE_ACCEL
     if (!ret)
     {
         wxWindow *ancestor = win;
@@ -451,8 +775,28 @@ static gint gtk_window_key_press_callback( GtkWidget *widget, GdkEventKey *gdk_e
             ancestor = ancestor->GetParent();
         }
     }
+#endif // wxUSE_ACCEL
+    /* wxMSW doesn't send char events with Alt pressed */
+    /* Only send wxEVT_CHAR event if not processed yet. Thus, ALT-x
+       will only be sent if it is not a menu accelerator. */
+    if ((key_code != 0) && ! ret )
+    {
+        wxKeyEvent event2( wxEVT_CHAR );
+        event2.SetTimestamp( gdk_event->time );
+        event2.m_shiftDown = (gdk_event->state & GDK_SHIFT_MASK);
+        event2.m_controlDown = (gdk_event->state & GDK_CONTROL_MASK);
+        event2.m_altDown = (gdk_event->state & GDK_MOD1_MASK);
+        event2.m_metaDown = (gdk_event->state & GDK_MOD2_MASK);
+        event2.m_keyCode = key_code;
+        event2.m_scanCode = gdk_event->keyval;
+        event2.m_x = x;
+        event2.m_y = y;
+        event2.SetEventObject( win );
+        ret = (ret || win->GetEventHandler()->ProcessEvent( event2 ));
+    }
 
-    // win is a control: tab can be propagated up
+
+    /* win is a control: tab can be propagated up */
     if ( (!ret) &&
          ((gdk_event->keyval == GDK_Tab) || (gdk_event->keyval == GDK_ISO_Left_Tab)) &&
          (win->HasFlag(wxTE_PROCESS_TAB) == 0))
@@ -466,6 +810,7 @@ static gint gtk_window_key_press_callback( GtkWidget *widget, GdkEventKey *gdk_e
         ret = win->GetEventHandler()->ProcessEvent( new_event );
     }
 
+    /* generate wxID_CANCEL if <esc> has been pressed (typically in dialogs) */
     if ( (!ret) &&
          (gdk_event->keyval == GDK_Escape) )
     {
@@ -474,11 +819,41 @@ static gint gtk_window_key_press_callback( GtkWidget *widget, GdkEventKey *gdk_e
         ret = win->GetEventHandler()->ProcessEvent( new_event );
     }
 
+#if (GTK_MINOR_VERSION > 0)
+    /* pressing F10 will activate the menu bar of the top frame */
+    if ( (!ret) &&
+         (gdk_event->keyval == GDK_F10) )
+    {
+        wxWindow *ancestor = win;
+        while (ancestor)
+        {
+            if (wxIsKindOf(ancestor,wxFrame))
+            {
+                wxFrame *frame = (wxFrame*) ancestor;
+                wxMenuBar *menubar = frame->GetMenuBar();
+                if (menubar)
+                {
+                    wxNode *node = menubar->GetMenus().First();
+                    if (node)
+                    {
+                        // doesn't work correctly
+            // wxMenu *firstMenu = (wxMenu*) node->Data();
+                        // gtk_menu_item_select( GTK_MENU_ITEM(firstMenu->m_owner) );
+                        // ret = TRUE;
+                        break;
+                    }
+                }
+            }
+            ancestor = ancestor->GetParent();
+        }
+    }
+#endif
+
 /*
     Damn, I forgot why this didn't work, but it didn't work.
 
     // win is a panel: up can be propagated to the panel
-    if ((!ret) && (win->GetWxWindow()) && (win->m_parent) && (win->m_parent->AcceptsFocus()) &&
+    if ((!ret) && (win->m_wxwindow) && (win->m_parent) && (win->m_parent->AcceptsFocus()) &&
         (gdk_event->keyval == GDK_Up))
     {
         win->m_parent->SetFocus();
@@ -486,7 +861,7 @@ static gint gtk_window_key_press_callback( GtkWidget *widget, GdkEventKey *gdk_e
     }
 
     // win is a panel: left/right can be propagated to the panel
-    if ((!ret) && (win->GetWxWindow()) &&
+    if ((!ret) && (win->m_wxwindow) &&
         ((gdk_event->keyval == GDK_Right) || (gdk_event->keyval == GDK_Left) ||
          (gdk_event->keyval == GDK_Up) || (gdk_event->keyval == GDK_Down)))
     {
@@ -512,105 +887,45 @@ static gint gtk_window_key_press_callback( GtkWidget *widget, GdkEventKey *gdk_e
 
 static gint gtk_window_key_release_callback( GtkWidget *widget, GdkEventKey *gdk_event, wxWindow *win )
 {
-    if (!win->HasVMT()) return FALSE;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
+    if (!win->m_hasVMT) return FALSE;
     if (g_blockEventsOnDrag) return FALSE;
 
 /*
-    printf( "OnKeyRelease from " );
-    if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-        printf( win->GetClassInfo()->GetClassName() );
-    printf( ".\n" );
+    printf( "KeyUp-ScanCode is: %d.\n", gdk_event->keyval );
+    if (gdk_event->state & GDK_SHIFT_MASK)
+      printf( "ShiftDown.\n" );
+    else
+      printf( "ShiftUp.\n" );
+    if (gdk_event->state & GDK_CONTROL_MASK)
+      printf( "ControlDown.\n" );
+    else
+      printf( "ControlUp.\n" );
+    printf( "\n" );
 */
 
-    long key_code = 0;
-    switch (gdk_event->keyval)
-    {
-        case GDK_BackSpace:     key_code = WXK_BACK;        break;
-        case GDK_ISO_Left_Tab:
-        case GDK_KP_Tab:
-        case GDK_Tab:           key_code = WXK_TAB;         break;
-        case GDK_Linefeed:      key_code = WXK_RETURN;      break;
-        case GDK_Clear:         key_code = WXK_CLEAR;       break;
-        case GDK_Return:        key_code = WXK_RETURN;      break;
-        case GDK_Pause:         key_code = WXK_PAUSE;       break;
-        case GDK_Scroll_Lock:   key_code = WXK_SCROLL;      break;
-        case GDK_Escape:        key_code = WXK_ESCAPE;      break;
-        case GDK_Delete:        key_code = WXK_DELETE;      break;
-        case GDK_Home:          key_code = WXK_HOME;        break;
-        case GDK_Left:          key_code = WXK_LEFT;        break;
-        case GDK_Up:            key_code = WXK_UP;          break;
-        case GDK_Right:         key_code = WXK_RIGHT;       break;
-        case GDK_Down:          key_code = WXK_DOWN;        break;
-        case GDK_Prior:         key_code = WXK_PRIOR;       break;
-//      case GDK_Page_Up:       key_code = WXK_PAGEUP;      break;
-        case GDK_Next:          key_code = WXK_NEXT;        break;
-//      case GDK_Page_Down:     key_code = WXK_PAGEDOWN;    break;
-        case GDK_End:           key_code = WXK_END;         break;
-        case GDK_Begin:         key_code = WXK_HOME;        break;
-        case GDK_Select:        key_code = WXK_SELECT;      break;
-        case GDK_Print:         key_code = WXK_PRINT;       break;
-        case GDK_Execute:       key_code = WXK_EXECUTE;     break;
-        case GDK_Insert:        key_code = WXK_INSERT;      break;
-        case GDK_Num_Lock:      key_code = WXK_NUMLOCK;     break;
-        case GDK_KP_Enter:      key_code = WXK_RETURN;      break;
-        case GDK_KP_Home:       key_code = WXK_HOME;        break;
-        case GDK_KP_Left:       key_code = WXK_LEFT;        break;
-        case GDK_KP_Up:         key_code = WXK_UP;          break;
-        case GDK_KP_Right:      key_code = WXK_RIGHT;       break;
-        case GDK_KP_Down:       key_code = WXK_DOWN;        break;
-        case GDK_KP_Prior:      key_code = WXK_PRIOR;       break;
-//      case GDK_KP_Page_Up:    key_code = WXK_PAGEUP;      break;
-        case GDK_KP_Next:       key_code = WXK_NEXT;        break;
-//      case GDK_KP_Page_Down:  key_code = WXK_PAGEDOWN;    break;
-        case GDK_KP_End:        key_code = WXK_END;         break;
-        case GDK_KP_Begin:      key_code = WXK_HOME;        break;
-        case GDK_KP_Insert:     key_code = WXK_INSERT;      break;
-        case GDK_KP_Delete:     key_code = WXK_DELETE;      break;
-        case GDK_KP_Multiply:   key_code = WXK_MULTIPLY;    break;
-        case GDK_KP_Add:        key_code = WXK_ADD;         break;
-        case GDK_KP_Separator:  key_code = WXK_SEPARATOR;   break;
-        case GDK_KP_Subtract:   key_code = WXK_SUBTRACT;    break;
-        case GDK_KP_Decimal:    key_code = WXK_DECIMAL;     break;
-        case GDK_KP_Divide:     key_code = WXK_DIVIDE;      break;
-        case GDK_KP_0:          key_code = WXK_NUMPAD0;     break;
-        case GDK_KP_1:          key_code = WXK_NUMPAD1;     break;
-        case GDK_KP_2:          key_code = WXK_NUMPAD2;     break;
-        case GDK_KP_3:          key_code = WXK_NUMPAD3;     break;
-        case GDK_KP_4:          key_code = WXK_NUMPAD4;     break;
-        case GDK_KP_5:          key_code = WXK_NUMPAD5;     break;
-        case GDK_KP_6:          key_code = WXK_NUMPAD6;     break;
-        case GDK_KP_7:          key_code = WXK_NUMPAD7;     break;
-        case GDK_KP_8:          key_code = WXK_NUMPAD7;     break;
-        case GDK_KP_9:          key_code = WXK_NUMPAD9;     break;
-        case GDK_F1:            key_code = WXK_F1;          break;
-        case GDK_F2:            key_code = WXK_F2;          break;
-        case GDK_F3:            key_code = WXK_F3;          break;
-        case GDK_F4:            key_code = WXK_F4;          break;
-        case GDK_F5:            key_code = WXK_F5;          break;
-        case GDK_F6:            key_code = WXK_F6;          break;
-        case GDK_F7:            key_code = WXK_F7;          break;
-        case GDK_F8:            key_code = WXK_F8;          break;
-        case GDK_F9:            key_code = WXK_F9;          break;
-        case GDK_F10:           key_code = WXK_F10;         break;
-        case GDK_F11:           key_code = WXK_F11;         break;
-        case GDK_F12:           key_code = WXK_F12;         break;
-        default:
-        {
-            if ((gdk_event->keyval >= 0x20) && (gdk_event->keyval <= 0xFF))
-                key_code = gdk_event->keyval;
-        }
-    }
+    long key_code = map_to_unmodified_wx_keysym( gdk_event->keyval );
 
-    if (!key_code) return FALSE;
+    /* sending unknown key events doesn't really make sense */
+    if (key_code == 0) return FALSE;
+
+    int x = 0;
+    int y = 0;
+    GdkModifierType state;
+    if (gdk_event->window) gdk_window_get_pointer(gdk_event->window, &x, &y, &state);
 
     wxKeyEvent event( wxEVT_KEY_UP );
+    event.SetTimestamp( gdk_event->time );
     event.m_shiftDown = (gdk_event->state & GDK_SHIFT_MASK);
     event.m_controlDown = (gdk_event->state & GDK_CONTROL_MASK);
     event.m_altDown = (gdk_event->state & GDK_MOD1_MASK);
     event.m_metaDown = (gdk_event->state & GDK_MOD2_MASK);
     event.m_keyCode = key_code;
-    event.m_x = 0;
-    event.m_y = 0;
+    event.m_scanCode = gdk_event->keyval;
+    event.m_x = x;
+    event.m_y = y;
     event.SetEventObject( win );
 
     if (win->GetEventHandler()->ProcessEvent( event ))
@@ -628,33 +943,42 @@ static gint gtk_window_key_release_callback( GtkWidget *widget, GdkEventKey *gdk
 
 static gint gtk_window_button_press_callback( GtkWidget *widget, GdkEventButton *gdk_event, wxWindow *win )
 {
-    if (!win->HasVMT()) return FALSE;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
+/*
+    wxPrintf( _T("1) OnButtonPress from ") );
+    if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
+        wxPrintf( win->GetClassInfo()->GetClassName() );
+    wxPrintf( _T(".\n") );
+*/
+    if (!win->m_hasVMT) return FALSE;
     if (g_blockEventsOnDrag) return TRUE;
     if (g_blockEventsOnScroll) return TRUE;
 
     if (!win->IsOwnGtkWindow( gdk_event->window )) return FALSE;
 
-    if (win->GetWxWindow())
+    if (win->m_wxwindow)
     {
-        if (GTK_WIDGET_CAN_FOCUS(win->GetWxWindow()) && !GTK_WIDGET_HAS_FOCUS (win->GetWxWindow()) )
+        if (GTK_WIDGET_CAN_FOCUS(win->m_wxwindow) && !GTK_WIDGET_HAS_FOCUS (win->m_wxwindow) )
         {
-            gtk_widget_grab_focus (win->GetWxWindow());
+            gtk_widget_grab_focus (win->m_wxwindow);
 
 /*
-            printf( "GrabFocus from " );
+            wxPrintf( _T("GrabFocus from ") );
             if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-                printf( win->GetClassInfo()->GetClassName() );
-            printf( ".\n" );
+                wxPrintf( win->GetClassInfo()->GetClassName() );
+            wxPrintf( _T(".\n") );
 */
 
         }
     }
 
 /*
-    printf( "OnButtonPress from " );
+    wxPrintf( _T("2) OnButtonPress from ") );
     if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-        printf( win->GetClassInfo()->GetClassName() );
-    printf( ".\n" );
+        wxPrintf( win->GetClassInfo()->GetClassName() );
+    wxPrintf( _T(".\n") );
 */
 
     wxEventType event_type = wxEVT_LEFT_DOWN;
@@ -688,6 +1012,7 @@ static gint gtk_window_button_press_callback( GtkWidget *widget, GdkEventButton
     }
 
     wxMouseEvent event( event_type );
+    event.SetTimestamp( gdk_event->time );
     event.m_shiftDown = (gdk_event->state & GDK_SHIFT_MASK);
     event.m_controlDown = (gdk_event->state & GDK_CONTROL_MASK);
     event.m_altDown = (gdk_event->state & GDK_MOD1_MASK);
@@ -702,24 +1027,22 @@ static gint gtk_window_button_press_callback( GtkWidget *widget, GdkEventButton
     // Some control don't have their own X window and thus cannot get
     // any events.
 
-    if (!g_capturing)
+    if (!g_captureWindow)
     {
         wxNode *node = win->GetChildren().First();
         while (node)
         {
             wxWindow *child = (wxWindow*)node->Data();
 
-            if ( child->IsStaticBox() )
+            if (child->m_isStaticBox)
             {
                 // wxStaticBox is transparent in the box itself
-                int x = event.m_x,
-                    y = event.m_y;
-
-                wxRect rectChild(child->GetRect());
-                int xx1 = rectChild.GetLeft(),
-                    yy1 = rectChild.GetTop(),
-                    xx2 = rectChild.GetRight(),
-                    yy2 = rectChild.GetBottom();
+                int x = event.m_x;
+                int y = event.m_y;
+                int xx1 = child->m_x;
+                int yy1 = child->m_y;
+                int xx2 = child->m_x + child->m_width;
+                int yy2 = child->m_x + child->m_height;
 
                 // left
                 if (((x >= xx1) && (x <= xx1+10) && (y >= yy1) && (y <= yy2)) ||
@@ -731,23 +1054,23 @@ static gint gtk_window_button_press_callback( GtkWidget *widget, GdkEventButton
                     ((x >= xx1) && (x <= xx2) && (y >= yy2-1) && (y <= yy2)))
                 {
                     win = child;
-                    event.m_x -= child->GetX();
-                    event.m_y -= child->GetY();
+                    event.m_x -= child->m_x;
+                    event.m_y -= child->m_y;
                     break;
                 }
 
             }
             else
             {
-                if ((child->GetWxWindow() == (GtkWidget*) NULL) &&
-                    (child->GetX() <= event.m_x) &&
-                    (child->GetY() <= event.m_y) &&
-                    (child->GetX()+child->GetWidth()  >= event.m_x) &&
-                    (child->GetY()+child->GetHeight() >= event.m_y))
+                if ((child->m_wxwindow == (GtkWidget*) NULL) &&
+                    (child->m_x <= event.m_x) &&
+                    (child->m_y <= event.m_y) &&
+                    (child->m_x+child->m_width  >= event.m_x) &&
+                    (child->m_y+child->m_height >= event.m_y))
                 {
                     win = child;
-                    event.m_x -= child->GetX();
-                    event.m_y -= child->GetY();
+                    event.m_x -= child->m_x;
+                    event.m_y -= child->m_y;
                     break;
                 }
             }
@@ -774,7 +1097,10 @@ static gint gtk_window_button_press_callback( GtkWidget *widget, GdkEventButton
 
 static gint gtk_window_button_release_callback( GtkWidget *widget, GdkEventButton *gdk_event, wxWindow *win )
 {
-    if (!win->HasVMT()) return FALSE;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
+    if (!win->m_hasVMT) return FALSE;
     if (g_blockEventsOnDrag) return FALSE;
     if (g_blockEventsOnScroll) return FALSE;
 
@@ -797,6 +1123,7 @@ static gint gtk_window_button_release_callback( GtkWidget *widget, GdkEventButto
     }
 
     wxMouseEvent event( event_type );
+    event.SetTimestamp( gdk_event->time );
     event.m_shiftDown = (gdk_event->state & GDK_SHIFT_MASK);
     event.m_controlDown = (gdk_event->state & GDK_CONTROL_MASK);
     event.m_altDown = (gdk_event->state & GDK_MOD1_MASK);
@@ -810,22 +1137,22 @@ static gint gtk_window_button_release_callback( GtkWidget *widget, GdkEventButto
     // Some control don't have their own X window and thus cannot get
     // any events.
 
-    if (!g_capturing)
+    if (!g_captureWindow)
     {
         wxNode *node = win->GetChildren().First();
         while (node)
         {
             wxWindow *child = (wxWindow*)node->Data();
 
-            if (child->IsStaticBox() )
+            if (child->m_isStaticBox)
             {
                 // wxStaticBox is transparent in the box itself
                 int x = event.m_x;
                 int y = event.m_y;
-                int xx1 = child->GetX();
-                int yy1 = child->GetY();
-                int xx2 = child->GetX() + child->GetWidth();
-                int yy2 = child->GetX() + child->GetHeight();
+                int xx1 = child->m_x;
+                int yy1 = child->m_y;
+                int xx2 = child->m_x + child->m_width;
+                int yy2 = child->m_x + child->m_height;
 
                 // left
                 if (((x >= xx1) && (x <= xx1+10) && (y >= yy1) && (y <= yy2)) ||
@@ -837,23 +1164,23 @@ static gint gtk_window_button_release_callback( GtkWidget *widget, GdkEventButto
                     ((x >= xx1) && (x <= xx2) && (y >= yy2-1) && (y <= yy2)))
                 {
                     win = child;
-                    event.m_x -= child->GetX();
-                    event.m_y -= child->GetY();
+                    event.m_x -= child->m_x;
+                    event.m_y -= child->m_y;
                     break;
                 }
 
             }
             else
             {
-                if ((child->GetWxWindow() == (GtkWidget*) NULL) &&
-                    (child->GetX() <= event.m_x) &&
-                    (child->GetY() <= event.m_y) &&
-                    (child->GetX()+child->GetWidth()  >= event.m_x) &&
-                    (child->GetY()+child->GetHeight() >= event.m_y))
+                if ((child->m_wxwindow == (GtkWidget*) NULL) &&
+                    (child->m_x <= event.m_x) &&
+                    (child->m_y <= event.m_y) &&
+                    (child->m_x+child->m_width  >= event.m_x) &&
+                    (child->m_y+child->m_height >= event.m_y))
                 {
                     win = child;
-                    event.m_x -= child->GetX();
-                    event.m_y -= child->GetY();
+                    event.m_x -= child->m_x;
+                    event.m_y -= child->m_y;
                     break;
                 }
             }
@@ -878,7 +1205,10 @@ static gint gtk_window_button_release_callback( GtkWidget *widget, GdkEventButto
 
 static gint gtk_window_motion_notify_callback( GtkWidget *widget, GdkEventMotion *gdk_event, wxWindow *win )
 {
-    if (!win->HasVMT()) return FALSE;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
+    if (!win->m_hasVMT) return FALSE;
     if (g_blockEventsOnDrag) return FALSE;
     if (g_blockEventsOnScroll) return FALSE;
 
@@ -903,6 +1233,7 @@ static gint gtk_window_motion_notify_callback( GtkWidget *widget, GdkEventMotion
 */
 
     wxMouseEvent event( wxEVT_MOTION );
+    event.SetTimestamp( gdk_event->time );
     event.m_shiftDown = (gdk_event->state & GDK_SHIFT_MASK);
     event.m_controlDown = (gdk_event->state & GDK_CONTROL_MASK);
     event.m_altDown = (gdk_event->state & GDK_MOD1_MASK);
@@ -917,22 +1248,22 @@ static gint gtk_window_motion_notify_callback( GtkWidget *widget, GdkEventMotion
     // Some control don't have their own X window and thus cannot get
     // any events.
 
-    if (!g_capturing)
+    if (!g_captureWindow)
     {
         wxNode *node = win->GetChildren().First();
         while (node)
         {
             wxWindow *child = (wxWindow*)node->Data();
 
-            if ( child->IsStaticBox() )
+            if (child->m_isStaticBox)
             {
                 // wxStaticBox is transparent in the box itself
                 int x = event.m_x;
                 int y = event.m_y;
-                int xx1 = child->GetX();
-                int yy1 = child->GetY();
-                int xx2 = child->GetX() + child->GetWidth();
-                int yy2 = child->GetX() + child->GetHeight();
+                int xx1 = child->m_x;
+                int yy1 = child->m_y;
+                int xx2 = child->m_x + child->m_width;
+                int yy2 = child->m_x + child->m_height;
 
                 // left
                 if (((x >= xx1) && (x <= xx1+10) && (y >= yy1) && (y <= yy2)) ||
@@ -944,23 +1275,23 @@ static gint gtk_window_motion_notify_callback( GtkWidget *widget, GdkEventMotion
                     ((x >= xx1) && (x <= xx2) && (y >= yy2-1) && (y <= yy2)))
                 {
                     win = child;
-                    event.m_x -= child->GetX();
-                    event.m_y -= child->GetY();
+                    event.m_x -= child->m_x;
+                    event.m_y -= child->m_y;
                     break;
                 }
 
             }
             else
             {
-                if ((child->GetWxWindow() == (GtkWidget*) NULL) &&
-                    (child->GetX() <= event.m_x) &&
-                    (child->GetY() <= event.m_y) &&
-                    (child->GetX()+child->GetWidth()  >= event.m_x) &&
-                    (child->GetY()+child->GetHeight() >= event.m_y))
+                if ((child->m_wxwindow == (GtkWidget*) NULL) &&
+                    (child->m_x <= event.m_x) &&
+                    (child->m_y <= event.m_y) &&
+                    (child->m_x+child->m_width  >= event.m_x) &&
+                    (child->m_y+child->m_height >= event.m_y))
                 {
                     win = child;
-                    event.m_x -= child->GetX();
-                    event.m_y -= child->GetY();
+                    event.m_x -= child->m_x;
+                    event.m_y -= child->m_y;
                     break;
                 }
             }
@@ -985,16 +1316,19 @@ static gint gtk_window_motion_notify_callback( GtkWidget *widget, GdkEventMotion
 
 static gint gtk_window_focus_in_callback( GtkWidget *widget, GdkEvent *WXUNUSED(event), wxWindow *win )
 {
-    if (!win->HasVMT()) return FALSE;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
+    if (!win->m_hasVMT) return FALSE;
     if (g_blockEventsOnDrag) return FALSE;
 
     g_focusWindow = win;
 
-    if (win->GetWxWindow())
+    if (win->m_wxwindow)
     {
-        if (GTK_WIDGET_CAN_FOCUS(win->GetWxWindow()))
+        if (GTK_WIDGET_CAN_FOCUS(win->m_wxwindow))
         {
-            GTK_WIDGET_SET_FLAGS (win->GetWxWindow(), GTK_HAS_FOCUS);
+            GTK_WIDGET_SET_FLAGS (win->m_wxwindow, GTK_HAS_FOCUS);
 /*
             printf( "SetFocus flag from " );
             if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
@@ -1032,13 +1366,16 @@ static gint gtk_window_focus_in_callback( GtkWidget *widget, GdkEvent *WXUNUSED(
 
 static gint gtk_window_focus_out_callback( GtkWidget *widget, GdkEvent *WXUNUSED(event), wxWindow *win )
 {
-    if (!win->HasVMT()) return FALSE;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
+    if (!win->m_hasVMT) return FALSE;
     if (g_blockEventsOnDrag) return FALSE;
 
-    if (win->GetWxWindow())
+    if (win->m_wxwindow)
     {
-      if (GTK_WIDGET_CAN_FOCUS(win->GetWxWindow()))
-          GTK_WIDGET_UNSET_FLAGS (win->GetWxWindow(), GTK_HAS_FOCUS);
+      if (GTK_WIDGET_CAN_FOCUS(win->m_wxwindow))
+          GTK_WIDGET_UNSET_FLAGS (win->m_wxwindow, GTK_HAS_FOCUS);
     }
 
 /*
@@ -1066,31 +1403,25 @@ static gint gtk_window_focus_out_callback( GtkWidget *widget, GdkEvent *WXUNUSED
 
 static gint gtk_window_enter_callback( GtkWidget *widget, GdkEventCrossing *gdk_event, wxWindow *win )
 {
-    if ( !win->HasVMT() || g_blockEventsOnDrag )
-        return FALSE;
-
-    GdkWindow *window = widget->window;
-    if ( window != gdk_event->window )
-        return FALSE;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
 
-    if ( window && win->GetCursor().Ok() )
-        gdk_window_set_cursor( window, win->GetCursor().GetCursor() );
+    if (!win->m_hasVMT) return FALSE;
+    if (g_blockEventsOnDrag) return FALSE;
 
-/*
-    printf( "OnEnter from " );
-    if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-        printf( win->GetClassInfo()->GetClassName() );
-    printf( ".\n" );
-*/
+    if (!win->IsOwnGtkWindow( gdk_event->window )) return FALSE;
 
     wxMouseEvent event( wxEVT_ENTER_WINDOW );
+#if (GTK_MINOR_VERSION > 0)
+    event.SetTimestamp( gdk_event->time );
+#endif
     event.SetEventObject( win );
 
     int x = 0;
     int y = 0;
     GdkModifierType state = (GdkModifierType)0;
 
-    gdk_window_get_pointer( window, &x, &y, &state );
+    gdk_window_get_pointer( widget->window, &x, &y, &state );
 
     event.m_shiftDown = (state & GDK_SHIFT_MASK);
     event.m_controlDown = (state & GDK_CONTROL_MASK);
@@ -1118,24 +1449,18 @@ static gint gtk_window_enter_callback( GtkWidget *widget, GdkEventCrossing *gdk_
 
 static gint gtk_window_leave_callback( GtkWidget *widget, GdkEventCrossing *gdk_event, wxWindow *win )
 {
-    if ( !win->HasVMT() || g_blockEventsOnDrag )
-        return FALSE;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
 
-    GdkWindow *window = widget->window;
-    if ( window != gdk_event->window )
-        return FALSE;
-
-    if ( window && win->GetCursor().Ok() )
-        gdk_window_set_cursor( window, wxSTANDARD_CURSOR->GetCursor() );
+    if (!win->m_hasVMT) return FALSE;
+    if (g_blockEventsOnDrag) return FALSE;
 
-/*
-    printf( "OnLeave from " );
-    if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-        printf( win->GetClassInfo()->GetClassName() );
-    printf( ".\n" );
-*/
+    if (!win->IsOwnGtkWindow( gdk_event->window )) return FALSE;
 
     wxMouseEvent event( wxEVT_LEAVE_WINDOW );
+#if (GTK_MINOR_VERSION > 0)
+    event.SetTimestamp( gdk_event->time );
+#endif
     event.SetEventObject( win );
 
     int x = 0;
@@ -1170,44 +1495,40 @@ static gint gtk_window_leave_callback( GtkWidget *widget, GdkEventCrossing *gdk_
 
 static void gtk_window_vscroll_callback( GtkWidget *WXUNUSED(widget), wxWindow *win )
 {
-    if (g_blockEventsOnDrag) return;
+    if (g_isIdle)
+        wxapp_install_idle_handler();
 
-/*
-    printf( "OnVScroll from " );
-    if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-        printf( win->GetClassInfo()->GetClassName() );
-    printf( ".\n" );
-*/
+    if (g_blockEventsOnDrag) return;
 
-    if (!win->HasVMT()) return;
+    if (!win->m_hasVMT) return;
 
-    float diff = win->GetVAdjust()->value - win->GetOldVerticalPos();
+    float diff = win->m_vAdjust->value - win->m_oldVerticalPos;
     if (fabs(diff) < 0.2) return;
-    win->SetOldVerticalPos(win->GetVAdjust()->value);
+    win->m_oldVerticalPos = win->m_vAdjust->value;
 
     wxEventType command = wxEVT_NULL;
 
-    float line_step = win->GetVAdjust()->step_increment;
-    float page_step = win->GetVAdjust()->page_increment;
+    float line_step = win->m_vAdjust->step_increment;
+    float page_step = win->m_vAdjust->page_increment;
 
     if (win->IsScrolling())
     {
-        command = wxEVT_SCROLL_THUMBTRACK;
+        command = wxEVT_SCROLLWIN_THUMBTRACK;
     }
     else
     {
-        if (fabs(win->GetVAdjust()->value-win->GetVAdjust()->lower) < 0.2) command = wxEVT_SCROLL_BOTTOM;
-        else if (fabs(win->GetVAdjust()->value-win->GetVAdjust()->upper) < 0.2) command = wxEVT_SCROLL_TOP;
-        else if (fabs(diff-line_step) < 0.2) command = wxEVT_SCROLL_LINEDOWN;
-        else if (fabs(diff+line_step) < 0.2) command = wxEVT_SCROLL_LINEUP;
-        else if (fabs(diff-page_step) < 0.2) command = wxEVT_SCROLL_PAGEDOWN;
-        else if (fabs(diff+page_step) < 0.2) command = wxEVT_SCROLL_PAGEUP;
-        else command = wxEVT_SCROLL_THUMBTRACK;
+        if (fabs(win->m_vAdjust->value-win->m_vAdjust->lower) < 0.2) command = wxEVT_SCROLLWIN_BOTTOM;
+        else if (fabs(win->m_vAdjust->value-win->m_vAdjust->upper) < 0.2) command = wxEVT_SCROLLWIN_TOP;
+        else if (fabs(diff-line_step) < 0.2) command = wxEVT_SCROLLWIN_LINEDOWN;
+        else if (fabs(diff+line_step) < 0.2) command = wxEVT_SCROLLWIN_LINEUP;
+        else if (fabs(diff-page_step) < 0.2) command = wxEVT_SCROLLWIN_PAGEDOWN;
+        else if (fabs(diff+page_step) < 0.2) command = wxEVT_SCROLLWIN_PAGEUP;
+        else command = wxEVT_SCROLLWIN_THUMBTRACK;
     }
 
-    int value = (int)(win->GetVAdjust()->value+0.5);
+    int value = (int)(win->m_vAdjust->value+0.5);
 
-    wxScrollEvent event( command, win->GetId(), value, wxVERTICAL );
+    wxScrollWinEvent event( command, value, wxVERTICAL );
     event.SetEventObject( win );
     win->GetEventHandler()->ProcessEvent( event );
 }
@@ -1218,44 +1539,39 @@ static void gtk_window_vscroll_callback( GtkWidget *WXUNUSED(widget), wxWindow *
 
 static void gtk_window_hscroll_callback( GtkWidget *WXUNUSED(widget), wxWindow *win )
 {
-    if (g_blockEventsOnDrag) return;
-
-/*
-    printf( "OnHScroll from " );
-    if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-        printf( win->GetClassInfo()->GetClassName() );
-    printf( ".\n" );
-*/
+    if (g_isIdle)
+        wxapp_install_idle_handler();
 
-    if (!win->HasVMT()) return;
+    if (g_blockEventsOnDrag) return;
+    if (!win->m_hasVMT) return;
 
-    float diff = win->GetHAdjust()->value - win->GetOldHorizontalPos();
+    float diff = win->m_hAdjust->value - win->m_oldHorizontalPos;
     if (fabs(diff) < 0.2) return;
-    win->SetOldHorizontalPos( win->GetHAdjust()->value );
+    win->m_oldHorizontalPos = win->m_hAdjust->value;
 
     wxEventType command = wxEVT_NULL;
 
-    float line_step = win->GetHAdjust()->step_increment;
-    float page_step = win->GetHAdjust()->page_increment;
+    float line_step = win->m_hAdjust->step_increment;
+    float page_step = win->m_hAdjust->page_increment;
 
     if (win->IsScrolling())
     {
-        command = wxEVT_SCROLL_THUMBTRACK;
+        command = wxEVT_SCROLLWIN_THUMBTRACK;
     }
     else
     {
-        if (fabs(win->GetHAdjust()->value-win->GetHAdjust()->lower) < 0.2) command = wxEVT_SCROLL_BOTTOM;
-        else if (fabs(win->GetHAdjust()->value-win->GetHAdjust()->upper) < 0.2) command = wxEVT_SCROLL_TOP;
-        else if (fabs(diff-line_step) < 0.2) command = wxEVT_SCROLL_LINEDOWN;
-        else if (fabs(diff+line_step) < 0.2) command = wxEVT_SCROLL_LINEUP;
-        else if (fabs(diff-page_step) < 0.2) command = wxEVT_SCROLL_PAGEDOWN;
-        else if (fabs(diff+page_step) < 0.2) command = wxEVT_SCROLL_PAGEUP;
-        else command = wxEVT_SCROLL_THUMBTRACK;
+        if (fabs(win->m_hAdjust->value-win->m_hAdjust->lower) < 0.2) command = wxEVT_SCROLLWIN_BOTTOM;
+        else if (fabs(win->m_hAdjust->value-win->m_hAdjust->upper) < 0.2) command = wxEVT_SCROLLWIN_TOP;
+        else if (fabs(diff-line_step) < 0.2) command = wxEVT_SCROLLWIN_LINEDOWN;
+        else if (fabs(diff+line_step) < 0.2) command = wxEVT_SCROLLWIN_LINEUP;
+        else if (fabs(diff-page_step) < 0.2) command = wxEVT_SCROLLWIN_PAGEDOWN;
+        else if (fabs(diff+page_step) < 0.2) command = wxEVT_SCROLLWIN_PAGEUP;
+        else command = wxEVT_SCROLLWIN_THUMBTRACK;
     }
 
-    int value = (int)(win->GetHAdjust()->value+0.5);
+    int value = (int)(win->m_hAdjust->value+0.5);
 
-    wxScrollEvent event( command, win->GetId(), value, wxHORIZONTAL );
+    wxScrollWinEvent event( command, value, wxHORIZONTAL );
     event.SetEventObject( win );
     win->GetEventHandler()->ProcessEvent( event );
 }
@@ -1266,21 +1582,16 @@ static void gtk_window_hscroll_callback( GtkWidget *WXUNUSED(widget), wxWindow *
 
 static void gtk_window_vscroll_change_callback( GtkWidget *WXUNUSED(widget), wxWindow *win )
 {
-    if (g_blockEventsOnDrag) return;
-
-/*
-    printf( "OnVScroll change from " );
-    if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-        printf( win->GetClassInfo()->GetClassName() );
-    printf( ".\n" );
-*/
+    if (g_isIdle)
+        wxapp_install_idle_handler();
 
-    if (!win->HasVMT()) return;
+    if (g_blockEventsOnDrag) return;
+    if (!win->m_hasVMT) return;
 
-    wxEventType command = wxEVT_SCROLL_THUMBTRACK;
-    int value = (int)(win->GetVAdjust()->value+0.5);
+    wxEventType command = wxEVT_SCROLLWIN_THUMBTRACK;
+    int value = (int)(win->m_vAdjust->value+0.5);
 
-    wxScrollEvent event( command, win->GetId(), value, wxVERTICAL );
+    wxScrollWinEvent event( command, value, wxVERTICAL );
     event.SetEventObject( win );
     win->GetEventHandler()->ProcessEvent( event );
 }
@@ -1291,21 +1602,16 @@ static void gtk_window_vscroll_change_callback( GtkWidget *WXUNUSED(widget), wxW
 
 static void gtk_window_hscroll_change_callback( GtkWidget *WXUNUSED(widget), wxWindow *win )
 {
-    if (g_blockEventsOnDrag) return;
-
-/*
-    printf( "OnHScroll change from " );
-    if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
-        printf( win->GetClassInfo()->GetClassName() );
-    printf( ".\n" );
-*/
+    if (g_isIdle)
+        wxapp_install_idle_handler();
 
-    if (!win->HasVMT()) return;
+    if (g_blockEventsOnDrag) return;
+    if (!win->m_hasVMT) return;
 
-    wxEventType command = wxEVT_SCROLL_THUMBTRACK;
-    int value = (int)(win->GetHAdjust()->value+0.5);
+    wxEventType command = wxEVT_SCROLLWIN_THUMBTRACK;
+    int value = (int)(win->m_hAdjust->value+0.5);
 
-    wxScrollEvent event( command, win->GetId(), value, wxHORIZONTAL );
+    wxScrollWinEvent event( command, value, wxHORIZONTAL );
     event.SetEventObject( win );
     win->GetEventHandler()->ProcessEvent( event );
 }
@@ -1318,6 +1624,9 @@ static gint gtk_scrollbar_button_press_callback( GtkRange *WXUNUSED(widget),
                                                  GdkEventButton *WXUNUSED(gdk_event),
                                                  wxWindow *win )
 {
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
 //  don't test here as we can release the mouse while being over
 //  a different window then the slider
 //
@@ -1342,12 +1651,12 @@ static gint gtk_scrollbar_button_release_callback( GtkRange *widget,
 //
 //    if (gdk_event->window != widget->slider) return FALSE;
 
-    GtkScrolledWindow *scrolledWindow = GTK_SCROLLED_WINDOW(win->GetHandle());
+    GtkScrolledWindow *scrolledWindow = GTK_SCROLLED_WINDOW(win->m_widget);
 
     if (widget == GTK_RANGE(scrolledWindow->vscrollbar))
-        gtk_signal_emit_by_name( GTK_OBJECT(win->GetHAdjust()), "value_changed" );
+        gtk_signal_emit_by_name( GTK_OBJECT(win->m_hAdjust), "value_changed" );
     else
-        gtk_signal_emit_by_name( GTK_OBJECT(win->GetVAdjust()), "value_changed" );
+        gtk_signal_emit_by_name( GTK_OBJECT(win->m_vAdjust), "value_changed" );
 
     win->SetScrolling( FALSE );
 
@@ -1364,6 +1673,37 @@ wxWindow *wxWindowBase::FindFocus()
     return g_focusWindow;
 }
 
+//-----------------------------------------------------------------------------
+// "realize" from m_widget
+//-----------------------------------------------------------------------------
+
+/* we cannot set colours, fonts and cursors before the widget has
+   been realized, so we do this directly after realization */
+
+static gint
+gtk_window_realized_callback( GtkWidget * WXUNUSED(widget), wxWindow *win )
+{
+    if (g_isIdle)
+        wxapp_install_idle_handler();
+
+    if (win->m_delayedFont)
+        win->SetFont( win->GetFont() );
+
+    if (win->m_delayedBackgroundColour)
+        win->SetBackgroundColour( win->GetBackgroundColour() );
+
+    if (win->m_delayedForegroundColour)
+        win->SetForegroundColour( win->GetForegroundColour() );
+
+    win->SetCursor( win->GetCursor() );
+
+    wxWindowCreateEvent event( win );
+    event.SetEventObject( win );
+    win->GetEventHandler()->ProcessEvent( event );
+
+    return FALSE;
+}
+
 //-----------------------------------------------------------------------------
 // InsertChild for wxWindow.
 //-----------------------------------------------------------------------------
@@ -1377,22 +1717,18 @@ wxWindow *wxWindowBase::FindFocus()
 
 static void wxInsertChildInWindow( wxWindow* parent, wxWindow* child )
 {
-    gtk_myfixed_put( GTK_MYFIXED(parent->GetWxWindow()),
-                     GTK_WIDGET(child->GetHandle()),
-                     child->GetX(),
-                     child->GetY(),
-                     child->GetWidth(),
-                     child->GetHeight() );
-
-    gtk_widget_set_usize( GTK_WIDGET(child->GetHandle()),
-                          child->GetWidth(),
-                          child->GetHeight() );
+    gtk_myfixed_put( GTK_MYFIXED(parent->m_wxwindow),
+                     GTK_WIDGET(child->m_widget),
+                     child->m_x,
+                     child->m_y,
+                     child->m_width,
+                     child->m_height );
 
     if (parent->HasFlag(wxTAB_TRAVERSAL))
     {
         /* we now allow a window to get the focus as long as it
            doesn't have any children. */
-        GTK_WIDGET_UNSET_FLAGS( parent->GetWxWindow(), GTK_CAN_FOCUS );
+        GTK_WIDGET_UNSET_FLAGS( parent->m_wxwindow, GTK_CAN_FOCUS );
     }
 }
 
@@ -1411,44 +1747,39 @@ wxWindow* wxGetActiveWindow()
 
 IMPLEMENT_DYNAMIC_CLASS(wxWindow, wxWindowBase)
 
-BEGIN_EVENT_TABLE(wxWindow, wxWindowBase)
-    EVT_KEY_DOWN(wxWindow::OnKeyDown)
-END_EVENT_TABLE()
-
 void wxWindow::Init()
 {
     // common init
     InitBase();
 
     // GTK specific
+    m_widget = (GtkWidget *) NULL;
     m_wxwindow = (GtkWidget *) NULL;
 
     // position/size
-    m_x =
-    m_y =
-    m_width =
+    m_x = 0;
+    m_y = 0;
+    m_width = 0;
     m_height = 0;
 
-    m_font = *wxSWISS_FONT;
-    m_windowName = "noname";
-
     m_sizeSet = FALSE;
     m_hasVMT = FALSE;
     m_needParent = TRUE;
+    m_isBeingDeleted = FALSE;
 
-    m_hasScrolling =
+    m_hasScrolling = FALSE;
     m_isScrolling = FALSE;
 
-    m_hAdjust =
+    m_hAdjust = (GtkAdjustment*) NULL;
     m_vAdjust = (GtkAdjustment*) NULL;
-    m_oldHorizontalPos =
+    m_oldHorizontalPos = 0.0;
     m_oldVerticalPos = 0.0;
 
     m_resizing = FALSE;
     m_scrollGC = (GdkGC*) NULL;
     m_widgetStyle = (GtkStyle*) NULL;
 
-    m_insertCallback = wxInsertChildInWindow;
+    m_insertCallback = (wxInsertChildFunction) NULL;
 
     m_isStaticBox = FALSE;
     m_acceptsFocus = FALSE;
@@ -1474,6 +1805,8 @@ bool wxWindow::Create( wxWindow *parent, wxWindowID id,
 {
     PreCreation( parent, id, pos, size, style, name );
 
+    m_insertCallback = wxInsertChildInWindow;
+
     m_widget = gtk_scrolled_window_new( (GtkAdjustment *) NULL, (GtkAdjustment *) NULL );
     GTK_WIDGET_UNSET_FLAGS( m_widget, GTK_CAN_FOCUS );
 
@@ -1556,8 +1889,20 @@ bool wxWindow::Create( wxWindow *parent, wxWindowID id,
 #endif // GTK_MINOR_VERSION == 0
 
     // I _really_ don't want scrollbars in the beginning
-    InitAdjustment(m_vAdjust);
-    InitAdjustment(m_hAdjust);
+    m_vAdjust->lower = 0.0;
+    m_vAdjust->upper = 1.0;
+    m_vAdjust->value = 0.0;
+    m_vAdjust->step_increment = 1.0;
+    m_vAdjust->page_increment = 1.0;
+    m_vAdjust->page_size = 5.0;
+    gtk_signal_emit_by_name( GTK_OBJECT(m_vAdjust), "changed" );
+    m_hAdjust->lower = 0.0;
+    m_hAdjust->upper = 1.0;
+    m_hAdjust->value = 0.0;
+    m_hAdjust->step_increment = 1.0;
+    m_hAdjust->page_increment = 1.0;
+    m_hAdjust->page_size = 5.0;
+    gtk_signal_emit_by_name( GTK_OBJECT(m_hAdjust), "changed" );
 
     // these handlers block mouse events to any window during scrolling such as
     // motion events and prevent GTK and wxWindows from fighting over where the
@@ -1603,25 +1948,40 @@ bool wxWindow::Create( wxWindow *parent, wxWindowID id,
 
 wxWindow::~wxWindow()
 {
+    m_isBeingDeleted = TRUE;
     m_hasVMT = FALSE;
 
     if (m_widget)
         Show( FALSE );
 
+    DestroyChildren();
+
     if (m_parent)
         m_parent->RemoveChild( this );
 
     if (m_widgetStyle)
+    {
         gtk_style_unref( m_widgetStyle );
+        m_widgetStyle = (GtkStyle*) NULL;
+    }
 
     if (m_scrollGC)
+    {
         gdk_gc_unref( m_scrollGC );
+        m_scrollGC = (GdkGC*) NULL;
+    }
 
     if (m_wxwindow)
+    {
         gtk_widget_destroy( m_wxwindow );
+        m_wxwindow = (GtkWidget*) NULL;
+    }
 
     if (m_widget)
+    {
         gtk_widget_destroy( m_widget );
+        m_widget = (GtkWidget*) NULL;
+    }
 }
 
 void wxWindow::PreCreation( wxWindow *parent,
@@ -1682,16 +2042,14 @@ void wxWindow::PostCreation()
 #endif
     }
 
-    ConnectWidget( GetConnectWidget() );
+    GtkWidget *connect_widget = GetConnectWidget();
 
-    /* we force the creation of wxFrame and wxDialog in the respective code */
-    if (m_parent)
-        gtk_widget_realize( m_widget );
+    ConnectWidget( connect_widget );
 
-    if (m_wxwindow)
-        gtk_widget_realize( m_wxwindow );
-
-    SetCursor( *wxSTANDARD_CURSOR );
+   /*  we cannot set colours, fonts and cursors before the widget has
+       been realized, so we do this directly after realization */
+    gtk_signal_connect( GTK_OBJECT(connect_widget), "realize",
+                            GTK_SIGNAL_FUNC(gtk_window_realized_callback), (gpointer) this );
 
     m_hasVMT = TRUE;
 }
@@ -1743,7 +2101,7 @@ void wxWindow::DoSetSize( int x, int y, int width, int height, int sizeFlags )
     if (m_resizing) return; /* I don't like recursions */
     m_resizing = TRUE;
 
-    if (m_parent->GetWxWindow() == NULL) /* i.e. wxNotebook */
+    if (m_parent->m_wxwindow == NULL) /* i.e. wxNotebook */
     {
         /* don't set the size for children of wxNotebook, just take the values. */
         m_x = x;
@@ -1753,10 +2111,7 @@ void wxWindow::DoSetSize( int x, int y, int width, int height, int sizeFlags )
     }
     else
     {
-        int old_width = m_width;
-        int old_height = m_height;
-
-        if ((sizeFlags & wxSIZE_USE_EXISTING) == wxSIZE_USE_EXISTING)
+        if ((sizeFlags & wxSIZE_ALLOW_MINUS_ONE) == 0)
         {
             if (x != -1) m_x = x;
             if (y != -1) m_y = y;
@@ -1786,22 +2141,43 @@ void wxWindow::DoSetSize( int x, int y, int width, int height, int sizeFlags )
         if ((m_maxWidth != -1) && (m_width > m_maxWidth)) m_width = m_maxWidth;
         if ((m_maxHeight != -1) && (m_height > m_maxHeight)) m_height = m_maxHeight;
 
-        if (GTK_WIDGET_HAS_DEFAULT(m_widget))
+        int border = 0;
+        int bottom_border = 0;
+
+        if (GTK_WIDGET_CAN_DEFAULT(m_widget))
         {
             /* the default button has a border around it */
-            int border = 5;
-
-            gtk_myfixed_move( GTK_MYFIXED(m_parent->GetWxWindow()), m_widget, m_x-border, m_y-border );
-
-            gtk_widget_set_usize( m_widget, m_width+2*border, m_height+2*border );
+            border = 6;
+            bottom_border = 5;
         }
-        else
-        {
-            gtk_myfixed_move( GTK_MYFIXED(m_parent->GetWxWindow()), m_widget, m_x, m_y );
 
-            if ((old_width != m_width) || (old_height != m_height))
-              gtk_widget_set_usize( m_widget, m_width, m_height );
-        }
+        /* this is the result of hours of debugging: the following code
+           means that if we have a m_wxwindow and we set the size of
+           m_widget, m_widget (which is a GtkScrolledWindow) does NOT
+           automatically propagate its size down to its m_wxwindow,
+           which is its client area. therefore, we have to tell the
+           client area directly that it has to resize itself.
+           this will lead to that m_widget (GtkScrolledWindow) will
+           calculate how much size it needs for scrollbars etc and
+           it will then call XXX_size_allocate of its child, which
+           is m_wxwindow. m_wxwindow in turn will do the same with its
+           children and so on. problems can arise if this happens
+           before all the children have been realized as some widgets
+           stupidy need to be realized during XXX_size_allocate (e.g.
+           GtkNotebook) and they will segv if called otherwise. this
+           emergency is tested in gtk_myfixed_size_allocate. Normally
+           this shouldn't be needed and only gtk_widget_queue_resize()
+           should be enough to provoke a resize at the next appropriate
+           moment, but this seems to fail, e.g. when a wxNotebook contains
+           a wxSplitterWindow: the splitter window's children won't
+           show up properly resized then. */
+
+        gtk_myfixed_set_size( GTK_MYFIXED(m_parent->m_wxwindow),
+                              m_widget,
+                              m_x-border,
+                              m_y-border,
+                              m_width+2*border,
+                              m_height+border+bottom_border );
     }
 
     m_sizeSet = TRUE;
@@ -1815,6 +2191,19 @@ void wxWindow::DoSetSize( int x, int y, int width, int height, int sizeFlags )
 
 void wxWindow::OnInternalIdle()
 {
+        GdkWindow *window = GetConnectWidget()->window;
+        if (window)
+        {
+            wxCursor cursor = m_cursor;
+            if (g_globalCursor.Ok()) cursor = g_globalCursor;
+
+            if (cursor.Ok() && m_currentGdkCursor != cursor)
+            {
+                gdk_window_set_cursor( window, cursor.GetCursor() );
+                m_currentGdkCursor = cursor;
+            }
+        }
+
     UpdateWindowUI();
 }
 
@@ -1881,7 +2270,7 @@ void wxWindow::DoSetClientSize( int width, int height )
             if (scroll_window->hscrollbar_visible)
             {
                 dh += 15;   /* dh += hscrollbar->allocation.height; */
-                dw += scroll_class->scrollbar_spacing;
+                dh += scroll_class->scrollbar_spacing;
             }
        }
 
@@ -1961,10 +2350,12 @@ void wxWindow::DoGetPosition( int *x, int *y ) const
     if (y) (*y) = m_y;
 }
 
-void wxWindow::ClientToScreen( int *x, int *y ) const
+void wxWindow::DoClientToScreen( int *x, int *y ) const
 {
     wxCHECK_RET( (m_widget != NULL), _T("invalid window") );
 
+    if (!m_widget->window) return;
+
     GdkWindow *source = (GdkWindow *) NULL;
     if (m_wxwindow)
         source = m_wxwindow->window;
@@ -1988,10 +2379,12 @@ void wxWindow::ClientToScreen( int *x, int *y ) const
     if (y) *y += org_y;
 }
 
-void wxWindow::ScreenToClient( int *x, int *y ) const
+void wxWindow::DoScreenToClient( int *x, int *y ) const
 {
     wxCHECK_RET( (m_widget != NULL), _T("invalid window") );
 
+    if (!m_widget->window) return;
+
     GdkWindow *source = (GdkWindow *) NULL;
     if (m_wxwindow)
         source = m_wxwindow->window;
@@ -2019,8 +2412,11 @@ bool wxWindow::Show( bool show )
 {
     wxCHECK_MSG( (m_widget != NULL), FALSE, _T("invalid window") );
 
-    if ( !wxWindowBase::Show(show) )
+    if (!wxWindowBase::Show(show))
+    {
+        // nothing to do
         return FALSE;
+    }
 
     if (show)
         gtk_widget_show( m_widget );
@@ -2034,8 +2430,11 @@ bool wxWindow::Enable( bool enable )
 {
     wxCHECK_MSG( (m_widget != NULL), FALSE, _T("invalid window") );
 
-    if ( !wxWindowBase::Enable(enable) )
+    if (!wxWindowBase::Enable(enable))
+    {
+        // nothing to do
         return FALSE;
+    }
 
     gtk_widget_set_sensitive( m_widget, enable );
     if ( m_wxwindow )
@@ -2085,16 +2484,6 @@ void wxWindow::GetTextExtent( const wxString& string,
     if (externalLeading) (*externalLeading) = 0;  // ??
 }
 
-void wxWindow::OnKeyDown( wxKeyEvent &event )
-{
-    event.SetEventType( wxEVT_CHAR );
-
-    if (!GetEventHandler()->ProcessEvent( event ))
-    {
-        event.Skip();
-    }
-}
-
 void wxWindow::SetFocus()
 {
     wxCHECK_RET( (m_widget != NULL), _T("invalid window") );
@@ -2123,20 +2512,48 @@ bool wxWindow::AcceptsFocus() const
 
 bool wxWindow::Reparent( wxWindow *newParent )
 {
-    wxCHECK_MSG( (m_widget != NULL), (wxWindow*) NULL, _T("invalid window") );
+    wxCHECK_MSG( (m_widget != NULL), FALSE, _T("invalid window") );
+
+    wxWindow *oldParent = m_parent;
 
     if ( !wxWindowBase::Reparent(newParent) )
         return FALSE;
 
-    gtk_widget_unparent( m_widget );
+    if (oldParent)
+    {
+        gtk_container_remove( GTK_CONTAINER(oldParent->m_wxwindow), m_widget );
+    }
+
+    if (newParent)
+    {
+        /* insert GTK representation */
+        (*(newParent->m_insertCallback))(newParent, this);
+    }
 
     return TRUE;
 }
 
+void wxWindow::DoAddChild(wxWindow *child)
+{
+    wxASSERT_MSG( (m_widget != NULL), _T("invalid window") );
+
+    wxASSERT_MSG( (child != NULL), _T("invalid child window") );
+
+    wxASSERT_MSG( (m_insertCallback != NULL), _T("invalid child insertion function") );
+
+    /* add to list */
+    AddChild( child );
+
+    /* insert GTK representation */
+    (*m_insertCallback)(this, child);
+}
+
 void wxWindow::Raise()
 {
     wxCHECK_RET( (m_widget != NULL), _T("invalid window") );
 
+    if (!m_widget->window) return;
+
     gdk_window_raise( m_widget->window );
 }
 
@@ -2144,6 +2561,8 @@ void wxWindow::Lower()
 {
     wxCHECK_RET( (m_widget != NULL), _T("invalid window") );
 
+    if (!m_widget->window) return;
+
     gdk_window_lower( m_widget->window );
 }
 
@@ -2151,33 +2570,50 @@ bool wxWindow::SetCursor( const wxCursor &cursor )
 {
     wxCHECK_MSG( (m_widget != NULL), FALSE, _T("invalid window") );
 
-    if ( wxWindowBase::SetCursor(cursor) )
+    if (!wxWindowBase::SetCursor(cursor))
     {
-        if ((m_widget) && (m_widget->window))
-             gdk_window_set_cursor( m_widget->window, GetCursor().GetCursor() );
+        // don't leave if the GTK widget has just
+        // been realized
+        if (!m_delayedCursor) return FALSE;
+    }
 
-        if ((m_wxwindow) && (m_wxwindow->window))
-             gdk_window_set_cursor( m_wxwindow->window, GetCursor().GetCursor() );
+    GtkWidget *connect_widget = GetConnectWidget();
+    if (!connect_widget->window)
+    {
+        // indicate that a new style has been set
+        // but it couldn't get applied as the
+        // widget hasn't been realized yet.
+        m_delayedCursor = TRUE;
 
-        // cursor was set
+        // pretend we have done something
         return TRUE;
     }
-    else
-    {
-        // cursor hasn't been changed
-        return FALSE;
-    }
+
+//    gdk_window_set_cursor( connect_widget->window, GetCursor().GetCursor() );
+
+    // cursor was set
+    return TRUE;
 }
 
-void wxWindow::WarpPointer( int WXUNUSED(x), int WXUNUSED(y) )
+void wxWindow::WarpPointer( int x, int y )
 {
-    // TODO
+    wxCHECK_RET( (m_widget != NULL), _T("invalid window") );
+
+    GtkWidget *connect_widget = GetConnectWidget();
+    if (connect_widget->window)
+    {
+        /* we provide this function ourselves as it is
+           missing in GDK */
+        gdk_window_warp_pointer( connect_widget->window, x, y );
+    }
 }
 
 void wxWindow::Refresh( bool eraseBackground, const wxRect *rect )
 {
     wxCHECK_RET( (m_widget != NULL), _T("invalid window") );
 
+    if (!m_widget->window) return;
+
     if (eraseBackground && m_wxwindow && m_wxwindow->window)
     {
         if (rect)
@@ -2218,6 +2654,8 @@ void wxWindow::Clear()
 {
     wxCHECK_RET( m_widget != NULL, _T("invalid window") );
 
+    if (!m_widget->window) return;
+
     if (m_wxwindow && m_wxwindow->window)
     {
         gdk_window_clear( m_wxwindow->window );
@@ -2235,7 +2673,7 @@ void wxWindow::DoSetToolTip( wxToolTip *tip )
 
 void wxWindow::ApplyToolTip( GtkTooltips *tips, const wxChar *tip )
 {
-    gtk_tooltips_set_tip( tips, GetConnectWidget(), wxConv_current->cWX2MB(tip), (gchar*) NULL );
+    gtk_tooltips_set_tip( tips, GetConnectWidget(), wxConvCurrent->cWX2MB(tip), (gchar*) NULL );
 }
 #endif // wxUSE_TOOLTIPS
 
@@ -2243,21 +2681,36 @@ bool wxWindow::SetBackgroundColour( const wxColour &colour )
 {
     wxCHECK_MSG( m_widget != NULL, FALSE, _T("invalid window") );
 
-    if ( !wxWindowBase::SetBackgroundColour(colour) )
-        return FALSE;
+    if (!wxWindowBase::SetBackgroundColour(colour))
+    {
+        // don't leave if the GTK widget has just
+        // been realized
+        if (!m_delayedBackgroundColour) return FALSE;
+    }
+
+    GtkWidget *connect_widget = GetConnectWidget();
+    if (!connect_widget->window)
+    {
+        // indicate that a new style has been set
+        // but it couldn't get applied as the
+        // widget hasn't been realized yet.
+        m_delayedBackgroundColour = TRUE;
+
+        // pretend we have done something
+        return TRUE;
+    }
 
     if (m_wxwindow && m_wxwindow->window)
     {
-        // wxMSW doesn't clear the window here. I don't do that either to
-        // provide compatibility. call Clear() to do the job.
+        /* wxMSW doesn't clear the window here. I don't do that either to
+          provide compatibility. call Clear() to do the job. */
 
         m_backgroundColour.CalcPixel( gdk_window_get_colormap( m_wxwindow->window ) );
         gdk_window_set_background( m_wxwindow->window, m_backgroundColour.GetColor() );
     }
 
     wxColour sysbg = wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNFACE );
-
-    if ( sysbg == m_backgroundColour )
+    if (sysbg == m_backgroundColour)
     {
         m_backgroundColour = wxNullColour;
         ApplyWidgetStyle();
@@ -2275,11 +2728,27 @@ bool wxWindow::SetForegroundColour( const wxColour &colour )
 {
     wxCHECK_MSG( m_widget != NULL, FALSE, _T("invalid window") );
 
-    if ( !wxWindowBase::SetForegroundColour(colour) )
-        return FALSE;
+    if (!wxWindowBase::SetForegroundColour(colour))
+    {
+        // don't leave if the GTK widget has just
+        // been realized
+        if (!m_delayedForegroundColour) return FALSE;
+    }
+
+    GtkWidget *connect_widget = GetConnectWidget();
+    if (!connect_widget->window)
+    {
+        // indicate that a new style has been set
+        // but it couldn't get applied as the
+        // widget hasn't been realized yet.
+        m_delayedForegroundColour = TRUE;
+
+        // pretend we have done something
+        return TRUE;
+    }
 
     wxColour sysbg = wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNFACE );
-    if ( sysbg == m_foregroundColour )
+    if ( sysbg == m_backgroundColour )
     {
         m_backgroundColour = wxNullColour;
         ApplyWidgetStyle();
@@ -2353,7 +2822,9 @@ static void SetInvokingWindow( wxMenu *menu, wxWindow *win )
 static gint gs_pop_x = 0;
 static gint gs_pop_y = 0;
 
-static void pop_pos_callback( GtkMenu *menu, gint *x, gint *y, wxWindow *win )
+static void pop_pos_callback( GtkMenu * WXUNUSED(menu),
+                              gint *x, gint *y,
+                              wxWindow *win )
 {
     win->ClientToScreen( &gs_pop_x, &gs_pop_y );
     *x = gs_pop_x;
@@ -2419,12 +2890,25 @@ bool wxWindow::IsOwnGtkWindow( GdkWindow *window )
 
 bool wxWindow::SetFont( const wxFont &font )
 {
-    wxCHECK_MSG( m_widget != NULL, FALSE, _T("invalid window") );
+    wxCHECK_MSG( m_widget != NULL, FALSE, _T(        "invalid window") );
 
-    if ( !wxWindowBase::SetFont(font) )
+    if (!wxWindowBase::SetFont(font))
     {
-        // nothing to do
-        return FALSE;
+        // don't leave if the GTK widget has just
+        // been realized
+        if (!m_delayedFont) return FALSE;
+    }
+
+    GtkWidget *connect_widget = GetConnectWidget();
+    if (!connect_widget->window)
+    {
+        // indicate that a new style has been set
+        // but it couldn't get applied as the
+        // widget hasn't been realized yet.
+        m_delayedFont = TRUE;
+
+        // pretend we have done something
+        return TRUE;
     }
 
     wxColour sysbg = wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNFACE );
@@ -2446,31 +2930,33 @@ void wxWindow::CaptureMouse()
 {
     wxCHECK_RET( m_widget != NULL, _T("invalid window") );
 
-    wxCHECK_RET( g_capturing == FALSE, _T("CaptureMouse called twice") );
+    wxCHECK_RET( g_captureWindow == NULL, _T("CaptureMouse called twice") );
 
     GtkWidget *connect_widget = GetConnectWidget();
-    gtk_grab_add( connect_widget );
+    if (!connect_widget->window) return;
+
     gdk_pointer_grab( connect_widget->window, FALSE,
                       (GdkEventMask)
                          (GDK_BUTTON_PRESS_MASK |
                           GDK_BUTTON_RELEASE_MASK |
                           GDK_POINTER_MOTION_MASK),
                       (GdkWindow *) NULL,
-                      (GdkCursor *) NULL,
+                      m_cursor.GetCursor(),
                       GDK_CURRENT_TIME );
-    g_capturing = TRUE;
+    g_captureWindow = this;
 }
 
 void wxWindow::ReleaseMouse()
 {
     wxCHECK_RET( m_widget != NULL, _T("invalid window") );
 
-    wxCHECK_RET( g_capturing == TRUE, _T("ReleaseMouse called twice") );
+    wxCHECK_RET( g_captureWindow, _T("ReleaseMouse called twice") );
 
     GtkWidget *connect_widget = GetConnectWidget();
-    gtk_grab_remove( connect_widget );
+    if (!connect_widget->window) return;
+
     gdk_pointer_ungrab ( GDK_CURRENT_TIME );
-    g_capturing = FALSE;
+    g_captureWindow = (wxWindow*) NULL;
 }
 
 bool wxWindow::IsRetained() const
@@ -2536,15 +3022,10 @@ void wxWindow::SetScrollbar( int orient, int pos, int thumbVisible,
         m_vAdjust->page_size = fthumb;
     }
 
-    if (m_wxwindow->window)
-    {
-        if (orient == wxHORIZONTAL)
-            gtk_signal_emit_by_name( GTK_OBJECT(m_hAdjust), "changed" );
-        else
-            gtk_signal_emit_by_name( GTK_OBJECT(m_vAdjust), "changed" );
-
-        gtk_widget_set_usize( m_widget, m_width, m_height );
-    }
+    if (orient == wxHORIZONTAL)
+        gtk_signal_emit_by_name( GTK_OBJECT(m_hAdjust), "changed" );
+    else
+        gtk_signal_emit_by_name( GTK_OBJECT(m_vAdjust), "changed" );
 }
 
 void wxWindow::SetScrollPos( int orient, int pos, bool WXUNUSED(refresh) )
@@ -2574,7 +3055,7 @@ void wxWindow::SetScrollPos( int orient, int pos, bool WXUNUSED(refresh) )
         m_vAdjust->value = fpos;
     }
 
-    if (!m_isScrolling)
+    if (!m_isScrolling)  /* prevent recursion */
     {
         if (m_wxwindow->window)
         {
@@ -2628,50 +3109,55 @@ void wxWindow::ScrollWindow( int dx, int dy, const wxRect* WXUNUSED(rect) )
 
     wxCHECK_RET( m_wxwindow != NULL, _T("window needs client area for scrolling") );
 
+    if (!m_scrollGC)
+    {
+        m_scrollGC = gdk_gc_new( m_wxwindow->window );
+        gdk_gc_set_exposures( m_scrollGC, TRUE );
+    }
+
     wxNode *node = m_children.First();
     while (node)
     {
         wxWindow *child = (wxWindow*) node->Data();
-        child->Move( child->GetX() + dx, child->GetY() + dy );
+        int sx = 0;
+        int sy = 0;
+        child->GetSize( &sx, &sy );
+        child->SetSize( child->m_x + dx, child->m_y + dy, sx, sy, wxSIZE_ALLOW_MINUS_ONE );
         node = node->Next();
     }
 
     int cw = 0;
     int ch = 0;
     GetClientSize( &cw, &ch );
-
     int w = cw - abs(dx);
     int h = ch - abs(dy);
+
     if ((h < 0) || (w < 0))
     {
         Refresh();
-        return;
     }
-    int s_x = 0;
-    int s_y = 0;
-    if (dx < 0) s_x = -dx;
-    if (dy < 0) s_y = -dy;
-    int d_x = 0;
-    int d_y = 0;
-    if (dx > 0) d_x = dx;
-    if (dy > 0) d_y = dy;
-
-    if (!m_scrollGC)
+    else
     {
-        m_scrollGC = gdk_gc_new( m_wxwindow->window );
-        gdk_gc_set_exposures( m_scrollGC, TRUE );
-    }
+        int s_x = 0;
+        int s_y = 0;
+        if (dx < 0) s_x = -dx;
+        if (dy < 0) s_y = -dy;
+        int d_x = 0;
+        int d_y = 0;
+        if (dx > 0) d_x = dx;
+        if (dy > 0) d_y = dy;
 
-    gdk_window_copy_area( m_wxwindow->window, m_scrollGC, d_x, d_y,
-        m_wxwindow->window, s_x, s_y, w, h );
+        gdk_window_copy_area( m_wxwindow->window, m_scrollGC, d_x, d_y,
+            m_wxwindow->window, s_x, s_y, w, h );
 
-    wxRect rect;
-    if (dx < 0) rect.x = cw+dx; else rect.x = 0;
-    if (dy < 0) rect.y = ch+dy; else rect.y = 0;
-    if (dy != 0) rect.width = cw; else rect.width = abs(dx);
-    if (dx != 0) rect.height = ch; else rect.height = abs(dy);
+        wxRect rect;
+        if (dx < 0) rect.x = cw+dx; else rect.x = 0;
+        if (dy < 0) rect.y = ch+dy; else rect.y = 0;
+        if (dy != 0) rect.width = cw; else rect.width = abs(dx);
+        if (dx != 0) rect.height = ch; else rect.height = abs(dy);
 
-    Refresh( TRUE, &rect );
+        Refresh( TRUE, &rect );
+    }
 }
 
 void wxWindow::SetScrolling(bool scroll)