]> git.saurik.com Git - wxWidgets.git/blobdiff - src/univ/themes/win32.cpp
setting clipping correctly
[wxWidgets.git] / src / univ / themes / win32.cpp
index 68178a25e31f1ae59142ed5324a89098b6a66dfd..1a08bde723740ef9c65256e0ca3d862d81e2d0df 100644 (file)
@@ -1,12 +1,12 @@
 ///////////////////////////////////////////////////////////////////////////////
 ///////////////////////////////////////////////////////////////////////////////
-// Name:        univ/themes/win32.cpp
+// Name:        src/univ/themes/win32.cpp
 // Purpose:     wxUniversal theme implementing Win32-like LNF
 // Author:      Vadim Zeitlin
 // Modified by:
 // Created:     06.08.00
 // RCS-ID:      $Id$
 // Copyright:   (c) 2000 SciTech Software, Inc. (www.scitechsoft.com)
 // Purpose:     wxUniversal theme implementing Win32-like LNF
 // Author:      Vadim Zeitlin
 // Modified by:
 // Created:     06.08.00
 // RCS-ID:      $Id$
 // Copyright:   (c) 2000 SciTech Software, Inc. (www.scitechsoft.com)
-// Licence:     wxWindows license
+// Licence:     wxWindows licence
 ///////////////////////////////////////////////////////////////////////////////
 
 // ===========================================================================
 ///////////////////////////////////////////////////////////////////////////////
 
 // ===========================================================================
     #pragma hdrstop
 #endif
 
     #pragma hdrstop
 #endif
 
+#include "wx/univ/theme.h"
+
+#if wxUSE_THEME_WIN32
+
 #ifndef WX_PRECOMP
     #include "wx/timer.h"
     #include "wx/intl.h"
 #ifndef WX_PRECOMP
     #include "wx/timer.h"
     #include "wx/intl.h"
     #include "wx/dcmemory.h"
 
     #include "wx/button.h"
     #include "wx/dcmemory.h"
 
     #include "wx/button.h"
+    #include "wx/bmpbuttn.h"
     #include "wx/listbox.h"
     #include "wx/checklst.h"
     #include "wx/combobox.h"
     #include "wx/scrolbar.h"
     #include "wx/slider.h"
     #include "wx/textctrl.h"
     #include "wx/listbox.h"
     #include "wx/checklst.h"
     #include "wx/combobox.h"
     #include "wx/scrolbar.h"
     #include "wx/slider.h"
     #include "wx/textctrl.h"
+    #include "wx/toolbar.h"
+    #include "wx/statusbr.h"
+
+    #ifdef __WXMSW__
+        // for COLOR_* constants
+        #include "wx/msw/private.h"
+    #endif
+    #include "wx/menu.h"
+    #include "wx/settings.h"
+    #include "wx/toplevel.h"
+    #include "wx/image.h"
 #endif // WX_PRECOMP
 
 #include "wx/notebook.h"
 #include "wx/spinbutt.h"
 #endif // WX_PRECOMP
 
 #include "wx/notebook.h"
 #include "wx/spinbutt.h"
-#include "wx/settings.h"
-#include "wx/menu.h"
+#include "wx/artprov.h"
+#ifdef wxUSE_TOGGLEBTN
+#include "wx/tglbtn.h"
+#endif // wxUSE_TOGGLEBTN
 
 #include "wx/univ/scrtimer.h"
 
 #include "wx/univ/scrtimer.h"
-
-#include "wx/univ/renderer.h"
+#include "wx/univ/stdrend.h"
+#include "wx/univ/inpcons.h"
 #include "wx/univ/inphand.h"
 #include "wx/univ/colschem.h"
 #include "wx/univ/inphand.h"
 #include "wx/univ/colschem.h"
-#include "wx/univ/theme.h"
 
 // ----------------------------------------------------------------------------
 // constants
 
 // ----------------------------------------------------------------------------
 // constants
 
 static const int BORDER_THICKNESS = 2;
 
 
 static const int BORDER_THICKNESS = 2;
 
-// the offset between the label and focus rect around it
-static const int FOCUS_RECT_OFFSET_X = 1;
-static const int FOCUS_RECT_OFFSET_Y = 1;
-
-enum IndicatorType
-{
-    IndicatorType_Check,
-    IndicatorType_Radio,
-    IndicatorType_Menu,
-    IndicatorType_Max
-};
-
-enum IndicatorState
-{
-    IndicatorState_Normal,
-    IndicatorState_Pressed, // this one is for check/radioboxes
-    IndicatorState_Selected = IndicatorState_Pressed, // for menus
-    IndicatorState_Disabled,
-    IndicatorState_SelectedDisabled,    // only for the menus
-    IndicatorState_Max
-};
+static const size_t NUM_STATUSBAR_GRIP_BANDS = 3;
+static const size_t WIDTH_STATUSBAR_GRIP_BAND = 4;
+static const size_t STATUSBAR_GRIP_SIZE =
+    WIDTH_STATUSBAR_GRIP_BAND*NUM_STATUSBAR_GRIP_BANDS;
 
 
-enum IndicatorStatus
-{
-    IndicatorStatus_Checked,
-    IndicatorStatus_Unchecked,
-    IndicatorStatus_Max
-};
+static const wxCoord SLIDER_MARGIN = 6; // margin around slider
+static const wxCoord SLIDER_THUMB_LENGTH = 18;
+static const wxCoord SLIDER_TICK_LENGTH = 6;
 
 
-// ----------------------------------------------------------------------------
 // wxWin32Renderer: draw the GUI elements in Win32 style
 // ----------------------------------------------------------------------------
 
 // wxWin32Renderer: draw the GUI elements in Win32 style
 // ----------------------------------------------------------------------------
 
