]> git.saurik.com Git - wxWidgets.git/blobdiff - src/msw/window.cpp
argc == 0 bug fixed
[wxWidgets.git] / src / msw / window.cpp
index e5a66c3c52f8d4df815f4ba5c7c515d0ab121805..a8fd5cc4e3abb548e7e28e1635ae427965d009ac 100644 (file)
 #include "wx/wxprec.h"
 
 #ifdef __BORLANDC__
-#pragma hdrstop
+    #pragma hdrstop
 #endif
 
 #ifndef WX_PRECOMP
-#include <stdio.h>
-#include "wx/setup.h"
-#include "wx/menu.h"
-#include "wx/dc.h"
-#include "wx/dcclient.h"
-#include "wx/utils.h"
-#include "wx/app.h"
-#include "wx/panel.h"
-#include "wx/layout.h"
-#include "wx/dialog.h"
-#include "wx/listbox.h"
-#include "wx/button.h"
-#include "wx/settings.h"
-#include "wx/msgdlg.h"
+    #include "wx/setup.h"
+    #include "wx/menu.h"
+    #include "wx/dc.h"
+    #include "wx/dcclient.h"
+    #include "wx/utils.h"
+    #include "wx/app.h"
+    #include "wx/panel.h"
+    #include "wx/layout.h"
+    #include "wx/dialog.h"
+    #include "wx/frame.h"
+    #include "wx/listbox.h"
+    #include "wx/button.h"
+    #include "wx/settings.h"
+    #include "wx/msgdlg.h"
+
+    #include <stdio.h>
 #endif
 
 #if     wxUSE_OWNER_DRAWN
-#include "wx/ownerdrw.h"
+    #include "wx/ownerdrw.h"
 #endif
 
 #if     wxUSE_DRAG_AND_DROP
-#include "wx/msw/ole/droptgt.h"
+    #include "wx/msw/ole/droptgt.h"
 #endif
 
 #include "wx/menuitem.h"
 #include "wx/log.h"
+
+#if wxUSE_TOOLTIPS
+#include "wx/tooltip.h"
+#endif
+
+#include "wx/intl.h"
+#include "wx/log.h"
+
 #include "wx/msw/private.h"
 
+#include "wx/textctrl.h"
+
 #include <string.h>
 
 #ifndef __GNUWIN32__
-#include <shellapi.h>
-#include <mmsystem.h>
+    #include <shellapi.h>
+    #include <mmsystem.h>
 #endif
 
 #ifdef __WIN32__
-#include <windowsx.h>
+    #include <windowsx.h>
 #endif
 
-#ifdef __GNUWIN32__
-#include <wx/msw/gnuwin32/extra.h>
+#if (defined(__WIN95__) && !defined(__GNUWIN32__)) || defined(__TWIN32__)
+#include <commctrl.h>
 #endif
 
+#ifndef __TWIN32__
+    #ifdef __GNUWIN32__
+        #include <wx/msw/gnuwin32/extra.h>
+    #endif
+#endif
+
+// all these are defined in <windows.h>
 #ifdef GetCharWidth
 #undef GetCharWidth
 #endif
 #endif
 
 #ifdef  __WXDEBUG__
-const char *wxGetMessageName(int message);
-#endif  //WXDEBUG
+    const char *wxGetMessageName(int message);
+#endif  //__WXDEBUG__
 
 #define WINDOW_MARGIN 3 // This defines sensitivity of Leave events
 
 wxMenu *wxCurrentPopupMenu = NULL;
-extern wxList wxPendingDelete;
+extern wxList WXDLLEXPORT wxPendingDelete;
 
 void wxRemoveHandleAssociation(wxWindow *win);
 void wxAssociateWinWithHandle(HWND hWnd, wxWindow *win);
 wxWindow *wxFindWinFromHandle(WXHWND hWnd);
 
 #if !USE_SHARED_LIBRARY
-IMPLEMENT_DYNAMIC_CLASS(wxWindow, wxEvtHandler)
+    IMPLEMENT_DYNAMIC_CLASS(wxWindow, wxEvtHandler)
+#endif
 
 BEGIN_EVENT_TABLE(wxWindow, wxEvtHandler)
-EVT_CHAR(wxWindow::OnChar)
-EVT_ERASE_BACKGROUND(wxWindow::OnEraseBackground)
-EVT_SYS_COLOUR_CHANGED(wxWindow::OnSysColourChanged)
-EVT_INIT_DIALOG(wxWindow::OnInitDialog)
-EVT_IDLE(wxWindow::OnIdle)
+    EVT_CHAR(wxWindow::OnChar)
+    EVT_ERASE_BACKGROUND(wxWindow::OnEraseBackground)
+    EVT_SYS_COLOUR_CHANGED(wxWindow::OnSysColourChanged)
+    EVT_INIT_DIALOG(wxWindow::OnInitDialog)
+    EVT_IDLE(wxWindow::OnIdle)
 END_EVENT_TABLE()
 