-class wxWin32Renderer : public wxRenderer
+class wxWin32Renderer : public wxStdRenderer
 {
 public:
 {
 public:
-    // constants
-    enum wxArrowDirection
-    {
-        Arrow_Left,
-        Arrow_Right,
-        Arrow_Up,
-        Arrow_Down,
-        Arrow_Max
-    };
-
-    enum wxArrowStyle
-    {
-        Arrow_Normal,
-        Arrow_Disabled,
-        Arrow_Pressed,
-        Arrow_Inversed,
-        Arrow_InversedDisabled,
-        Arrow_StateMax
-    };
-
     // ctor
     wxWin32Renderer(const wxColourScheme *scheme);
 
     // ctor
     wxWin32Renderer(const wxColourScheme *scheme);
 
-    // implement the base class pure virtuals
-    virtual void DrawBackground(wxDC& dc,
-                                const wxColour& col,
-                                const wxRect& rect,
-                                int flags = 0);
+    // reimplement the renderer methods which are different for this theme
     virtual void DrawLabel(wxDC& dc,
                            const wxString& label,
                            const wxRect& rect,
     virtual void DrawLabel(wxDC& dc,
                            const wxString& label,
                            const wxRect& rect,
@@ -138,39 +110,15 @@ public:
                                  int alignment = wxALIGN_LEFT | wxALIGN_TOP,
                                  int indexAccel = -1,
                                  wxRect *rectBounds = NULL);
                                  int alignment = wxALIGN_LEFT | wxALIGN_TOP,
                                  int indexAccel = -1,
                                  wxRect *rectBounds = NULL);
-    virtual void DrawBorder(wxDC& dc,
-                            wxBorder border,
-                            const wxRect& rect,
-                            int flags = 0,
-                            wxRect *rectIn = (wxRect *)NULL);
-    virtual void DrawHorizontalLine(wxDC& dc,
-                                    wxCoord y, wxCoord x1, wxCoord x2);
-    virtual void DrawVerticalLine(wxDC& dc,
-                                  wxCoord x, wxCoord y1, wxCoord y2);
-    virtual void DrawFrame(wxDC& dc,
-                           const wxString& label,
-                           const wxRect& rect,
-                           int flags = 0,
-                           int alignment = wxALIGN_LEFT,
-                           int indexAccel = -1);
-    virtual void DrawTextBorder(wxDC& dc,
-                                wxBorder border,
-                                const wxRect& rect,
-                                int flags = 0,
-                                wxRect *rectIn = (wxRect *)NULL);
     virtual void DrawButtonBorder(wxDC& dc,
                                   const wxRect& rect,
                                   int flags = 0,
     virtual void DrawButtonBorder(wxDC& dc,
                                   const wxRect& rect,
                                   int flags = 0,
-                                  wxRect *rectIn = (wxRect *)NULL);
+                                  wxRect *rectIn = NULL);
+
     virtual void DrawArrow(wxDC& dc,
                            wxDirection dir,
                            const wxRect& rect,
                            int flags = 0);
     virtual void DrawArrow(wxDC& dc,
                            wxDirection dir,
                            const wxRect& rect,
                            int flags = 0);
-    virtual void DrawScrollbarArrow(wxDC& dc,
-                                    wxDirection dir,
-                                    const wxRect& rect,
-                                    int flags = 0)
-        { DrawArrow(dc, dir, rect, flags); }
     virtual void DrawScrollbarThumb(wxDC& dc,
                                     wxOrientation orient,
                                     const wxRect& rect,
     virtual void DrawScrollbarThumb(wxDC& dc,
                                     wxOrientation orient,
                                     const wxRect& rect,
@@ -179,38 +127,18 @@ public:
                                     wxOrientation orient,
                                     const wxRect& rect,
                                     int flags = 0);
                                     wxOrientation orient,
                                     const wxRect& rect,
                                     int flags = 0);
-    virtual void DrawScrollCorner(wxDC& dc,
-                                  const wxRect& rect);
-    virtual void DrawItem(wxDC& dc,
-                          const wxString& label,
-                          const wxRect& rect,
-                          int flags = 0);
-    virtual void DrawCheckItem(wxDC& dc,
-                               const wxString& label,
-                               const wxBitmap& bitmap,
-                               const wxRect& rect,
-                               int flags = 0);
-    virtual void DrawCheckButton(wxDC& dc,
-                                 const wxString& label,
-                                 const wxBitmap& bitmap,
-                                 const wxRect& rect,
-                                 int flags = 0,
-                                 wxAlignment align = wxALIGN_LEFT,
-                                 int indexAccel = -1);
-    virtual void DrawRadioButton(wxDC& dc,
-                                 const wxString& label,
-                                 const wxBitmap& bitmap,
-                                 const wxRect& rect,
-                                 int flags = 0,
-                                 wxAlignment align = wxALIGN_LEFT,
-                                 int indexAccel = -1);
-    virtual void DrawTextLine(wxDC& dc,
-                              const wxString& text,
-                              const wxRect& rect,
-                              int selStart = -1,
-                              int selEnd = -1,
-                              int flags = 0);
-    virtual void DrawLineWrapMark(wxDC& dc, const wxRect& rect);
+
+#if wxUSE_TOOLBAR
+    virtual void DrawToolBarButton(wxDC& dc,
+                                   const wxString& label,
+                                   const wxBitmap& bitmap,
+                                   const wxRect& rect,
+                                   int flags = 0,
+                                   long style = 0,
+                                   int tbarStyle = 0);
+#endif // wxUSE_TOOLBAR
+
+#if wxUSE_NOTEBOOK
     virtual void DrawTab(wxDC& dc,
                          const wxRect& rect,
                          wxDirection dir,
     virtual void DrawTab(wxDC& dc,
                          const wxRect& rect,
                          wxDirection dir,
@@ -218,26 +146,33 @@ public:
                          const wxBitmap& bitmap = wxNullBitmap,
                          int flags = 0,
                          int indexAccel = -1);
                          const wxBitmap& bitmap = wxNullBitmap,
                          int flags = 0,
                          int indexAccel = -1);
+#endif // wxUSE_NOTEBOOK
 
 
+#if wxUSE_SLIDER
     virtual void DrawSliderShaft(wxDC& dc,
                                  const wxRect& rect,
     virtual void DrawSliderShaft(wxDC& dc,
                                  const wxRect& rect,
+                                 int lenThumb,
                                  wxOrientation orient,
                                  int flags = 0,
                                  wxOrientation orient,
                                  int flags = 0,
+                                 long style = 0,
                                  wxRect *rectShaft = NULL);
     virtual void DrawSliderThumb(wxDC& dc,
                                  const wxRect& rect,
                                  wxOrientation orient,
                                  wxRect *rectShaft = NULL);
     virtual void DrawSliderThumb(wxDC& dc,
                                  const wxRect& rect,
                                  wxOrientation orient,
-                                 int flags = 0);
+                                 int flags = 0,
+                                 long style = 0);
     virtual void DrawSliderTicks(wxDC& dc,
                                  const wxRect& rect,
     virtual void DrawSliderTicks(wxDC& dc,
                                  const wxRect& rect,
-                                 const wxSize& sizeThumb,
+                                 int lenThumb,
                                  wxOrientation orient,
                                  int start,
                                  int end,
                                  int step = 1,
                                  wxOrientation orient,
                                  int start,
                                  int end,
                                  int step = 1,
-                                 int flags = 0);
-#if wxUSE_MENUS
+                                 int flags = 0,
+                                 long style = 0);
+#endif // wxUSE_SLIDER
 
 
+#if wxUSE_MENUS
     virtual void DrawMenuBarItem(wxDC& dc,
                                  const wxRect& rect,
                                  const wxString& label,
     virtual void DrawMenuBarItem(wxDC& dc,
                                  const wxRect& rect,
                                  const wxString& label,
@@ -254,28 +189,26 @@ public:
     virtual void DrawMenuSeparator(wxDC& dc,
                                    wxCoord y,
                                    const wxMenuGeometryInfo& geomInfo);
     virtual void DrawMenuSeparator(wxDC& dc,
                                    wxCoord y,
                                    const wxMenuGeometryInfo& geomInfo);
-#endif
+#endif // wxUSE_MENUS
+
+#if wxUSE_STATUSBAR
+    virtual void DrawStatusField(wxDC& dc,
+                                 const wxRect& rect,
+                                 const wxString& label,
+                                 int flags = 0, int style = 0);
+#endif // wxUSE_STATUSBAR
+
     virtual void GetComboBitmaps(wxBitmap *bmpNormal,
     virtual void GetComboBitmaps(wxBitmap *bmpNormal,
+                                 wxBitmap *bmpFocus,
                                  wxBitmap *bmpPressed,
                                  wxBitmap *bmpDisabled);
 
     virtual void AdjustSize(wxSize *size, const wxWindow *window);
                                  wxBitmap *bmpPressed,
                                  wxBitmap *bmpDisabled);
 
     virtual void AdjustSize(wxSize *size, const wxWindow *window);
-    virtual wxRect GetBorderDimensions(wxBorder border) const;
     virtual bool AreScrollbarsInsideBorder() const;
 
     virtual wxSize GetScrollbarArrowSize() const
         { return m_sizeScrollbarArrow; }
     virtual bool AreScrollbarsInsideBorder() const;
 
     virtual wxSize GetScrollbarArrowSize() const
         { return m_sizeScrollbarArrow; }
-    virtual wxRect GetScrollbarRect(const wxScrollBar *scrollbar,
-                                    wxScrollBar::Element elem,
-                                    int thumbPos = -1) const;
-    virtual wxCoord GetScrollbarSize(const wxScrollBar *scrollbar);
-    virtual wxHitTest HitTestScrollbar(const wxScrollBar *scrollbar,
-                                       const wxPoint& pt) const;
-    virtual wxCoord ScrollbarToPixel(const wxScrollBar *scrollbar,
-                                     int thumbPos = -1);
-    virtual int PixelToScrollbar(const wxScrollBar *scrollbar, wxCoord coord);
-    virtual wxCoord GetListboxItemHeight(wxCoord fontHeight)
-        { return fontHeight + 2; }
+
     virtual wxSize GetCheckBitmapSize() const
         { return wxSize(13, 13); }
     virtual wxSize GetRadioBitmapSize() const
     virtual wxSize GetCheckBitmapSize() const
         { return wxSize(13, 13); }
     virtual wxSize GetRadioBitmapSize() const
@@ -283,103 +216,81 @@ public:
     virtual wxCoord GetCheckItemMargin() const
         { return 0; }
 
     virtual wxCoord GetCheckItemMargin() const
         { return 0; }
 
+#if wxUSE_TOOLBAR
+    virtual wxSize GetToolBarButtonSize(wxCoord *separator) const
+        { if ( separator ) *separator = 5; return wxSize(16, 15); }
+    virtual wxSize GetToolBarMargin() const
+        { return wxSize(4, 4); }
+#endif // wxUSE_TOOLBAR
+
+#if wxUSE_TEXTCTRL
     virtual wxRect GetTextTotalArea(const wxTextCtrl *text,
     virtual wxRect GetTextTotalArea(const wxTextCtrl *text,
-                                    const wxRect& rect);
+                                    const wxRect& rect) const;
     virtual wxRect GetTextClientArea(const wxTextCtrl *text,
                                      const wxRect& rect,
     virtual wxRect GetTextClientArea(const wxTextCtrl *text,
                                      const wxRect& rect,
-                                     wxCoord *extraSpaceBeyond);
+                                     wxCoord *extraSpaceBeyond) const;
+#endif // wxUSE_TEXTCTRL
 
 
+#if wxUSE_NOTEBOOK
     virtual wxSize GetTabIndent() const { return wxSize(2, 2); }
     virtual wxSize GetTabPadding() const { return wxSize(6, 5); }
     virtual wxSize GetTabIndent() const { return wxSize(2, 2); }
     virtual wxSize GetTabPadding() const { return wxSize(6, 5); }
+#endif // wxUSE_NOTEBOOK
+
+#if wxUSE_SLIDER
 
 
-    virtual wxCoord GetSliderDim() const { return 20; }
-    virtual wxCoord GetSliderTickLen() const { return 4; }
+    virtual wxCoord GetSliderDim() const { return SLIDER_THUMB_LENGTH + 2*BORDER_THICKNESS; }
+    virtual wxCoord GetSliderTickLen() const { return SLIDER_TICK_LENGTH; }
     virtual wxRect GetSliderShaftRect(const wxRect& rect,
     virtual wxRect GetSliderShaftRect(const wxRect& rect,
-                                      wxOrientation orient) const;
+                                      int lenThumb,
+                                      wxOrientation orient,
+                                      long style = 0) const;
     virtual wxSize GetSliderThumbSize(const wxRect& rect,
     virtual wxSize GetSliderThumbSize(const wxRect& rect,
+                                      int lenThumb,
                                       wxOrientation orient) const;
                                       wxOrientation orient) const;
+#endif // wxUSE_SLIDER
+
     virtual wxSize GetProgressBarStep() const { return wxSize(16, 32); }
 
 #if wxUSE_MENUS
     virtual wxSize GetMenuBarItemSize(const wxSize& sizeText) const;
     virtual wxMenuGeometryInfo *GetMenuGeometry(wxWindow *win,
                                                 const wxMenu& menu) const;
     virtual wxSize GetProgressBarStep() const { return wxSize(16, 32); }
 
 #if wxUSE_MENUS
     virtual wxSize GetMenuBarItemSize(const wxSize& sizeText) const;
     virtual wxMenuGeometryInfo *GetMenuGeometry(wxWindow *win,
                                                 const wxMenu& menu) const;
-#endif
-protected:
-    // helper of DrawLabel() and DrawCheckOrRadioButton()
-    void DoDrawLabel(wxDC& dc,
-                     const wxString& label,
-                     const wxRect& rect,
-                     int flags = 0,
-                     int alignment = wxALIGN_LEFT | wxALIGN_TOP,
-                     int indexAccel = -1,
-                     wxRect *rectBounds = NULL,
-                     const wxPoint& focusOffset
-                        = wxPoint(FOCUS_RECT_OFFSET_X, FOCUS_RECT_OFFSET_Y));
-
-    // common part of DrawLabel() and DrawItem()
-    void DrawFocusRect(wxDC& dc, const wxRect& rect);
-
-    // DrawLabel() and DrawButtonLabel() helper
-    void DrawLabelShadow(wxDC& dc,
-                         const wxString& label,
-                         const wxRect& rect,
-                         int alignment,
-                         int indexAccel);
+#endif // wxUSE_MENUS
 
 
-    // DrawButtonBorder() helper
-    void DoDrawBackground(wxDC& dc,
-                          const wxColour& col,
-                          const wxRect& rect);
-
-    // DrawBorder() helpers: all of them shift and clip the DC after drawing
-    // the border
-
-    // just draw a rectangle with the given pen
-    void DrawRect(wxDC& dc, wxRect *rect, const wxPen& pen);
-
-    // draw the lower left part of rectangle
-    void DrawHalfRect(wxDC& dc, wxRect *rect, const wxPen& pen);
-
-    // draw the rectange using the first brush for the left and top sides and
-    // the second one for the bottom and right ones
-    void DrawShadedRect(wxDC& dc, wxRect *rect,
-                        const wxPen& pen1, const wxPen& pen2);
-
-    // draw the normal 3D border
-    void DrawRaisedBorder(wxDC& dc, wxRect *rect);
+protected:
+    // overridden wxStdRenderer methods
+    virtual void DrawFrameWithLabel(wxDC& dc,
+                                    const wxString& label,
+                                    const wxRect& rectFrame,
+                                    const wxRect& rectText,
+                                    int flags,
+                                    int alignment,
+                                    int indexAccel);
+
+    virtual void DrawCheckItemBitmap(wxDC& dc,
+                                     const wxBitmap& bitmap,
+                                     const wxRect& rect,
+                                     int flags);
 
 
-    // draw the sunken 3D border
-    void DrawSunkenBorder(wxDC& dc, wxRect *rect);
 
     // draw the border used for scrollbar arrows
 
     // draw the border used for scrollbar arrows
-    void DrawArrowBorder(wxDC& dc, wxRect *rect, bool isPressed = FALSE);
+    void DrawArrowBorder(wxDC& dc, wxRect *rect, bool isPressed = false);
 
     // public DrawArrow()s helper
     void DrawArrow(wxDC& dc, const wxRect& rect,
 
     // public DrawArrow()s helper
     void DrawArrow(wxDC& dc, const wxRect& rect,
-                   wxArrowDirection arrowDir, wxArrowStyle arrowStyle);
+                   ArrowDirection arrowDir, ArrowStyle arrowStyle);
 
     // DrawArrowButton is used by DrawScrollbar and DrawComboButton
     void DrawArrowButton(wxDC& dc, const wxRect& rect,
 
     // DrawArrowButton is used by DrawScrollbar and DrawComboButton
     void DrawArrowButton(wxDC& dc, const wxRect& rect,
-                         wxArrowDirection arrowDir,
-                         wxArrowStyle arrowStyle);
-
-    // DrawCheckButton/DrawRadioButton helper
-    void DrawCheckOrRadioButton(wxDC& dc,
-                                const wxString& label,
-                                const wxBitmap& bitmap,
-                                const wxRect& rect,
-                                int flags,
-                                wxAlignment align,
-                                int indexAccel,
-                                wxCoord focusOffsetY);
+                         ArrowDirection arrowDir,
+                         ArrowStyle arrowStyle);
 
     // draw a normal or transposed line (useful for using the same code fo both
     // horizontal and vertical widgets)
     void DrawLine(wxDC& dc,
                   wxCoord x1, wxCoord y1,
                   wxCoord x2, wxCoord y2,
 
     // draw a normal or transposed line (useful for using the same code fo both
     // horizontal and vertical widgets)
     void DrawLine(wxDC& dc,
                   wxCoord x1, wxCoord y1,
                   wxCoord x2, wxCoord y2,
-                  bool transpose = FALSE)
+                  bool transpose = false)
     {
         if ( transpose )
             dc.DrawLine(y1, x1, y2, x2);
     {
         if ( transpose )
             dc.DrawLine(y1, x1, y2, x2);
@@ -389,25 +300,34 @@ protected:
 
     // get the standard check/radio button bitmap
     wxBitmap GetIndicator(IndicatorType indType, int flags);
 
     // get the standard check/radio button bitmap
     wxBitmap GetIndicator(IndicatorType indType, int flags);
-    wxBitmap GetCheckBitmap(int flags)
+    virtual wxBitmap GetCheckBitmap(int flags)
         { return GetIndicator(IndicatorType_Check, flags); }
         { return GetIndicator(IndicatorType_Check, flags); }
-    wxBitmap GetRadioBitmap(int flags)
+    virtual wxBitmap GetRadioBitmap(int flags)
         { return GetIndicator(IndicatorType_Radio, flags); }
 
         { return GetIndicator(IndicatorType_Radio, flags); }
 
-private:
-    const wxColourScheme *m_scheme;
+    virtual wxBitmap GetFrameButtonBitmap(FrameButtonType type);
 
 
+private:
     // the sizing parameters (TODO make them changeable)
     wxSize m_sizeScrollbarArrow;
 
     // the sizing parameters (TODO make them changeable)
     wxSize m_sizeScrollbarArrow;
 
-    // GDI objects we use for drawing
-    wxColour m_colDarkGrey,
-             m_colHighlight;
+    // the checked and unchecked bitmaps for DrawCheckItemBitmap()
+    wxBitmap m_bmpCheckBitmaps[IndicatorStatus_Max];
+
+    // the bitmaps returned by GetIndicator()
+    wxBitmap m_bmpIndicators[IndicatorType_Max]
+                            [IndicatorState_MaxMenu]
+                            [IndicatorStatus_Max];
 
 
-    wxPen m_penBlack,
-          m_penDarkGrey,
-          m_penLightGrey,
-          m_penHighlight;
+    // titlebar icons:
+    wxBitmap m_bmpFrameButtons[FrameButton_Max];
+
+    // standard defaults for the above bitmaps
+    static const char **ms_xpmChecked[IndicatorStatus_Max];
+    static const char **ms_xpmIndicators[IndicatorType_Max]
+                                        [IndicatorState_MaxMenu]
+                                        [IndicatorStatus_Max];
+    static const char **ms_xpmFrameButtons[FrameButton_Max];
 
     // first row is for the normal state, second - for the disabled
     wxBitmap m_bmpArrows[Arrow_StateMax][Arrow_Max];
 
     // first row is for the normal state, second - for the disabled
     wxBitmap m_bmpArrows[Arrow_StateMax][Arrow_Max];
@@ -421,34 +341,33 @@ private:
 class wxWin32InputHandler : public wxInputHandler
 {
 public:
 class wxWin32InputHandler : public wxInputHandler
 {
 public:
-    wxWin32InputHandler(wxWin32Renderer *renderer);
+    wxWin32InputHandler() { }
 
 
-    virtual bool HandleKey(wxControl *control,
+    virtual bool HandleKey(wxInputConsumer *control,
                            const wxKeyEvent& event,
                            bool pressed);
                            const wxKeyEvent& event,
                            bool pressed);
-    virtual bool HandleMouse(wxControl *control,
+    virtual bool HandleMouse(wxInputConsumer *control,
                              const wxMouseEvent& event);
                              const wxMouseEvent& event);
-
-protected:
-    wxWin32Renderer *m_renderer;
 };
 
 };
 
+#if wxUSE_SCROLLBAR
 class wxWin32ScrollBarInputHandler : public wxStdScrollBarInputHandler
 {
 public:
 class wxWin32ScrollBarInputHandler : public wxStdScrollBarInputHandler
 {
 public:
-    wxWin32ScrollBarInputHandler(wxWin32Renderer *renderer,
+    wxWin32ScrollBarInputHandler(wxRenderer *renderer,
                                  wxInputHandler *handler);
 
                                  wxInputHandler *handler);
 
-    virtual bool HandleMouse(wxControl *control, const wxMouseEvent& event);
-    virtual bool HandleMouseMove(wxControl *control, const wxMouseEvent& event);
+    virtual bool HandleMouse(wxInputConsumer *control,
+                             const wxMouseEvent& event);
+    virtual bool HandleMouseMove(wxInputConsumer *control,
+                                 const wxMouseEvent& event);
 
     virtual bool OnScrollTimer(wxScrollBar *scrollbar,
                                const wxControlAction& action);
 
 protected:
 
     virtual bool OnScrollTimer(wxScrollBar *scrollbar,
                                const wxControlAction& action);
 
 protected:
-    virtual bool IsAllowedButton(int button) { return button == 1; }
-
-    virtual void Highlight(wxScrollBar *scrollbar, bool doIt)
+    virtual void Highlight(wxScrollBar * WXUNUSED(scrollbar),
+                           bool WXUNUSED(doIt))
     {
         // we don't highlight anything
     }
     {
         // we don't highlight anything
     }
@@ -463,28 +382,78 @@ protected:
     // we remember the interval of the timer to be able to restart it
     int m_interval;
 };
     // we remember the interval of the timer to be able to restart it
     int m_interval;
 };
+#endif // wxUSE_SCROLLBAR
 
 
-class wxWin32CheckboxInputHandler : public wxStdCheckboxInputHandler
+#if wxUSE_CHECKBOX
+class wxWin32CheckboxInputHandler : public wxStdInputHandler
 {
 public:
     wxWin32CheckboxInputHandler(wxInputHandler *handler)
 {
 public:
     wxWin32CheckboxInputHandler(wxInputHandler *handler)
-        : wxStdCheckboxInputHandler(handler) { }
+        : wxStdInputHandler(handler) { }
 
 
-    virtual bool HandleKey(wxControl *control,
+    virtual bool HandleKey(wxInputConsumer *control,
                            const wxKeyEvent& event,
                            bool pressed);
 };
                            const wxKeyEvent& event,
                            bool pressed);
 };
+#endif // wxUSE_CHECKBOX
 
 
-class wxWin32TextCtrlInputHandler : public wxStdTextCtrlInputHandler
+#if wxUSE_TEXTCTRL
+class wxWin32TextCtrlInputHandler : public wxStdInputHandler
 {
 public:
     wxWin32TextCtrlInputHandler(wxInputHandler *handler)
 {
 public:
     wxWin32TextCtrlInputHandler(wxInputHandler *handler)
-        : wxStdTextCtrlInputHandler(handler) { }
+        : wxStdInputHandler(handler) { }
 
 
-    virtual bool HandleKey(wxControl *control,
+    virtual bool HandleKey(wxInputConsumer *control,
                            const wxKeyEvent& event,
                            bool pressed);
 };
                            const wxKeyEvent& event,
                            bool pressed);
 };
+#endif // wxUSE_TEXTCTRL
+
+class wxWin32StatusBarInputHandler : public wxStdInputHandler
+{
+public:
+    wxWin32StatusBarInputHandler(wxInputHandler *handler);
+
+    virtual bool HandleMouse(wxInputConsumer *consumer,
+                             const wxMouseEvent& event);
+
+    virtual bool HandleMouseMove(wxInputConsumer *consumer,
+                                 const wxMouseEvent& event);
+
+protected:
+    // is the given point over the statusbar grip?
+    bool IsOnGrip(wxWindow *statbar, const wxPoint& pt) const;
+
+private:
+    // the cursor we had replaced with the resize one
+    wxCursor m_cursorOld;
+
+    // was the mouse over the grip last time we checked?
+    bool m_isOnGrip;
+};
+
+class wxWin32SystemMenuEvtHandler;
+
+class wxWin32FrameInputHandler : public wxStdInputHandler
+{
+public:
+    wxWin32FrameInputHandler(wxInputHandler *handler);
+    virtual ~wxWin32FrameInputHandler();
+
+    virtual bool HandleMouse(wxInputConsumer *control,
+                             const wxMouseEvent& event);
+
+    virtual bool HandleActivation(wxInputConsumer *consumer, bool activated);
+
+#if wxUSE_MENUS
+    void PopupSystemMenu(wxTopLevelWindow *window) const;
+#endif // wxUSE_MENUS
+
+private:
+    // was the mouse over the grip last time we checked?
+    wxWin32SystemMenuEvtHandler *m_menuHandler;
+};
 
 // ----------------------------------------------------------------------------
 // wxWin32ColourScheme: uses (default) Win32 colours
 
 // ----------------------------------------------------------------------------
 // wxWin32ColourScheme: uses (default) Win32 colours
@@ -497,11 +466,23 @@ public:
     virtual wxColour GetBackground(wxWindow *win) const;
 };
 
     virtual wxColour GetBackground(wxWindow *win) const;
 };
 
+// ----------------------------------------------------------------------------
+// wxWin32ArtProvider
+// ----------------------------------------------------------------------------
+
+class wxWin32ArtProvider : public wxArtProvider
+{
+protected:
+    virtual wxBitmap CreateBitmap(const wxArtID& id,
+                                  const wxArtClient& client,
+                                  const wxSize& size);
+};
+
 // ----------------------------------------------------------------------------
 // wxWin32Theme
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 // wxWin32Theme
 // ----------------------------------------------------------------------------
 
-WX_DEFINE_ARRAY(wxInputHandler *, wxArrayHandlers);
+WX_DEFINE_ARRAY_PTR(wxInputHandler *, wxArrayHandlers);
 
 class wxWin32Theme : public wxTheme
 {
 
 class wxWin32Theme : public wxTheme
 {
@@ -509,23 +490,22 @@ public:
     wxWin32Theme();
     virtual ~wxWin32Theme();
 
     wxWin32Theme();
     virtual ~wxWin32Theme();
 
-    virtual wxRenderer *GetRenderer() { return m_renderer; }
-    virtual wxInputHandler *GetInputHandler(const wxString& control);
+    virtual wxRenderer *GetRenderer();
+    virtual wxArtProvider *GetArtProvider();
+    virtual wxInputHandler *GetInputHandler(const wxString& control,
+                                            wxInputConsumer *consumer);
     virtual wxColourScheme *GetColourScheme();
 
 private:
     virtual wxColourScheme *GetColourScheme();
 
 private:
-    // get the default input handler
-    wxInputHandler *GetDefaultInputHandler();
-
     wxWin32Renderer *m_renderer;
 
     wxWin32Renderer *m_renderer;
 
+    wxWin32ArtProvider *m_artProvider;
+
     // the names of the already created handlers and the handlers themselves
     // (these arrays are synchronized)
     wxSortedArrayString m_handlerNames;
     wxArrayHandlers m_handlers;
 
     // the names of the already created handlers and the handlers themselves
     // (these arrays are synchronized)
     wxSortedArrayString m_handlerNames;
     wxArrayHandlers m_handlers;
 
-    wxWin32InputHandler *m_handlerDefault;
-
     wxWin32ColourScheme *m_scheme;
 
     WX_DECLARE_THEME(win32)
     wxWin32ColourScheme *m_scheme;
 
     WX_DECLARE_THEME(win32)
@@ -535,6 +515,91 @@ private:
 // standard bitmaps
 // ----------------------------------------------------------------------------
 
 // standard bitmaps
 // ----------------------------------------------------------------------------
 
+// frame buttons bitmaps
+static const char *frame_button_close_xpm[] = {
+"12 10 2 1",
+"         c None",
+"X        c black",
+"            ",
+"  XX    XX  ",
+"   XX  XX   ",
+"    XXXX    ",
+"     XX     ",
+"    XXXX    ",
+"   XX  XX   ",
+"  XX    XX  ",
+"            ",
+"            "};
+
+static const char *frame_button_help_xpm[] = {
+"12 10 2 1",
+"         c None",
+"X        c #000000",
+"    XXXX    ",
+"   XX  XX   ",
+"   XX  XX   ",
+"      XX    ",
+"     XX     ",
+"     XX     ",
+"            ",
+"     XX     ",
+"     XX     ",
+"            "};
+
+static const char *frame_button_maximize_xpm[] = {
+"12 10 2 1",
+"         c None",
+"X        c #000000",
+" XXXXXXXXX  ",
+" XXXXXXXXX  ",
+" X       X  ",
+" X       X  ",
+" X       X  ",
+" X       X  ",
+" X       X  ",
+" X       X  ",
+" XXXXXXXXX  ",
+"            "};
+
+static const char *frame_button_minimize_xpm[] = {
+"12 10 2 1",
+"         c None",
+"X        c #000000",
+"            ",
+"            ",
+"            ",
+"            ",
+"            ",
+"            ",
+"            ",
+"  XXXXXX    ",
+"  XXXXXX    ",
+"            "};
+
+static const char *frame_button_restore_xpm[] = {
+"12 10 2 1",
+"         c None",
+"X        c #000000",
+"   XXXXXX   ",
+"   XXXXXX   ",
+"   X    X   ",
+" XXXXXX X   ",
+" XXXXXX X   ",
+" X    XXX   ",
+" X    X     ",
+" X    X     ",
+" XXXXXX     ",
+"            "};
+
+const char **wxWin32Renderer::ms_xpmFrameButtons[FrameButton_Max] =
+{
+    frame_button_close_xpm,
+    frame_button_minimize_xpm,
+    frame_button_maximize_xpm,
+    frame_button_restore_xpm,
+    frame_button_help_xpm,
+};
+
 // menu bitmaps
 
 static const char *checked_menu_xpm[] = {
 // menu bitmaps
 
 static const char *checked_menu_xpm[] = {
@@ -768,6 +833,54 @@ static const char *unchecked_item_xpm[] = {
 "wwwwwwwwwwwww"
 };
 
 "wwwwwwwwwwwww"
 };
 
+static const char *undetermined_xpm[] = {
+/* columns rows colors chars-per-pixel */
+"13 13 5 1",
+"A c #030303",
+"B c #838383",
+"C c #C3C3C3",
+"D c #FBFBFB",
+"E c #DBDBDB",
+/* pixels */
+"BBBBBBBBBBBBD",
+"BAAAAAAAAAAED",
+"BACDCDCDCDCED",
+"BADCDCDCDBDED",
+"BACDCDCDBBCED",
+"BADBDCEBBBDED",
+"BACBBDBBBDCED",
+"BADBBBBBDCDED",
+"BACDBBBDCDCED",
+"BADCDBDCDCDED",
+"BACDCDCDCDCED",
+"BEEEEEEEEEEED",
+"DDDDDDDDDDDDD"
+};
+
+static const char *pressed_undetermined_xpm[] = {
+/* columns rows colors chars-per-pixel */
+"13 13 5 1",
+"A c #040404",
+"B c #848484",
+"C c #C4C4C4",
+"D c #FCFCFC",
+"E c #DCDCDC",
+/* pixels */
+"BBBBBBBBBBBBD",
+"BAAAAAAAAAAED",
+"BACCCCCCCCCCD",
+"BACCCCCCCACED",
+"BACCCCCCAACED",
+"BACACCCAAACED",
+"BACAACAAACCED",
+"BACAAAAACCCED",
+"BACCAAACCCCCD",
+"BACCCACCCCCED",
+"BACCCCCCCCCED",
+"BEEEEEEEEEEED",
+"DDDDDDDDDDDDD"
+};
+
 static const char *checked_radio_xpm[] = {
 /* columns rows colors chars-per-pixel */
 "12 12 6 1",
 static const char *checked_radio_xpm[] = {
 /* columns rows colors chars-per-pixel */
 "12 12 6 1",
@@ -888,49 +1001,56 @@ static const char *pressed_unchecked_radio_xpm[] = {
 "    hhhh    "
 };
 
 "    hhhh    "
 };
 
-static const char **
-    bmpIndicators[IndicatorType_Max][IndicatorState_Max][IndicatorStatus_Max] =
+const char **wxWin32Renderer::ms_xpmIndicators[IndicatorType_Max]
+                                              [IndicatorState_MaxMenu]
+                                              [IndicatorStatus_Max] =
 {
     // checkboxes first
     {
         // normal state
 {
     // checkboxes first
     {
         // normal state
-        { checked_xpm, unchecked_xpm },
+        { checked_xpm, unchecked_xpm, undetermined_xpm },
 
         // pressed state
 
         // pressed state
-        { pressed_checked_xpm, pressed_unchecked_xpm },
+        { pressed_checked_xpm, pressed_unchecked_xpm, pressed_undetermined_xpm },
 
         // disabled state
 
         // disabled state
-        { pressed_disabled_checked_xpm, pressed_unchecked_xpm },
+        { pressed_disabled_checked_xpm, pressed_unchecked_xpm, pressed_disabled_checked_xpm },
     },
 
     // radio
     {
         // normal state
     },
 
     // radio
     {
         // normal state
-        { checked_radio_xpm, unchecked_radio_xpm },
+        { checked_radio_xpm, unchecked_radio_xpm, NULL },
 
         // pressed state
 
         // pressed state
-        { pressed_checked_radio_xpm, pressed_unchecked_radio_xpm },
+        { pressed_checked_radio_xpm, pressed_unchecked_radio_xpm, NULL },
 
         // disabled state
 
         // disabled state
-        { pressed_disabled_checked_radio_xpm, pressed_unchecked_radio_xpm },
+        { pressed_disabled_checked_radio_xpm, pressed_unchecked_radio_xpm, NULL },
     },
 
     // menu
     {
         // normal state
     },
 
     // menu
     {
         // normal state
-        { checked_menu_xpm, NULL },
+        { checked_menu_xpm, NULL, NULL },
 
         // selected state
 
         // selected state
-        { selected_checked_menu_xpm, NULL },
+        { selected_checked_menu_xpm, NULL, NULL },
 
         // disabled state
 
         // disabled state
-        { disabled_checked_menu_xpm, NULL },
+        { disabled_checked_menu_xpm, NULL, NULL },
 
         // disabled selected state
 
         // disabled selected state
-        { selected_disabled_checked_menu_xpm, NULL },
+        { selected_disabled_checked_menu_xpm, NULL, NULL },
     }
 };
 
     }
 };
 
+const char **wxWin32Renderer::ms_xpmChecked[IndicatorStatus_Max] =
+{
+    checked_item_xpm,
+    unchecked_item_xpm
+};
+
 // ============================================================================
 // implementation
 // ============================================================================
 // ============================================================================
 // implementation
 // ============================================================================
@@ -943,84 +1063,95 @@ WX_IMPLEMENT_THEME(wxWin32Theme, win32, wxTRANSLATE("Win32 theme"));
 
 wxWin32Theme::wxWin32Theme()
 {
 
 wxWin32Theme::wxWin32Theme()
 {
-    m_scheme = new wxWin32ColourScheme;
-    m_renderer = new wxWin32Renderer(m_scheme);
-    m_handlerDefault = NULL;
+    m_scheme = NULL;
+    m_renderer = NULL;
+    m_artProvider = NULL;
 }
 
 wxWin32Theme::~wxWin32Theme()
 {
 }
 
 wxWin32Theme::~wxWin32Theme()
 {
-    size_t count = m_handlers.GetCount();
-    for ( size_t n = 0; n < count; n++ )
+    delete m_renderer;
+    delete m_scheme;
+    delete m_artProvider;
+}
+
+wxRenderer *wxWin32Theme::GetRenderer()
+{
+    if ( !m_renderer )
     {
     {
-        if ( m_handlers[n] != m_handlerDefault )
-            delete m_handlers[n];
+        m_renderer = new wxWin32Renderer(GetColourScheme());
     }
 
     }
 
-    delete m_handlerDefault;
-
-    delete m_renderer;
-    delete m_scheme;
+    return m_renderer;
 }
 
 }
 
-wxInputHandler *wxWin32Theme::GetDefaultInputHandler()
+wxArtProvider *wxWin32Theme::GetArtProvider()
 {
 {
-    if ( !m_handlerDefault )
+    if ( !m_artProvider )
     {
     {
-        m_handlerDefault = new wxWin32InputHandler(m_renderer);
+        m_artProvider = new wxWin32ArtProvider;
     }
 
     }
 
-    return m_handlerDefault;
+    return m_artProvider;
 }
 
 }
 
-wxInputHandler *wxWin32Theme::GetInputHandler(const wxString& control)
+wxInputHandler *
+wxWin32Theme::GetInputHandler(const wxString& control,
+                              wxInputConsumer *consumer)
 {
 {
-    wxInputHandler *handler;
+    wxInputHandler *handler = NULL;
     int n = m_handlerNames.Index(control);
     if ( n == wxNOT_FOUND )
     {
     int n = m_handlerNames.Index(control);
     if ( n == wxNOT_FOUND )
     {
+        static wxWin32InputHandler s_handlerDef;
+
+        wxInputHandler * const
+          handlerStd = consumer->DoGetStdInputHandler(&s_handlerDef);
+
         // create a new handler
         // create a new handler
-        if ( control == wxINP_HANDLER_SCROLLBAR )
-            handler = new wxWin32ScrollBarInputHandler(m_renderer,
-                                                       GetDefaultInputHandler());
-#if wxUSE_BUTTON
-        else if ( control == wxINP_HANDLER_BUTTON )
-            handler = new wxStdButtonInputHandler(GetDefaultInputHandler());
-#endif // wxUSE_BUTTON
+        if ( control == wxINP_HANDLER_TOPLEVEL )
+        {
+            static wxWin32FrameInputHandler s_handler(handlerStd);
+
+            handler = &s_handler;
+        }
 #if wxUSE_CHECKBOX
         else if ( control == wxINP_HANDLER_CHECKBOX )
 #if wxUSE_CHECKBOX
         else if ( control == wxINP_HANDLER_CHECKBOX )
-            handler = new wxWin32CheckboxInputHandler(GetDefaultInputHandler());
+        {
+            static wxWin32CheckboxInputHandler s_handler(handlerStd);
+
+            handler = &s_handler;
+        }
 #endif // wxUSE_CHECKBOX
 #endif // wxUSE_CHECKBOX
-#if wxUSE_COMBOBOX
-        else if ( control == wxINP_HANDLER_COMBOBOX )
-            handler = new wxStdComboBoxInputHandler(GetDefaultInputHandler());
-#endif // wxUSE_COMBOBOX
-#if wxUSE_LISTBOX
-        else if ( control == wxINP_HANDLER_LISTBOX )
-            handler = new wxStdListboxInputHandler(GetDefaultInputHandler());
-#endif // wxUSE_LISTBOX
-#if wxUSE_CHECKLISTBOX
-        else if ( control == wxINP_HANDLER_CHECKLISTBOX )
-            handler = new wxStdCheckListboxInputHandler(GetDefaultInputHandler());
-#endif // wxUSE_CHECKLISTBOX
+#if wxUSE_SCROLLBAR
+        else if ( control == wxINP_HANDLER_SCROLLBAR )
+        {
+            static wxWin32ScrollBarInputHandler
+                s_handler(GetRenderer(), handlerStd);
+
+            handler = &s_handler;
+        }
+#endif // wxUSE_SCROLLBAR
+#if wxUSE_STATUSBAR
+        else if ( control == wxINP_HANDLER_STATUSBAR )
+        {
+            static wxWin32StatusBarInputHandler s_handler(handlerStd);
+
+            handler = &s_handler;
+        }
+#endif // wxUSE_STATUSBAR
 #if wxUSE_TEXTCTRL
         else if ( control == wxINP_HANDLER_TEXTCTRL )
 #if wxUSE_TEXTCTRL
         else if ( control == wxINP_HANDLER_TEXTCTRL )
-            handler = new wxWin32TextCtrlInputHandler(GetDefaultInputHandler());
+        {
+            static wxWin32TextCtrlInputHandler s_handler(handlerStd);
+
+            handler = &s_handler;
+        }
 #endif // wxUSE_TEXTCTRL
 #endif // wxUSE_TEXTCTRL
-#if wxUSE_SLIDER
-        else if ( control == wxINP_HANDLER_SLIDER )
-            handler = new wxStdSliderButtonInputHandler(GetDefaultInputHandler());
-#endif // wxUSE_SLIDER
-#if wxUSE_SPINBTN
-        else if ( control == wxINP_HANDLER_SPINBTN )
-            handler = new wxStdSpinButtonInputHandler(GetDefaultInputHandler());
-#endif // wxUSE_SPINBTN
-#if wxUSE_NOTEBOOK
-        else if ( control == wxINP_HANDLER_NOTEBOOK )
-            handler = new wxStdNotebookInputHandler(GetDefaultInputHandler());
-#endif // wxUSE_NOTEBOOK
-        else
-            handler = GetDefaultInputHandler();
+        else // no special handler for this control
+        {
+            handler = handlerStd;
+        }
 
         n = m_handlerNames.Add(control);
         m_handlers.Insert(handler, n);
 
         n = m_handlerNames.Add(control);
         m_handlers.Insert(handler, n);
@@ -1035,6 +1166,10 @@ wxInputHandler *wxWin32Theme::GetInputHandler(const wxString& control)
 
 wxColourScheme *wxWin32Theme::GetColourScheme()
 {
 
 wxColourScheme *wxWin32Theme::GetColourScheme()
 {
+    if ( !m_scheme )
+    {
+        m_scheme = new wxWin32ColourScheme;
+    }
     return m_scheme;
 }
 
     return m_scheme;
 }
 
@@ -1051,21 +1186,37 @@ wxColour wxWin32ColourScheme::GetBackground(wxWindow *win) const
         col = win->GetBackgroundColour();
     }
 
         col = win->GetBackgroundColour();
     }
 
-    if ( win->IsContainerWindow() )
+    if ( !win->ShouldInheritColours() )
     {
     {
+#if wxUSE_TEXTCTRL
         wxTextCtrl *text = wxDynamicCast(win, wxTextCtrl);
         wxTextCtrl *text = wxDynamicCast(win, wxTextCtrl);
-        if ( text )
+#endif // wxUSE_TEXTCTRL
+#if wxUSE_LISTBOX
+        wxListBox* listBox = wxDynamicCast(win, wxListBox);
+#endif // wxUSE_LISTBOX
+
+#if wxUSE_TEXTCTRL
+        if ( text
+#if wxUSE_LISTBOX
+         || listBox
+#endif
+          )
         {
         {
-            if ( !text->IsEnabled() ) // not IsEditable()
+            if ( !win->IsEnabled() ) // not IsEditable()
                 col = Get(CONTROL);
                 col = Get(CONTROL);
-            //else: execute code below
+            else
+            {
+                if ( !col.Ok() )
+                {
+                    // doesn't depend on the state
+                    col = Get(WINDOW);
+                }
+            }
         }
         }
+#endif // wxUSE_TEXTCTRL
 
 
-        if ( !col.Ok() )
-        {
-            // doesn't depend on the state
-            col = Get(WINDOW);
-        }
+        if (!col.Ok())
+            col = Get(CONTROL); // Most controls should be this colour, not WINDOW
     }
     else
     {
     }
     else
     {
@@ -1073,12 +1224,14 @@ wxColour wxWin32ColourScheme::GetBackground(wxWindow *win) const
 
         // the colour set by the user should be used for the normal state
         // and for the states for which we don't have any specific colours
 
         // the colour set by the user should be used for the normal state
         // and for the states for which we don't have any specific colours
-        if ( !col.Ok() || (flags != 0) )
+        if ( !col.Ok() || (flags & wxCONTROL_PRESSED) != 0 )
         {
         {
+#if wxUSE_SCROLLBAR
             if ( wxDynamicCast(win, wxScrollBar) )
                 col = Get(flags & wxCONTROL_PRESSED ? SCROLLBAR_PRESSED
                                                     : SCROLLBAR);
             else
             if ( wxDynamicCast(win, wxScrollBar) )
                 col = Get(flags & wxCONTROL_PRESSED ? SCROLLBAR_PRESSED
                                                     : SCROLLBAR);
             else
+#endif // wxUSE_SCROLLBAR
                 col = Get(CONTROL);
         }
     }
                 col = Get(CONTROL);
         }
     }
@@ -1090,6 +1243,48 @@ wxColour wxWin32ColourScheme::Get(wxWin32ColourScheme::StdColour col) const
 {
     switch ( col )
     {
 {
     switch ( col )
     {
+        // use the system colours under Windows
+#if defined(__WXMSW__)
+        case WINDOW:            return wxColour(GetSysColor(COLOR_WINDOW));
+
+        case CONTROL_PRESSED:
+        case CONTROL_CURRENT:
+        case CONTROL:           return wxColour(GetSysColor(COLOR_BTNFACE));
+
+        case CONTROL_TEXT:      return wxColour(GetSysColor(COLOR_BTNTEXT));
+
+#if defined(COLOR_3DLIGHT)
+        case SCROLLBAR:         return wxColour(GetSysColor(COLOR_3DLIGHT));
+#else
+        case SCROLLBAR:         return wxColour(0xe0e0e0);
+#endif
+        case SCROLLBAR_PRESSED: return wxColour(GetSysColor(COLOR_BTNTEXT));
+
+        case HIGHLIGHT:         return wxColour(GetSysColor(COLOR_HIGHLIGHT));
+        case HIGHLIGHT_TEXT:    return wxColour(GetSysColor(COLOR_HIGHLIGHTTEXT));
+
+#if defined(COLOR_3DDKSHADOW)
+        case SHADOW_DARK:       return wxColour(GetSysColor(COLOR_3DDKSHADOW));
+#else
+        case SHADOW_DARK:       return wxColour(GetSysColor(COLOR_3DHADOW));
+#endif
+
+        case CONTROL_TEXT_DISABLED:
+        case SHADOW_HIGHLIGHT:  return wxColour(GetSysColor(COLOR_BTNHIGHLIGHT));
+
+        case SHADOW_IN:         return wxColour(GetSysColor(COLOR_BTNFACE));
+
+        case CONTROL_TEXT_DISABLED_SHADOW:
+        case SHADOW_OUT:        return wxColour(GetSysColor(COLOR_BTNSHADOW));
+
+        case TITLEBAR:          return wxColour(GetSysColor(COLOR_INACTIVECAPTION));
+        case TITLEBAR_ACTIVE:   return wxColour(GetSysColor(COLOR_ACTIVECAPTION));
+        case TITLEBAR_TEXT:     return wxColour(GetSysColor(COLOR_INACTIVECAPTIONTEXT));
+        case TITLEBAR_ACTIVE_TEXT: return wxColour(GetSysColor(COLOR_CAPTIONTEXT));
+
+        case DESKTOP:           return wxColour(0x808000);
+#else // !__WXMSW__
+        // use the standard Windows colours elsewhere
         case WINDOW:            return *wxWHITE;
 
         case CONTROL_PRESSED:
         case WINDOW:            return *wxWHITE;
 
         case CONTROL_PRESSED:
@@ -1106,14 +1301,24 @@ wxColour wxWin32ColourScheme::Get(wxWin32ColourScheme::StdColour col) const
 
         case SHADOW_DARK:       return *wxBLACK;
 
 
         case SHADOW_DARK:       return *wxBLACK;
 
-        case CONTROL_TEXT_DISABLED:
-        case SHADOW_HIGHLIGHT:  return wxColour(0xe0e0e0);
+        case CONTROL_TEXT_DISABLED:return wxColour(0xe0e0e0);
+        case SHADOW_HIGHLIGHT:  return wxColour(0xffffff);
 
         case SHADOW_IN:         return wxColour(0xc0c0c0);
 
         case CONTROL_TEXT_DISABLED_SHADOW:
         case SHADOW_OUT:        return wxColour(0x7f7f7f);
 
 
         case SHADOW_IN:         return wxColour(0xc0c0c0);
 
         case CONTROL_TEXT_DISABLED_SHADOW:
         case SHADOW_OUT:        return wxColour(0x7f7f7f);
 
+        case TITLEBAR:          return wxColour(0xaeaaae);
+        case TITLEBAR_ACTIVE:   return wxColour(0x820300);
+        case TITLEBAR_TEXT:     return wxColour(0xc0c0c0);
+        case TITLEBAR_ACTIVE_TEXT:return *wxWHITE;
+
+        case DESKTOP:           return wxColour(0x808000);
+#endif // __WXMSW__
+
+        case GAUGE:             return Get(HIGHLIGHT);
+
         case MAX:
         default:
             wxFAIL_MSG(_T("invalid standard colour"));
         case MAX:
         default:
             wxFAIL_MSG(_T("invalid standard colour"));
@@ -1130,22 +1335,11 @@ wxColour wxWin32ColourScheme::Get(wxWin32ColourScheme::StdColour col) const
 // ----------------------------------------------------------------------------
 
 wxWin32Renderer::wxWin32Renderer(const wxColourScheme *scheme)
 // ----------------------------------------------------------------------------
 
 wxWin32Renderer::wxWin32Renderer(const wxColourScheme *scheme)
+               : wxStdRenderer(scheme)
 {
     // init data
 {
     // init data
-    m_scheme = scheme;
     m_sizeScrollbarArrow = wxSize(16, 16);
 
     m_sizeScrollbarArrow = wxSize(16, 16);
 
-    // init colours and pens
-    m_penBlack = wxPen(wxSCHEME_COLOUR(scheme, SHADOW_DARK), 0, wxSOLID);
-
-    m_colDarkGrey = wxSCHEME_COLOUR(scheme, SHADOW_OUT);
-    m_penDarkGrey = wxPen(m_colDarkGrey, 0, wxSOLID);
-
-    m_penLightGrey = wxPen(wxSCHEME_COLOUR(scheme, SHADOW_IN), 0, wxSOLID);
-
-    m_colHighlight = wxSCHEME_COLOUR(scheme, SHADOW_HIGHLIGHT);
-    m_penHighlight = wxPen(m_colHighlight, 0, wxSOLID);
-
     // init the arrow bitmaps
     static const size_t ARROW_WIDTH = 7;
     static const size_t ARROW_LENGTH = 4;
     // init the arrow bitmaps
     static const size_t ARROW_WIDTH = 7;
     static const size_t ARROW_LENGTH = 4;
@@ -1278,31 +1472,31 @@ wxWin32Renderer::wxWin32Renderer(const wxColourScheme *scheme)
 
         }
 
 
         }
 
-        // create the inversed bitmap but only for the right arrow as we only
+        // create the inverted bitmap but only for the right arrow as we only
         // use it for the menus
         if ( n == Arrow_Right )
         {
         // use it for the menus
         if ( n == Arrow_Right )
         {
-            m_bmpArrows[Arrow_Inversed][n].Create(w, h);
-            dcInverse.SelectObject(m_bmpArrows[Arrow_Inversed][n]);
+            m_bmpArrows[Arrow_Inverted][n].Create(w, h);
+            dcInverse.SelectObject(m_bmpArrows[Arrow_Inverted][n]);
             dcInverse.Clear();
             dcInverse.Blit(0, 0, w, h,
                           &dcNormal, 0, 0,
                           wxXOR);
             dcInverse.SelectObject(wxNullBitmap);
 
             dcInverse.Clear();
             dcInverse.Blit(0, 0, w, h,
                           &dcNormal, 0, 0,
                           wxXOR);
             dcInverse.SelectObject(wxNullBitmap);
 
-            mask = new wxMask(m_bmpArrows[Arrow_Inversed][n], *wxBLACK);
-            m_bmpArrows[Arrow_Inversed][n].SetMask(mask);
+            mask = new wxMask(m_bmpArrows[Arrow_Inverted][n], *wxBLACK);
+            m_bmpArrows[Arrow_Inverted][n].SetMask(mask);
 
 
-            m_bmpArrows[Arrow_InversedDisabled][n].Create(w, h);
-            dcInverse.SelectObject(m_bmpArrows[Arrow_InversedDisabled][n]);
+            m_bmpArrows[Arrow_InvertedDisabled][n].Create(w, h);
+            dcInverse.SelectObject(m_bmpArrows[Arrow_InvertedDisabled][n]);
             dcInverse.Clear();
             dcInverse.Blit(0, 0, w, h,
                           &dcDisabled, 0, 0,
                           wxXOR);
             dcInverse.SelectObject(wxNullBitmap);
 
             dcInverse.Clear();
             dcInverse.Blit(0, 0, w, h,
                           &dcDisabled, 0, 0,
                           wxXOR);
             dcInverse.SelectObject(wxNullBitmap);
 
-            mask = new wxMask(m_bmpArrows[Arrow_InversedDisabled][n], *wxBLACK);
-            m_bmpArrows[Arrow_InversedDisabled][n].SetMask(mask);
+            mask = new wxMask(m_bmpArrows[Arrow_InvertedDisabled][n], *wxBLACK);
+            m_bmpArrows[Arrow_InvertedDisabled][n].SetMask(mask);
         }
 
         dcNormal.SelectObject(wxNullBitmap);
         }
 
         dcNormal.SelectObject(wxNullBitmap);
@@ -1317,264 +1511,84 @@ wxWin32Renderer::wxWin32Renderer(const wxColourScheme *scheme)
     }
 }
 
     }
 }
 
+bool wxWin32Renderer::AreScrollbarsInsideBorder() const
+{
+    return true;
+}
+
 // ----------------------------------------------------------------------------
 // ----------------------------------------------------------------------------
-// border stuff
+// label
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 
-/*
-   The raised border in Win32 looks like this:
-
-   IIIIIIIIIIIIIIIIIIIIIIB
-   I                    GB
-   I                    GB  I = white       (HILIGHT)
-   I                    GB  H = light grey  (LIGHT)
-   I                    GB  G = dark grey   (SHADOI)
-   I                    GB  B = black       (DKSHADOI)
-   I                    GB  I = hIghlight (COLOR_3DHILIGHT)
-   I                    GB
-   IGGGGGGGGGGGGGGGGGGGGGB
-   BBBBBBBBBBBBBBBBBBBBBBB
-
-   The sunken border looks like this:
-
-   GGGGGGGGGGGGGGGGGGGGGGI
-   GBBBBBBBBBBBBBBBBBBBBHI
-   GB                   HI
-   GB                   HI
-   GB                   HI
-   GB                   HI
-   GB                   HI
-   GB                   HI
-   GHHHHHHHHHHHHHHHHHHHHHI
-   IIIIIIIIIIIIIIIIIIIIIII
-
-   The static border (used for the controls which don't get focus) is like
-   this:
-
-   GGGGGGGGGGGGGGGGGGGGGGW
-   G                     W
-   G                     W
-   G                     W
-   G                     W
-   G                     W
-   G                     W
-   G                     W
-   WWWWWWWWWWWWWWWWWWWWWWW
-
-   The most complicated is the double border:
-
-   HHHHHHHHHHHHHHHHHHHHHHB
-   HWWWWWWWWWWWWWWWWWWWWGB
-   HWHHHHHHHHHHHHHHHHHHHGB
-   HWH                 HGB
-   HWH                 HGB
-   HWH                 HGB
-   HWH                 HGB
-   HWHHHHHHHHHHHHHHHHHHHGB
-   HGGGGGGGGGGGGGGGGGGGGGB
-   BBBBBBBBBBBBBBBBBBBBBBB
-
-   And the simple border is, well, simple:
-
-   BBBBBBBBBBBBBBBBBBBBBBB
-   B                     B
-   B                     B
-   B                     B
-   B                     B
-   B                     B
-   B                     B
-   B                     B
-   B                     B
-   BBBBBBBBBBBBBBBBBBBBBBB
-*/
-
-void wxWin32Renderer::DrawRect(wxDC& dc, wxRect *rect, const wxPen& pen)
-{
-    // draw
-    dc.SetPen(pen);
-    dc.SetBrush(*wxTRANSPARENT_BRUSH);
-    dc.DrawRectangle(*rect);
-
-    // adjust the rect
-    rect->Inflate(-1);
-}
-
-void wxWin32Renderer::DrawHalfRect(wxDC& dc, wxRect *rect, const wxPen& pen)
-{
-    // draw the bottom and right sides
-    dc.SetPen(pen);
-    dc.DrawLine(rect->GetLeft(), rect->GetBottom(),
-                rect->GetRight() + 1, rect->GetBottom());
-    dc.DrawLine(rect->GetRight(), rect->GetTop(),
-                rect->GetRight(), rect->GetBottom());
-
-    // adjust the rect
-    rect->width--;
-    rect->height--;
-}
-
-void wxWin32Renderer::DrawShadedRect(wxDC& dc, wxRect *rect,
-                                     const wxPen& pen1, const wxPen& pen2)
-{
-    // draw the rectangle
-    dc.SetPen(pen1);
-    dc.DrawLine(rect->GetLeft(), rect->GetTop(),
-                rect->GetLeft(), rect->GetBottom());
-    dc.DrawLine(rect->GetLeft() + 1, rect->GetTop(),
-                rect->GetRight(), rect->GetTop());
-    dc.SetPen(pen2);
-    dc.DrawLine(rect->GetRight(), rect->GetTop(),
-                rect->GetRight(), rect->GetBottom());
-    dc.DrawLine(rect->GetLeft(), rect->GetBottom(),
-                rect->GetRight() + 1, rect->GetBottom());
-
-    // adjust the rect
-    rect->Inflate(-1);
-}
-
-void wxWin32Renderer::DrawRaisedBorder(wxDC& dc, wxRect *rect)
+void wxWin32Renderer::DrawLabel(wxDC& dc,
+                                const wxString& label,
+                                const wxRect& rect,
+                                int flags,
+                                int alignment,
+                                int indexAccel,
+                                wxRect *rectBounds)
 {
 {
-    DrawShadedRect(dc, rect, m_penHighlight, m_penBlack);
-    DrawShadedRect(dc, rect, m_penLightGrey, m_penDarkGrey);
-}
-
-void wxWin32Renderer::DrawSunkenBorder(wxDC& dc, wxRect *rect)
-{
-    DrawShadedRect(dc, rect, m_penDarkGrey, m_penHighlight);
-    DrawShadedRect(dc, rect, m_penBlack, m_penLightGrey);
+    // the underscores are not drawn for focused controls in wxMSW
+    if ( flags & wxCONTROL_FOCUSED )
+    {
+        indexAccel = -1;
+    }
+
+    if ( flags & wxCONTROL_DISABLED )
+    {
+        // the combination of wxCONTROL_SELECTED and wxCONTROL_DISABLED
+        // currently only can happen for a menu item and it seems that Windows
+        // doesn't draw the shadow in this case, so we don't do it neither
+        if ( flags & wxCONTROL_SELECTED )
+        {
+            // just make the label text greyed out
+            dc.SetTextForeground(m_penDarkGrey.GetColour());
+
+            flags &= ~wxCONTROL_DISABLED;
+        }
+    }
+
+    wxStdRenderer::DrawLabel(dc, label, rect, flags, alignment,
+                             indexAccel, rectBounds);
 }
 
 }
 
-void wxWin32Renderer::DrawArrowBorder(wxDC& dc, wxRect *rect, bool isPressed)
+void wxWin32Renderer::DrawFrameWithLabel(wxDC& dc,
+                                         const wxString& label,
+                                         const wxRect& rectFrame,
+                                         const wxRect& rectText,
+                                         int flags,
+                                         int alignment,
+                                         int indexAccel)
 {
 {
-    if ( isPressed )
+    wxString label2;
+    label2 << _T(' ') << label << _T(' ');
+    if ( indexAccel != -1 )
     {
     {
-        DrawRect(dc, rect, m_penDarkGrey);
+        // adjust it as we prepended a space
+        indexAccel++;
+    }
 
 
-        // the arrow is usually drawn inside border of width 2 and is offset by
-        // another pixel in both directions when it's pressed - as the border
-        // in this case is more narrow as well, we have to adjust rect like
-        // this:
-        rect->Inflate(-1);
-        rect->x++;
-        rect->y++;
-    }
-    else
-    {
-        DrawShadedRect(dc, rect, m_penLightGrey, m_penBlack);
-        DrawShadedRect(dc, rect, m_penHighlight, m_penDarkGrey);
-    }
+    wxStdRenderer::DrawFrameWithLabel(dc, label2, rectFrame, rectText,
+                                      flags, alignment, indexAccel);
 }
 
 }
 
-void wxWin32Renderer::DrawBorder(wxDC& dc,
-                                 wxBorder border,
-                                 const wxRect& rectTotal,
-                                 int WXUNUSED(flags),
-                                 wxRect *rectIn)
-{
-    int i;
-
-    wxRect rect = rectTotal;
-
-    switch ( border )
-    {
-        case wxBORDER_SUNKEN:
-            for ( i = 0; i < BORDER_THICKNESS / 2; i++ )
-            {
-                DrawSunkenBorder(dc, &rect);
-            }
-            break;
-
-        case wxBORDER_STATIC:
-            DrawShadedRect(dc, &rect, m_penDarkGrey, m_penHighlight);
-            break;
-
-        case wxBORDER_RAISED:
-            for ( i = 0; i < BORDER_THICKNESS / 2; i++ )
-            {
-                DrawRaisedBorder(dc, &rect);
-            }
-            break;
-
-        case wxBORDER_DOUBLE:
-            DrawArrowBorder(dc, &rect);
-            DrawRect(dc, &rect, m_penLightGrey);
-            break;
-
-        case wxBORDER_SIMPLE:
-            for ( i = 0; i < BORDER_THICKNESS / 2; i++ )
-            {
-                DrawRect(dc, &rect, m_penBlack);
-            }
-            break;
-
-        default:
-            wxFAIL_MSG(_T("unknown border type"));
-            // fall through
-
-        case wxBORDER_DEFAULT:
-        case wxBORDER_NONE:
-            break;
-    }
-
-    if ( rectIn )
-        *rectIn = rect;
-}
-
-wxRect wxWin32Renderer::GetBorderDimensions(wxBorder border) const
+void wxWin32Renderer::DrawButtonLabel(wxDC& dc,
+                                      const wxString& label,
+                                      const wxBitmap& image,
+                                      const wxRect& rect,
+                                      int flags,
+                                      int alignment,
+                                      int indexAccel,
+                                      wxRect *rectBounds)
 {
 {
-    wxCoord width;
-    switch ( border )
+    // the underscores are not drawn for focused controls in wxMSW
+    if ( flags & wxCONTROL_PRESSED )
     {
     {
-        case wxBORDER_RAISED:
-        case wxBORDER_SUNKEN:
-            width = BORDER_THICKNESS;
-            break;
-
-        case wxBORDER_SIMPLE:
-        case wxBORDER_STATIC:
-            width = 1;
-            break;
-
-        case wxBORDER_DOUBLE:
-            width = 3;
-            break;
-
-        default:
-            wxFAIL_MSG(_T("unknown border type"));
-            // fall through
-
-        case wxBORDER_DEFAULT:
-        case wxBORDER_NONE:
-            width = 0;
-            break;
+        indexAccel = -1;
     }
 
     }
 
-    wxRect rect;
-    rect.x =
-    rect.y =
-    rect.width =
-    rect.height = width;
-
-    return rect;
-}
-
-bool wxWin32Renderer::AreScrollbarsInsideBorder() const
-{
-    return TRUE;
-}
-
-// ----------------------------------------------------------------------------
-// borders
-// ----------------------------------------------------------------------------
-
-void wxWin32Renderer::DrawTextBorder(wxDC& dc,
-                                     wxBorder border,
-                                     const wxRect& rect,
-                                     int flags,
-                                     wxRect *rectIn)
-{
-    // text controls are not special under windows
-    DrawBorder(dc, border, rect, flags, rectIn);
+    wxStdRenderer::DrawButtonLabel(dc, label, image, rect, flags, alignment,
+                                   indexAccel, rectBounds);
 }
 
 void wxWin32Renderer::DrawButtonBorder(wxDC& dc,
 }
 
 void wxWin32Renderer::DrawButtonBorder(wxDC& dc,
@@ -1584,476 +1598,160 @@ void wxWin32Renderer::DrawButtonBorder(wxDC& dc,
 {
     wxRect rect = rectTotal;
 
 {
     wxRect rect = rectTotal;
 
+    wxPen penOut(*wxBLACK);
     if ( flags & wxCONTROL_PRESSED )
     {
         // button pressed: draw a double border around it
     if ( flags & wxCONTROL_PRESSED )
     {
         // button pressed: draw a double border around it
-        DrawRect(dc, &rect, m_penBlack);
+        DrawRect(dc, &rect, penOut);
         DrawRect(dc, &rect, m_penDarkGrey);
     }
         DrawRect(dc, &rect, m_penDarkGrey);
     }
-    else
+    else // button not pressed
     {
     {
-        // button not pressed
-
         if ( flags & (wxCONTROL_FOCUSED | wxCONTROL_ISDEFAULT) )
         {
         if ( flags & (wxCONTROL_FOCUSED | wxCONTROL_ISDEFAULT) )
         {
-            // button either default or focused (or both): add an extra border around it
-            DrawRect(dc, &rect, m_penBlack);
+            // button either default or focused (or both): add an extra border
+            // around it
+            DrawRect(dc, &rect, penOut);
         }
 
         }
 
-        // now draw a normal button
-        DrawShadedRect(dc, &rect, m_penHighlight, m_penBlack);
-        DrawHalfRect(dc, &rect, m_penDarkGrey);
+        // now draw a normal button border
+        DrawRaisedBorder(dc, &rect);
     }
 
     if ( rectIn )
     }
 
     if ( rectIn )
-    {
         *rectIn = rect;
         *rectIn = rect;
-    }
 }
 
 // ----------------------------------------------------------------------------
 }
 
 // ----------------------------------------------------------------------------
-// lines and frame
+// (check)listbox items
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 
-void wxWin32Renderer::DrawHorizontalLine(wxDC& dc,
-                                         wxCoord y, wxCoord x1, wxCoord x2)
-{
-    dc.SetPen(m_penDarkGrey);
-    dc.DrawLine(x1, y, x2 + 1, y);
-    dc.SetPen(m_penHighlight);
-    y++;
-    dc.DrawLine(x1, y, x2 + 1, y);
-}
-
-void wxWin32Renderer::DrawVerticalLine(wxDC& dc,
-                                       wxCoord x, wxCoord y1, wxCoord y2)
-{
-    dc.SetPen(m_penDarkGrey);
-    dc.DrawLine(x, y1, x, y2 + 1);
-    dc.SetPen(m_penHighlight);
-    x++;
-    dc.DrawLine(x, y1, x, y2 + 1);
-}
-
-void wxWin32Renderer::DrawFrame(wxDC& dc,
-                                const wxString& label,
-                                const wxRect& rect,
-                                int flags,
-                                int alignment,
-                                int indexAccel)
+void wxWin32Renderer::DrawCheckItemBitmap(wxDC& dc,
+                                          const wxBitmap& bitmap,
+                                          const wxRect& rect,
+                                          int flags)
 {
 {
-    wxCoord height = 0; // of the label
-    wxRect rectFrame = rect;
-    if ( !label.empty() )
+    wxBitmap bmp;
+    if ( bitmap.Ok() )
     {
     {
-        // the text should touch the top border of the rect, so the frame
-        // itself should be lower
-        dc.GetTextExtent(label, NULL, &height);
-        rectFrame.y += height / 2;
-        rectFrame.height -= height / 2;
-
-        // we have to draw each part of the frame individually as we can't
-        // erase the background beyond the label as it might contain some
-        // pixmap already, so drawing everything and then overwriting part of
-        // the frame with label doesn't work
-
-        // TODO: the +5 and space insertion should be customizable
-
-        wxRect rectText;
-        rectText.x = rectFrame.x + 5;
-        rectText.y = rect.y;
-        rectText.width = rectFrame.width - 7; // +2 border width
-        rectText.height = height;
+        bmp = bitmap;
+    }
+    else // use default bitmap
+    {
+        IndicatorStatus i = flags & wxCONTROL_CHECKED
+                                ? IndicatorStatus_Checked
+                                : IndicatorStatus_Unchecked;
 
 
-        wxString label2;
-        label2 << _T(' ') << label << _T(' ');
-        if ( indexAccel != -1 )
+        if ( !m_bmpCheckBitmaps[i].Ok() )
         {
         {
-            // adjust it as we prepended a space
-            indexAccel++;
+            m_bmpCheckBitmaps[i] = wxBitmap(ms_xpmChecked[i]);
         }
 
         }
 
-        wxRect rectLabel;
-        DrawLabel(dc, label2, rectText, flags, alignment, indexAccel, &rectLabel);
-
-        StandardDrawFrame(dc, rectFrame, rectLabel);
-    }
-    else
-    {
-        // just draw the complete frame
-        DrawShadedRect(dc, &rectFrame, m_penDarkGrey, m_penHighlight);
-        DrawShadedRect(dc, &rectFrame, m_penHighlight, m_penDarkGrey);
+        bmp = m_bmpCheckBitmaps[i];
     }
     }
+
+    dc.DrawBitmap(bmp, rect.x, rect.y + (rect.height - bmp.GetHeight()) / 2 - 1,
+                  true /* use mask */);
 }
 
 // ----------------------------------------------------------------------------
 }
 
 // ----------------------------------------------------------------------------
-// label
+// check/radio buttons
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 
-void wxWin32Renderer::DrawFocusRect(wxDC& dc, const wxRect& rect)
-{
-    // VZ: this doesn't work under Windows, the dotted pen has dots of 3
-    //     pixels each while we really need dots here... PS_ALTERNATE might
-    //     work, but it is for NT 5 only
-#if 0
-    DrawRect(dc, &rect, wxPen(*wxBLACK, 0, wxDOT));
-#else
-    // draw the pixels manually: note that to behave in the same manner as
-    // DrawRect(), we must exclude the bottom and right borders from the
-    // rectangle
-    wxCoord x1 = rect.GetLeft(),
-            y1 = rect.GetTop(),
-            x2 = rect.GetRight(),
-            y2 = rect.GetBottom();
-
-    dc.SetPen(wxPen(*wxBLACK, 0, wxSOLID));
-
-    // this seems to be closer than what Windows does than wxINVERT although
-    // I'm still not sure if it's correct
-    dc.SetLogicalFunction(wxAND_REVERSE);
-
-    wxCoord z;
-    for ( z = x1 + 1; z < x2; z += 2 )
-        dc.DrawPoint(z, rect.GetTop());
-
-    wxCoord shift = z == x2 ? 0 : 1;
-    for ( z = y1 + shift; z < y2; z += 2 )
-        dc.DrawPoint(x2, z);
-
-    shift = z == y2 ? 0 : 1;
-    for ( z = x2 - shift; z > x1; z -= 2 )
-        dc.DrawPoint(z, y2);
-
-    shift = z == x1 ? 0 : 1;
-    for ( z = y2 - shift; z > y1; z -= 2 )
-        dc.DrawPoint(x1, z);
-
-    dc.SetLogicalFunction(wxCOPY);
-#endif // 0/1
-}
-
-void wxWin32Renderer::DrawLabelShadow(wxDC& dc,
-                                      const wxString& label,
-                                      const wxRect& rect,
-                                      int alignment,
-                                      int indexAccel)
-{
-    // draw shadow of the text
-    dc.SetTextForeground(m_colHighlight);
-    wxRect rectShadow = rect;
-    rectShadow.x++;
-    rectShadow.y++;
-    dc.DrawLabel(label, rectShadow, alignment, indexAccel);
-
-    // make the text grey
-    dc.SetTextForeground(m_colDarkGrey);
-}
-
-void wxWin32Renderer::DrawLabel(wxDC& dc,
-                                const wxString& label,
-                                const wxRect& rect,
-                                int flags,
-                                int alignment,
-                                int indexAccel,
-                                wxRect *rectBounds)
-{
-    DoDrawLabel(dc, label, rect, flags, alignment, indexAccel, rectBounds);
-}
-
-void wxWin32Renderer::DoDrawLabel(wxDC& dc,
-                                  const wxString& label,
-                                  const wxRect& rect,
-                                  int flags,
-                                  int alignment,
-                                  int indexAccel,
-                                  wxRect *rectBounds,
-                                  const wxPoint& focusOffset)
+wxBitmap wxWin32Renderer::GetIndicator(IndicatorType indType, int flags)
 {
 {
-    // the underscores are not drawn for focused controls in wxMSW
-    if ( flags & wxCONTROL_FOCUSED )
-    {
-        indexAccel = -1;
-    }
-
-    if ( flags & wxCONTROL_DISABLED )
-    {
-        // the combination of wxCONTROL_SELECTED and wxCONTROL_DISABLED
-        // currently only can happen for a menu item and it seems that Windows
-        // doesn't draw the shadow in this case, so we don't do it neither
-        if ( flags & wxCONTROL_SELECTED )
-        {
-            // just make the label text greyed out
-            dc.SetTextForeground(m_colDarkGrey);
-        }
-        else // draw normal disabled label
-        {
-            DrawLabelShadow(dc, label, rect, alignment, indexAccel);
-        }
-    }
-
-    wxRect rectLabel;
-    dc.DrawLabel(label, wxNullBitmap, rect, alignment, indexAccel, &rectLabel);
-
-    if ( flags & wxCONTROL_DISABLED )
-    {
-        // restore the fg colour
-        dc.SetTextForeground(*wxBLACK);
-    }
+    IndicatorState indState;
+    IndicatorStatus indStatus;
+    GetIndicatorsFromFlags(flags, indState, indStatus);
 
 
-    if ( flags & wxCONTROL_FOCUSED )
+    wxBitmap& bmp = m_bmpIndicators[indType][indState][indStatus];
+    if ( !bmp.Ok() )
     {
     {
-        if ( focusOffset.x || focusOffset.y )
+        const char **xpm = ms_xpmIndicators[indType][indState][indStatus];
+        if ( xpm )
         {
         {
-            rectLabel.Inflate(focusOffset.x, focusOffset.y);
+            // create and cache it
+            bmp = wxBitmap(xpm);
         }
         }
-
-        DrawFocusRect(dc, rectLabel);
     }
 
     }
 
-    if ( rectBounds )
-        *rectBounds = rectLabel;
+    return bmp;
 }
 
 }
 
-void wxWin32Renderer::DrawButtonLabel(wxDC& dc,
-                                      const wxString& label,
-                                      const wxBitmap& image,
-                                      const wxRect& rect,
-                                      int flags,
-                                      int alignment,
-                                      int indexAccel,
-                                      wxRect *rectBounds)
+// ----------------------------------------------------------------------------
+// toolbar stuff
+// ----------------------------------------------------------------------------
+
+#if wxUSE_TOOLBAR
+void wxWin32Renderer::DrawToolBarButton(wxDC& dc,
+                                        const wxString& label,
+                                        const wxBitmap& bitmap,
+                                        const wxRect& rectOrig,
+                                        int flags,
+                                        long style,
+                                        int tbarStyle)
 {
 {
-    // the underscores are not drawn for focused controls in wxMSW
-    if ( flags & wxCONTROL_PRESSED )
+    if (style == wxTOOL_STYLE_BUTTON)
     {
     {
-        indexAccel = -1;
-    }
+        wxRect rect = rectOrig;
+        rect.Deflate(BORDER_THICKNESS);
 
 
-    wxRect rectLabel = rect;
-    if ( !label.empty() )
-    {
-        // shift the label if a button is pressed
         if ( flags & wxCONTROL_PRESSED )
         {
         if ( flags & wxCONTROL_PRESSED )
         {
-            rectLabel.x++;
-            rectLabel.y++;
+            DrawBorder(dc, wxBORDER_SUNKEN, rect, flags);
         }
         }
-
-        if ( flags & wxCONTROL_DISABLED )
+        else if ( flags & wxCONTROL_CURRENT )
         {
         {
-            DrawLabelShadow(dc, label, rectLabel, alignment, indexAccel);
+            DrawBorder(dc, wxBORDER_RAISED, rect, flags);
         }
 
         }
 
-        // leave enough space for the focus rectangle
-        if ( flags & wxCONTROL_FOCUSED )
+        if(tbarStyle & wxTB_TEXT)
         {
         {
-            rectLabel.Inflate(-2);
+            if(tbarStyle & wxTB_HORIZONTAL)
+            {
+                dc.DrawLabel(label, bitmap, rect, wxALIGN_CENTRE);
+            }
+            else
+            {
+                dc.DrawLabel(label, bitmap, rect, wxALIGN_LEFT|wxALIGN_CENTER_VERTICAL);
+            }
         }
         }
-    }
-
-    dc.DrawLabel(label, image, rectLabel, alignment, indexAccel, rectBounds);
-
-    if ( !label.empty() && (flags & wxCONTROL_FOCUSED) )
-    {
-        if ( flags & wxCONTROL_PRESSED )
+        else
         {
         {
-            // the focus rectangle is never pressed, so undo the shift done
-            // above
-            rectLabel.x--;
-            rectLabel.y--;
-            rectLabel.width--;
-            rectLabel.height--;
+            int xpoint = (rect.GetLeft() + rect.GetRight() + 1 - bitmap.GetWidth()) / 2;
+            int ypoint = (rect.GetTop() + rect.GetBottom() + 1 - bitmap.GetHeight()) / 2;
+            dc.DrawBitmap(bitmap, xpoint, ypoint);
         }
         }
-
-        DrawFocusRect(dc, rectLabel);
-    }
-}
-
-// ----------------------------------------------------------------------------
-// (check)listbox items
-// ----------------------------------------------------------------------------
-
-void wxWin32Renderer::DrawItem(wxDC& dc,
-                               const wxString& label,
-                               const wxRect& rect,
-                               int flags)
-{
-    wxDCTextColourChanger colChanger(dc);
-
-    if ( flags & wxCONTROL_SELECTED )
-    {
-        colChanger.Set(wxSCHEME_COLOUR(m_scheme, HIGHLIGHT_TEXT));
-
-        wxColour colBg = wxSCHEME_COLOUR(m_scheme, HIGHLIGHT);
-        dc.SetBrush(wxBrush(colBg, wxSOLID));
-        dc.SetPen(wxPen(colBg, 0, wxSOLID));
-        dc.DrawRectangle(rect);
-    }
-
-    wxRect rectText = rect;
-    rectText.x += 2;
-    rectText.width -= 2;
-    dc.DrawLabel(label, wxNullBitmap, rectText);
-
-    if ( flags & wxCONTROL_FOCUSED )
-    {
-        DrawFocusRect(dc, rect);
-    }
-}
-
-void wxWin32Renderer::DrawCheckItem(wxDC& dc,
-                                    const wxString& label,
-                                    const wxBitmap& bitmap,
-                                    const wxRect& rect,
-                                    int flags)
-{
-    wxBitmap bmp;
-    if ( bitmap.Ok() )
-    {
-        bmp = bitmap;
     }
     }
-    else // use default bitmap
+    else if (style == wxTOOL_STYLE_SEPARATOR)
     {
     {
-        bmp = wxBitmap(flags & wxCONTROL_CHECKED ? checked_item_xpm
-                                                 : unchecked_item_xpm);
-    }
-
-    dc.DrawBitmap(bmp, rect.x, rect.y + (rect.height - bmp.GetHeight()) / 2 - 1,
-                  TRUE /* use mask */);
-
-    wxRect rectLabel = rect;
-    int bmpWidth = bmp.GetWidth();
-    rectLabel.x += bmpWidth;
-    rectLabel.width -= bmpWidth;
-
-    DrawItem(dc, label, rectLabel, flags);
-}
-
-// ----------------------------------------------------------------------------
-// check/radio buttons
-// ----------------------------------------------------------------------------
-
-wxBitmap wxWin32Renderer::GetIndicator(IndicatorType indType, int flags)
-{
-    IndicatorState indState;
-    if ( flags & wxCONTROL_SELECTED )
-        indState = flags & wxCONTROL_DISABLED ? IndicatorState_SelectedDisabled
-                                              : IndicatorState_Selected;
-    else if ( flags & wxCONTROL_DISABLED )
-        indState = IndicatorState_Disabled;
-    else if ( flags & wxCONTROL_PRESSED )
-        indState = IndicatorState_Pressed;
-    else
-        indState = IndicatorState_Normal;
-
-    IndicatorStatus indStatus = flags & wxCONTROL_CHECKED
-                                    ? IndicatorStatus_Checked
-                                    : IndicatorStatus_Unchecked;
-
-    const char **xpm = bmpIndicators[indType][indState][indStatus];
-    return xpm ? wxBitmap(xpm) : wxNullBitmap;
-}
-
-void wxWin32Renderer::DrawCheckOrRadioButton(wxDC& dc,
-                                             const wxString& label,
-                                             const wxBitmap& bitmap,
-                                             const wxRect& rect,
-                                             int flags,
-                                             wxAlignment align,
-                                             int indexAccel,
-                                             wxCoord focusOffsetY)
-{
-    // calculate the position of the bitmap and of the label
-    wxCoord heightBmp = bitmap.GetHeight();
-    wxCoord xBmp,
-            yBmp = rect.y + (rect.height - heightBmp) / 2;
-
-    wxRect rectLabel;
-    dc.GetMultiLineTextExtent(label, NULL, &rectLabel.height);
-    rectLabel.y = rect.y + (rect.height - rectLabel.height) / 2;
-
-    // align label vertically with the bitmap - looks nicer like this
-    rectLabel.y -= (rectLabel.height - heightBmp) % 2;
-
-    // calc horz position
-    if ( align == wxALIGN_RIGHT )
-    {
-        xBmp = rect.GetRight() - bitmap.GetWidth();
-        rectLabel.x = rect.x + 3;
-        rectLabel.SetRight(xBmp);
-    }
-    else // normal (checkbox to the left of the text) case
-    {
-        xBmp = rect.x;
-        rectLabel.x = xBmp + bitmap.GetWidth() + 5;
-        rectLabel.SetRight(rect.GetRight());
+        // leave a small gap aroudn the line, also account for the toolbar
+        // border itself
+        if(rectOrig.height > rectOrig.width)
+        {
+            // horizontal
+            DrawVerticalLine(dc, rectOrig.x + rectOrig.width/2,
+                             rectOrig.y + 2*BORDER_THICKNESS,
+                             rectOrig.GetBottom() - BORDER_THICKNESS);
+        }
+        else
+        {
+            // vertical
+            DrawHorizontalLine(dc, rectOrig.y + rectOrig.height/2,
+                         rectOrig.x + 2*BORDER_THICKNESS,
+                         rectOrig.GetRight() - BORDER_THICKNESS);
+        }
     }
     }
-
-    dc.DrawBitmap(bitmap, xBmp, yBmp, TRUE /* use mask */);
-
-    DoDrawLabel(
-                dc, label, rectLabel,
-                flags,
-                wxALIGN_LEFT | wxALIGN_TOP,
-                indexAccel,
-                NULL,         // we don't need bounding rect
-                // use custom vert focus rect offset
-                wxPoint(FOCUS_RECT_OFFSET_X, focusOffsetY)
-               );
-}
-
-void wxWin32Renderer::DrawRadioButton(wxDC& dc,
-                                      const wxString& label,
-                                      const wxBitmap& bitmap,
-                                      const wxRect& rect,
-                                      int flags,
-                                      wxAlignment align,
-                                      int indexAccel)
-{
-    DrawCheckOrRadioButton(dc, label,
-                           bitmap.Ok() ? bitmap : GetRadioBitmap(flags),
-                           rect, flags, align, indexAccel,
-                           FOCUS_RECT_OFFSET_Y); // default focus rect offset
-}
-
-void wxWin32Renderer::DrawCheckButton(wxDC& dc,
-                                      const wxString& label,
-                                      const wxBitmap& bitmap,
-                                      const wxRect& rect,
-                                      int flags,
-                                      wxAlignment align,
-                                      int indexAccel)
-{
-    DrawCheckOrRadioButton(dc, label,
-                           bitmap.Ok() ? bitmap : GetCheckBitmap(flags),
-                           rect, flags, align, indexAccel,
-                           0); // no focus rect offset for checkboxes
-}
-
-// ----------------------------------------------------------------------------
-// text control
-// ----------------------------------------------------------------------------
-
-void wxWin32Renderer::DrawTextLine(wxDC& dc,
-                                   const wxString& text,
-                                   const wxRect& rect,
-                                   int selStart,
-                                   int selEnd,
-                                   int flags)
-{
-    // nothing special to do here
-    StandardDrawTextLine(dc, text, rect, selStart, selEnd, flags);
-}
-
-void wxWin32Renderer::DrawLineWrapMark(wxDC& dc, const wxRect& rect)
-{
-    // we don't draw them
+    // don't draw wxTOOL_STYLE_CONTROL
 }
 }
+#endif // wxUSE_TOOLBAR
 
 // ----------------------------------------------------------------------------
 // notebook
 // ----------------------------------------------------------------------------
 
 
 // ----------------------------------------------------------------------------
 // notebook
 // ----------------------------------------------------------------------------
 
+#if wxUSE_NOTEBOOK
+
 void wxWin32Renderer::DrawTab(wxDC& dc,
                               const wxRect& rectOrig,
                               wxDirection dir,
 void wxWin32Renderer::DrawTab(wxDC& dc,
                               const wxRect& rectOrig,
                               wxDirection dir,
@@ -2062,13 +1760,23 @@ void wxWin32Renderer::DrawTab(wxDC& dc,
                               int flags,
                               int indexAccel)
 {
                               int flags,
                               int indexAccel)
 {
+    #define SELECT_FOR_VERTICAL(X,Y) ( isVertical ? Y : X )
+    #define REVERSE_FOR_VERTICAL(X,Y) \
+        SELECT_FOR_VERTICAL(X,Y)      \
+        ,                             \
+        SELECT_FOR_VERTICAL(Y,X)
+
     wxRect rect = rectOrig;
 
     wxRect rect = rectOrig;
 
+    bool isVertical = ( dir == wxLEFT ) || ( dir == wxRIGHT );
+
     // the current tab is drawn indented (to the top for default case) and
     // bigger than the other ones
     const wxSize indent = GetTabIndent();
     if ( flags & wxCONTROL_SELECTED )
     {
     // the current tab is drawn indented (to the top for default case) and
     // bigger than the other ones
     const wxSize indent = GetTabIndent();
     if ( flags & wxCONTROL_SELECTED )
     {
+        rect.Inflate( SELECT_FOR_VERTICAL( indent.x , 0),
+                      SELECT_FOR_VERTICAL( 0, indent.y ));
         switch ( dir )
         {
             default:
         switch ( dir )
         {
             default:
@@ -2076,153 +1784,240 @@ void wxWin32Renderer::DrawTab(wxDC& dc,
                 // fall through
 
             case wxTOP:
                 // fall through
 
             case wxTOP:
-                rect.Inflate(indent.x, 0);
                 rect.y -= indent.y;
                 rect.y -= indent.y;
-                rect.height += indent.y;
-                break;
-
+                // fall through
             case wxBOTTOM:
             case wxBOTTOM:
-                rect.Inflate(indent.x, 0);
                 rect.height += indent.y;
                 break;
 
             case wxLEFT:
                 rect.height += indent.y;
                 break;
 
             case wxLEFT:
+                rect.x -= indent.x;
+                // fall through
             case wxRIGHT:
             case wxRIGHT:
-                wxFAIL_MSG(_T("TODO"));
+                rect.width += indent.x;
                 break;
         }
     }
 
     // draw the text, image and the focus around them (if necessary)
                 break;
         }
     }
 
     // draw the text, image and the focus around them (if necessary)
-    wxRect rectLabel = rect;
+    wxRect rectLabel( REVERSE_FOR_VERTICAL(rect.x,rect.y),
+                      REVERSE_FOR_VERTICAL(rect.width,rect.height)
+                    );
     rectLabel.Deflate(1, 1);
     rectLabel.Deflate(1, 1);
-    DrawButtonLabel(dc, label, bitmap, rectLabel,
-                    flags, wxALIGN_CENTRE, indexAccel);
+    if ( isVertical )
+    {
+        // draw it horizontally into memory and rotate for screen
+        wxMemoryDC dcMem;
+        wxBitmap bitmapRotated,
+                 bitmapMem( rectLabel.x + rectLabel.width,
+                            rectLabel.y + rectLabel.height );
+        dcMem.SelectObject(bitmapMem);
+        dcMem.SetBackground(dc.GetBackground());
+        dcMem.SetFont(dc.GetFont());
+        dcMem.SetTextForeground(dc.GetTextForeground());
+        dcMem.Clear();
+        bitmapRotated =
+#if wxUSE_IMAGE
+                        wxBitmap( wxImage( bitmap.ConvertToImage() ).Rotate90(dir==wxLEFT) )
+#else
+                        bitmap
+#endif // wxUSE_IMAGE
+                        ;
+        DrawButtonLabel(dcMem, label, bitmapRotated, rectLabel,
+                        flags, wxALIGN_CENTRE, indexAccel);
+        dcMem.SelectObject(wxNullBitmap);
+        bitmapMem = bitmapMem.GetSubBitmap(rectLabel);
+#if wxUSE_IMAGE
+        bitmapMem = wxBitmap(wxImage(bitmapMem.ConvertToImage()).Rotate90(dir==wxRIGHT));
+#endif // wxUSE_IMAGE
+        dc.DrawBitmap(bitmapMem, rectLabel.y, rectLabel.x, false);
+    }
+    else
+    {
+        DrawButtonLabel(dc, label, bitmap, rectLabel,
+                        flags, wxALIGN_CENTRE, indexAccel);
+    }
 
     // now draw the tab border itself (maybe use DrawRoundedRectangle()?)
     static const wxCoord CUTOFF = 2; // radius of the rounded corner
 
     // now draw the tab border itself (maybe use DrawRoundedRectangle()?)
     static const wxCoord CUTOFF = 2; // radius of the rounded corner
-    wxCoord x = rect.x,
-            y = rect.y,
-            x2 = rect.GetRight(),
-            y2 = rect.GetBottom();
+    wxCoord x = SELECT_FOR_VERTICAL(rect.x,rect.y),
+            y = SELECT_FOR_VERTICAL(rect.y,rect.x),
+            x2 = SELECT_FOR_VERTICAL(rect.GetRight(),rect.GetBottom()),
+            y2 = SELECT_FOR_VERTICAL(rect.GetBottom(),rect.GetRight());
 
     // FIXME: all this code will break if the tab indent or the border width,
     //        it is tied to the fact that both of them are equal to 2
     switch ( dir )
     {
         default:
 
     // FIXME: all this code will break if the tab indent or the border width,
     //        it is tied to the fact that both of them are equal to 2
     switch ( dir )
     {
         default:
+            // default is top
+        case wxLEFT:
+            // left orientation looks like top but IsVertical makes x and y reversed
         case wxTOP:
         case wxTOP:
+            // top is not vertical so use coordinates in written order
             dc.SetPen(m_penHighlight);
             dc.SetPen(m_penHighlight);
-            dc.DrawLine(x, y2, x, y + CUTOFF);
-            dc.DrawLine(x, y + CUTOFF, x + CUTOFF, y);
-            dc.DrawLine(x + CUTOFF, y, x2 - CUTOFF + 1, y);
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x, y2),
+                        REVERSE_FOR_VERTICAL(x, y + CUTOFF));
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x, y + CUTOFF),
+                        REVERSE_FOR_VERTICAL(x + CUTOFF, y));
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x + CUTOFF, y),
+                        REVERSE_FOR_VERTICAL(x2 - CUTOFF + 1, y));
 
             dc.SetPen(m_penBlack);
 
             dc.SetPen(m_penBlack);
-            dc.DrawLine(x2, y2, x2, y + CUTOFF);
-            dc.DrawLine(x2, y + CUTOFF, x2 - CUTOFF, y);
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x2, y2),
+                        REVERSE_FOR_VERTICAL(x2, y + CUTOFF));
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x2, y + CUTOFF),
+                        REVERSE_FOR_VERTICAL(x2 - CUTOFF, y));
 
             dc.SetPen(m_penDarkGrey);
 
             dc.SetPen(m_penDarkGrey);
-            dc.DrawLine(x2 - 1, y2, x2 - 1, y + CUTOFF - 1);
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x2 - 1, y2),
+                        REVERSE_FOR_VERTICAL(x2 - 1, y + CUTOFF - 1));
 
             if ( flags & wxCONTROL_SELECTED )
             {
                 dc.SetPen(m_penLightGrey);
 
                 // overwrite the part of the border below this tab
 
             if ( flags & wxCONTROL_SELECTED )
             {
                 dc.SetPen(m_penLightGrey);
 
                 // overwrite the part of the border below this tab
-                dc.DrawLine(x + 1, y2 + 1, x2 - 1, y2 + 1);
+                dc.DrawLine(REVERSE_FOR_VERTICAL(x + 1, y2 + 1),
+                            REVERSE_FOR_VERTICAL(x2 - 1, y2 + 1));
 
                 // and the shadow of the tab to the left of us
 
                 // and the shadow of the tab to the left of us
-                dc.DrawLine(x + 1, y + CUTOFF + 1, x + 1, y2 + 1);
+                dc.DrawLine(REVERSE_FOR_VERTICAL(x + 1, y + CUTOFF + 1),
+                            REVERSE_FOR_VERTICAL(x + 1, y2 + 1));
             }
             break;
 
             }
             break;
 
+        case wxRIGHT:
+            // right orientation looks like bottom but IsVertical makes x and y reversed
         case wxBOTTOM:
         case wxBOTTOM:
+            // bottom is not vertical so use coordinates in written order
             dc.SetPen(m_penHighlight);
             // we need to continue one pixel further to overwrite the corner of
             // the border for the selected tab
             dc.SetPen(m_penHighlight);
             // we need to continue one pixel further to overwrite the corner of
             // the border for the selected tab
-            dc.DrawLine(x, y - (flags & wxCONTROL_SELECTED ? 1 : 0),
-                        x, y2 - CUTOFF);
-            dc.DrawLine(x, y2 - CUTOFF, x + CUTOFF, y2);
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x, y - (flags & wxCONTROL_SELECTED ? 1 : 0)),
+                        REVERSE_FOR_VERTICAL(x, y2 - CUTOFF));
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x, y2 - CUTOFF),
+                        REVERSE_FOR_VERTICAL(x + CUTOFF, y2));
 
             dc.SetPen(m_penBlack);
 
             dc.SetPen(m_penBlack);
-            dc.DrawLine(x + CUTOFF, y2, x2 - CUTOFF + 1, y2);
-            dc.DrawLine(x2, y, x2, y2 - CUTOFF);
-            dc.DrawLine(x2, y2 - CUTOFF, x2 - CUTOFF, y2);
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x + CUTOFF, y2),
+                        REVERSE_FOR_VERTICAL(x2 - CUTOFF + 1, y2));
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x2, y),
+                        REVERSE_FOR_VERTICAL(x2, y2 - CUTOFF));
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x2, y2 - CUTOFF),
+                        REVERSE_FOR_VERTICAL(x2 - CUTOFF, y2));
 
             dc.SetPen(m_penDarkGrey);
 
             dc.SetPen(m_penDarkGrey);
-            dc.DrawLine(x + CUTOFF, y2 - 1, x2 - CUTOFF + 1, y2 - 1);
-            dc.DrawLine(x2 - 1, y, x2 - 1, y2 - CUTOFF + 1);
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x + CUTOFF, y2 - 1),
+                        REVERSE_FOR_VERTICAL(x2 - CUTOFF + 1, y2 - 1));
+            dc.DrawLine(REVERSE_FOR_VERTICAL(x2 - 1, y),
+                        REVERSE_FOR_VERTICAL(x2 - 1, y2 - CUTOFF + 1));
 
             if ( flags & wxCONTROL_SELECTED )
             {
                 dc.SetPen(m_penLightGrey);
 
                 // overwrite the part of the (double!) border above this tab
 
             if ( flags & wxCONTROL_SELECTED )
             {
                 dc.SetPen(m_penLightGrey);
 
                 // overwrite the part of the (double!) border above this tab
-                dc.DrawLine(x + 1, y - 1, x2 - 1, y - 1);
-                dc.DrawLine(x + 1, y - 2, x2 - 1, y - 2);
+                dc.DrawLine(REVERSE_FOR_VERTICAL(x + 1, y - 1),
+                            REVERSE_FOR_VERTICAL(x2 - 1, y - 1));
+                dc.DrawLine(REVERSE_FOR_VERTICAL(x + 1, y - 2),
+                            REVERSE_FOR_VERTICAL(x2 - 1, y - 2));
 
                 // and the shadow of the tab to the left of us
 
                 // and the shadow of the tab to the left of us
-                dc.DrawLine(x + 1, y2 - CUTOFF, x + 1, y - 1);
+                dc.DrawLine(REVERSE_FOR_VERTICAL(x + 1, y2 - CUTOFF),
+                            REVERSE_FOR_VERTICAL(x + 1, y - 1));
             }
             break;
             }
             break;