-#endif
-
 // Find an item given the MS Windows id
 wxWindow *wxWindow::FindItem(int id) const
 {
-    if (!GetChildren())
-        return NULL;
-    wxNode *current = GetChildren()->First();
+//    if (!GetChildren())
+//        return NULL;
+    wxNode *current = GetChildren().First();
     while (current)
     {
         wxWindow *childWin = (wxWindow *)current->Data();
@@ -123,7 +141,7 @@ wxWindow *wxWindow::FindItem(int id) const
         if (childWin->IsKindOf(CLASSINFO(wxControl)))
         {
             wxControl *item = (wxControl *)childWin;
-            if (item->m_windowId == id)
+            if (item->GetId() == id)
                 return item;
             else
             {
@@ -140,9 +158,9 @@ wxWindow *wxWindow::FindItem(int id) const
 // Find an item given the MS Windows handle
 wxWindow *wxWindow::FindItemByHWND(WXHWND hWnd, bool controlOnly) const
 {
-    if (!GetChildren())
-        return NULL;
-    wxNode *current = GetChildren()->First();
+//    if (!GetChildren())
+//        return NULL;
+    wxNode *current = GetChildren().First();
     while (current)
     {
         wxObject *obj = (wxObject *)current->Data() ;
@@ -174,8 +192,24 @@ bool wxWindow::MSWCommand(WXUINT WXUNUSED(param), WXWORD WXUNUSED(id))
     return FALSE;
 }
 
-bool wxWindow::MSWNotify(WXWPARAM WXUNUSED(wParam), WXLPARAM WXUNUSED(lParam))
+bool wxWindow::MSWNotify(WXWPARAM WXUNUSED(wParam),
+                         WXLPARAM lParam,
+                         WXLPARAM* WXUNUSED(result))
 {
+#ifdef __WIN95__
+#if wxUSE_TOOLTIPS
+    NMHDR* hdr = (NMHDR *)lParam;
+    if ( hdr->code == TTN_NEEDTEXT && m_tooltip )
+    {
+        TOOLTIPTEXT *ttt = (TOOLTIPTEXT *)lParam;
+        ttt->lpszText = (char *)m_tooltip->GetTip().c_str();
+
+        // processed
+        return TRUE;
+    }
+#endif
+#endif
+
     return FALSE;
 }
 
@@ -193,17 +227,21 @@ void wxWindow::SetHWND(WXHWND hWnd)
     m_hWnd = hWnd;
 }
 
-// Constructor
-wxWindow::wxWindow(void)
+// ----------------------------------------------------------------------------
+// constructors and such
+// ----------------------------------------------------------------------------
+
+void wxWindow::Init()
 {
+    m_isWindow = TRUE;
+
     // Generic
+//    m_windowCursor = * wxSTANDARD_CURSOR;
     m_windowId = 0;
     m_isShown = TRUE;
     m_windowStyle = 0;
     m_windowParent = NULL;
     m_windowEventHandler = this;
-    m_windowName = "";
-    m_windowCursor = *wxSTANDARD_CURSOR;
     m_children = new wxList;
     m_doubleClickAllowed = 0 ;
     m_winCaptured = FALSE;
@@ -217,41 +255,35 @@ wxWindow::wxWindow(void)
     // MSW-specific
     m_hWnd = 0;
     m_winEnabled = TRUE;
-    m_caretWidth = 0; m_caretHeight = 0;
-    m_caretEnabled = FALSE;
+    m_caretWidth = m_caretHeight = 0;
+    m_caretEnabled =
     m_caretShown = FALSE;
     m_inOnSize = FALSE;
-    m_minSizeX = -1;
-    m_minSizeY = -1;
-    m_maxSizeX = -1;
+    m_minSizeX =
+    m_minSizeY =
+    m_maxSizeX =
     m_maxSizeY = -1;
-    //  m_paintHDC = 0;
-    //  m_tempHDC = 0;
+
     m_isBeingDeleted = FALSE;
     m_oldWndProc = 0;
 #ifndef __WIN32__
     m_globalHandle = 0;
 #endif
     m_useCtl3D = FALSE;
+    m_mouseInWindow = FALSE;
 
+    m_windowParent = NULL;
     m_defaultItem = NULL;
 
     wxSystemSettings settings;
 
     m_backgroundColour = settings.GetSystemColour(wxSYS_COLOUR_3DFACE) ;
-    // m_backgroundColour = settings.GetSystemColour(wxSYS_COLOUR_WINDOW) ; ;
     m_foregroundColour = *wxBLACK;
 
-    /*
-    wxColour(GetRValue(GetSysColor(COLOR_WINDOW)),
-    GetGValue(GetSysColor(COLOR_BTNFACE)), GetBValue(GetSysColor(COLOR_BTNFACE)));
-    */
-
     // wxWnd
     m_lastMsg = 0;
     m_lastWParam = 0;
     m_lastLParam = 0;
-    //  m_acceleratorTable = 0;
     m_hMenu = 0;
 
     m_xThumbSize = 0;
@@ -266,13 +298,28 @@ wxWindow::wxWindow(void)
 #if  wxUSE_DRAG_AND_DROP
     m_pDropTarget = NULL;
 #endif
+
+#if wxUSE_TOOLTIPS
+    m_tooltip = NULL;
+#endif
+}
+
+wxWindow::wxWindow()
+{
+    Init();
 }
 
 // Destructor
-wxWindow::~wxWindow(void)
+wxWindow::~wxWindow()
 {
     m_isBeingDeleted = TRUE;
 
+    // first of all, delete the things on which nothing else depends
+
+#if wxUSE_TOOLTIPS
+    wxDELETE(m_tooltip);
+#endif
+
     // JACS - if behaviour is odd, restore this
     // to the start of ~wxWindow. Vadim has changed
     // it to nearer the end. Unsure of side-effects
@@ -285,6 +332,7 @@ wxWindow::~wxWindow(void)
     // delete themselves.
 #if wxUSE_CONSTRAINTS
     DeleteRelatedConstraints();
+
     if (m_constraints)
     {
         // This removes any dangling pointers to this window
@@ -293,16 +341,14 @@ wxWindow::~wxWindow(void)
         delete m_constraints;
         m_constraints = NULL;
     }
-    if (m_windowSizer)
-    {
-        delete m_windowSizer;
-        m_windowSizer = NULL;
-    }
+
+    wxDELETE(m_windowSizer);
+
     // If this is a child of a sizer, remove self from parent
     if (m_sizerParent)
         m_sizerParent->RemoveChild((wxWindow *)this);
 #endif
-    
+
     // wxWnd
     MSWDetachWindowMenu();
 
@@ -323,7 +369,7 @@ wxWindow::~wxWindow(void)
         m_globalHandle = 0;
     }
 #endif
-    
+
     delete m_children;
     m_children = NULL;
 
@@ -340,13 +386,13 @@ wxWindow::~wxWindow(void)
     if ( m_windowValidator )
         delete m_windowValidator;
 
-    // Restore old Window proc, if required 
+    // Restore old Window proc, if required
     // and remove hWnd <-> wxWindow association
     UnsubclassWin();
 }
 
 // Destroy the window (delayed, if a managed window)
-bool wxWindow::Destroy(void)
+bool wxWindow::Destroy()
 {
     delete this;
     return TRUE;
@@ -354,72 +400,16 @@ bool wxWindow::Destroy(void)
 
 extern char wxCanvasClassName[];
 
-// Constructor
+// real construction (Init() must have been called before!)
 bool wxWindow::Create(wxWindow *parent, wxWindowID id,
                       const wxPoint& pos,
                       const wxSize& size,
                       long style,
                       const wxString& name)
 {
-    // Generic
-    m_isBeingDeleted = FALSE;
-    m_windowId = 0;
-    m_isShown = TRUE;
-    m_windowStyle = 0;
-    m_windowParent = NULL;
-    m_windowEventHandler = this;
-    m_windowName = "";
-    m_windowCursor = *wxSTANDARD_CURSOR;
-    m_doubleClickAllowed = 0 ;
-    m_winCaptured = FALSE;
-    m_constraints = NULL;
-    m_constraintsInvolvedIn = NULL;
-    m_windowSizer = NULL;
-    m_sizerParent = NULL;
-    m_autoLayout = FALSE;
-    m_windowValidator = NULL;
-#if  wxUSE_DRAG_AND_DROP
-    m_pDropTarget = NULL;
-#endif
-    
-    // MSW-specific
-    m_hWnd = 0;
-    m_winEnabled = TRUE;
-    m_caretWidth = 0; m_caretHeight = 0;
-    m_caretEnabled = FALSE;
-    m_caretShown = FALSE;
-    m_inOnSize = FALSE;
-    m_minSizeX = -1;
-    m_minSizeY = -1;
-    m_maxSizeX = -1;
-    m_maxSizeY = -1;
-    m_oldWndProc = 0;
-#ifndef __WIN32__
-    m_globalHandle = 0;
-#endif
-    m_useCtl3D = FALSE;
-    m_defaultItem = NULL;
-    m_windowParent = NULL;
-    m_mouseInWindow = FALSE;
-    if (!parent)
-        return FALSE;
-
-    if (parent) parent->AddChild(this);
-
-    // wxWnd
-    m_lastMsg = 0;
-    m_lastWParam = 0;
-    m_lastLParam = 0;
-    m_hMenu = 0;
-
-    m_xThumbSize = 0;
-    m_yThumbSize = 0;
-    m_backgroundTransparent = FALSE;
+    wxCHECK_MSG( parent, FALSE, "can't create wxWindow without parent" );
 
-    m_lastXPos = (float)-1.0;
-    m_lastYPos = (float)-1.0;
-    m_lastEvent = -1;
-    m_returnCode = 0;
+    parent->AddChild(this);
 
     SetName(name);
 
@@ -433,11 +423,13 @@ bool wxWindow::Create(wxWindow *parent, wxWindowID id,
     int width = size.x;
     int height = size.y;
 
-    wxSystemSettings settings;
+    // To be consistent with wxGTK
+    if (width == -1)
+        width = 20;
+    if (height == -1)
+        height = 20;
 
-    m_backgroundColour = settings.GetSystemColour(wxSYS_COLOUR_WINDOW) ; ;
-    // m_backgroundColour = settings.GetSystemColour(wxSYS_COLOUR_3DFACE) ;
-    m_foregroundColour = *wxBLACK;
+    wxSystemSettings settings;
 
     m_windowStyle = style;
 
@@ -460,15 +452,13 @@ bool wxWindow::Create(wxWindow *parent, wxWindowID id,
         (m_windowStyle & wxSUNKEN_BORDER) || (m_windowStyle & wxDOUBLE_BORDER))
         msflags |= WS_BORDER;
 
-    m_mouseInWindow = FALSE ;
-
     MSWCreate(m_windowId, parent, wxCanvasClassName, this, NULL,
-        x, y, width, height, msflags, NULL, exStyle);
+              x, y, width, height, msflags, NULL, exStyle);
 
     return TRUE;
 }
 
-void wxWindow::SetFocus(void)
+void wxWindow::SetFocus()
 {
     HWND hWnd = (HWND) GetHWND();
     if (hWnd)
@@ -483,7 +473,7 @@ void wxWindow::Enable(bool enable)
         ::EnableWindow(hWnd, (BOOL)enable);
 }
 
-void wxWindow::CaptureMouse(void)
+void wxWindow::CaptureMouse()
 {
     HWND hWnd = (HWND) GetHWND();
     if (hWnd && !m_winCaptured)
@@ -493,7 +483,7 @@ void wxWindow::CaptureMouse(void)
     }
 }
 
-void wxWindow::ReleaseMouse(void)
+void wxWindow::ReleaseMouse()
 {
     if (m_winCaptured)
     {
@@ -550,7 +540,8 @@ void wxWindow::SetDropTarget(wxDropTarget *pDropTarget)
         m_pDropTarget->Register(m_hWnd);
 }
 
-#endif
+#endif // wxUSE_DRAG_AND_DROP
+
 
 //old style file-manager drag&drop support
 // I think we should retain the old-style
@@ -563,6 +554,28 @@ void wxWindow::DragAcceptFiles(bool accept)
         ::DragAcceptFiles(hWnd, (BOOL)accept);
 }
 
+// ----------------------------------------------------------------------------
+// tooltips
+// ----------------------------------------------------------------------------
+
+#if wxUSE_TOOLTIPS
+
+void wxWindow::SetToolTip(const wxString &tip)
+{
+    SetToolTip(new wxToolTip(tip));
+}
+
+void wxWindow::SetToolTip(wxToolTip *tooltip)
+{
+    if ( m_tooltip )
+        delete m_tooltip;
+
+    m_tooltip = tooltip;
+    m_tooltip->SetWindow(this);
+}
+
+#endif // wxUSE_TOOLTIPS
+
 // Get total size
 void wxWindow::GetSize(int *x, int *y) const
 {
@@ -612,19 +625,8 @@ void wxWindow::ScreenToClient(int *x, int *y) const
     POINT pt;
     pt.x = *x;
     pt.y = *y;
-    ::ScreenToClient(hWnd, &pt);
 
-    /*
-    // We may be faking the client origin.
-    // So a window that's really at (0, 30) may appear
-    // (to wxWin apps) to be at (0, 0).
-    if (GetParent())
-    {
-    wxPoint pt1(GetParent()->GetClientAreaOrigin());
-    pt.x -= pt1.x;
-    pt.y -= pt1.y;
-    }
-    */
+    ::ScreenToClient(hWnd, &pt);
 
     *x = pt.x;
     *y = pt.y;
@@ -637,18 +639,6 @@ void wxWindow::ClientToScreen(int *x, int *y) const
     pt.x = *x;
     pt.y = *y;
 
-    /*
-    // We may be faking the client origin.
-    // So a window that's really at (0, 30) may appear
-    // (to wxWin apps) to be at (0, 0).
-    if (GetParent())
-    {
-    wxPoint pt1(GetParent()->GetClientAreaOrigin());
-    pt.x += pt1.x;
-    pt.y += pt1.y;
-    }
-    */
-
     ::ClientToScreen(hWnd, &pt);
 
     *x = pt.x;
@@ -684,15 +674,21 @@ void wxWindow::GetClientSize(int *x, int *y) const
 {
     HWND hWnd = (HWND) GetHWND();
     RECT rect;
-    GetClientRect(hWnd, &rect);
+    ::GetClientRect(hWnd, &rect);
     *x = rect.right;
     *y = rect.bottom;
 }
 
-void wxWindow::SetSize(int x, int y, int width, int height, int sizeFlags)
+void wxWindow::DoSetSize(int x, int y, int width, int height, int sizeFlags)
 {
     int currentX, currentY;
     GetPosition(&currentX, &currentY);
+    int currentW,currentH;
+    GetSize(&currentW, &currentH);
+
+    if (x == currentX && y == currentY && width == currentW && height == currentH)
+        return;
+
     int actualWidth = width;
     int actualHeight = height;
     int actualX = x;
@@ -704,8 +700,6 @@ void wxWindow::SetSize(int x, int y, int width, int height, int sizeFlags)
 
     AdjustForParentClientOrigin(actualX, actualY, sizeFlags);
 
-    int currentW,currentH;
-    GetSize(&currentW, &currentH);
     if (width == -1)
         actualWidth = currentW ;
     if (height == -1)
@@ -716,14 +710,16 @@ void wxWindow::SetSize(int x, int y, int width, int height, int sizeFlags)
         MoveWindow(hWnd, actualX, actualY, actualWidth, actualHeight, (BOOL)TRUE);
 }
 
-void wxWindow::SetClientSize(int width, int height)
+void wxWindow::DoSetClientSize(int width, int height)
 {
     wxWindow *parent = GetParent();
     HWND hWnd = (HWND) GetHWND();
-    HWND hParentWnd = (HWND) (HWND) parent->GetHWND();
+    HWND hParentWnd = (HWND) 0;
+    if (parent)
+        hParentWnd = (HWND) parent->GetHWND();
 
     RECT rect;
-    GetClientRect(hWnd, &rect);
+    ::GetClientRect(hWnd, &rect);
 
     RECT rect2;
     GetWindowRect(hWnd, &rect2);
@@ -772,13 +768,14 @@ void wxWindow::AdjustForParentClientOrigin(int& x, int& y, int sizeFlags)
 
 bool wxWindow::Show(bool show)
 {
+    m_isShown = show;
     HWND hWnd = (HWND) GetHWND();
     int cshow;
     if (show)
         cshow = SW_SHOW;
     else
         cshow = SW_HIDE;
-    ShowWindow(hWnd, (BOOL)cshow);
+    ShowWindow(hWnd, cshow);
     if (show)
     {
         BringWindowToTop(hWnd);
@@ -790,7 +787,11 @@ bool wxWindow::Show(bool show)
 
 bool wxWindow::IsShown(void) const
 {
-    return (::IsWindowVisible((HWND) GetHWND()) != 0);
+    // Can't rely on IsWindowVisible, since it will return FALSE
+    // if the parent is not visible.
+    return m_isShown;
+//    int ret = ::IsWindowVisible((HWND) GetHWND()) ;
+//    return (ret != 0);
 }
 
 int wxWindow::GetCharHeight(void) const
@@ -827,11 +828,12 @@ void wxWindow::GetTextExtent(const wxString& string, int *x, int *y,
     HWND hWnd = (HWND) GetHWND();
     HDC dc = ::GetDC(hWnd);
 
-    HFONT fnt = 0; 
+    HFONT fnt = 0;
     HFONT was = 0;
     if (fontToUse && fontToUse->Ok())
     {
-        if ((fnt=(HFONT) fontToUse->GetResourceHandle()))
+        fnt = (HFONT)fontToUse->GetResourceHandle();
+        if ( fnt )
             was = (HFONT) SelectObject(dc,fnt) ;
     }
 
@@ -840,7 +842,7 @@ void wxWindow::GetTextExtent(const wxString& string, int *x, int *y,
     GetTextExtentPoint(dc, (const char *)string, (int)string.Length(), &sizeRect);
     GetTextMetrics(dc, &tm);
 
-    if (fontToUse && fnt && was) 
+    if (fontToUse && fnt && was)
         SelectObject(dc,was) ;
 
     ReleaseDC(hWnd, dc);
@@ -854,7 +856,7 @@ void wxWindow::GetTextExtent(const wxString& string, int *x, int *y,
     //    fontToUse->ReleaseResource();
 }
 
-void wxWindow::Refresh(bool eraseBack, const wxRectangle *rect)
+void wxWindow::Refresh(bool eraseBack, const wxRect *rect)
 {
     HWND hWnd = (HWND) GetHWND();
     if (hWnd)
@@ -912,13 +914,9 @@ LRESULT APIENTRY _EXPORT wxWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARA
         wxWndHook = NULL;
         wnd->m_hWnd = (WXHWND) hWnd;
     }
-#if (WXDEBUG > 1)
-    wxDebugMsg("hWnd = %d, m_hWnd = %d, msg = %d\n", hWnd, m_hWnd, message);
-#endif
-    // Stop right here if we don't have a valid handle
-    // in our wxWnd object.
+
+    // Stop right here if we don't have a valid handle in our wxWindow object.
     if (wnd && !wnd->m_hWnd) {
-        //    wxDebugMsg("Warning: could not find a valid handle, wx_win.cc/wxWndProc.\n");
         wnd->m_hWnd = (WXHWND) hWnd;
         long res = wnd->MSWDefWindowProc(message, wParam, lParam );
         wnd->m_hWnd = 0;
@@ -938,23 +936,22 @@ LRESULT APIENTRY _EXPORT wxWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARA
 
 // Should probably have a test for 'genuine' NT
 #if defined(__WIN32__)
-#define DIMENSION_TYPE short
+    #define DIMENSION_TYPE short
 #else
-#define DIMENSION_TYPE int
+    #define DIMENSION_TYPE int
 #endif
 
-// Main Windows window proc
+// Main Windows window proc
 long wxWindow::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
 {
     wxASSERT( m_lastMsg == message &&
-        m_lastWParam == wParam &&
-        m_lastLParam == lParam );
+              m_lastWParam == wParam && m_lastLParam == lParam );
 
 #ifdef __WXDEBUG__
     wxLogTrace(wxTraceMessages, "Processing %s(%lx, %lx)",
-        wxGetMessageName(message), wParam, lParam);
-#endif // WXDEBUG
-    
+               wxGetMessageName(message), wParam, lParam);
+#endif // __WXDEBUG__
+
     HWND hWnd = (HWND)m_hWnd;
 
     switch (message)
@@ -1014,13 +1011,14 @@ long wxWindow::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
         }
     case WM_QUERYDRAGICON:
         {
-            HICON hIcon = 0;
-            if ((hIcon = (HICON) MSWOnQueryDragIcon()))
+            HICON hIcon = (HICON)MSWOnQueryDragIcon();
+            if ( hIcon )
                 return (long)hIcon;
-            else return MSWDefWindowProc(message, wParam, lParam );
+            else
+                return MSWDefWindowProc(message, wParam, lParam );
             break;
         }
-        
+
     case WM_SIZE:
         {
             int width = LOWORD(lParam);
@@ -1028,7 +1026,7 @@ long wxWindow::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
             MSWOnSize(width, height, wParam);
             break;
         }
-        
+
     case WM_MOVE:
         {
             wxMoveEvent event(wxPoint(LOWORD(lParam), HIWORD(lParam)),
@@ -1044,7 +1042,7 @@ long wxWindow::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
             MSWOnWindowPosChanging((void *)lParam);
             break;
         }
-        
+
     case WM_RBUTTONDOWN:
         {
             int x = (DIMENSION_TYPE) LOWORD(lParam);
@@ -1181,6 +1179,7 @@ long wxWindow::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
             return MSWOnSysCommand(wParam, lParam);
             break;
         }
+
     case WM_COMMAND:
         {
 #ifdef __WIN32__
@@ -1199,9 +1198,10 @@ long wxWindow::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
 #if defined(__WIN95__)
     case WM_NOTIFY:
         {
-            if (!MSWOnNotify(wParam, lParam))
-                return MSWDefWindowProc(message, wParam, lParam );
-            break;
+            // for some messages (TVN_ITEMEXPANDING for example), the return
+            // value of WM_NOTIFY handler is important, so don't just return 0
+            // if we processed the message
+            return MSWOnNotify(wParam, lParam);
         }
 #endif
     case WM_MENUSELECT:
@@ -1231,33 +1231,84 @@ long wxWindow::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
             return MSWOnMeasureItem((int)wParam, (WXMEASUREITEMSTRUCT *)lParam);
             break;
         }
-        
     case WM_KEYDOWN:
-        // we consider these message "not interesting"
+        // If this has been processed by an event handler,
+        // return 0 now (we've handled it).
+        if (MSWOnKeyDown((WORD) wParam, lParam))
+        {
+            return 0;
+        }
+
+        // we consider these message "not interesting" to OnChar
         if ( wParam == VK_SHIFT || wParam == VK_CONTROL )
+        {
             return Default();
+        }
 
-        // Avoid duplicate messages to OnChar
-        if ( (wParam != VK_ESCAPE) && (wParam != VK_SPACE) &&
-            (wParam != VK_RETURN) && (wParam != VK_BACK) &&
-            (wParam != VK_TAB) )
+        // Avoid duplicate messages to OnChar for these special keys
+        switch ( wParam )
         {
-            MSWOnChar((WORD)wParam, lParam);
-            if ( ::GetKeyState(VK_CONTROL) & 0x100 )
+            case VK_ESCAPE:
+            case VK_SPACE:
+            case VK_RETURN:
+            case VK_BACK:
+            case VK_TAB:
+            case VK_LEFT:
+            case VK_RIGHT:
+            case VK_DOWN:
+            case VK_UP:
                 return Default();
+
+#ifdef VK_APPS
+            // special case of VK_APPS: treat it the same as right mouse click
+            // because both usually pop up a context menu
+            case VK_APPS:
+                {
+
+#ifndef GET_X_LPARAM
+#define GET_X_LPARAM(lp)                        ((int)(short)LOWORD(lp))
+#define GET_Y_LPARAM(lp)                        ((int)(short)HIWORD(lp))
+#endif
+
+                    // construct the key mask
+                    WPARAM fwKeys = MK_RBUTTON;
+                    if ( (::GetKeyState(VK_CONTROL) & 0x100) != 0 )
+                        fwKeys |= MK_CONTROL;
+                    if ( (::GetKeyState(VK_SHIFT) & 0x100) != 0 )
+                        fwKeys |= MK_SHIFT;
+
+                    // simulate right mouse button click
+                    DWORD dwPos = ::GetMessagePos();
+                    int x = GET_X_LPARAM(dwPos),
+                        y = GET_Y_LPARAM(dwPos);
+
+                    ScreenToClient(&x, &y);
+                    MSWOnRButtonDown(x, y, fwKeys);
+                }
+                break;
+#endif // VK_APPS
+
+            default:
+                if (!MSWOnChar((WORD)wParam, lParam))
+                {
+                    return Default();
+                }
+                break;
         }
-        else if ( ::GetKeyState(VK_CONTROL) & 0x100 )
-            MSWOnChar((WORD)wParam, lParam);
-        else
+
+        break;
+    case WM_KEYUP:
+    {
+        if (!MSWOnKeyUp((WORD) wParam, lParam))
             return Default();
         break;
-
+    }
     case WM_CHAR: // Always an ASCII character
         {
-            MSWOnChar((WORD)wParam, lParam, TRUE);
+            if (!MSWOnChar((WORD)wParam, lParam, TRUE))
+                return Default();
             break;
         }
-
     case WM_HSCROLL:
         {
 #ifdef __WIN32__
@@ -1435,7 +1486,6 @@ long wxWindow::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
                 return 1L;
             break;
         }
-        
     case WM_GETMINMAXINFO:
         {
             MINMAXINFO *info = (MINMAXINFO *)lParam;
@@ -1450,13 +1500,69 @@ long wxWindow::MSWWindowProc(WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
             return MSWDefWindowProc(message, wParam, lParam );
             break;
         }
-        
     case WM_GETDLGCODE:
-        return MSWGetDlgCode();
+        {
+            return MSWGetDlgCode();
+        }
+    case WM_SETCURSOR:
+        {
+            // don't set cursor for other windows, only for this one: this
+            // prevents children of this window from gettign the same cursor
+            // as the parent has (don't forget that this message is propagated
+            // by default up the window parent-child hierarchy)
+            if ( (HWND)wParam == hWnd )
+            {
+                // don't set cursor when the mouse is not in the client part
+                short nHitTest = LOWORD(lParam);
+                if ( nHitTest == HTCLIENT || nHitTest == HTERROR )
+                {
+                    HCURSOR hcursor = 0;
+                    if ( wxIsBusy() )
+                    {
+                        // from msw\utils.cpp
+                        extern HCURSOR gs_wxBusyCursor;
+
+                        hcursor = gs_wxBusyCursor;
+                    }
+                    else
+                    {
+                        wxCursor *cursor = NULL;
+
+                        if ( m_windowCursor.Ok() )
+                        {
+                            cursor = &m_windowCursor;
+                        }
+                        else
+                        {
+                            // from msw\data.cpp
+                            extern wxCursor *g_globalCursor;
+
+                            if ( g_globalCursor && g_globalCursor->Ok() )
+                                cursor = g_globalCursor;
+                        }
+
+                        if ( cursor )
+                            hcursor = (HCURSOR)cursor->GetHCURSOR();
+                    }
+
+                    if ( hcursor )
+                    {
+                        ::SetCursor(hcursor);
+
+                        // returning TRUE stops the DefWindowProc() from
+                        // further processing this message - exactly what we
+                        // need because we've just set the cursor.
+                        return TRUE;
+                    }
+                }
+            }
+        }
+        return MSWDefWindowProc(message, wParam, lParam );
 
     default:
         return MSWDefWindowProc(message, wParam, lParam );
     }
+
     return 0; // Success: we processed this command.
 }
 
@@ -1480,7 +1586,7 @@ void wxAssociateWinWithHandle(HWND hWnd, wxWindow *win)
 {
     // adding NULL hWnd is (first) surely a result of an error and
     // (secondly) breaks menu command processing
-    wxCHECK_RET( hWnd != NULL, "attempt to add a NULL hWnd to window list" );
+    wxCHECK_RET( hWnd != (HWND) NULL, "attempt to add a NULL hWnd to window list" );
 
     if ( !wxWinHandleList->Find((long)hWnd) )
         wxWinHandleList->Append((long)hWnd, win);
@@ -1493,7 +1599,7 @@ void wxRemoveHandleAssociation(wxWindow *win)
 
 // Default destroyer - override if you destroy it in some other way
 // (e.g. with MDI child windows)
-void wxWindow::MSWDestroyWindow(void)
+void wxWindow::MSWDestroyWindow()
 {
 }
 
@@ -1539,12 +1645,20 @@ void wxWindow::MSWCreate(int id, wxWindow *parent, const char *wclass, wxWindow
         m_hWnd = (WXHWND) ::CreateDialog(wxGetInstance(), dialog_template, hParent,
             (DLGPROC)wxDlgProc);
 #else
+        // N.B.: if we _don't_ use this form,
+        // then with VC++ 1.5, it crashes horribly.
+#if 1
+       m_hWnd = (WXHWND) ::CreateDialog(wxGetInstance(), dialog_template, hParent,
+                            (DLGPROC)wxDlgProc);
+#else
+        // Crashes when we use this.
         DLGPROC dlgproc = (DLGPROC)MakeProcInstance((DLGPROC)wxWndProc, wxGetInstance());
 
         m_hWnd = (WXHWND) ::CreateDialog(wxGetInstance(), dialog_template, hParent,
             (DLGPROC)dlgproc);
 #endif
-        
+#endif
+
         if (m_hWnd == 0)
             MessageBox(NULL, "Can't find dummy dialog template!\nCheck resource include path for finding wx.rc.",
             "wxWindows Error", MB_ICONEXCLAMATION | MB_OK);
@@ -1574,24 +1688,22 @@ void wxWindow::MSWCreate(int id, wxWindow *parent, const char *wclass, wxWindow
 
     wxWndHook = NULL;
     wxWinHandleList->Append((long)m_hWnd, this);
-
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWCreate %d\n", m_hWnd);
-#endif
 }
 
 void wxWindow::MSWOnCreate(WXLPCREATESTRUCT WXUNUSED(cs))
 {
 }
 
-bool wxWindow::MSWOnClose(void)
+bool wxWindow::MSWOnClose()
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnClose %d\n", handle);
-#endif
     return FALSE;
 }
 
+// Some compilers don't define this
+#ifndef ENDSESSION_LOGOFF
+#define ENDSESSION_LOGOFF    0x80000000
+#endif
+
 // Return TRUE to end session, FALSE to veto end session.
 bool wxWindow::MSWOnQueryEndSession(long logOff)
 {
@@ -1624,11 +1736,8 @@ bool wxWindow::MSWOnEndSession(bool endSession, long logOff)
     return TRUE;
 }
 
-bool wxWindow::MSWOnDestroy(void)
+bool wxWindow::MSWOnDestroy()
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnDestroy %d\n", handle);
-#endif
     // delete our drop target if we've got one
 #if wxUSE_DRAG_AND_DROP
     if ( m_pDropTarget != NULL ) {
@@ -1638,13 +1747,13 @@ bool wxWindow::MSWOnDestroy(void)
         m_pDropTarget = NULL;
     }
 #endif
-    
+
     return TRUE;
 }
 
 // Deal with child commands from buttons etc.
 
-bool wxWindow::MSWOnNotify(WXWPARAM wParam, WXLPARAM lParam)
+long wxWindow::MSWOnNotify(WXWPARAM wParam, WXLPARAM lParam)
 {
 #if defined(__WIN95__)
     // Find a child window to send the notification to, e.g. a toolbar.
@@ -1662,34 +1771,39 @@ bool wxWindow::MSWOnNotify(WXWPARAM wParam, WXLPARAM lParam)
     NMHDR *hdr = (NMHDR *)lParam;
     HWND hWnd = (HWND)hdr->hwndFrom;
     wxWindow *win = wxFindWinFromHandle((WXHWND) hWnd);
-    
+
+    WXLPARAM result = 0;
+
     if ( win )
-        return win->MSWNotify(wParam, lParam);
+    {
+        if ( win->MSWNotify(wParam, lParam, &result) )
+            return result;
+    }
     else
     {
         // Rely on MSWNotify to check whether the message
         // belongs to the window or not
-        wxNode *node = GetChildren()->First();
+        wxNode *node = GetChildren().First();
         while (node)
         {
             wxWindow *child = (wxWindow *)node->Data();
-            if ( child->MSWNotify(wParam, lParam) )
-                return TRUE;
+            if ( child->MSWNotify(wParam, lParam, &result) )
+                return result;
             node = node->Next();
         }
+
+        // finally try this window too (catches toolbar case)
+        if ( MSWNotify(wParam, lParam, &result) )
+            return result;
     }
+#endif  // Win95
 
-    return FALSE;
-    
-#endif
-    return FALSE;
+    // not processed
+    return Default();
 }
 
 void wxWindow::MSWOnMenuHighlight(WXWORD WXUNUSED(item), WXWORD WXUNUSED(flags), WXHMENU WXUNUSED(sysmenu))
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnMenuHighlight %d\n", handle);
-#endif
 }
 
 void wxWindow::MSWOnInitMenuPopup(WXHMENU menu, int pos, bool isSystem)
@@ -1698,10 +1812,6 @@ void wxWindow::MSWOnInitMenuPopup(WXHMENU menu, int pos, bool isSystem)
 
 bool wxWindow::MSWOnActivate(int state, bool WXUNUSED(minimized), WXHWND WXUNUSED(activate))
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnActivate %d\n", handle);
-#endif
-    
     wxActivateEvent event(wxEVT_ACTIVATE, ((state == WA_ACTIVE) || (state == WA_CLICKACTIVE)),
         m_windowId);
     event.SetEventObject(this);
@@ -1711,9 +1821,6 @@ bool wxWindow::MSWOnActivate(int state, bool WXUNUSED(minimized), WXHWND WXUNUSE
 
 bool wxWindow::MSWOnSetFocus(WXHWND WXUNUSED(hwnd))
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnSetFocus %d\n", m_hWnd);
-#endif
     // Deal with caret
     if (m_caretEnabled && (m_caretWidth > 0) && (m_caretHeight > 0))
     {
@@ -1721,7 +1828,14 @@ bool wxWindow::MSWOnSetFocus(WXHWND WXUNUSED(hwnd))
         if (m_caretShown)
             ::ShowCaret((HWND) GetHWND());
     }
-    
+
+    // panel wants to track the window which was the last to have focus in it
+    wxWindow *parent = GetParent();
+    if ( parent && parent->IsKindOf(CLASSINFO(wxPanel)) )
+    {
+        ((wxPanel *)parent)->SetLastFocus(GetId());
+    }
+
     wxFocusEvent event(wxEVT_SET_FOCUS, m_windowId);
     event.SetEventObject(this);
     if (!GetEventHandler()->ProcessEvent(event))
@@ -1731,15 +1845,12 @@ bool wxWindow::MSWOnSetFocus(WXHWND WXUNUSED(hwnd))
 
 bool wxWindow::MSWOnKillFocus(WXHWND WXUNUSED(hwnd))
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnKillFocus %d\n", m_hWnd);
-#endif
     // Deal with caret
     if (m_caretEnabled)
     {
         ::DestroyCaret();
     }
-    
+
     wxFocusEvent event(wxEVT_KILL_FOCUS, m_windowId);
     event.SetEventObject(this);
     if (!GetEventHandler()->ProcessEvent(event))
@@ -1749,10 +1860,7 @@ bool wxWindow::MSWOnKillFocus(WXHWND WXUNUSED(hwnd))
 
 void wxWindow::MSWOnDropFiles(WXWPARAM wParam)
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnDropFiles %d\n", m_hWnd);
-#endif
-    
+
     HDROP hFilesInfo = (HDROP) wParam;
     POINT dropPoint;
     DragQueryPoint(hFilesInfo, (LPPOINT) &dropPoint);
@@ -1803,7 +1911,7 @@ bool wxWindow::MSWOnDrawItem(int id, WXDRAWITEMSTRUCT *itemStruct)
             );
     }
 #endif  // owner-drawn menus
-    
+
     wxWindow *item = FindItem(id);
 #if wxUSE_DYNAMIC_CLASSES
     if (item && item->IsKindOf(CLASSINFO(wxControl)))
@@ -1823,11 +1931,11 @@ bool wxWindow::MSWOnMeasureItem(int id, WXMEASUREITEMSTRUCT *itemStruct)
         wxMenuItem *pMenuItem = (wxMenuItem *)(pMeasureStruct->itemData);
         wxCHECK( pMenuItem->IsKindOf(CLASSINFO(wxMenuItem)), FALSE );
 
-        return pMenuItem->OnMeasureItem(&pMeasureStruct->itemWidth, 
+        return pMenuItem->OnMeasureItem(&pMeasureStruct->itemWidth,
             &pMeasureStruct->itemHeight);
     }
 #endif  // owner-drawn menus
-    
+
     wxWindow *item = FindItem(id);
 #if wxUSE_DYNAMIC_CLASSES
     if (item && item->IsKindOf(CLASSINFO(wxControl)))
@@ -1842,9 +1950,6 @@ bool wxWindow::MSWOnMeasureItem(int id, WXMEASUREITEMSTRUCT *itemStruct)
 WXHBRUSH wxWindow::MSWOnCtlColor(WXHDC pDC, WXHWND pWnd, WXUINT nCtlColor,
                                  WXUINT message, WXWPARAM wParam, WXLPARAM lParam)
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnCtlColour %d\n", m_hWnd);
-#endif
     if (nCtlColor == CTLCOLOR_DLG)
     {
         return OnCtlColor(pDC, pWnd, nCtlColor, message, wParam, lParam);
@@ -1909,7 +2014,7 @@ long wxWindow::MSWOnQueryNewPalette()
 // Responds to colour changes: passes event on to children.
 void wxWindow::OnSysColourChanged(wxSysColourChangedEvent& event)
 {
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while ( node )
     {
         // Only propagate to non-top-level windows
@@ -1920,7 +2025,7 @@ void wxWindow::OnSysColourChanged(wxSysColourChangedEvent& event)
             event.m_eventObject = win;
             win->GetEventHandler()->ProcessEvent(event2);
         }
-        
+
         node = node->Next();
     }
 }
@@ -1938,12 +2043,12 @@ long wxWindow::Default()
     // Ignore 'fake' events (perhaps generated as a result of a separate real event)
     if (m_lastMsg == 0)
         return 0;
-    
+
 #ifdef __WXDEBUG__
     wxLogTrace(wxTraceMessages, "Forwarding %s to DefWindowProc.",
         wxGetMessageName(m_lastMsg));
-#endif // WXDEBUG
-    
+#endif // __WXDEBUG__
+
     return this->MSWDefWindowProc(m_lastMsg, m_lastWParam, m_lastLParam);
 }
 
@@ -1956,60 +2061,115 @@ bool wxWindow::MSWProcessMessage(WXMSG* pMsg)
         if ( msg->message != WM_KEYDOWN )
             bProcess = FALSE;
 
-        if ( (HIWORD(msg->lParam) & KF_ALTDOWN) == KF_ALTDOWN )
+        if ( bProcess && (HIWORD(msg->lParam) & KF_ALTDOWN) == KF_ALTDOWN )
             bProcess = FALSE;
 
-        bool bCtrlDown = (::GetKeyState(VK_CONTROL) & 0x100) != 0;
+        if ( bProcess )
+        {
+            bool bCtrlDown = (::GetKeyState(VK_CONTROL) & 0x100) != 0;
 
-        // WM_GETDLGCODE: if the control wants it for itself, don't process it
-        // (except for Ctrl-Tab combination which is always processed)
-        LONG lDlgCode = 0;
-        if ( bProcess && !bCtrlDown ) {
-            lDlgCode = ::SendMessage(msg->hwnd, WM_GETDLGCODE, 0, 0);
-        }
+            // WM_GETDLGCODE: ask the control if it wants the key for itself,
+            // don't process it if it's the case (except for Ctrl-Tab/Enter
+            // combinations which are always processed)
+            LONG lDlgCode = 0;
+            if ( !bCtrlDown )
+            {
+                lDlgCode = ::SendMessage(msg->hwnd, WM_GETDLGCODE, 0, 0);
+            }
 
-        bool bForward;
-        if ( bProcess ) {
-            switch ( msg->wParam ) {
-            case VK_TAB:
-                if ( lDlgCode & DLGC_WANTTAB )  // this is FALSE for Ctrl-Tab
-                    bProcess = FALSE;
-                else
-                    bForward = !(::GetKeyState(VK_SHIFT) & 0x100);
-                break;
+            bool bForward = TRUE,
+                 bWindowChange = FALSE;
 
-            case VK_UP:
-            case VK_LEFT:
-                if ( (lDlgCode & DLGC_WANTARROWS) || bCtrlDown )
-                    bProcess = FALSE;
-                else
-                    bForward = FALSE;
-                break;
+            switch ( msg->wParam ) 
+            {
+                case VK_TAB:
+                    if ( lDlgCode & DLGC_WANTTAB ) {
+                        bProcess = FALSE;
+                    }
+                    else {
+                        // Ctrl-Tab cycles thru notebook pages
+                        bWindowChange = bCtrlDown;
+                        bForward = !(::GetKeyState(VK_SHIFT) & 0x100);
+                    }
+                    break;
 
-            case VK_DOWN:
-            case VK_RIGHT:
-                if ( (lDlgCode & DLGC_WANTARROWS) || bCtrlDown )
+                case VK_UP:
+                case VK_LEFT:
+                    if ( (lDlgCode & DLGC_WANTARROWS) || bCtrlDown )
+                        bProcess = FALSE;
+                    else
+                        bForward = FALSE;
+                    break;
+
+                case VK_DOWN:
+                case VK_RIGHT:
+                    if ( (lDlgCode & DLGC_WANTARROWS) || bCtrlDown )
+                        bProcess = FALSE;
+                    break;
+
+                case VK_RETURN:
+                    {
+                        if ( lDlgCode & DLGC_WANTMESSAGE )
+                        {
+                            // control wants to process Enter itself, don't
+                            // call IsDialogMessage() which would interpret
+                            // it
+                            return FALSE;
+                        }
+#ifndef __WIN16__
+                        wxButton *btnDefault = GetDefaultItem();
+                        if ( btnDefault && !bCtrlDown )
+                        {
+                            // if there is a default button, Enter should
+                            // press it
+                            (void)::SendMessage((HWND)btnDefault->GetHWND(),
+                                                BM_CLICK, 0, 0);
+                            return TRUE;
+                        }
+                        // else: but if there is not it makes sense to make it
+                        //       work like a TAB - and that's what we do.
+                        //       Note that Ctrl-Enter always works this way.
+#endif
+                    }
+                    break;
+
+                default:
                     bProcess = FALSE;
-                else
-                    bForward = TRUE;
-                break;
+            }
 
-            default:
-                bProcess = FALSE;
+            if ( bProcess )
+            {
+                wxNavigationKeyEvent event;
+                event.SetDirection(bForward);
+                event.SetWindowChange(bWindowChange);
+                event.SetEventObject(this);
+
+                if ( GetEventHandler()->ProcessEvent(event) )
+                    return TRUE;
             }
         }
 
-        if ( bProcess ) {
-            wxNavigationKeyEvent event;
-            event.SetDirection(bForward);
-            event.SetWindowChange(bCtrlDown);
-            event.SetEventObject(this);
+        if ( ::IsDialogMessage((HWND)GetHWND(), msg) )
+            return TRUE;
+    }
 
-            if ( GetEventHandler()->ProcessEvent(event) )
-                return TRUE;
-        }
+#if wxUSE_TOOLTIPS
+    if ( m_tooltip )
+    {
+        // relay mouse move events to the tooltip control
+        MSG *msg = (MSG *)pMsg;
+        if ( msg->message == WM_MOUSEMOVE )
+            m_tooltip->RelayEvent(pMsg);
+    }
+#endif // wxUSE_TOOLTIPS
 
-        return ::IsDialogMessage((HWND)GetHWND(), msg) != 0;
+    // In case we don't have wxTAB_TRAVERSAL style on.
+    // If we don't call this, we may never process Enter correctly.
+    if ( m_hWnd != 0 && (GetWindowStyleFlag() & wxTAB_TRAVERSAL) == 0 )
+    {
+        MSG *msg = (MSG *)pMsg;
+        if ( ::IsDialogMessage((HWND)GetHWND(), msg) )
+            return TRUE;
     }
 
     return FALSE;
@@ -2026,13 +2186,10 @@ bool wxWindow::MSWTranslateMessage(WXMSG* pMsg)
 
 long wxWindow::MSWOnMDIActivate(long WXUNUSED(flag), WXHWND WXUNUSED(activate), WXHWND WXUNUSED(deactivate))
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnMDIActivate %d\n", m_hWnd);
-#endif
     return 1;
 }
 
-void wxWindow::MSWDetachWindowMenu(void)
+void wxWindow::MSWDetachWindowMenu()
 {
     if (m_hMenu)
     {
@@ -2051,7 +2208,7 @@ void wxWindow::MSWDetachWindowMenu(void)
     }
 }
 
-bool wxWindow::MSWOnPaint(void)
+bool wxWindow::MSWOnPaint()
 {
 #ifdef __WIN32__
     HRGN hRegion = ::CreateRectRgn(0, 0, 0, 0); // Dummy call to get a handle
@@ -2065,7 +2222,7 @@ bool wxWindow::MSWOnPaint(void)
     m_updateRegion = wxRegion(updateRect.left, updateRect.top,
         updateRect.right - updateRect.left, updateRect.bottom - updateRect.top);
 #endif
-    
+
     wxPaintEvent event(m_windowId);
     event.SetEventObject(this);
     if (!GetEventHandler()->ProcessEvent(event))
@@ -2078,9 +2235,6 @@ void wxWindow::MSWOnSize(int w, int h, WXUINT WXUNUSED(flag))
     if (m_inOnSize)
         return;
 
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnSize %d\n", m_hWnd);
-#endif
     if (!m_hWnd)
         return;
 
@@ -2102,9 +2256,6 @@ void wxWindow::MSWOnWindowPosChanging(void *WXUNUSED(lpPos))
 // Deal with child commands from buttons etc.
 bool wxWindow::MSWOnCommand(WXWORD id, WXWORD cmd, WXHWND control)
 {
-#if WXDEBUG > 1
-    wxDebugMsg("wxWindow::MSWOnCommand\n");
-#endif
     if (wxCurrentPopupMenu)
     {
         wxMenu *popupMenu = wxCurrentPopupMenu;
@@ -2112,22 +2263,11 @@ bool wxWindow::MSWOnCommand(WXWORD id, WXWORD cmd, WXHWND control)
         bool succ = popupMenu->MSWCommand(cmd, id);
         return succ;
     }
-#if WXDEBUG > 1
-    char buf[80];
-    sprintf(buf, "Looking for item %d...\n", id);
-    wxDebugMsg(buf);
-#endif
-    
+
     wxWindow *item = FindItem(id);
     if (item)
     {
         bool value = item->MSWCommand(cmd, id);
-#if WXDEBUG > 1
-        if (value)
-            wxDebugMsg("MSWCommand succeeded\n");
-        else
-            wxDebugMsg("MSWCommand failed\n");
-#endif
         return value;
     }
     else
@@ -2141,7 +2281,7 @@ bool wxWindow::MSWOnCommand(WXWORD id, WXWORD cmd, WXHWND control)
 
 long wxWindow::MSWOnSysCommand(WXWPARAM wParam, WXLPARAM lParam)
 {
-    switch (wParam)
+    switch (wParam & 0xFFFFFFF0)
     {
     case SC_MAXIMIZE:
         {
@@ -2182,7 +2322,7 @@ void wxWindow::MSWOnLButtonDown(int x, int y, WXUINT flags)
     event.SetTimestamp(wxApp::sm_lastMessageTime);
     event.m_eventObject = this;
 
-    m_lastXPos = event.m_x; m_lastYPos = event.m_y; m_lastEvent = wxEVENT_TYPE_LEFT_DOWN;
+    m_lastXPos = event.m_x; m_lastYPos = event.m_y; m_lastEvent = wxEVT_LEFT_DOWN;
 
     if (!GetEventHandler()->ProcessEvent(event))
         Default();
@@ -2247,7 +2387,6 @@ void wxWindow::MSWOnMButtonDown(int x, int y, WXUINT flags)
 
 void wxWindow::MSWOnMButtonUp(int x, int y, WXUINT flags)
 {
-    //wxDebugMsg("MButtonUp\n") ;
     wxMouseEvent event(wxEVT_MIDDLE_UP);
 
     event.m_x = x; event.m_y = y;
@@ -2344,11 +2483,6 @@ void wxWindow::MSWOnRButtonDClick(int x, int y, WXUINT flags)
 void wxWindow::MSWOnMouseMove(int x, int y, WXUINT flags)
 {
     // 'normal' move event...
-    // Set cursor, but only if we're not in 'busy' mode
-
-    // Trouble with this is that it sets the cursor for controls too :-(
-    if (m_windowCursor.Ok() && !wxIsBusy())
-        ::SetCursor((HCURSOR) m_windowCursor.GetHCURSOR());
 
     if (!m_mouseInWindow)
     {
@@ -2427,7 +2561,7 @@ void wxWindow::MSWOnMouseLeave(int x, int y, WXUINT flags)
     GetEventHandler()->ProcessEvent(event);
 }
 
-void wxWindow::MSWOnChar(WXWORD wParam, WXLPARAM lParam, bool isASCII)
+bool wxWindow::MSWOnChar(WXWORD wParam, WXLPARAM lParam, bool isASCII)
 {
     int id;
     bool tempControlDown = FALSE;
@@ -2489,9 +2623,92 @@ void wxWindow::MSWOnChar(WXWORD wParam, WXLPARAM lParam, bool isASCII)
 
         event.m_x = pt.x; event.m_y = pt.y;
 
-        if (!GetEventHandler()->ProcessEvent(event))
-            Default();
+        if (GetEventHandler()->ProcessEvent(event))
+            return TRUE;
+        else
+            return FALSE;
+    }
+    else
+        return FALSE;
+}
+
+bool wxWindow::MSWOnKeyDown(WXWORD wParam, WXLPARAM lParam, bool isASCII)
+{
+    int id;
+
+    if ((id = wxCharCodeMSWToWX(wParam)) == 0) {
+        id = wParam;
+    }
+
+    if (id != -1)
+    {
+        wxKeyEvent event(wxEVT_KEY_DOWN);
+        event.m_shiftDown = (::GetKeyState(VK_SHIFT)&0x100?TRUE:FALSE);
+        event.m_controlDown = (::GetKeyState(VK_CONTROL)&0x100?TRUE:FALSE);
+        if ((HIWORD(lParam) & KF_ALTDOWN) == KF_ALTDOWN)
+            event.m_altDown = TRUE;
+
+        event.m_eventObject = this;
+        event.m_keyCode = id;
+        event.SetTimestamp(wxApp::sm_lastMessageTime);
+
+        POINT pt ;
+        GetCursorPos(&pt) ;
+        RECT rect ;
+        GetWindowRect((HWND) GetHWND(),&rect) ;
+        pt.x -= rect.left ;
+        pt.y -= rect.top ;
+
+        event.m_x = pt.x; event.m_y = pt.y;
+
+        if (GetEventHandler()->ProcessEvent(event))
+        {
+            return TRUE;
+        }
+        else return FALSE;
+    }
+    else
+    {
+        return FALSE;
+    }
+}
+
+bool wxWindow::MSWOnKeyUp(WXWORD wParam, WXLPARAM lParam, bool isASCII)
+{
+    int id;
+
+    if ((id = wxCharCodeMSWToWX(wParam)) == 0) {
+        id = wParam;
+    }
+
+    if (id != -1)
+    {
+        wxKeyEvent event(wxEVT_KEY_UP);
+        event.m_shiftDown = (::GetKeyState(VK_SHIFT)&0x100?TRUE:FALSE);
+        event.m_controlDown = (::GetKeyState(VK_CONTROL)&0x100?TRUE:FALSE);
+        if ((HIWORD(lParam) & KF_ALTDOWN) == KF_ALTDOWN)
+            event.m_altDown = TRUE;
+
+        event.m_eventObject = this;
+        event.m_keyCode = id;
+        event.SetTimestamp(wxApp::sm_lastMessageTime);
+
+        POINT pt ;
+        GetCursorPos(&pt) ;
+        RECT rect ;
+        GetWindowRect((HWND) GetHWND(),&rect) ;
+        pt.x -= rect.left ;
+        pt.y -= rect.top ;
+
+        event.m_x = pt.x; event.m_y = pt.y;
+
+        if (GetEventHandler()->ProcessEvent(event))
+            return TRUE;
+        else
+            return FALSE;
     }
+    else
+        return FALSE;
 }
 
 void wxWindow::MSWOnJoyDown(int joystick, int x, int y, WXUINT flags)
@@ -2506,7 +2723,7 @@ void wxWindow::MSWOnJoyDown(int joystick, int x, int y, WXUINT flags)
         change = wxJOY_BUTTON3;
     if (flags & JOY_BUTTON4CHG)
         change = wxJOY_BUTTON4;
-    
+
     if (flags & JOY_BUTTON1)
         buttons |= wxJOY_BUTTON1;
     if (flags & JOY_BUTTON2)
@@ -2515,11 +2732,11 @@ void wxWindow::MSWOnJoyDown(int joystick, int x, int y, WXUINT flags)
         buttons |= wxJOY_BUTTON3;
     if (flags & JOY_BUTTON4)
         buttons |= wxJOY_BUTTON4;
-    
+
     wxJoystickEvent event(wxEVT_JOY_BUTTON_DOWN, buttons, joystick, change);
     event.SetPosition(wxPoint(x, y));
     event.SetEventObject(this);
-    
+
     GetEventHandler()->ProcessEvent(event);
 }
 
@@ -2535,7 +2752,7 @@ void wxWindow::MSWOnJoyUp(int joystick, int x, int y, WXUINT flags)
         change = wxJOY_BUTTON3;
     if (flags & JOY_BUTTON4CHG)
         change = wxJOY_BUTTON4;
-    
+
     if (flags & JOY_BUTTON1)
         buttons |= wxJOY_BUTTON1;
     if (flags & JOY_BUTTON2)
@@ -2544,11 +2761,11 @@ void wxWindow::MSWOnJoyUp(int joystick, int x, int y, WXUINT flags)
         buttons |= wxJOY_BUTTON3;
     if (flags & JOY_BUTTON4)
         buttons |= wxJOY_BUTTON4;
-    
+
     wxJoystickEvent event(wxEVT_JOY_BUTTON_UP, buttons, joystick, change);
     event.SetPosition(wxPoint(x, y));
     event.SetEventObject(this);
-    
+
     GetEventHandler()->ProcessEvent(event);
 }
 
@@ -2563,11 +2780,11 @@ void wxWindow::MSWOnJoyMove(int joystick, int x, int y, WXUINT flags)
         buttons |= wxJOY_BUTTON3;
     if (flags & JOY_BUTTON4)
         buttons |= wxJOY_BUTTON4;
-    
+
     wxJoystickEvent event(wxEVT_JOY_MOVE, buttons, joystick, 0);
     event.SetPosition(wxPoint(x, y));
     event.SetEventObject(this);
-    
+
     GetEventHandler()->ProcessEvent(event);
 }
 
@@ -2582,11 +2799,11 @@ void wxWindow::MSWOnJoyZMove(int joystick, int z, WXUINT flags)
         buttons |= wxJOY_BUTTON3;
     if (flags & JOY_BUTTON4)
         buttons |= wxJOY_BUTTON4;
-    
+
     wxJoystickEvent event(wxEVT_JOY_ZMOVE, buttons, joystick, 0);
     event.SetZPosition(z);
     event.SetEventObject(this);
-    
+
     GetEventHandler()->ProcessEvent(event);
 }
 
@@ -2640,7 +2857,7 @@ void wxWindow::MSWOnVScroll(WXWORD wParam, WXWORD pos, WXHWND control)
         return;
         break;
     }
-    
+
     if (!GetEventHandler()->ProcessEvent(event))
         Default();
 }
@@ -2721,7 +2938,7 @@ bool wxWindow::MSWOnInitDialog(WXHWND WXUNUSED(hWndFocus))
     return TRUE;
 }
 
-void wxWindow::InitDialog(void)
+void wxWindow::InitDialog()
 {
     wxInitDialogEvent event(GetId());
     event.SetEventObject( this );
@@ -2742,20 +2959,15 @@ void wxGetCharSize(WXHWND wnd, int *x, int *y,wxFont *the_font)
     HFONT was = 0;
     if (the_font)
     {
-#if WXDEBUG > 1
-        wxDebugMsg("wxGetCharSize: Selecting HFONT %X\n", fnt);
-#endif
         //    the_font->UseResource();
         //    the_font->RealizeResource();
-        if ((fnt=(HFONT) the_font->GetResourceHandle()))
+        fnt = (HFONT)the_font->GetResourceHandle();
+        if ( fnt )
             was = (HFONT) SelectObject(dc,fnt) ;
     }
     GetTextMetrics(dc, &tm);
     if (the_font && fnt && was)
     {
-#if WXDEBUG > 1
-        wxDebugMsg("wxGetCharSize: Selecting old HFONT %X\n", was);
-#endif
         SelectObject(dc,was) ;
     }
     ReleaseDC((HWND)wnd, dc);
@@ -2949,7 +3161,7 @@ void wxWindow::ShowCaret(bool show)
     }
 }
 
-void wxWindow::DestroyCaret(void)
+void wxWindow::DestroyCaret()
 {
     m_caretEnabled = FALSE;
 }
@@ -2967,7 +3179,7 @@ void wxWindow::GetCaretPos(int *x, int *y) const
     *y = point.y;
 }
 
-wxWindow *wxGetActiveWindow(void)
+wxWindow *wxGetActiveWindow()
 {
     HWND hWnd = GetActiveWindow();
     if (hWnd != 0)
@@ -2990,7 +3202,7 @@ void wxSetKeyboardHook(bool doIt)
     {
         wxTheKeyboardHookProc = MakeProcInstance((FARPROC) wxKeyboardHook, wxGetInstance());
         wxTheKeyboardHook = SetWindowsHookEx(WH_KEYBOARD, (HOOKPROC) wxTheKeyboardHookProc, wxGetInstance(),
-#ifdef __WIN32__
+#if defined(__WIN32__) && !defined(__TWIN32__)
             GetCurrentThreadId());
         //      (DWORD)GetCurrentProcess()); // This is another possibility. Which is right?
 #else
@@ -3074,26 +3286,19 @@ void wxWindow::Centre(int direction)
 
 }
 
-/* TODO (maybe)
-void wxWindow::OnPaint(void)
-{
-PaintSelectionHandles();
-}
-*/
-
 void wxWindow::WarpPointer (int x_pos, int y_pos)
 {
     // Move the pointer to (x_pos,y_pos) coordinates. They are expressed in
     // pixel coordinates, relatives to the canvas -- So, we first need to
     // substract origin of the window, then convert to screen position
-    
+
     int x = x_pos; int y = y_pos;
     RECT rect;
     GetWindowRect ((HWND) GetHWND(), &rect);
-    
+
     x += rect.left;
     y += rect.top;
-    
+
     SetCursorPos (x, y);
 }
 
@@ -3104,11 +3309,11 @@ void wxWindow::MSWDeviceToLogical (float *x, float *y) const
 bool wxWindow::MSWOnEraseBkgnd (WXHDC pDC)
 {
     wxDC dc ;
-    
+
     dc.SetHDC(pDC);
     dc.SetWindow(this);
     dc.BeginDrawing();
-    
+
     wxEraseEvent event(m_windowId, &dc);
     event.m_eventObject = this;
     if (!GetEventHandler()->ProcessEvent(event))
@@ -3122,17 +3327,21 @@ bool wxWindow::MSWOnEraseBkgnd (WXHDC pDC)
         dc.EndDrawing();
         dc.SelectOldObjects(pDC);
     }
-    
+
     dc.SetHDC((WXHDC) NULL);
     return TRUE;
 }
 
 void wxWindow::OnEraseBackground(wxEraseEvent& event)
 {
+    if (!GetHWND())
+        return;
+
     RECT rect;
     ::GetClientRect((HWND) GetHWND(), &rect);
 
-    HBRUSH hBrush = ::CreateSolidBrush(PALETTERGB(GetBackgroundColour().Red(), GetBackgroundColour().Green(), GetBackgroundColour().Blue()));
+    COLORREF ref = PALETTERGB(m_backgroundColour.Red(), m_backgroundColour.Green(), m_backgroundColour.Blue()) ;
+    HBRUSH hBrush = ::CreateSolidBrush(ref);
     int mode = ::SetMapMode((HDC) event.GetDC()->GetHDC(), MM_TEXT);
 
     //  ::GetClipBox((HDC) event.GetDC()->GetHDC(), &rect);
@@ -3155,7 +3364,7 @@ void wxWindow::OnEraseBackground(wxEraseEvent& event)
 void wxWindow::SetScrollRange(int orient, int range, bool refresh)
 {
 #if defined(__WIN95__)
-    
+
     int range1 = range;
 
     // Try to adjust the range to cope with page size > 1
@@ -3307,7 +3516,7 @@ int wxWindow::GetScrollRange(int orient) const
 #if defined(__WIN95__)
         // Try to adjust the range to cope with page size > 1
         // - a Windows API quirk
-        int pageSize = GetScrollPage(orient);
+        int pageSize = GetScrollThumb(orient);
         if ( pageSize > 1 )
         {
             maxPos -= (pageSize - 1);
@@ -3315,7 +3524,7 @@ int wxWindow::GetScrollRange(int orient) const
         // October 10th: new range concept.
         maxPos += pageSize;
 #endif
-        
+
         return maxPos;
     }
     else
@@ -3373,7 +3582,7 @@ SetScrollPage(orient, thumbVisible, FALSE);
 
   int oldRange = range - thumbVisible ;
   SetScrollRange(orient, oldRange, FALSE);
-  
+
     SetScrollPos(orient, pos, refresh);
     */
 #if defined(__WIN95__)
@@ -3429,7 +3638,7 @@ SetScrollPage(orient, thumbVisible, FALSE);
     }
 }
 
-void wxWindow::ScrollWindow(int dx, int dy, const wxRectangle *rect)
+void wxWindow::ScrollWindow(int dx, int dy, const wxRect *rect)
 {
     RECT rect2;
     if ( rect )
@@ -3439,7 +3648,7 @@ void wxWindow::ScrollWindow(int dx, int dy, const wxRectangle *rect)
         rect2.right = rect->x + rect->width;
         rect2.bottom = rect->y + rect->height;
     }
-    
+
     if ( rect )
         ::ScrollWindow((HWND) GetHWND(), dx, dy, &rect2, NULL);
     else
@@ -3472,10 +3681,10 @@ void wxWindow::SubclassWin(WXHWND hWnd)
     SetWindowLong((HWND) hWnd, GWL_WNDPROC, (LONG) wxWndProc);
 }
 
-void wxWindow::UnsubclassWin(void)
+void wxWindow::UnsubclassWin()
 {
     wxRemoveHandleAssociation(this);
-    
+
     // Restore old Window proc
     if ((HWND) GetHWND())
     {
@@ -3494,7 +3703,7 @@ WXDWORD wxWindow::MakeExtendedStyle(long style, bool eliminateBorders)
     WXDWORD exStyle = 0;
     if ( style & wxTRANSPARENT_WINDOW )
         exStyle |= WS_EX_TRANSPARENT ;
-    
+
     if ( !eliminateBorders )
     {
         if ( style & wxSUNKEN_BORDER )
@@ -3550,46 +3759,47 @@ WXDWORD wxWindow::Determine3DEffects(WXDWORD defaultBorderStyle, bool *want3D)
 
     // 5) If this isn't a Win95 app, and we are using CTL3D, remove border
     // effects from extended style
-#if CTL3D
+#if wxUSE_CTL3D
     if ( *want3D )
         nativeBorder = FALSE;
 #endif
-    
+
     DWORD exStyle = MakeExtendedStyle(m_windowStyle, !nativeBorder);
 
     // If we want 3D, but haven't specified a border here,
     // apply the default border style specified.
     // TODO what about non-Win95 WIN32? Does it have borders?
-#if defined(__WIN95__) && !CTL3D
+#if defined(__WIN95__) && !wxUSE_CTL3D
     if (defaultBorderStyle && (*want3D) && ! ((m_windowStyle & wxDOUBLE_BORDER) || (m_windowStyle & wxRAISED_BORDER) ||
         (m_windowStyle & wxSTATIC_BORDER) || (m_windowStyle & wxSIMPLE_BORDER) ))
         exStyle |= defaultBorderStyle; // WS_EX_CLIENTEDGE ;
 #endif
-    
+
     return exStyle;
 }
 
 void wxWindow::OnChar(wxKeyEvent& event)
 {
-    if ( event.KeyCode() == WXK_TAB ) {
-        // propagate the TABs to the parent - it's up to it to decide what
-        // to do with it
-        if ( GetParent() ) {
-            if ( GetParent()->ProcessEvent(event) )
-                return;
-        }
-    }
-    
     bool isVirtual;
     int id = wxCharCodeWXToMSW((int)event.KeyCode(), &isVirtual);
-    
+
     if ( id == -1 )
         id= m_lastWParam;
-    
-    if ( !event.ControlDown() )
+
+    if ( !event.ControlDown() ) // Why this test?
         (void) MSWDefWindowProc(m_lastMsg, (WPARAM) id, m_lastLParam);
 }
 
+void wxWindow::OnKeyDown(wxKeyEvent& event)
+{
+    Default();
+}
+
+void wxWindow::OnKeyUp(wxKeyEvent& event)
+{
+    Default();
+}
+
 void wxWindow::OnPaint(wxPaintEvent& event)
 {
     Default();
@@ -3609,19 +3819,19 @@ bool wxWindow::IsEnabled(void) const
 
 // Transfer values to controls. If returns FALSE,
 // it's an application error (pops up a dialog)
-bool wxWindow::TransferDataToWindow(void)
+bool wxWindow::TransferDataToWindow()
 {
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while ( node )
     {
         wxWindow *child = (wxWindow *)node->Data();
         if ( child->GetValidator() && /* child->GetValidator()->Ok() && */
             !child->GetValidator()->TransferToWindow() )
         {
-            wxMessageBox("Application Error", "Could not transfer data to window", wxOK|wxICON_EXCLAMATION);
+            wxLogError(_("Could not transfer data to window"));
             return FALSE;
         }
-        
+
         node = node->Next();
     }
     return TRUE;
@@ -3629,9 +3839,9 @@ bool wxWindow::TransferDataToWindow(void)
 
 // Transfer values from controls. If returns FALSE,
 // validation failed: don't quit
-bool wxWindow::TransferDataFromWindow(void)
+bool wxWindow::TransferDataFromWindow()
 {
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while ( node )
     {
         wxWindow *child = (wxWindow *)node->Data();
@@ -3639,15 +3849,15 @@ bool wxWindow::TransferDataFromWindow(void)
         {
             return FALSE;
         }
-        
+
         node = node->Next();
     }
     return TRUE;
 }
 
-bool wxWindow::Validate(void)
+bool wxWindow::Validate()
 {
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while ( node )
     {
         wxWindow *child = (wxWindow *)node->Data();
@@ -3655,14 +3865,14 @@ bool wxWindow::Validate(void)
         {
             return FALSE;
         }
-        
+
         node = node->Next();
     }
     return TRUE;
 }
 
 // Get the window with the focus
-wxWindow *wxWindow::FindFocus(void)
+wxWindow *wxWindow::FindFocus()
 {
     HWND hWnd = ::GetFocus();
     if ( hWnd )
@@ -3674,30 +3884,28 @@ wxWindow *wxWindow::FindFocus(void)
 
 void wxWindow::AddChild(wxWindow *child)
 {
-    GetChildren()->Append(child);
+    GetChildren().Append(child);
     child->m_windowParent = this;
 }
 
 void wxWindow::RemoveChild(wxWindow *child)
 {
-    if (GetChildren())
-        GetChildren()->DeleteObject(child);
+//    if (GetChildren())
+    GetChildren().DeleteObject(child);
     child->m_windowParent = NULL;
 }
 
-void wxWindow::DestroyChildren(void)
+void wxWindow::DestroyChildren()
 {
-    if (GetChildren()) {
         wxNode *node;
-        while ((node = GetChildren()->First()) != (wxNode *)NULL) {
+        while ((node = GetChildren().First()) != (wxNode *)NULL) {
             wxWindow *child;
             if ((child = (wxWindow *)node->Data()) != (wxWindow *)NULL) {
                 delete child;
-                if ( GetChildren()->Member(child) )
+                if ( GetChildren().Member(child) )
                     delete node;
             }
         } /* while */
-    }
 }
 
 void wxWindow::MakeModal(bool modal)
@@ -3801,7 +4009,7 @@ void wxWindow::RemoveConstraintReference(wxWindow *otherWin)
 }
 
 // Reset any constraints that mention this window
-void wxWindow::DeleteRelatedConstraints(void)
+void wxWindow::DeleteRelatedConstraints()
 {
     if (m_constraintsInvolvedIn)
     {
@@ -3843,7 +4051,7 @@ void wxWindow::SetSizer(wxSizer *sizer)
 * New version
 */
 
-bool wxWindow::Layout(void)
+bool wxWindow::Layout()
 {
     if (GetConstraints())
     {
@@ -3912,7 +4120,7 @@ bool wxWindow::DoPhase(int phase)
     {
         noChanges = 0;
         noFailures = 0;
-        wxNode *node = GetChildren()->First();
+        wxNode *node = GetChildren().First();
         while (node)
         {
             wxWindow *child = (wxWindow *)node->Data();
@@ -3943,7 +4151,7 @@ bool wxWindow::DoPhase(int phase)
     return TRUE;
 }
 
-void wxWindow::ResetConstraints(void)
+void wxWindow::ResetConstraints()
 {
     wxLayoutConstraints *constr = GetConstraints();
     if (constr)
@@ -3957,7 +4165,7 @@ void wxWindow::ResetConstraints(void)
         constr->centreX.SetDone(FALSE);
         constr->centreY.SetDone(FALSE);
     }
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while (node)
     {
         wxWindow *win = (wxWindow *)node->Data();
@@ -4002,21 +4210,22 @@ void wxWindow::SetConstraintSizes(bool recurse)
             winName = "unnamed";
         else
             winName = GetName();
-        wxDebugMsg("Constraint(s) not satisfied for window of type %s, name %s:\n", (const char *)windowClass, (const char *)winName);
+        wxLogDebug("Constraint(s) not satisfied for window of type %s, name %s:",
+                    (const char *)windowClass, (const char *)winName);
         if (!constr->left.GetDone())
-            wxDebugMsg("  unsatisfied 'left' constraint.\n");
+            wxLogDebug("  unsatisfied 'left' constraint.");
         if (!constr->right.GetDone())
-            wxDebugMsg("  unsatisfied 'right' constraint.\n");
+            wxLogDebug("  unsatisfied 'right' constraint.");
         if (!constr->width.GetDone())
-            wxDebugMsg("  unsatisfied 'width' constraint.\n");
+            wxLogDebug("  unsatisfied 'width' constraint.");
         if (!constr->height.GetDone())
-            wxDebugMsg("  unsatisfied 'height' constraint.\n");
-        wxDebugMsg("Please check constraints: try adding AsIs() constraints.\n");
+            wxLogDebug("  unsatisfied 'height' constraint.");
+        wxLogDebug("Please check constraints: try adding AsIs() constraints.\n");
     }
 
     if (recurse)
     {
-        wxNode *node = GetChildren()->First();
+        wxNode *node = GetChildren().First();
         while (node)
         {
             wxWindow *win = (wxWindow *)node->Data();
@@ -4145,7 +4354,9 @@ bool wxWindow::Close(bool force)
 {
     wxCloseEvent event(wxEVT_CLOSE_WINDOW, m_windowId);
     event.SetEventObject(this);
+#if WXWIN_COMPATIBILITY
     event.SetForce(force);
+#endif
     event.SetCanVeto(!force);
 
     return (GetEventHandler()->ProcessEvent(event) && !event.GetVeto());
@@ -4154,9 +4365,9 @@ bool wxWindow::Close(bool force)
 wxObject* wxWindow::GetChild(int number) const
 {
     // Return a pointer to the Nth object in the Panel
-    if (!GetChildren())
-        return(NULL) ;
-    wxNode *node = GetChildren()->First();
+//    if (!GetChildren())
+//        return(NULL) ;
+    wxNode *node = GetChildren().First();
     int n = number;
     while (node && n--)
         node = node->Next() ;
@@ -4187,9 +4398,9 @@ void wxWindow::OnDefaultAction(wxControl *initiatingItem)
   event.m_clientData = lbox->wxListBox::GetClientData(event.m_commandInt);
   }
   event.m_eventObject = lbox;
-  
+
     lbox->ProcessCommand(event);
-    
+
       if (event.m_commandString)
       delete[] event.m_commandString;
       return;
@@ -4205,7 +4416,7 @@ void wxWindow::OnDefaultAction(wxControl *initiatingItem)
     */
 }
 
-void wxWindow::Clear(void)
+void wxWindow::Clear()
 {
     wxClientDC dc(this);
     wxBrush brush(GetBackgroundColour(), wxSOLID);
@@ -4214,11 +4425,11 @@ void wxWindow::Clear(void)
 }
 
 // Fits the panel around the items
-void wxWindow::Fit(void)
+void wxWindow::Fit()
 {
     int maxX = 0;
     int maxY = 0;
-    wxNode *node = GetChildren()->First();
+    wxNode *node = GetChildren().First();
     while ( node )
     {
         wxWindow *win = (wxWindow *)node->Data();
@@ -4229,7 +4440,7 @@ void wxWindow::Fit(void)
             maxX = wx + ww;
         if ( wy + wh > maxY )
             maxY = wy + wh;
-        
+
         node = node->Next();
     }
     SetClientSize(maxX + 5, maxY + 5);
@@ -4240,7 +4451,7 @@ void wxWindow::SetValidator(const wxValidator& validator)
     if ( m_windowValidator )
         delete m_windowValidator;
     m_windowValidator = validator.Clone();
-    
+
     if ( m_windowValidator )
         m_windowValidator->SetWindow(this) ;
 }
@@ -4250,8 +4461,8 @@ wxWindow *wxWindow::FindWindow(long id)
 {
     if ( GetId() == id)
         return this;
-    
-    wxNode *node = GetChildren()->First();
+
+    wxNode *node = GetChildren().First();
     while ( node )
     {
         wxWindow *child = (wxWindow *)node->Data();
@@ -4267,8 +4478,8 @@ wxWindow *wxWindow::FindWindow(const wxString& name)
 {
     if ( GetName() == name)
         return this;
-    
-    wxNode *node = GetChildren()->First();
+
+    wxNode *node = GetChildren().First();
     while ( node )
     {
         wxWindow *child = (wxWindow *)node->Data();
@@ -4303,7 +4514,7 @@ int y_pages = 0;
   // Bugfix begin
   if (vert_units)
   y_pages = (int)(v_height/vert_units) - y_page;
-  
+
     #ifdef __WXMSW__
     int y = 0;
     #else
@@ -4383,7 +4594,7 @@ int y_pages = 0;
 */
 
 // Setup background and foreground colours correctly
-void wxWindow::SetupColours(void)
+void wxWindow::SetupColours()
 {
     if (GetParent())
         SetBackgroundColour(GetParent()->GetBackgroundColour());
@@ -4400,17 +4611,17 @@ void wxWindow::OnIdle(wxIdleEvent& event)
         {
             // Generate a LEAVE event
             m_mouseInWindow = FALSE;
-            
+
             int state = 0;
             if (::GetKeyState(VK_SHIFT) != 0)
                 state |= MK_SHIFT;
             if (::GetKeyState(VK_CONTROL) != 0)
                 state |= MK_CONTROL;
-            
+
             // Unfortunately the mouse button and keyboard state may have changed
             // by the time the OnIdle function is called, so 'state' may be
             // meaningless.
-            
+
             MSWOnMouseLeave(pt.x, pt.y, state);
         }
     }
@@ -4418,13 +4629,13 @@ void wxWindow::OnIdle(wxIdleEvent& event)
 }
 
 // Raise the window to the top of the Z order
-void wxWindow::Raise(void)
+void wxWindow::Raise()
 {
     ::BringWindowToTop((HWND) GetHWND());
 }
 
 // Lower the window to the bottom of the Z order
-void wxWindow::Lower(void)
+void wxWindow::Lower()
 {
     ::SetWindowPos((HWND) GetHWND(), HWND_BOTTOM, 0, 0, 0, 0, SWP_NOMOVE|SWP_NOSIZE|SWP_NOACTIVATE);
 }
@@ -4437,6 +4648,7 @@ long wxWindow::MSWGetDlgCode()
 
 bool wxWindow::AcceptsFocus() const
 {
+    // invisible and disabled controls don't need focus
     return IsShown() && IsEnabled();
 }
 
@@ -4461,6 +4673,35 @@ bool wxWindow::IsExposed(const wxRect& rect) const
     return (m_updateRegion.Contains(rect) != wxOutRegion);
 }
 
+// Set this window to be the child of 'parent'.
+bool wxWindow::Reparent(wxWindow *parent)
+{
+    if (parent == GetParent())
+        return TRUE;
+
+    // Unlink this window from the existing parent.
+    if (GetParent())
+    {
+        GetParent()->RemoveChild(this);
+    }
+    else
+        wxTopLevelWindows.DeleteObject(this);
+
+    HWND hWndParent = 0;
+    HWND hWndChild = (HWND) GetHWND();
+    if (parent != (wxWindow*) NULL)
+    {
+        parent->AddChild(this);
+        hWndParent = (HWND) parent->GetHWND();
+    }
+    else
+        wxTopLevelWindows.Append(this);
+
+    ::SetParent(hWndChild, hWndParent);
+
+    return TRUE;
+}
+
 #ifdef __WXDEBUG__
 const char *wxGetMessageName(int message)
 {
@@ -4518,7 +4759,7 @@ const char *wxGetMessageName(int message)
     case 0x0046: return "WM_WINDOWPOSCHANGING";
     case 0x0047: return "WM_WINDOWPOSCHANGED";
     case 0x0048: return "WM_POWER";
-        
+
 #ifdef  __WIN32__
     case 0x004A: return "WM_COPYDATA";
     case 0x004B: return "WM_CANCELJOURNAL";
@@ -4536,7 +4777,7 @@ const char *wxGetMessageName(int message)
     case 0x007F: return "WM_GETICON";
     case 0x0080: return "WM_SETICON";
 #endif  //WIN32
-        
+
     case 0x0081: return "WM_NCCREATE";
     case 0x0082: return "WM_NCDESTROY";
     case 0x0083: return "WM_NCCALCSIZE";
@@ -4563,13 +4804,13 @@ const char *wxGetMessageName(int message)
     case 0x0106: return "WM_SYSCHAR";
     case 0x0107: return "WM_SYSDEADCHAR";
     case 0x0108: return "WM_KEYLAST";
-        
+
 #ifdef  __WIN32__
     case 0x010D: return "WM_IME_STARTCOMPOSITION";
     case 0x010E: return "WM_IME_ENDCOMPOSITION";
     case 0x010F: return "WM_IME_COMPOSITION";
 #endif  //WIN32
-        
+
     case 0x0110: return "WM_INITDIALOG";
     case 0x0111: return "WM_COMMAND";
     case 0x0112: return "WM_SYSCOMMAND";
@@ -4594,7 +4835,7 @@ const char *wxGetMessageName(int message)
     case 0x0210: return "WM_PARENTNOTIFY";
     case 0x0211: return "WM_ENTERMENULOOP";
     case 0x0212: return "WM_EXITMENULOOP";
-        
+
 #ifdef  __WIN32__
     case 0x0213: return "WM_NEXTMENU";
     case 0x0214: return "WM_SIZING";
@@ -4603,7 +4844,7 @@ const char *wxGetMessageName(int message)
     case 0x0218: return "WM_POWERBROADCAST";
     case 0x0219: return "WM_DEVICECHANGE";
 #endif  //WIN32
-        
+
     case 0x0220: return "WM_MDICREATE";
     case 0x0221: return "WM_MDIDESTROY";
     case 0x0222: return "WM_MDIACTIVATE";
@@ -4616,7 +4857,7 @@ const char *wxGetMessageName(int message)
     case 0x0229: return "WM_MDIGETACTIVE";
     case 0x0230: return "WM_MDISETMENU";
     case 0x0233: return "WM_DROPFILES";
-        
+
 #ifdef  __WIN32__
     case 0x0281: return "WM_IME_SETCONTEXT";
     case 0x0282: return "WM_IME_NOTIFY";
@@ -4627,7 +4868,7 @@ const char *wxGetMessageName(int message)
     case 0x0290: return "WM_IME_KEYDOWN";
     case 0x0291: return "WM_IME_KEYUP";
 #endif  //WIN32
-        
+
     case 0x0300: return "WM_CUT";
     case 0x0301: return "WM_COPY";
     case 0x0302: return "WM_PASTE";
@@ -4646,7 +4887,7 @@ const char *wxGetMessageName(int message)
     case 0x030F: return "WM_QUERYNEWPALETTE";
     case 0x0310: return "WM_PALETTEISCHANGING";
     case 0x0311: return "WM_PALETTECHANGED";
-        
+
 #ifdef __WIN32__
         // common controls messages - although they're not strictly speaking
         // standard, it's nice to decode them nevertheless
@@ -4729,7 +4970,7 @@ const char *wxGetMessageName(int message)
     case 0x1000 + 63: return "LVM_GETHOTCURSOR";
     case 0x1000 + 64: return "LVM_APPROXIMATEVIEWRECT";
     case 0x1000 + 65: return "LVM_SETWORKAREA";
-        
+
         // tree view
     case 0x1100 + 0: return "TVM_INSERTITEMA";
     case 0x1100 + 50: return "TVM_INSERTITEMW";
@@ -4761,7 +5002,7 @@ const char *wxGetMessageName(int message)
     case 0x1100 + 64: return "TVM_GETISEARCHSTRINGW";
     case 0x1100 + 24: return "TVM_SETTOOLTIPS";
     case 0x1100 + 25: return "TVM_GETTOOLTIPS";
-        
+
         // header
     case 0x1200 + 0: return "HDM_GETITEMCOUNT";
     case 0x1200 + 1: return "HDM_INSERTITEMA";
@@ -4781,7 +5022,7 @@ const char *wxGetMessageName(int message)
     case 0x1200 + 17: return "HDM_GETORDERARRAY";
     case 0x1200 + 18: return "HDM_SETORDERARRAY";
     case 0x1200 + 19: return "HDM_SETHOTDIVIDER";
-        
+
         // tab control
     case 0x1300 + 2: return "TCM_GETIMAGELIST";
     case 0x1300 + 3: return "TCM_SETIMAGELIST";
@@ -4810,7 +5051,7 @@ const char *wxGetMessageName(int message)
     case 0x1300 + 48: return "TCM_SETCURFOCUS";
     case 0x1300 + 49: return "TCM_SETMINTABWIDTH";
     case 0x1300 + 50: return "TCM_DESELECTALL";
-        
+
         // toolbar
     case WM_USER+1: return "TB_ENABLEBUTTON";
     case WM_USER+2: return "TB_CHECKBUTTON";
@@ -4868,13 +5109,13 @@ const char *wxGetMessageName(int message)
     case WM_USER+60: return "TB_SETMAXTEXTROWS";
     case WM_USER+61: return "TB_GETTEXTROWS";
     case WM_USER+41: return "TB_GETBITMAPFLAGS";
-        
+
 #endif //WIN32
-        
+
     default:
         static char s_szBuf[128];
         sprintf(s_szBuf, "<unknown message = %d>", message);
         return s_szBuf;
   }
 }
-#endif //WXDEBUG
\ No newline at end of file
+#endif //__WXDEBUG__