-
-        case wxLEFT:
-        case wxRIGHT:
-            wxFAIL_MSG(_T("TODO"));
     }
     }
+
+    #undef SELECT_FOR_VERTICAL
+    #undef REVERSE_FOR_VERTICAL
 }
 
 }
 
+#endif // wxUSE_NOTEBOOK
+
+#if wxUSE_SLIDER
+
 // ----------------------------------------------------------------------------
 // slider
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 // slider
 // ----------------------------------------------------------------------------
 
-wxSize wxWin32Renderer::GetSliderThumbSize(const wxRect& rect,
-                                           wxOrientation orient) const
+wxSize
+wxWin32Renderer::GetSliderThumbSize(const wxRect& WXUNUSED(rect),
+                                    int lenThumb,
+                                    wxOrientation orient) const
 {
     wxSize size;
 {
     wxSize size;
+    wxCoord width  = wxMax (lenThumb, SLIDER_THUMB_LENGTH) / 2;
+    wxCoord height = wxMax (lenThumb, SLIDER_THUMB_LENGTH);
 
 
-    wxRect rectShaft = GetSliderShaftRect(rect, orient);
-    if ( orient == wxHORIZONTAL )
+    if (orient == wxHORIZONTAL)
     {
     {
-        size.y = rect.height - 6;
-        size.x = wxMin(size.y / 2, rectShaft.width);
+        size.x = width;
+        size.y = height;
     }
     }
-    else // vertical
-    {
-        size.x = rect.width - 6;
-        size.y = wxMin(size.x / 2, rectShaft.height);
+    else
+    { // == wxVERTICAL
+        size.x = height;
+        size.y = width;
     }
 
     return size;
 }
 
 wxRect wxWin32Renderer::GetSliderShaftRect(const wxRect& rectOrig,
     }
 
     return size;
 }
 
 wxRect wxWin32Renderer::GetSliderShaftRect(const wxRect& rectOrig,
-                                           wxOrientation orient) const
-{
-    static const wxCoord SLIDER_MARGIN = 6;
+                                           int lenThumb,
+                                           wxOrientation orient,
+                                           long style) const
+{
+    bool transpose = (orient == wxVERTICAL);
+    bool left  = ((style & wxSL_AUTOTICKS) != 0) &
+                 (((style & wxSL_TOP) != 0) & !transpose |
+                  ((style & wxSL_LEFT) != 0) & transpose |
+                  ((style & wxSL_BOTH) != 0));
+    bool right = ((style & wxSL_AUTOTICKS) != 0) &
+                 (((style & wxSL_BOTTOM) != 0) & !transpose |
+                  ((style & wxSL_RIGHT) != 0) & transpose |
+                  ((style & wxSL_BOTH) != 0));
 
     wxRect rect = rectOrig;
 
 
     wxRect rect = rectOrig;
 
-    if ( orient == wxHORIZONTAL )
-    {
-        // make the rect of minimal width and centre it
-        rect.height = 2*BORDER_THICKNESS;
-        rect.y = rectOrig.y + (rectOrig.height - rect.height) / 2;
-        if ( rect.y < 0 )
-            rect.y = 0;
+    wxSize sizeThumb = GetSliderThumbSize (rect, lenThumb, orient);
 
 
-        // leave margins on the sides
-        rect.Deflate(SLIDER_MARGIN, 0);
+    if (orient == wxHORIZONTAL) {
+        rect.x += SLIDER_MARGIN;
+        if (left & right)
+        {
+            rect.y += wxMax ((rect.height - 2*BORDER_THICKNESS) / 2, sizeThumb.y/2);
+        }
+        else if (left)
+        {
+            rect.y += wxMax ((rect.height - 2*BORDER_THICKNESS - sizeThumb.y/2), sizeThumb.y/2);
+        }
+        else
+        {
+            rect.y += sizeThumb.y/2;
+        }
+        rect.width -= 2*SLIDER_MARGIN;
+        rect.height = 2*BORDER_THICKNESS;
     }
     }
-    else // vertical
-    {
-        // same as above but in other direction
+    else
+    { // == wxVERTICAL
+        rect.y += SLIDER_MARGIN;
+        if (left & right)
+        {
+            rect.x += wxMax ((rect.width - 2*BORDER_THICKNESS) / 2, sizeThumb.x/2);
+        }
+        else if (left)
+        {
+            rect.x += wxMax ((rect.width - 2*BORDER_THICKNESS - sizeThumb.x/2), sizeThumb.x/2);
+        }
+        else
+        {
+            rect.x += sizeThumb.x/2;
+        }
         rect.width = 2*BORDER_THICKNESS;
         rect.width = 2*BORDER_THICKNESS;
-        rect.x = rectOrig.x + (rectOrig.width - rect.width) / 2;
-        if ( rect.x < 0 )
-            rect.x = 0;
-
-        rect.Deflate(0, SLIDER_MARGIN);
+        rect.height -= 2*SLIDER_MARGIN;
     }
 
     return rect;
     }
 
     return rect;
@@ -2230,19 +2025,37 @@ wxRect wxWin32Renderer::GetSliderShaftRect(const wxRect& rectOrig,
 
 void wxWin32Renderer::DrawSliderShaft(wxDC& dc,
                                       const wxRect& rectOrig,
 
 void wxWin32Renderer::DrawSliderShaft(wxDC& dc,
                                       const wxRect& rectOrig,
+                                      int lenThumb,
                                       wxOrientation orient,
                                       int flags,
                                       wxOrientation orient,
                                       int flags,
+                                      long style,
                                       wxRect *rectShaft)
 {
                                       wxRect *rectShaft)
 {
-    if ( flags & wxCONTROL_FOCUSED )
-    {
+    /*    show shaft geometry
+
+             shaft
+        +-------------+
+        |             |
+        |     XXX     |  <-- x1
+        |     XXX     |
+        |     XXX     |
+        |     XXX     |
+        |     XXX     |  <-- x2
+        |             |
+        +-------------+
+
+              ^ ^
+              | |
+             y1 y2
+    */
+
+    if (flags & wxCONTROL_FOCUSED) {
         DrawFocusRect(dc, rectOrig);
     }
 
         DrawFocusRect(dc, rectOrig);
     }
 
-    wxRect rect = GetSliderShaftRect(rectOrig, orient);
+    wxRect rect = GetSliderShaftRect(rectOrig, lenThumb, orient, style);
 
 
-    if ( rectShaft )
-        *rectShaft = rect;
+    if (rectShaft) *rectShaft = rect;
 
     DrawSunkenBorder(dc, &rect);
 }
 
     DrawSunkenBorder(dc, &rect);
 }
@@ -2250,26 +2063,31 @@ void wxWin32Renderer::DrawSliderShaft(wxDC& dc,
 void wxWin32Renderer::DrawSliderThumb(wxDC& dc,
                                       const wxRect& rect,
                                       wxOrientation orient,
 void wxWin32Renderer::DrawSliderThumb(wxDC& dc,
                                       const wxRect& rect,
                                       wxOrientation orient,
-                                      int flags)
-{
-    /*
-       we are drawing a shape of this form
-
-       HHHHHHB <--- y
-       H    DB
-       H    DB
-       H    DB   where H is hightlight colour
-       H    DB         D    dark grey
-       H    DB         B    black
-       H    DB
-       H    DB <--- y3
-        H  DB
-         HDB
-          B    <--- y2
-
-       ^  ^  ^
-       |  |  |
-       x x3  x2
+                                      int flags,
+                                      long style)
+{
+    /*    show thumb geometry
+
+             H       <--- y1
+           H H B
+         H     H B
+       H         H B <--- y3
+       H         D B
+       H         D B
+       H         D B
+       H         D B   where H is highlight colour
+       H         D B         D    dark grey
+       H         D B         B    black
+       H         D B
+       H         D B
+       H         D B <--- y4
+         H     D B
+           H D B
+             B       <--- y2
+
+       ^     ^     ^
+       |     |     |
+       x1    x3    x2
 
        The interior of this shape is filled with the hatched brush if the thumb
        is pressed.
 
        The interior of this shape is filled with the hatched brush if the thumb
        is pressed.
@@ -2277,53 +2095,84 @@ void wxWin32Renderer::DrawSliderThumb(wxDC& dc,
 
     DrawBackground(dc, wxNullColour, rect, flags);
 
 
     DrawBackground(dc, wxNullColour, rect, flags);
 
-    bool transpose = orient == wxVERTICAL;
+    bool transpose = (orient == wxVERTICAL);
+    bool left  = ((style & wxSL_AUTOTICKS) != 0) &
+                 (((style & wxSL_TOP) != 0) & !transpose |
+                  ((style & wxSL_LEFT) != 0) & transpose) &
+                 ((style & wxSL_BOTH) == 0);
+    bool right = ((style & wxSL_AUTOTICKS) != 0) &
+                 (((style & wxSL_BOTTOM) != 0) & !transpose |
+                  ((style & wxSL_RIGHT) != 0) & transpose) &
+                 ((style & wxSL_BOTH) == 0);
+
+    wxCoord sizeArrow = (transpose ? rect.height : rect.width) / 2;
+    wxCoord c = ((transpose ? rect.height : rect.width) - 2*sizeArrow);
+
+    wxCoord x1, x2, x3, y1, y2, y3, y4;
+    x1 = (transpose ? rect.y : rect.x);
+    x2 = (transpose ? rect.GetBottom() : rect.GetRight());
+    x3 = (x1-1+c) + sizeArrow;
+    y1 = (transpose ? rect.x : rect.y);
+    y2 = (transpose ? rect.GetRight() : rect.GetBottom());
+    y3 = (left  ? (y1-1+c) + sizeArrow : y1);
+    y4 = (right ? (y2+1-c) - sizeArrow : y2);
 
 
-    wxCoord x, y, x2, y2;
-    if ( transpose )
+    dc.SetPen(m_penBlack);
+    if (left) {
+        DrawLine(dc, x3+1-c, y1, x2, y3, transpose);
+    }
+    DrawLine(dc, x2, y3, x2, y4, transpose);
+    if (right)
     {
     {
-        x = rect.y;
-        y = rect.x;
-        x2 = rect.GetBottom();
-        y2 = rect.GetRight();
+        DrawLine(dc, x3+1-c, y2, x2, y4, transpose);
     }
     else
     {
     }
     else
     {
-        x = rect.x;
-        y = rect.y;
-        x2 = rect.GetRight();
-        y2 = rect.GetBottom();
+        DrawLine(dc, x1, y2, x2, y2, transpose);
     }
 
     }
 
-    // the size of the pointed part of the thumb
-    wxCoord sizeArrow = (transpose ? rect.height : rect.width) / 2;
-
-    wxCoord x3 = x + sizeArrow,
-            y3 = y2 - sizeArrow;
-
-    dc.SetPen(m_penHighlight);
-    DrawLine(dc, x, y, x2, y, transpose);
-    DrawLine(dc, x, y + 1, x, y2 - sizeArrow, transpose);
-    DrawLine(dc, x, y3, x3, y2, transpose);
-
-    dc.SetPen(m_penBlack);
-    DrawLine(dc, x3, y2, x2, y3, transpose);
-    DrawLine(dc, x2, y3, x2, y - 1, transpose);
-
     dc.SetPen(m_penDarkGrey);
     dc.SetPen(m_penDarkGrey);
-    DrawLine(dc, x3, y2 - 1, x2 - 1, y3, transpose);
-    DrawLine(dc, x2 - 1, y3, x2 - 1, y, transpose);
+    DrawLine(dc, x2-1, y3+1, x2-1, y4-1, transpose);
+    if (right) {
+        DrawLine(dc, x3+1-c, y2-1, x2-1, y4, transpose);
+    }
+    else
+    {
+        DrawLine(dc, x1+1, y2-1, x2-1, y2-1, transpose);
+    }
 
 
-    if ( flags & wxCONTROL_PRESSED )
+    dc.SetPen(m_penHighlight);
+    if (left)
+    {
+        DrawLine(dc, x1, y3, x3, y1, transpose);
+        DrawLine(dc, x3+1-c, y1+1, x2-1, y3, transpose);
+    }
+    else
+    {
+        DrawLine(dc, x1, y1, x2, y1, transpose);
+    }
+    DrawLine(dc, x1, y3, x1, y4, transpose);
+    if (right)
     {
     {
+        DrawLine(dc, x1, y4, x3+c, y2+c, transpose);
+    }
+
+    if (flags & wxCONTROL_PRESSED) {
         // TODO: MSW fills the entire area inside, not just the rect
         wxRect rectInt = rect;
         if ( transpose )
         // TODO: MSW fills the entire area inside, not just the rect
         wxRect rectInt = rect;
         if ( transpose )
-            rectInt.SetRight(y3);
+        {
+            rectInt.SetLeft(y3);
+            rectInt.SetRight(y4);
+        }
         else
         else
-            rectInt.SetBottom(y3);
+        {
+            rectInt.SetTop(y3);
+            rectInt.SetBottom(y4);
+        }
         rectInt.Deflate(2);
 
         rectInt.Deflate(2);
 
+#if !defined(__WXMGL__)
         static const char *stipple_xpm[] = {
             /* columns rows colors chars-per-pixel */
             "2 2 2 1",
         static const char *stipple_xpm[] = {
             /* columns rows colors chars-per-pixel */
             "2 2 2 1",
@@ -2333,6 +2182,24 @@ void wxWin32Renderer::DrawSliderThumb(wxDC& dc,
             "w ",
             " w",
         };
             "w ",
             " w",
         };
+#else
+        // VS: MGL can only do 8x8 stipple brushes
+        static const char *stipple_xpm[] = {
+            /* columns rows colors chars-per-pixel */
+            "8 8 2 1",
+            "  c None",
+            "w c white",
+            /* pixels */
+            "w w w w ",
+            " w w w w",
+            "w w w w ",
+            " w w w w",
+            "w w w w ",
+            " w w w w",
+            "w w w w ",
+            " w w w w",
+        };
+#endif
         dc.SetBrush(wxBrush(stipple_xpm));
 
         dc.SetTextForeground(wxSCHEME_COLOUR(m_scheme, SHADOW_HIGHLIGHT));
         dc.SetBrush(wxBrush(stipple_xpm));
 
         dc.SetTextForeground(wxSCHEME_COLOUR(m_scheme, SHADOW_HIGHLIGHT));
@@ -2344,79 +2211,90 @@ void wxWin32Renderer::DrawSliderThumb(wxDC& dc,
 
 void wxWin32Renderer::DrawSliderTicks(wxDC& dc,
                                       const wxRect& rect,
 
 void wxWin32Renderer::DrawSliderTicks(wxDC& dc,
                                       const wxRect& rect,
-                                      const wxSize& sizeThumb,
+                                      int lenThumb,
                                       wxOrientation orient,
                                       int start,
                                       int end,
                                       int step,
                                       wxOrientation orient,
                                       int start,
                                       int end,
                                       int step,
-                                      int flags)
+                                      int WXUNUSED(flags),
+                                      long style)
 {
 {
-    if ( end == start )
-    {
-        // empty slider?
-        return;
-    }
-
-    // the variable names correspond to horizontal case, but they can be used
-    // for both orientations
-    wxCoord x1, x2, y1, y2, len, widthThumb;
-    if ( orient == wxHORIZONTAL )
-    {
-        x1 = rect.GetLeft();
-        x2 = rect.GetRight();
+    /*    show ticks geometry
 
 
-        // draw from bottom to top to leave one pixel space between the ticks
-        // and the slider as Windows do
-        y1 = rect.GetBottom();
-        y2 = rect.GetTop();
+        left        right
+        ticks shaft ticks
+        ----   XX   ----  <-- x1
+        ----   XX   ----
+        ----   XX   ----
+        ----   XX   ----  <-- x2
 
 
-        len = rect.width;
-
-        widthThumb = sizeThumb.x;
-    }
-    else // vertical
-    {
-        x1 = rect.GetTop();
-        x2 = rect.GetBottom();
-
-        y1 = rect.GetRight();
-        y2 = rect.GetLeft();
-
-        len = rect.height;
-
-        widthThumb = sizeThumb.y;
-    }
-
-    // the first tick should be positioned in such way that a thumb drawn in
-    // the first position points down directly to it
-    x1 += widthThumb / 2;
-    x2 -= widthThumb / 2;
+        ^  ^        ^  ^
+        |  |        |  |
+        y3 y1       y2 y4
+    */
 
 
-    // this also means that we have slightly less space for the ticks in
-    // between the first and the last
-    len -= widthThumb;
+    // empty slider?
+    if (end == start) return;
+
+    bool transpose = (orient == wxVERTICAL);
+    bool left  = ((style & wxSL_AUTOTICKS) != 0) &
+                 (((style & wxSL_TOP) != 0) & !transpose |
+                  ((style & wxSL_LEFT) != 0) & transpose |
+                  ((style & wxSL_BOTH) != 0));
+    bool right = ((style & wxSL_AUTOTICKS) != 0) &
+                 (((style & wxSL_BOTTOM) != 0) & !transpose |
+                  ((style & wxSL_RIGHT) != 0) & transpose |
+                  ((style & wxSL_BOTH) != 0));
+
+    // default thumb size
+    wxSize sizeThumb = GetSliderThumbSize (rect, 0, orient);
+    wxCoord defaultLen = (transpose ? sizeThumb.x : sizeThumb.y);
+
+    // normal thumb size
+    sizeThumb = GetSliderThumbSize (rect, lenThumb, orient);
+    wxCoord widthThumb  = (transpose ? sizeThumb.y : sizeThumb.x);
+
+    wxRect rectShaft = GetSliderShaftRect (rect, lenThumb, orient, style);
+
+    wxCoord x1, x2, y1, y2, y3, y4 , len;
+    x1 = (transpose ? rectShaft.y : rectShaft.x) + widthThumb/2;
+    x2 = (transpose ? rectShaft.GetBottom() : rectShaft.GetRight()) - widthThumb/2;
+    y1 = (transpose ? rectShaft.x : rectShaft.y) - defaultLen/2;
+    y2 = (transpose ? rectShaft.GetRight() : rectShaft.GetBottom()) + defaultLen/2;
+    y3 = (transpose ? rect.x : rect.y);
+    y4 = (transpose ? rect.GetRight() : rect.GetBottom());
+    len = x2 - x1;
 
     dc.SetPen(m_penBlack);
 
     int range = end - start;
 
     dc.SetPen(m_penBlack);
 
     int range = end - start;
-    for ( int n = 0; n < range; n += step )
-    {
+    for ( int n = 0; n < range; n += step ) {
         wxCoord x = x1 + (len*n) / range;
 
         wxCoord x = x1 + (len*n) / range;
 
-        DrawLine(dc, x, y1, x, y2, orient == wxVERTICAL);
+        if (left & (y1 > y3)) {
+            DrawLine(dc, x, y1, x, y3, orient == wxVERTICAL);
+        }
+        if (right & (y4 > y2)) {
+            DrawLine(dc, x, y2, x, y4, orient == wxVERTICAL);
+        }
     }
     }
-
     // always draw the line at the end position
     // always draw the line at the end position
-    DrawLine(dc, x2, y1, x2, y2, orient == wxVERTICAL);
+    if (left & (y1 > y3)) {
+        DrawLine(dc, x2, y1, x2, y3, orient == wxVERTICAL);
+    }
+    if (right & (y4 > y2)) {
+        DrawLine(dc, x2, y2, x2, y4, orient == wxVERTICAL);
+    }
 }
 
 }
 
+#endif // wxUSE_SLIDER
+
 #if wxUSE_MENUS
 #if wxUSE_MENUS
+
 // ----------------------------------------------------------------------------
 // menu and menubar
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 // menu and menubar
 // ----------------------------------------------------------------------------
 
-#if wxUSE_MENUS
-
 // wxWin32MenuGeometryInfo: the wxMenuGeometryInfo used by wxWin32Renderer
 class WXDLLEXPORT wxWin32MenuGeometryInfo : public wxMenuGeometryInfo
 {
 // wxWin32MenuGeometryInfo: the wxMenuGeometryInfo used by wxWin32Renderer
 class WXDLLEXPORT wxWin32MenuGeometryInfo : public wxMenuGeometryInfo
 {
@@ -2441,12 +2319,10 @@ private:
     // the height of a normal (not separator) item
     wxCoord m_heightItem;
 
     // the height of a normal (not separator) item
     wxCoord m_heightItem;
 
-    friend wxMenuGeometryInfo *wxWin32Renderer::
-                GetMenuGeometry(wxWindow *, const wxMenu&) const;
+    friend wxMenuGeometryInfo *
+        wxWin32Renderer::GetMenuGeometry(wxWindow *, const wxMenu&) const;
 };
 
 };
 
-#endif // wxUSE_WAVE
-
 // FIXME: all constants are hardcoded but shouldn't be
 static const wxCoord MENU_LEFT_MARGIN = 9;
 static const wxCoord MENU_RIGHT_MARGIN = 18;
 // FIXME: all constants are hardcoded but shouldn't be
 static const wxCoord MENU_LEFT_MARGIN = 9;
 static const wxCoord MENU_RIGHT_MARGIN = 18;
@@ -2466,10 +2342,6 @@ static const wxCoord MENU_SEPARATOR_HEIGHT = 3;
 // the size of the standard checkmark bitmap
 static const wxCoord MENU_CHECK_SIZE = 9;
 
 // the size of the standard checkmark bitmap
 static const wxCoord MENU_CHECK_SIZE = 9;
 
-// we can't implement these methods without wxMenuGeometryInfo implementation
-// which we don't have if !wxUSE_MENUS
-#if wxUSE_MENUS
-
 void wxWin32Renderer::DrawMenuBarItem(wxDC& dc,
                                       const wxRect& rectOrig,
                                       const wxString& label,
 void wxWin32Renderer::DrawMenuBarItem(wxDC& dc,
                                       const wxRect& rectOrig,
                                       const wxString& label,
@@ -2485,9 +2357,9 @@ void wxWin32Renderer::DrawMenuBarItem(wxDC& dc,
     {
         colChanger.Set(wxSCHEME_COLOUR(m_scheme, HIGHLIGHT_TEXT));
 
     {
         colChanger.Set(wxSCHEME_COLOUR(m_scheme, HIGHLIGHT_TEXT));
 
-        wxColour colBg = wxSCHEME_COLOUR(m_scheme, HIGHLIGHT);
-        dc.SetBrush(wxBrush(colBg, wxSOLID));
-        dc.SetPen(wxPen(colBg, 0, wxSOLID));
+        const wxColour colBg = wxSCHEME_COLOUR(m_scheme, HIGHLIGHT);
+        dc.SetBrush(colBg);
+        dc.SetPen(colBg);
         dc.DrawRectangle(rect);
     }
 
         dc.DrawRectangle(rect);
     }
 
@@ -2520,9 +2392,9 @@ void wxWin32Renderer::DrawMenuItem(wxDC& dc,
     {
         colChanger.Set(wxSCHEME_COLOUR(m_scheme, HIGHLIGHT_TEXT));
 
     {
         colChanger.Set(wxSCHEME_COLOUR(m_scheme, HIGHLIGHT_TEXT));
 
-        wxColour colBg = wxSCHEME_COLOUR(m_scheme, HIGHLIGHT);
-        dc.SetBrush(wxBrush(colBg, wxSOLID));
-        dc.SetPen(wxPen(colBg, 0, wxSOLID));
+        const wxColour colBg = wxSCHEME_COLOUR(m_scheme, HIGHLIGHT);
+        dc.SetBrush(colBg);
+        dc.SetPen(colBg);
         dc.DrawRectangle(rect);
     }
 
         dc.DrawRectangle(rect);
     }
 
@@ -2559,12 +2431,12 @@ void wxWin32Renderer::DrawMenuItem(wxDC& dc,
         rect.x = geometryInfo.GetSize().x - MENU_RIGHT_MARGIN;
         rect.width = MENU_RIGHT_MARGIN;
 
         rect.x = geometryInfo.GetSize().x - MENU_RIGHT_MARGIN;
         rect.width = MENU_RIGHT_MARGIN;
 
-        wxArrowStyle arrowStyle;
+        ArrowStyle arrowStyle;
         if ( flags & wxCONTROL_DISABLED )
         if ( flags & wxCONTROL_DISABLED )
-            arrowStyle = flags & wxCONTROL_SELECTED ? Arrow_InversedDisabled
+            arrowStyle = flags & wxCONTROL_SELECTED ? Arrow_InvertedDisabled
                                                     : Arrow_Disabled;
         else if ( flags & wxCONTROL_SELECTED )
                                                     : Arrow_Disabled;
         else if ( flags & wxCONTROL_SELECTED )
-            arrowStyle = Arrow_Inversed;
+            arrowStyle = Arrow_Inverted;
         else
             arrowStyle = Arrow_Normal;
 
         else
             arrowStyle = Arrow_Normal;
 
@@ -2595,7 +2467,7 @@ wxMenuGeometryInfo *wxWin32Renderer::GetMenuGeometry(wxWindow *win,
 {
     // prepare the dc: for now we draw all the items with the system font
     wxClientDC dc(win);
 {
     // prepare the dc: for now we draw all the items with the system font
     wxClientDC dc(win);
-    dc.SetFont(wxSystemSettings::GetSystemFont(wxSYS_DEFAULT_GUI_FONT));
+    dc.SetFont(wxSystemSettings::GetFont(wxSYS_DEFAULT_GUI_FONT));
 
     // the height of a normal item
     wxCoord heightText = dc.GetCharHeight();
 
     // the height of a normal item
     wxCoord heightText = dc.GetCharHeight();
@@ -2613,7 +2485,7 @@ wxMenuGeometryInfo *wxWin32Renderer::GetMenuGeometry(wxWindow *win,
             widthAccelMax = 0,
             widthBmpMax = MENU_LEFT_MARGIN;
 
             widthAccelMax = 0,
             widthBmpMax = MENU_LEFT_MARGIN;
 
-    for ( wxMenuItemList::Node *node = menu.GetMenuItems().GetFirst();
+    for ( wxMenuItemList::compatibility_iterator node = menu.GetMenuItems().GetFirst();
           node;
           node = node->GetNext() )
     {
           node;
           node = node->GetNext() )
     {
@@ -2680,57 +2552,94 @@ wxMenuGeometryInfo *wxWin32Renderer::GetMenuGeometry(wxWindow *win,
 
     return gi;
 }
 
     return gi;
 }
-<<<<<<< win32.cpp
-#endif
-=======
 
 
-#else // !wxUSE_MENUS
+#endif // wxUSE_MENUS
 
 
-void wxWin32Renderer::DrawMenuBarItem(wxDC& WXUNUSED(dc),
-                                      const wxRect& WXUNUSED(rectOrig),
-                                      const wxString& WXUNUSED(label),
-                                      int WXUNUSED(flags),
-                                      int WXUNUSED(indexAccel))
-{
-}
+#if wxUSE_STATUSBAR
 
 
-void wxWin32Renderer::DrawMenuItem(wxDC& WXUNUSED(dc),
-                                   wxCoord WXUNUSED(y),
-                                   const wxMenuGeometryInfo& WXUNUSED(gi),
-                                   const wxString& WXUNUSED(label),
-                                   const wxString& WXUNUSED(accel),
-                                   const wxBitmap& WXUNUSED(bitmap),
-                                   int WXUNUSED(flags),
-                                   int WXUNUSED(indexAccel))
-{
-}
+// ----------------------------------------------------------------------------
+// status bar
+// ----------------------------------------------------------------------------
 
 
-void wxWin32Renderer::DrawMenuSeparator(wxDC& WXUNUSED(dc),
-                                        wxCoord WXUNUSED(y),
-                                        const wxMenuGeometryInfo& WXUNUSED(gi))
+void wxWin32Renderer::DrawStatusField(wxDC& dc,
+                                      const wxRect& rect,
+                                      const wxString& label,
+                                      int flags,
+                                      int style)
 {
 {
-}
+    wxRect rectIn;
 
 
-wxSize wxWin32Renderer::GetMenuBarItemSize(const wxSize& size) const
-{
-    return size;
-}
+    if ( flags & wxCONTROL_SIZEGRIP )
+    {
+        // draw the size grip: it is a normal rect except that in the lower
+        // right corner we have several bands which may be used for dragging
+        // the status bar corner
+        //
+        // each band consists of 4 stripes: m_penHighlight, double
+        // m_penDarkGrey and transparent one
+        wxCoord x2 = rect.GetRight(),
+                y2 = rect.GetBottom();
+
+        // draw the upper left part of the rect normally
+        if (style != wxSB_FLAT)
+        {
+            if (style == wxSB_RAISED)
+                dc.SetPen(m_penHighlight);
+            else
+                dc.SetPen(m_penDarkGrey);
+            dc.DrawLine(rect.GetLeft(), rect.GetTop(), rect.GetLeft(), y2);
+            dc.DrawLine(rect.GetLeft() + 1, rect.GetTop(), x2, rect.GetTop());
+        }
+
+        // draw the grey stripes of the grip
+        size_t n;
+        wxCoord ofs = WIDTH_STATUSBAR_GRIP_BAND - 1;
+        for ( n = 0; n < NUM_STATUSBAR_GRIP_BANDS; n++, ofs += WIDTH_STATUSBAR_GRIP_BAND )
+        {
+            dc.DrawLine(x2 - ofs + 1, y2 - 1, x2, y2 - ofs);
+            dc.DrawLine(x2 - ofs, y2 - 1, x2, y2 - ofs - 1);
+        }
+
+        // draw the white stripes
+        dc.SetPen(m_penHighlight);
+        ofs = WIDTH_STATUSBAR_GRIP_BAND + 1;
+        for ( n = 0; n < NUM_STATUSBAR_GRIP_BANDS; n++, ofs += WIDTH_STATUSBAR_GRIP_BAND )
+        {
+            dc.DrawLine(x2 - ofs + 1, y2 - 1, x2, y2 - ofs);
+        }
+
+        // draw the remaining rect boundaries
+        if (style != wxSB_FLAT)
+        {
+            if (style == wxSB_RAISED)
+                dc.SetPen(m_penDarkGrey);
+            else
+                dc.SetPen(m_penHighlight);
+            ofs -= WIDTH_STATUSBAR_GRIP_BAND;
+            dc.DrawLine(x2, rect.GetTop(), x2, y2 - ofs + 1);
+            dc.DrawLine(rect.GetLeft(), y2, x2 - ofs + 1, y2);
+        }
+
+        rectIn = rect;
+        rectIn.Deflate(1);
 
 
-wxMenuGeometryInfo *
-wxWin32Renderer::GetMenuGeometry(wxWindow *WXUNUSED(win),
-                                 const wxMenu& WXUNUSED(menu)) const
-{
-    return NULL;
+        rectIn.width -= STATUSBAR_GRIP_SIZE;
+
+        // this will prevent the standard version from drawing any borders
+        style = wxSB_FLAT;
+    }
+
+    wxStdRenderer::DrawStatusField(dc, rect, label, flags, style);
 }
 
 }
 
-#endif // wxUSE_MENUS/!wxUSE_MENUS
+#endif // wxUSE_STATUSBAR
 
 
->>>>>>> 1.5
 // ----------------------------------------------------------------------------
 // combobox
 // ----------------------------------------------------------------------------
 
 void wxWin32Renderer::GetComboBitmaps(wxBitmap *bmpNormal,
 // ----------------------------------------------------------------------------
 // combobox
 // ----------------------------------------------------------------------------
 
 void wxWin32Renderer::GetComboBitmaps(wxBitmap *bmpNormal,
+                                      wxBitmap * WXUNUSED(bmpFocus),
                                       wxBitmap *bmpPressed,
                                       wxBitmap *bmpDisabled)
 {
                                       wxBitmap *bmpPressed,
                                       wxBitmap *bmpDisabled)
 {
@@ -2765,53 +2674,35 @@ void wxWin32Renderer::GetComboBitmaps(wxBitmap *bmpNormal,
 }
 
 // ----------------------------------------------------------------------------
 }
 
 // ----------------------------------------------------------------------------
-// background
+// scrollbar
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 
-void wxWin32Renderer::DoDrawBackground(wxDC& dc,
-                                       const wxColour& col,
-                                       const wxRect& rect)
+void wxWin32Renderer::DrawArrowBorder(wxDC& dc, wxRect *rect, bool isPressed)
 {
 {
-    wxBrush brush(col, wxSOLID);
-    dc.SetBrush(brush);
-    dc.SetPen(*wxTRANSPARENT_PEN);
-    dc.DrawRectangle(rect);
-}
+    if ( isPressed )
+    {
+        DrawRect(dc, rect, m_penDarkGrey);
 
 
-void wxWin32Renderer::DrawBackground(wxDC& dc,
-                                     const wxColour& col,
-                                     const wxRect& rect,
-                                     int flags)
-{
-    // just fill it with the given or default bg colour
-    wxColour colBg = col.Ok() ? col : wxSCHEME_COLOUR(m_scheme, CONTROL);
-    DoDrawBackground(dc, colBg, rect);
+        // the arrow is usually drawn inside border of width 2 and is offset by
+        // another pixel in both directions when it's pressed - as the border
+        // in this case is more narrow as well, we have to adjust rect like
+        // this:
+        rect->Inflate(-1);
+        rect->x++;
+        rect->y++;
+    }
+    else // !pressed
+    {
+        DrawAntiSunkenBorder(dc, rect);
+    }
 }
 
 }
 
-// ----------------------------------------------------------------------------
-// scrollbar
-// ----------------------------------------------------------------------------
-
 void wxWin32Renderer::DrawArrow(wxDC& dc,
                                 wxDirection dir,
                                 const wxRect& rect,
                                 int flags)
 {
 void wxWin32Renderer::DrawArrow(wxDC& dc,
                                 wxDirection dir,
                                 const wxRect& rect,
                                 int flags)
 {
-    // get the bitmap for this arrow
-    wxArrowDirection arrowDir;
-    switch ( dir )
-    {
-        case wxLEFT:    arrowDir = Arrow_Left; break;
-        case wxRIGHT:   arrowDir = Arrow_Right; break;
-        case wxUP:      arrowDir = Arrow_Up; break;
-        case wxDOWN:    arrowDir = Arrow_Down; break;
-
-        default:
-            wxFAIL_MSG(_T("unknown arrow direction"));
-            return;
-    }
-
-    wxArrowStyle arrowStyle;
+    ArrowStyle arrowStyle;
     if ( flags & wxCONTROL_PRESSED )
     {
         // can't be pressed and disabled
     if ( flags & wxCONTROL_PRESSED )
     {
         // can't be pressed and disabled
@@ -2822,13 +2713,13 @@ void wxWin32Renderer::DrawArrow(wxDC& dc,
         arrowStyle = flags & wxCONTROL_DISABLED ? Arrow_Disabled : Arrow_Normal;
     }
 
         arrowStyle = flags & wxCONTROL_DISABLED ? Arrow_Disabled : Arrow_Normal;
     }
 
-    DrawArrowButton(dc, rect, arrowDir, arrowStyle);
+    DrawArrowButton(dc, rect, GetArrowDirection(dir), arrowStyle);
 }
 
 void wxWin32Renderer::DrawArrow(wxDC& dc,
                                 const wxRect& rect,
 }
 
 void wxWin32Renderer::DrawArrow(wxDC& dc,
                                 const wxRect& rect,
-                                wxArrowDirection arrowDir,
-                                wxArrowStyle arrowStyle)
+                                ArrowDirection arrowDir,
+                                ArrowStyle arrowStyle)
 {
     const wxBitmap& bmp = m_bmpArrows[arrowStyle][arrowDir];
 
 {
     const wxBitmap& bmp = m_bmpArrows[arrowStyle][arrowDir];
 
@@ -2842,24 +2733,24 @@ void wxWin32Renderer::DrawArrow(wxDC& dc,
         x--;
 
     // draw it
         x--;
 
     // draw it
-    dc.DrawBitmap(bmp, x, y, TRUE /* use mask */);
+    dc.DrawBitmap(bmp, x, y, true /* use mask */);
 }
 
 void wxWin32Renderer::DrawArrowButton(wxDC& dc,
                                       const wxRect& rectAll,
 }
 
 void wxWin32Renderer::DrawArrowButton(wxDC& dc,
                                       const wxRect& rectAll,
-                                      wxArrowDirection arrowDir,
-                                      wxArrowStyle arrowStyle)
+                                      ArrowDirection arrowDir,
+                                      ArrowStyle arrowStyle)
 {
     wxRect rect = rectAll;
 {
     wxRect rect = rectAll;
-    DoDrawBackground(dc, wxSCHEME_COLOUR(m_scheme, CONTROL), rect);
+    DrawBackground(dc, wxSCHEME_COLOUR(m_scheme, CONTROL), rect);
     DrawArrowBorder(dc, &rect, arrowStyle == Arrow_Pressed);
     DrawArrow(dc, rect, arrowDir, arrowStyle);
 }
 
 void wxWin32Renderer::DrawScrollbarThumb(wxDC& dc,
     DrawArrowBorder(dc, &rect, arrowStyle == Arrow_Pressed);
     DrawArrow(dc, rect, arrowDir, arrowStyle);
 }
 
 void wxWin32Renderer::DrawScrollbarThumb(wxDC& dc,
-                                         wxOrientation orient,
+                                         wxOrientation WXUNUSED(orient),
                                          const wxRect& rect,
                                          const wxRect& rect,
-                                         int flags)
+                                         int WXUNUSED(flags))
 {
     // we don't use the flags, the thumb never changes appearance
     wxRect rectThumb = rect;
 {
     // we don't use the flags, the thumb never changes appearance
     wxRect rectThumb = rect;
@@ -2868,78 +2759,327 @@ void wxWin32Renderer::DrawScrollbarThumb(wxDC& dc,
 }
 
 void wxWin32Renderer::DrawScrollbarShaft(wxDC& dc,
 }
 
 void wxWin32Renderer::DrawScrollbarShaft(wxDC& dc,
-                                         wxOrientation orient,
+                                         wxOrientation WXUNUSED(orient),
                                          const wxRect& rectBar,
                                          int flags)
 {
     wxColourScheme::StdColour col = flags & wxCONTROL_PRESSED
                                     ? wxColourScheme::SCROLLBAR_PRESSED
                                     : wxColourScheme::SCROLLBAR;
                                          const wxRect& rectBar,
                                          int flags)
 {
     wxColourScheme::StdColour col = flags & wxCONTROL_PRESSED
                                     ? wxColourScheme::SCROLLBAR_PRESSED
                                     : wxColourScheme::SCROLLBAR;
-    DoDrawBackground(dc, m_scheme->Get(col), rectBar);
+    DrawBackground(dc, m_scheme->Get(col), rectBar);
 }
 
 }
 
-void wxWin32Renderer::DrawScrollCorner(wxDC& dc, const wxRect& rect)
-{
-    DoDrawBackground(dc, wxSCHEME_COLOUR(m_scheme, CONTROL), rect);
-}
+// ----------------------------------------------------------------------------
+// standard icons
+// ----------------------------------------------------------------------------
 
 
-wxRect wxWin32Renderer::GetScrollbarRect(const wxScrollBar *scrollbar,
-                                         wxScrollBar::Element elem,
-                                         int thumbPos) const
-{
-    return StandardGetScrollbarRect(scrollbar, elem,
-                                    thumbPos, m_sizeScrollbarArrow);
-}
+/* Copyright (c) Julian Smart */
+static char *error_xpm[]={
+/* columns rows colors chars-per-pixel */
+"32 32 70 1",
+"- c #BF0101",
+"b c #361F1F",
+"& c #C08484",
+"X c #BF3333",
+"# c #C08181",
+"% c #C01111",
+"d c #C51515",
+"s c #551818",
+"O c #C07E7E",
+": c #C00E0E",
+"u c #E28A8A",
+"2 c #C81F1F",
+"8 c #FFFFFF",
+"p c #E59494",
+"< c #BB0101",
+"y c #DA6A6A",
+"A c #4C4C4C",
+"9 c #F7DFDF",
+"@ c #BF5353",
+"w c #FAE9E9",
+"F c #272727",
+"5 c #D24A4A",
+". c #C06363",
+"n c #BF8282",
+"7 c #F2C9C9",
+"t c #C09292",
+"M c #3E3E3E",
+"x c #4D4D4D",
+"4 c #CA2A2A",
+"h c #E79F9F",
+"* c #C05454",
+"D c #711212",
+"V c #737373",
+"$ c #BF3232",
+"N c #900B0B",
+"6 c #BD0303",
+"3 c #DF7F7F",
+"K c #6F1212",
+"C c #BD0000",
+"m c #950909",
+"P c #8A8A8A",
+"j c #D75F5F",
+"  c None",
+"e c #F4D4D4",
+"S c #BF2020",
+"L c #747474",
+"G c #842C2C",
+"c c #ECB4B4",
+"l c #2E2121",
+"g c #BF7E7E",
+"k c #9B0808",
+"= c #BF0505",
+"a c #B10303",
+"q c #7E2020",
+"1 c #642222",
+"J c #676767",
+"B c #322020",
+"; c #C00303",
+"i c #242424",
+"o c #C00000",
+"> c #BF1F1F",
+", c #842B2B",
+"f c #701212",
+"0 c #BE0000",
+"r c #960909",
+"H c #686868",
+"v c #BC0000",
+"Z c #671414",
+"+ c #C02020",
+"z c #CD3535",
+/* pixels */
+"                                ",
+"                                ",
+"            .XoooOO             ",
+"         .+ooooooooo@#          ",
+"        $oooooooooooo%&         ",
+"      *=-ooooooooooooo;:        ",
+"     *oooooooooooooooooo>       ",
+"     =ooooooooooooooooooo,      ",
+"    $-ooooooooooooooooooo<1     ",
+"   .oooooo2334ooo533oooooo6     ",
+"   +ooooooo789oo2883oooooo0q    ",
+"   oooooooo2w83o78eoooooooor    ",
+"  toooooooooy88u884oooooooori   ",
+"  Xooooooooooe888poooooooooas   ",
+"  ooooooooooo4889doooooooooof   ",
+"  ooooooooooo588w2oooooooooofi  ",
+"  oooooooooodw8887oooooooooofi  ",
+"  goooooooooh8w588jooooooookli  ",
+"  tooooooooz885op8wdooooooorix  ",
+"   oooooood98cood98cooooooori   ",
+"   @oooooop8w2ooo5885ooooovbi   ",
+"   n%ooooooooooooooooooooomiM   ",
+"    &;oooooooooooooooooooNBiV   ",
+"     :ooooooooooooooooooCZiA    ",
+"     nSooooooooooooooooCDiF     ",
+"      nG<oooooooooooooNZiiH     ",
+"        160ooooooooovmBiFH      ",
+"         nqrraoookrrbiiA        ",
+"          nJisKKKliiiML         ",
+"             nPiiix             ",
+"                                ",
+"                                "
+};
 
 
-wxCoord wxWin32Renderer::GetScrollbarSize(const wxScrollBar *scrollbar)
-{
-    return StandardScrollBarSize(scrollbar, m_sizeScrollbarArrow);
-}
+/* Copyright (c) Julian Smart */
+static char *info_xpm[]={
+/* columns rows colors chars-per-pixel */
+"32 32 17 1",
+"* c #A1A3FB",
+"X c #FFFFFF",
+"O c #191EF4",
+"= c #777AF9",
+": c #4D51F7",
+"  c None",
+"- c #2328F5",
+"+ c #4247F6",
+"; c #C1C2FC",
+". c #C0C0C0",
+"& c #E0E1FE",
+"% c #242424",
+"> c #2D32F5",
+"o c #CBCCFD",
+"# c #0309F3",
+"@ c #8C8FFA",
+"$ c #EAEBFE",
+/* pixels */
+"          .......               ",
+"       ...XXXXXXX...            ",
+"     ..XXXXXXXXXXXXX..          ",
+"    .XXXXXXXXXXXXXXXXX.         ",
+"   .XXXXXXXXoO+XXXXXXXX.        ",
+"  .XXXXXXXXX@#OXXXXXXXXX.       ",
+" .XXXXXXXXXX$@oXXXXXXXXXX.      ",
+" .XXXXXXXXXXXXXXXXXXXXXXX.%     ",
+" .XXXXXXXXX&*=-XXXXXXXXXX.%%    ",
+".XXXXXXXXXX;:#>XXXXXXXXXXX.%    ",
+".XXXXXXXXXXX;#+XXXXXXXXXXX.%    ",
+".XXXXXXXXXXX;#+XXXXXXXXXXX.%%   ",
+" .XXXXXXXXXX;#+XXXXXXXXXX.%%%   ",
+" .XXXXXXXXXX;#+XXXXXXXXXX.%%%   ",
+" .XXXXXXXXXX;#+XXXXXXXXXX.%%    ",
+"  .XXXXXXXX*-##+XXXXXXXX.%%%    ",
+"   .XXXXXXXXXXXXXXXXXXX.%%%%    ",
+"    .XXXXXXXXXXXXXXXXX.%%%%     ",
+"     ..XXXXXXXXXXXXX..%%%%      ",
+"      %...XXXXXXXX..%%%%%       ",
+"       %%%..XXXXXX.%%%%%        ",
+"         %%%.XXXXX.%%%          ",
+"            %.XXXX.%%           ",
+"              .XXX.%%           ",
+"               .XX.%%           ",
+"                .X.%%           ",
+"                 ..%%           ",
+"                  .%%           ",
+"                   %%           ",
+"                    %           ",
+"                                ",
+"                                "
+};
 
 
-wxHitTest wxWin32Renderer::HitTestScrollbar(const wxScrollBar *scrollbar,
-                                            const wxPoint& pt) const
-{
-    return StandardHitTestScrollbar(scrollbar, pt, m_sizeScrollbarArrow);
-}
+/* Copyright (c) Julian Smart */
+static char *question_xpm[]={
+/* columns rows colors chars-per-pixel */
+"32 32 16 1",
+"O c #A3A3FF",
+"X c #FFFFFF",
+"% c #CACAFF",
+"- c #4141FF",
+"= c #6060FF",
+"* c #2B2BFF",
+"@ c #B5B5FF",
+"  c None",
+"# c #1616FF",
+"+ c #8181FF",
+"$ c #0000FF",
+". c #C0C0C0",
+"; c #5555FF",
+": c #242424",
+"o c #E7E7FF",
+"& c #7575FF",
+/* pixels */
+"          .......               ",
+"       ...XXXXXXX...            ",
+"     ..XXXXXXXXXXXXX..          ",
+"    .XXXXXXoO++@XXXXXX.         ",
+"   .XXXXXXO#$$$$#%XXXXX.        ",
+"  .XXXXXX@$$#&&#$#oXXXXX.       ",
+" .XXXXXXX*$$%XX%$$=XXXXXX.      ",
+" .XXXXXXX+-;XXXX$$-XXXXXX.:     ",
+" .XXXXXXXXXXXXX+$$&XXXXXX.::    ",
+".XXXXXXXXXXXXo;$$*oXXXXXXX.:    ",
+".XXXXXXXXXXXo*$$*oXXXXXXXX.:    ",
+".XXXXXXXXXXX+$$*oXXXXXXXXX.::   ",
+" .XXXXXXXXXX-$$oXXXXXXXXX.:::   ",
+" .XXXXXXXXXXX--XXXXXXXXXX.:::   ",
+" .XXXXXXXXXXXXXXXXXXXXXXX.::    ",
+"  .XXXXXXXXX-$$XXXXXXXXX.:::    ",
+"   .XXXXXXXX-$$XXXXXXXX.::::    ",
+"    .XXXXXXXO++XXXXXXX.::::     ",
+"     ..XXXXXXXXXXXXX..::::      ",
+"      :...XXXXXXXX..:::::       ",
+"       :::..XXXXXX.:::::        ",
+"         :::.XXXXX.:::          ",
+"            :.XXXX.::           ",
+"              .XXX.::           ",
+"               .XX.::           ",
+"                .X.::           ",
+"                 ..::           ",
+"                  .::           ",
+"                   ::           ",
+"                    :           ",
+"                                ",
+"                                "
+};
 
 
-wxCoord wxWin32Renderer::ScrollbarToPixel(const wxScrollBar *scrollbar,
-                                          int thumbPos)
-{
-    return StandardScrollbarToPixel(scrollbar, thumbPos, m_sizeScrollbarArrow);
-}
+/* Copyright (c) Julian Smart */
+static char *warning_xpm[]={
+/* columns rows colors chars-per-pixel */
+"32 32 9 1",
+"@ c Black",
+"o c #A6A800",
+"+ c #8A8C00",
+"$ c #B8BA00",
+"  c None",
+"O c #6E7000",
+"X c #DCDF00",
+". c #C00000",
+"# c #373800",
+/* pixels */
+"                                ",
+"                                ",
+"                                ",
+"                .               ",
+"               ...              ",
+"               ...              ",
+"              .....             ",
+"             ...X..             ",
+"             ..XXX..            ",
+"            ...XXX...           ",
+"            ..XXXXX..           ",
+"           ..XXXXXX...          ",
+"          ...XXoO+XX..          ",
+"          ..XXXO@#XXX..         ",
+"         ..XXXXO@#XXX...        ",
+"        ...XXXXO@#XXXX..        ",
+"        ..XXXXXO@#XXXX...       ",
+"       ...XXXXXo@OXXXXX..       ",
+"      ...XXXXXXo@OXXXXXX..      ",
+"      ..XXXXXXX$@OXXXXXX...     ",
+"     ...XXXXXXXX@XXXXXXXX..     ",
+"    ...XXXXXXXXXXXXXXXXXX...    ",
+"    ..XXXXXXXXXXOXXXXXXXXX..    ",
+"   ...XXXXXXXXXO@#XXXXXXXXX..   ",
+"   ..XXXXXXXXXXX#XXXXXXXXXX...  ",
+"  ...XXXXXXXXXXXXXXXXXXXXXXX..  ",
+" ...XXXXXXXXXXXXXXXXXXXXXXXX... ",
+" .............................. ",
+" .............................. ",
+"                                ",
+"                                ",
+"                                "
+};
 
 
-int wxWin32Renderer::PixelToScrollbar(const wxScrollBar *scrollbar,
-                                      wxCoord coord)
+
+wxBitmap wxWin32ArtProvider::CreateBitmap(const wxArtID& id,
+                                          const wxArtClient& WXUNUSED(client),
+                                          const wxSize& WXUNUSED(size))
 {
 {
-    return StandardPixelToScrollbar(scrollbar, coord, m_sizeScrollbarArrow);
+    if ( id == wxART_INFORMATION )
+        return wxBitmap(info_xpm);
+    if ( id == wxART_ERROR )
+        return wxBitmap(error_xpm);
+    if ( id == wxART_WARNING )
+        return wxBitmap(warning_xpm);
+    if ( id == wxART_QUESTION )
+        return wxBitmap(question_xpm);
+    return wxNullBitmap;
 }
 
 }
 
+
+#if wxUSE_TEXTCTRL
+
 // ----------------------------------------------------------------------------
 // text control geometry
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 // text control geometry
 // ----------------------------------------------------------------------------
 
-static inline int GetTextBorderWidth()
-{
-    return 1;
-}
-
-wxRect wxWin32Renderer::GetTextTotalArea(const wxTextCtrl *text,
-                                         const wxRect& rect)
+wxRect
+wxWin32Renderer::GetTextTotalArea(const wxTextCtrl *text,
+                                  const wxRect& rect) const
 {
 {
-    wxRect rectTotal = rect;
-
-    wxCoord widthBorder = GetTextBorderWidth();
-    rectTotal.Inflate(widthBorder);
+    wxRect rectTotal = wxStdRenderer::GetTextTotalArea(text, rect);
 
 
-    // this is what Windows does
+    // this is strange but it's what Windows does
     rectTotal.height++;
 
     return rectTotal;
 }
 
     rectTotal.height++;
 
     return rectTotal;
 }
 
-wxRect wxWin32Renderer::GetTextClientArea(const wxTextCtrl *text,
-                                          const wxRect& rect,
-                                          wxCoord *extraSpaceBeyond)
+wxRect
+wxWin32Renderer::GetTextClientArea(const wxTextCtrl *text,
+                                   const wxRect& rect,
+                                   wxCoord *extraSpaceBeyond) const
 {
     wxRect rectText = rect;
 
 {
     wxRect rectText = rect;
 
@@ -2947,15 +3087,11 @@ wxRect wxWin32Renderer::GetTextClientArea(const wxTextCtrl *text,
     if ( rectText.height > 0 )
         rectText.height--;
 
     if ( rectText.height > 0 )
         rectText.height--;
 
-    wxCoord widthBorder = GetTextBorderWidth();
-    rectText.Inflate(-widthBorder);
-
-    if ( extraSpaceBeyond )
-        *extraSpaceBeyond = 0;
-
-    return rectText;
+    return wxStdRenderer::GetTextClientArea(text, rect, extraSpaceBeyond);
 }
 
 }
 
+#endif // wxUSE_TEXTCTRL
+
 // ----------------------------------------------------------------------------
 // size adjustments
 // ----------------------------------------------------------------------------
 // ----------------------------------------------------------------------------
 // size adjustments
 // ----------------------------------------------------------------------------
@@ -2975,34 +3111,65 @@ void wxWin32Renderer::AdjustSize(wxSize *size, const wxWindow *window)
         // skip border width adjustments, they don't make sense for us
         return;
     }
         // skip border width adjustments, they don't make sense for us
         return;
     }
-#endif // wxUSE_SCROLLBAR/!wxUSE_SCROLLBAR
+#endif // wxUSE_SCROLLBAR
+
+#if wxUSE_BMPBUTTON
+    if ( wxDynamicCast(window, wxBitmapButton) )
+    {
+        // do nothing
+    } else
+#endif // wxUSE_BMPBUTTON
+#if wxUSE_BUTTON || wxUSE_TOGGLEBTN
+    if ( 0
+#  if wxUSE_BUTTON
+         || wxDynamicCast(window, wxButton)
+#  endif // wxUSE_BUTTON
+#  if wxUSE_TOGGLEBTN
+         || wxDynamicCast(window, wxToggleButton)
+#  endif // wxUSE_TOGGLEBTN
+        )
+    {
+        if ( !(window->GetWindowStyle() & wxBU_EXACTFIT) )
+        {
+            // TODO: don't harcode all this
+            size->x += 3*window->GetCharWidth();
 
 
-#if wxUSE_BUTTON
-    if ( wxDynamicCast(window, wxButton) )
-    {
-        // TODO
-        size->x += 3*window->GetCharWidth();
-#if 0 // do allow creating small buttons if wanted
-        wxSize sizeDef = wxButton::GetDefaultSize();
-        if ( size->x < sizeDef.x )
-            size->x = sizeDef.x;
-#endif // 0
+            wxCoord heightBtn = (11*(window->GetCharHeight() + 8))/10;
+            if ( size->y < heightBtn - 8 )
+                size->y = heightBtn;
+            else
+                size->y += 9;
+        }
 
 
-        wxCoord heightBtn = (11*(window->GetCharHeight() + 8))/10;
-        if ( size->y < heightBtn - 8 )
-            size->y = heightBtn;
-        else
-            size->y += 9;
+        // for compatibility with other ports, the buttons default size is never
+        // less than the standard one, but not when display not PDAs.
+        if (wxSystemSettings::GetScreenType() > wxSYS_SCREEN_PDA)
+        {
+            if ( !(window->GetWindowStyle() & wxBU_EXACTFIT) )
+            {
+                wxSize szDef = wxButton::GetDefaultSize();
+                if ( size->x < szDef.x )
+                    size->x = szDef.x;
+            }
+        }
 
         // no border width adjustments for buttons
         return;
     }
 
         // no border width adjustments for buttons
         return;
     }
-#endif // wxUSE_BUTTON
+#endif // wxUSE_BUTTON || wxUSE_TOGGLEBTN
+
+    wxStdRenderer::AdjustSize(size, window);
+}
+
+wxBitmap wxWin32Renderer::GetFrameButtonBitmap(FrameButtonType type)
+{
+    wxBitmap& bmp = m_bmpFrameButtons[type];
+    if ( !bmp.Ok() )
+    {
+        bmp = wxBitmap(ms_xpmFrameButtons[type]);
+    }
 
 
-    // take into account the border width
-    wxRect rectBorder = GetBorderDimensions(window->GetBorder());
-    size->x += rectBorder.x + rectBorder.width;
-    size->y += rectBorder.y + rectBorder.height;
+    return bmp;
 }
 
 // ============================================================================
 }
 
 // ============================================================================
@@ -3013,34 +3180,44 @@ void wxWin32Renderer::AdjustSize(wxSize *size, const wxWindow *window)
 // wxWin32InputHandler
 // ----------------------------------------------------------------------------
 
 // wxWin32InputHandler
 // ----------------------------------------------------------------------------
 
-wxWin32InputHandler::wxWin32InputHandler(wxWin32Renderer *renderer)
-{
-    m_renderer = renderer;
-}
-
-bool wxWin32InputHandler::HandleKey(wxControl *control,
-                                    const wxKeyEvent& event,
-                                    bool pressed)
+bool wxWin32InputHandler::HandleKey(wxInputConsumer * WXUNUSED(control),
+                                    const wxKeyEvent& WXUNUSED(event),
+                                    bool WXUNUSED(pressed))
 {
 {
-    return FALSE;
+    return false;
 }
 
 }
 
-bool wxWin32InputHandler::HandleMouse(wxControl *control,
+bool wxWin32InputHandler::HandleMouse(wxInputConsumer *control,
                                       const wxMouseEvent& event)
 {
                                       const wxMouseEvent& event)
 {
-    return FALSE;
+    // clicking on the control gives it focus
+    if ( event.ButtonDown() )
+    {
+        wxWindow *win = control->GetInputWindow();
+
+        if ( (wxWindow::FindFocus() != control->GetInputWindow()) &&
+             win->AcceptsFocus() )
+        {
+            win->SetFocus();
+
+            return true;
+        }
+    }
+
+    return false;
 }
 
 }
 
+#if wxUSE_SCROLLBAR
+
 // ----------------------------------------------------------------------------
 // wxWin32ScrollBarInputHandler
 // ----------------------------------------------------------------------------
 
 wxWin32ScrollBarInputHandler::
 // ----------------------------------------------------------------------------
 // wxWin32ScrollBarInputHandler
 // ----------------------------------------------------------------------------
 
 wxWin32ScrollBarInputHandler::
-wxWin32ScrollBarInputHandler(wxWin32Renderer *renderer,
-                             wxInputHandler *handler)
+wxWin32ScrollBarInputHandler(wxRenderer *renderer, wxInputHandler *handler)
         : wxStdScrollBarInputHandler(renderer, handler)
 {
         : wxStdScrollBarInputHandler(renderer, handler)
 {
-    m_scrollPaused = FALSE;
+    m_scrollPaused = false;
     m_interval = 0;
 }
 
     m_interval = 0;
 }
 
@@ -3049,7 +3226,7 @@ bool wxWin32ScrollBarInputHandler::OnScrollTimer(wxScrollBar *scrollbar,
 {
     // stop if went beyond the position of the original click (this can only
     // happen when we scroll by pages)
 {
     // stop if went beyond the position of the original click (this can only
     // happen when we scroll by pages)
-    bool stop = FALSE;
+    bool stop = false;
     if ( action == wxACTION_SCROLL_PAGE_DOWN )
     {
         stop = m_renderer->HitTestScrollbar(scrollbar, m_ptStartScrolling)
     if ( action == wxACTION_SCROLL_PAGE_DOWN )
     {
         stop = m_renderer->HitTestScrollbar(scrollbar, m_ptStartScrolling)
@@ -3067,13 +3244,13 @@ bool wxWin32ScrollBarInputHandler::OnScrollTimer(wxScrollBar *scrollbar,
 
         scrollbar->Refresh();
 
 
         scrollbar->Refresh();
 
-        return FALSE;
+        return false;
     }
 
     return wxStdScrollBarInputHandler::OnScrollTimer(scrollbar, action);
 }
 
     }
 
     return wxStdScrollBarInputHandler::OnScrollTimer(scrollbar, action);
 }
 
-bool wxWin32ScrollBarInputHandler::HandleMouse(wxControl *control,
+bool wxWin32ScrollBarInputHandler::HandleMouse(wxInputConsumer *control,
                                                const wxMouseEvent& event)
 {
     // remember the current state
                                                const wxMouseEvent& event)
 {
     // remember the current state
@@ -3093,22 +3270,22 @@ bool wxWin32ScrollBarInputHandler::HandleMouse(wxControl *control,
     return rc;
 }
 
     return rc;
 }
 
-bool wxWin32ScrollBarInputHandler::HandleMouseMove(wxControl *control,
+bool wxWin32ScrollBarInputHandler::HandleMouseMove(wxInputConsumer *control,
                                                    const wxMouseEvent& event)
 {
     // we don't highlight scrollbar elements, so there is no need to process
     // mouse move events normally - only do it while mouse is captured (i.e.
     // when we're dragging the thumb or pressing on something)
     if ( !m_winCapture )
                                                    const wxMouseEvent& event)
 {
     // we don't highlight scrollbar elements, so there is no need to process
     // mouse move events normally - only do it while mouse is captured (i.e.
     // when we're dragging the thumb or pressing on something)
     if ( !m_winCapture )
-        return FALSE;
+        return false;
 
     if ( event.Entering() )
     {
         // we're not interested in this at all
 
     if ( event.Entering() )
     {
         // we're not interested in this at all
-        return FALSE;
+        return false;
     }
 
     }
 
-    wxScrollBar *scrollbar = wxStaticCast(control, wxScrollBar);
+    wxScrollBar *scrollbar = wxStaticCast(control->GetInputWindow(), wxScrollBar);
     wxHitTest ht;
     if ( m_scrollPaused )
     {
     wxHitTest ht;
     if ( m_scrollPaused )
     {
@@ -3117,20 +3294,20 @@ bool wxWin32ScrollBarInputHandler::HandleMouseMove(wxControl *control,
         if ( event.Leaving() )
         {
             // it surely didn't
         if ( event.Leaving() )
         {
             // it surely didn't
-            return FALSE;
+            return false;
         }
 
         ht = m_renderer->HitTestScrollbar(scrollbar, event.GetPosition());
         if ( ht == m_htLast )
         {
             // yes it did, resume scrolling
         }
 
         ht = m_renderer->HitTestScrollbar(scrollbar, event.GetPosition());
         if ( ht == m_htLast )
         {
             // yes it did, resume scrolling
-            m_scrollPaused = FALSE;
+            m_scrollPaused = false;
             if ( m_timerScroll )
             {
                 // we were scrolling by line/page, restart timer
                 m_timerScroll->Start(m_interval);
 
             if ( m_timerScroll )
             {
                 // we were scrolling by line/page, restart timer
                 m_timerScroll->Start(m_interval);
 
-                Press(scrollbar, TRUE);
+                Press(scrollbar, true);
             }
             else // we were dragging the thumb
             {
             }
             else // we were dragging the thumb
             {
@@ -3138,7 +3315,7 @@ bool wxWin32ScrollBarInputHandler::HandleMouseMove(wxControl *control,
                 HandleThumbMove(scrollbar, m_eventLastDrag);
             }
 
                 HandleThumbMove(scrollbar, m_eventLastDrag);
             }
 
-            return TRUE;
+            return true;
         }
     }
     else // normal case, scrolling hasn't been paused
         }
     }
     else // normal case, scrolling hasn't been paused
@@ -3146,6 +3323,8 @@ bool wxWin32ScrollBarInputHandler::HandleMouseMove(wxControl *control,
         // if we're scrolling the scrollbar because the arrow or the shaft was
         // pressed, check that the mouse stays on the same scrollbar element
 
         // if we're scrolling the scrollbar because the arrow or the shaft was
         // pressed, check that the mouse stays on the same scrollbar element
 
+#if 0
+        // Always let thumb jump back if we leave the scrollbar
         if ( event.Moving() )
         {
             ht = m_renderer->HitTestScrollbar(scrollbar, event.GetPosition());
         if ( event.Moving() )
         {
             ht = m_renderer->HitTestScrollbar(scrollbar, event.GetPosition());
@@ -3154,6 +3333,21 @@ bool wxWin32ScrollBarInputHandler::HandleMouseMove(wxControl *control,
         {
             ht = wxHT_NOWHERE;
         }
         {
             ht = wxHT_NOWHERE;
         }
+#else
+        // Jump back only if we get far away from it
+        wxPoint pos = event.GetPosition();
+        if (scrollbar->HasFlag( wxVERTICAL ))
+        {
+            if (pos.x > -40 && pos.x < scrollbar->GetSize().x+40)
+               pos.x = 5;
+        }
+        else
+        {
+            if (pos.y > -40 && pos.y < scrollbar->GetSize().y+40)
+               pos.y = 5;
+        }
+        ht = m_renderer->HitTestScrollbar(scrollbar, pos );
+#endif
 
         // if we're dragging the thumb and the mouse stays in the scrollbar, it
         // is still ok - we only want to catch the case when the mouse leaves
 
         // if we're dragging the thumb and the mouse stays in the scrollbar, it
         // is still ok - we only want to catch the case when the mouse leaves
@@ -3173,10 +3367,10 @@ bool wxWin32ScrollBarInputHandler::HandleMouseMove(wxControl *control,
                 // pause scrolling
                 m_interval = m_timerScroll->GetInterval();
                 m_timerScroll->Stop();
                 // pause scrolling
                 m_interval = m_timerScroll->GetInterval();
                 m_timerScroll->Stop();
-                m_scrollPaused = TRUE;
+                m_scrollPaused = true;
 
                 // unpress the arrow
 
                 // unpress the arrow
-                Press(scrollbar, FALSE);
+                Press(scrollbar, false);
             }
             else // we were dragging the thumb
             {
             }
             else // we were dragging the thumb
             {
@@ -3189,18 +3383,22 @@ bool wxWin32ScrollBarInputHandler::HandleMouseMove(wxControl *control,
                 HandleThumbMove(scrollbar, m_eventStartDrag);
             }
 
                 HandleThumbMove(scrollbar, m_eventStartDrag);
             }
 
-            return TRUE;
+            return true;
         }
     }
 
         }
     }
 
-    return wxStdScrollBarInputHandler::HandleMouseMove(control, event);
+    return wxStdInputHandler::HandleMouseMove(control, event);
 }
 
 }
 
+#endif // wxUSE_SCROLLBAR
+
+#if wxUSE_CHECKBOX
+
 // ----------------------------------------------------------------------------
 // wxWin32CheckboxInputHandler
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 // wxWin32CheckboxInputHandler
 // ----------------------------------------------------------------------------
 
-bool wxWin32CheckboxInputHandler::HandleKey(wxControl *control,
+bool wxWin32CheckboxInputHandler::HandleKey(wxInputConsumer *control,
                                             const wxKeyEvent& event,
                                             bool pressed)
 {
                                             const wxKeyEvent& event,
                                             bool pressed)
 {
@@ -3226,22 +3424,26 @@ bool wxWin32CheckboxInputHandler::HandleKey(wxControl *control,
                 break;
         }
 
                 break;
         }
 
-        if ( !!action )
+        if ( !action.IsEmpty() )
         {
             control->PerformAction(action);
 
         {
             control->PerformAction(action);
 
-            return TRUE;
+            return true;
         }
     }
 
         }
     }
 
-    return FALSE;
+    return false;
 }
 
 }
 
+#endif // wxUSE_CHECKBOX
+
+#if wxUSE_TEXTCTRL
+
 // ----------------------------------------------------------------------------
 // wxWin32TextCtrlInputHandler
 // ----------------------------------------------------------------------------
 
 // ----------------------------------------------------------------------------
 // wxWin32TextCtrlInputHandler
 // ----------------------------------------------------------------------------
 
-bool wxWin32TextCtrlInputHandler::HandleKey(wxControl *control,
+bool wxWin32TextCtrlInputHandler::HandleKey(wxInputConsumer *control,
                                             const wxKeyEvent& event,
                                             bool pressed)
 {
                                             const wxKeyEvent& event,
                                             bool pressed)
 {
@@ -3268,10 +3470,310 @@ bool wxWin32TextCtrlInputHandler::HandleKey(wxControl *control,
         {
             control->PerformAction(action);
 
         {
             control->PerformAction(action);
 
-            return TRUE;
+            return true;
+        }
+    }
+
+    return wxStdInputHandler::HandleKey(control, event, pressed);
+}
+
+#endif // wxUSE_TEXTCTRL
+
+#if wxUSE_STATUSBAR
+
+// ----------------------------------------------------------------------------
+// wxWin32StatusBarInputHandler
+// ----------------------------------------------------------------------------
+
+wxWin32StatusBarInputHandler::
+wxWin32StatusBarInputHandler(wxInputHandler *handler)
+    : wxStdInputHandler(handler)
+{
+    m_isOnGrip = false;
+}
+
+bool wxWin32StatusBarInputHandler::IsOnGrip(wxWindow *statbar,
+                                            const wxPoint& pt) const
+{
+    if ( statbar->HasFlag(wxST_SIZEGRIP) &&
+         statbar->GetParent()->HasFlag(wxRESIZE_BORDER) )
+    {
+        wxTopLevelWindow *
+            parentTLW = wxDynamicCast(statbar->GetParent(), wxTopLevelWindow);
+
+        wxCHECK_MSG( parentTLW, false,
+                     _T("the status bar should be a child of a TLW") );
+
+        // a maximized window can't be resized anyhow
+        if ( !parentTLW->IsMaximized() )
+        {
+            // VZ: I think that the standard Windows behaviour is to only
+            //     show the resizing cursor when the mouse is on top of the
+            //     grip itself but apparently different Windows versions behave
+            //     differently (?) and it seems a better UI to allow resizing
+            //     the status bar even when the mouse is above the grip
+            wxSize sizeSbar = statbar->GetSize();
+
+            int diff = sizeSbar.x - pt.x;
+            return diff >= 0 && diff < (wxCoord)STATUSBAR_GRIP_SIZE;
+        }
+    }
+
+    return false;
+}
+
+bool wxWin32StatusBarInputHandler::HandleMouse(wxInputConsumer *consumer,
+                                               const wxMouseEvent& event)
+{
+    if ( event.Button(1) )
+    {
+        if ( event.ButtonDown(1) )
+        {
+            wxWindow *statbar = consumer->GetInputWindow();
+
+            if ( IsOnGrip(statbar, event.GetPosition()) )
+            {
+                wxTopLevelWindow *tlw = wxDynamicCast(statbar->GetParent(),
+                                                      wxTopLevelWindow);
+                if ( tlw )
+                {
+                    tlw->PerformAction(wxACTION_TOPLEVEL_RESIZE,
+                                       wxHT_TOPLEVEL_BORDER_SE);
+
+                    statbar->SetCursor(m_cursorOld);
+
+                    return true;
+                }
+            }
+        }
+    }
+
+    return wxStdInputHandler::HandleMouse(consumer, event);
+}
+
+bool wxWin32StatusBarInputHandler::HandleMouseMove(wxInputConsumer *consumer,
+                                                   const wxMouseEvent& event)
+{
+    wxWindow *statbar = consumer->GetInputWindow();
+
+    bool isOnGrip = IsOnGrip(statbar, event.GetPosition());
+    if ( isOnGrip != m_isOnGrip )
+    {
+        m_isOnGrip = isOnGrip;
+        if ( isOnGrip )
+        {
+            m_cursorOld = statbar->GetCursor();
+            statbar->SetCursor(wxCURSOR_SIZENWSE);
+        }
+        else
+        {
+            statbar->SetCursor(m_cursorOld);
+        }
+    }
+
+    return wxStdInputHandler::HandleMouseMove(consumer, event);
+}
+
+#endif // wxUSE_STATUSBAR
+
+// ----------------------------------------------------------------------------
+// wxWin32FrameInputHandler
+// ----------------------------------------------------------------------------
+
+class wxWin32SystemMenuEvtHandler : public wxEvtHandler
+{
+public:
+    wxWin32SystemMenuEvtHandler(wxWin32FrameInputHandler *handler);
+
+    void Attach(wxInputConsumer *consumer);
+    void Detach();
+
+private:
+    DECLARE_EVENT_TABLE()
+    void OnSystemMenu(wxCommandEvent &event);
+    void OnCloseFrame(wxCommandEvent &event);
+    void OnClose(wxCloseEvent &event);
+
+    wxWin32FrameInputHandler *m_inputHnd;
+    wxTopLevelWindow         *m_wnd;
+#if wxUSE_ACCEL
+    wxAcceleratorTable        m_oldAccelTable;
+#endif
+};
+
+wxWin32SystemMenuEvtHandler::
+wxWin32SystemMenuEvtHandler(wxWin32FrameInputHandler *handler)
+{
+    m_inputHnd = handler;
+    m_wnd = NULL;
+}
+
+void wxWin32SystemMenuEvtHandler::Attach(wxInputConsumer *consumer)
+{
+    wxASSERT_MSG( m_wnd == NULL, _T("can't attach the handler twice!") );
+
+    m_wnd = wxStaticCast(consumer->GetInputWindow(), wxTopLevelWindow);
+    m_wnd->PushEventHandler(this);
+
+#if wxUSE_ACCEL
+    // VS: This code relies on using generic implementation of
+    //     wxAcceleratorTable in wxUniv!
+    wxAcceleratorTable table = *m_wnd->GetAcceleratorTable();
+    m_oldAccelTable = table;
+    table.Add(wxAcceleratorEntry(wxACCEL_ALT, WXK_SPACE, wxID_SYSTEM_MENU));
+    table.Add(wxAcceleratorEntry(wxACCEL_ALT, WXK_F4, wxID_CLOSE_FRAME));
+    m_wnd->SetAcceleratorTable(table);
+#endif
+}
+
+void wxWin32SystemMenuEvtHandler::Detach()
+{
+    if ( m_wnd )
+    {
+#if wxUSE_ACCEL
+        m_wnd->SetAcceleratorTable(m_oldAccelTable);
+#endif
+        m_wnd->RemoveEventHandler(this);
+        m_wnd = NULL;
+    }
+}
+
+BEGIN_EVENT_TABLE(wxWin32SystemMenuEvtHandler, wxEvtHandler)
+    EVT_MENU(wxID_SYSTEM_MENU, wxWin32SystemMenuEvtHandler::OnSystemMenu)
+    EVT_MENU(wxID_CLOSE_FRAME, wxWin32SystemMenuEvtHandler::OnCloseFrame)
+    EVT_CLOSE(wxWin32SystemMenuEvtHandler::OnClose)
+END_EVENT_TABLE()
+
+void wxWin32SystemMenuEvtHandler::OnSystemMenu(wxCommandEvent &WXUNUSED(event))
+{
+#if wxUSE_ACCEL
+    wxAcceleratorTable table = *m_wnd->GetAcceleratorTable();
+    m_wnd->SetAcceleratorTable(wxNullAcceleratorTable);
+#endif
+
+#if wxUSE_MENUS
+    m_inputHnd->PopupSystemMenu(m_wnd);
+#endif // wxUSE_MENUS
+
+#if wxUSE_ACCEL
+    m_wnd->SetAcceleratorTable(table);
+#endif
+}
+
+void wxWin32SystemMenuEvtHandler::OnCloseFrame(wxCommandEvent &WXUNUSED(event))
+{
+    m_wnd->PerformAction(wxACTION_TOPLEVEL_BUTTON_CLICK,
+                         wxTOPLEVEL_BUTTON_CLOSE);
+}
+
+void wxWin32SystemMenuEvtHandler::OnClose(wxCloseEvent &event)
+{
+    m_wnd = NULL;
+    event.Skip();
+}
+
+
+wxWin32FrameInputHandler::wxWin32FrameInputHandler(wxInputHandler *handler)
+                        : wxStdInputHandler(handler)
+{
+    m_menuHandler = new wxWin32SystemMenuEvtHandler(this);
+}
+
+wxWin32FrameInputHandler::~wxWin32FrameInputHandler()
+{
+    if ( m_menuHandler )
+    {
+        m_menuHandler->Detach();
+        delete m_menuHandler;
+    }
+}
+
+bool wxWin32FrameInputHandler::HandleMouse(wxInputConsumer *consumer,
+                                           const wxMouseEvent& event)
+{
+    if ( event.LeftDClick() || event.LeftDown() || event.RightDown() )
+    {
+        wxTopLevelWindow *tlw =
+            wxStaticCast(consumer->GetInputWindow(), wxTopLevelWindow);
+
+        long hit = tlw->HitTest(event.GetPosition());
+
+        if ( event.LeftDClick() && hit == wxHT_TOPLEVEL_TITLEBAR )
+        {
+            tlw->PerformAction(wxACTION_TOPLEVEL_BUTTON_CLICK,
+                               tlw->IsMaximized() ? wxTOPLEVEL_BUTTON_RESTORE
+                                                  : wxTOPLEVEL_BUTTON_MAXIMIZE);
+            return true;
+        }
+        else if ( tlw->GetWindowStyle() & wxSYSTEM_MENU )
+        {
+            if ( (event.LeftDown() && hit == wxHT_TOPLEVEL_ICON) ||
+                 (event.RightDown() &&
+                      (hit == wxHT_TOPLEVEL_TITLEBAR ||
+                       hit == wxHT_TOPLEVEL_ICON)) )
+            {
+#if wxUSE_MENUS
+                PopupSystemMenu(tlw);
+#endif // wxUSE_MENUS
+                return true;
+            }
+        }
+    }
+
+    return wxStdInputHandler::HandleMouse(consumer, event);
+}
+
+#if wxUSE_MENUS
+
+void wxWin32FrameInputHandler::PopupSystemMenu(wxTopLevelWindow *window) const
+{
+    wxMenu menu;
+
+    if ( window->GetWindowStyle() & wxMAXIMIZE_BOX )
+        menu.Append(wxID_RESTORE_FRAME , _("&Restore"));
+    menu.Append(wxID_MOVE_FRAME , _("&Move"));
+    if ( window->GetWindowStyle() & wxRESIZE_BORDER )
+        menu.Append(wxID_RESIZE_FRAME , _("&Size"));
+    if ( wxSystemSettings::HasFeature(wxSYS_CAN_ICONIZE_FRAME) )
+        menu.Append(wxID_ICONIZE_FRAME , _("Mi&nimize"));
+    if ( window->GetWindowStyle() & wxMAXIMIZE_BOX )
+        menu.Append(wxID_MAXIMIZE_FRAME , _("Ma&ximize"));
+    menu.AppendSeparator();
+    menu.Append(wxID_CLOSE_FRAME, _("Close\tAlt-F4"));
+
+    if ( window->GetWindowStyle() & wxMAXIMIZE_BOX )
+    {
+        if ( window->IsMaximized() )
+        {
+            menu.Enable(wxID_MAXIMIZE_FRAME, false);
+            menu.Enable(wxID_MOVE_FRAME, false);
+            if ( window->GetWindowStyle() & wxRESIZE_BORDER )
+                menu.Enable(wxID_RESIZE_FRAME, false);
+        }
+        else
+            menu.Enable(wxID_RESTORE_FRAME, false);
+    }
+
+    window->PopupMenu(&menu, wxPoint(0, 0));
+}
+
+#endif // wxUSE_MENUS
+
+bool wxWin32FrameInputHandler::HandleActivation(wxInputConsumer *consumer,
+                                                bool activated)
+{
+    if ( consumer->GetInputWindow()->GetWindowStyle() & wxSYSTEM_MENU )
+    {
+        // always detach if active frame changed:
+        m_menuHandler->Detach();
+
+        if ( activated )
+        {
+            m_menuHandler->Attach(consumer);
         }
     }
 
         }
     }
 
-    return wxStdTextCtrlInputHandler::HandleKey(control, event, pressed);
+    return wxStdInputHandler::HandleActivation(consumer, activated);
 }
 
 }
 
+#endif // wxUSE_THEME_WIN32