]> git.saurik.com Git - wxWidgets.git/blobdiff - wxPython/contrib/gizmos/wxCode/src/treelistctrl.cpp
wxCheckListBox doesn't require wxUSE_OWNER_DRAWN when using WXUNIVERSAL
[wxWidgets.git] / wxPython / contrib / gizmos / wxCode / src / treelistctrl.cpp
index ab5984ab66a4825c325b2e65679ef51f23869b4d..351bb5696036af23915332bfcfc5b3f4fd450f2c 100644 (file)
@@ -39,6 +39,8 @@
 #include <wx/dcclient.h>
 #include <wx/dcscreen.h>
 #include <wx/scrolwin.h>
 #include <wx/dcclient.h>
 #include <wx/dcscreen.h>
 #include <wx/scrolwin.h>
+#include <wx/renderer.h>
+#include <wx/dcmemory.h>
 
 #include "wx/treelistctrl.h"
 
 
 #include "wx/treelistctrl.h"
 
     #include <wx/gtk/win_gtk.h>
 #endif
 
     #include <wx/gtk/win_gtk.h>
 #endif
 
+#ifdef __WXMAC__
+    #include "wx/mac/private.h"
+#endif
+
+
 // ---------------------------------------------------------------------------
 // array types
 // ---------------------------------------------------------------------------
 // ---------------------------------------------------------------------------
 // array types
 // ---------------------------------------------------------------------------
@@ -80,8 +87,18 @@ const int PIXELS_PER_UNIT = 10;
 const int LINEATROOT = 5;
 const int MARGIN = 2;
 const int MININDENT = 10;
 const int LINEATROOT = 5;
 const int MARGIN = 2;
 const int MININDENT = 10;
-const int BTNWIDTH = 11;
-const int BTNHEIGHT = 11;
+const int BTNWIDTH = 9; //11;
+const int BTNHEIGHT = 9; //11;
+
+// extra margins around the text label
+static const int EXTRA_WIDTH = 4;
+static const int EXTRA_HEIGHT = 4;
+
+// offset for the header window
+static const int HEADER_OFFSET_X = 1;
+static const int HEADER_OFFSET_Y = 1;
+
+
 
 const wxChar* wxTreeListCtrlNameStr = wxT("treelistctrl");
 
 
 const wxChar* wxTreeListCtrlNameStr = wxT("treelistctrl");
 
@@ -136,6 +153,7 @@ public:
     void DrawCurrent();
     void AdjustDC(wxDC& dc);
 
     void DrawCurrent();
     void AdjustDC(wxDC& dc);
 
+    void OnEraseBackground( wxEraseEvent& event );
     void OnPaint( wxPaintEvent &event );
     void OnMouse( wxMouseEvent &event );
     void OnSetFocus( wxFocusEvent &event );
     void OnPaint( wxPaintEvent &event );
     void OnMouse( wxMouseEvent &event );
     void OnSetFocus( wxFocusEvent &event );
@@ -549,7 +567,6 @@ public:
     void OnChar( wxKeyEvent &event );
     void OnMouse( wxMouseEvent &event );
     void OnIdle( wxIdleEvent &event );
     void OnChar( wxKeyEvent &event );
     void OnMouse( wxMouseEvent &event );
     void OnIdle( wxIdleEvent &event );
-    void OnSize(wxSizeEvent& event); // ALB
     void OnScroll(wxScrollWinEvent& event); // ALB
 
     // implementation helpers
     void OnScroll(wxScrollWinEvent& event); // ALB
 
     // implementation helpers
@@ -622,6 +639,7 @@ protected:
     wxTreeListItem   *m_dropTarget;
     wxCursor             m_oldCursor;  // cursor is changed while dragging
     wxTreeListItem   *m_oldSelection;
     wxTreeListItem   *m_dropTarget;
     wxCursor             m_oldCursor;  // cursor is changed while dragging
     wxTreeListItem   *m_oldSelection;
+    wxTreeListItem   *m_underMouse; // for visual effects
 
     wxTimer             *m_renameTimer;
     wxString             m_renameRes;
 
     wxTimer             *m_renameTimer;
     wxString             m_renameRes;
@@ -1059,9 +1077,10 @@ void wxTreeListTextCtrl::OnKillFocus( wxFocusEvent &event )
 IMPLEMENT_DYNAMIC_CLASS(wxTreeListHeaderWindow,wxWindow);
 
 BEGIN_EVENT_TABLE(wxTreeListHeaderWindow,wxWindow)
 IMPLEMENT_DYNAMIC_CLASS(wxTreeListHeaderWindow,wxWindow);
 
 BEGIN_EVENT_TABLE(wxTreeListHeaderWindow,wxWindow)
-    EVT_PAINT         (wxTreeListHeaderWindow::OnPaint)
-    EVT_MOUSE_EVENTS  (wxTreeListHeaderWindow::OnMouse)
-    EVT_SET_FOCUS     (wxTreeListHeaderWindow::OnSetFocus)
+    EVT_ERASE_BACKGROUND  (wxTreeListHeaderWindow::OnEraseBackground)
+    EVT_PAINT             (wxTreeListHeaderWindow::OnPaint)
+    EVT_MOUSE_EVENTS      (wxTreeListHeaderWindow::OnMouse)
+    EVT_SET_FOCUS         (wxTreeListHeaderWindow::OnSetFocus)
 END_EVENT_TABLE()
 
 void wxTreeListHeaderWindow::Init()
 END_EVENT_TABLE()
 
 void wxTreeListHeaderWindow::Init()
@@ -1094,7 +1113,7 @@ wxTreeListHeaderWindow::wxTreeListHeaderWindow( wxWindow *win,
     m_owner = owner;
     m_resizeCursor = new wxCursor(wxCURSOR_SIZEWE);
 
     m_owner = owner;
     m_resizeCursor = new wxCursor(wxCURSOR_SIZEWE);
 
-    SetBackgroundColour(wxSystemSettings::GetSystemColour(
+    SetBackgroundColour(wxSystemSettings::GetColour(
                             wxSYS_COLOUR_BTNFACE));
 }
 
                             wxSYS_COLOUR_BTNFACE));
 }
 
@@ -1120,7 +1139,7 @@ void wxTreeListHeaderWindow::DoDrawRect( wxDC *dc, int x, int y, int w, int h )
 
     dc->SetBrush( *wxTRANSPARENT_BRUSH );
 
 
     dc->SetBrush( *wxTRANSPARENT_BRUSH );
 
-    dc->SetPen( wxPen(wxSystemSettings::GetSystemColour(
+    dc->SetPen( wxPen(wxSystemSettings::GetColour(
                           wxSYS_COLOUR_BTNSHADOW), 1, wxSOLID));
     dc->DrawLine( x+w-m_corner+1, y, x+w, y+h );  // right (outer)
     dc->DrawRectangle( x, y+h, w+1, 1 );          // bottom (outer)
                           wxSYS_COLOUR_BTNSHADOW), 1, wxSOLID));
     dc->DrawLine( x+w-m_corner+1, y, x+w, y+h );  // right (outer)
     dc->DrawRectangle( x, y+h, w+1, 1 );          // bottom (outer)
@@ -1145,7 +1164,7 @@ void wxTreeListHeaderWindow::DoDrawRect( wxDC *dc, int x, int y, int w, int h )
     dc->DrawLine( x+w-m_corner+1, y, x+w, y+h );  // right (outer)
     dc->DrawRectangle( x, y+h, w+1, 1 );          // bottom (outer)
 
     dc->DrawLine( x+w-m_corner+1, y, x+w, y+h );  // right (outer)
     dc->DrawRectangle( x, y+h, w+1, 1 );          // bottom (outer)
 
-    wxPen pen(wxSystemSettings::GetSystemColour(
+    wxPen pen(wxSystemSettings::GetColour(
                   wxSYS_COLOUR_BTNSHADOW ), 1, wxSOLID);
 
     dc->SetPen( pen );
                   wxSYS_COLOUR_BTNSHADOW ), 1, wxSOLID);
 
     dc->SetPen( pen );
@@ -1174,34 +1193,42 @@ void wxTreeListHeaderWindow::AdjustDC(wxDC& dc)
     dc.SetDeviceOrigin( -x * xpix, 0 );
 }
 
     dc.SetDeviceOrigin( -x * xpix, 0 );
 }
 
+
+void wxTreeListHeaderWindow::OnEraseBackground( wxEraseEvent& event )
+{
+}
+
 void wxTreeListHeaderWindow::OnPaint( wxPaintEvent &WXUNUSED(event) )
 {
 void wxTreeListHeaderWindow::OnPaint( wxPaintEvent &WXUNUSED(event) )
 {
-    static const int HEADER_OFFSET_X = 1, HEADER_OFFSET_Y = 1;
 #ifdef __WXGTK__
 #ifdef __WXGTK__
-    wxClientDC dc( this );
+    wxClientDC real_dc( this );
 #else
 #else
-    wxPaintDC dc( this );
+    wxPaintDC real_dc( this );
 #endif
 
 #endif
 
-    PrepareDC( dc );
-    AdjustDC( dc );
-
-    dc.BeginDrawing();
-
-    dc.SetFont( GetFont() );
+    AdjustDC( real_dc );
 
     // width and height of the entire header window
     int w, h;
     GetClientSize( &w, &h );
     m_owner->CalcUnscrolledPosition(w, 0, &w, NULL);
 
 
     // width and height of the entire header window
     int w, h;
     GetClientSize( &w, &h );
     m_owner->CalcUnscrolledPosition(w, 0, &w, NULL);
 
+    // Setup double buffering to eliminate the flicker
+    wxMemoryDC dc;
+    wxBitmap   buffer(w, h);
+    dc.SelectObject(buffer);
+    dc.SetBackground(wxBrush(GetBackgroundColour()));
+    dc.Clear();
+    
+    dc.BeginDrawing();
+    dc.SetFont( GetFont() );
     dc.SetBackgroundMode(wxTRANSPARENT);
 
     // do *not* use the listctrl colour for headers - one day we will have a
     // function to set it separately
     //dc.SetTextForeground( *wxBLACK );
     dc.SetTextForeground(wxSystemSettings::
     dc.SetBackgroundMode(wxTRANSPARENT);
 
     // do *not* use the listctrl colour for headers - one day we will have a
     // function to set it separately
     //dc.SetTextForeground( *wxBLACK );
     dc.SetTextForeground(wxSystemSettings::
-                            GetSystemColour( wxSYS_COLOUR_WINDOWTEXT ));
+                            GetColour( wxSYS_COLOUR_WINDOWTEXT ));
 
     int x = HEADER_OFFSET_X;
 
 
     int x = HEADER_OFFSET_X;
 
@@ -1219,7 +1246,11 @@ void wxTreeListHeaderWindow::OnPaint( wxPaintEvent &WXUNUSED(event) )
 
         dc.SetPen( *wxWHITE_PEN );
 
 
         dc.SetPen( *wxWHITE_PEN );
 
-        DoDrawRect( &dc, x, HEADER_OFFSET_Y, cw, h-2 );
+        //DoDrawRect( &dc, x, HEADER_OFFSET_Y, cw, h-2 );
+        wxRendererNative::Get().DrawHeaderButton(
+            this, dc, wxRect(x, HEADER_OFFSET_Y, cw, h - 2),
+            m_parent->IsEnabled() ? 0 : wxCONTROL_DISABLED);
+        
 
         // if we have an image, draw it on the right of the label
         int image = column.GetImage(); //item.m_image;
 
         // if we have an image, draw it on the right of the label
         int image = column.GetImage(); //item.m_image;
@@ -1232,10 +1263,6 @@ void wxTreeListHeaderWindow::OnPaint( wxPaintEvent &WXUNUSED(event) )
         //else: ignore the column image
         }
 
         //else: ignore the column image
         }
 
-        // extra margins around the text label
-        static const int EXTRA_WIDTH = 3;
-        static const int EXTRA_HEIGHT = 4;
-
         int text_width = 0;
         int text_x = x;
         int image_offset = cw - ix - 1;
         int text_width = 0;
         int text_x = x;
         int image_offset = cw - ix - 1;
@@ -1274,14 +1301,19 @@ void wxTreeListHeaderWindow::OnPaint( wxPaintEvent &WXUNUSED(event) )
         x += wCol;
     }
 
         x += wCol;
     }
 
-    int more_w = m_owner->GetSize().x - x;
+    int more_w = m_owner->GetSize().x - x -1;
     if (more_w > 0)
     {
     if (more_w > 0)
     {
-        DoDrawRect( &dc, x, HEADER_OFFSET_Y, more_w, h-2 );
+        //DoDrawRect( &dc, x, HEADER_OFFSET_Y, more_w, h-2 );
+        wxRendererNative::Get().DrawHeaderButton(
+            this, dc, wxRect(x, HEADER_OFFSET_Y, more_w, h-2),
+            m_parent->IsEnabled() ? 0 : wxCONTROL_DISABLED);
     }
 
     }
 
-
+    // Finish up by drawing the buffer to the real dc
     dc.EndDrawing();
     dc.EndDrawing();
+    dc.SelectObject(wxNullBitmap);
+    real_dc.DrawBitmap(buffer, 0, 0, false);
 }
 
 void wxTreeListHeaderWindow::DrawCurrent()
 }
 
 void wxTreeListHeaderWindow::DrawCurrent()
@@ -1639,19 +1671,29 @@ wxTreeListItem *wxTreeListItem::HitTest(const wxPoint& point,
                 flags |= wxTREE_HITTEST_ONITEMLOWERPART;
 
             // check for button hit
                 flags |= wxTREE_HITTEST_ONITEMLOWERPART;
 
             // check for button hit
-            if (HasPlus() && theCtrl->HasButtons()) {
-                int bntX = m_x - theCtrl->m_btnWidth2;
-                int bntY = y_mid - theCtrl->m_btnHeight2;
-                if ((point.x > bntX) && (point.x < (bntX + theCtrl->m_btnWidth)) &&
-                    (point.y > bntY) && (point.y < (bntY + theCtrl->m_btnHeight))) {
-                    flags |= wxTREE_HITTEST_ONITEMBUTTON;
-                    return this;
-                }
+            int xCross = m_x; // - theCtrl->GetLineSpacing();
+#ifdef __WXMAC__
+            // according to the drawing code the triangels are drawn
+            // at -4 , -4  from the position up to +10/+10 max
+            if ((point.x > xCross-4) && (point.x < xCross+10) &&
+                (point.y > y_mid-4) && (point.y < y_mid+10) &&
+                HasPlus() && theCtrl->HasButtons() )
+#else
+            // 5 is the size of the plus sign
+            if ((point.x > xCross-6) && (point.x < xCross+6) &&
+                (point.y > y_mid-6) && (point.y < y_mid+6) &&
+                HasPlus() && theCtrl->HasButtons() )
+#endif
+            {
+                flags |= wxTREE_HITTEST_ONITEMBUTTON;
+                return this;
             }
 
             // check for image hit
             }
 
             // check for image hit
-            if (theCtrl->m_imgWidth > 0) {
+            if (theCtrl->m_imgWidth > 0 && GetImage() != NO_IMAGE) {
                 int imgX = m_x - theCtrl->m_imgWidth2;
                 int imgX = m_x - theCtrl->m_imgWidth2;
+                if (HasPlus() && theCtrl->HasButtons())
+                    imgX += theCtrl->m_btnWidth + LINEATROOT;
                 int imgY = y_mid - theCtrl->m_imgHeight2;
                 if ((point.x >= imgX) && (point.x <= (imgX + theCtrl->m_imgWidth)) &&
                     (point.y >= imgY) && (point.y <= (imgY + theCtrl->m_imgHeight))) {
                 int imgY = y_mid - theCtrl->m_imgHeight2;
                 if ((point.x >= imgX) && (point.x <= (imgX + theCtrl->m_imgWidth)) &&
                     (point.y >= imgY) && (point.y <= (imgY + theCtrl->m_imgHeight))) {
@@ -1744,6 +1786,7 @@ wxTreeListItem *wxTreeListItem::HitTest(const wxPoint& point,
                 column = i;
                 return res;
             }
                 column = i;
                 return res;
             }
+            x += w;
         }
     }
 
         }
     }
 
@@ -1794,7 +1837,6 @@ BEGIN_EVENT_TABLE(wxTreeListMainWindow, wxScrolledWindow)
     EVT_SET_FOCUS      (wxTreeListMainWindow::OnSetFocus)
     EVT_KILL_FOCUS     (wxTreeListMainWindow::OnKillFocus)
     EVT_IDLE           (wxTreeListMainWindow::OnIdle)
     EVT_SET_FOCUS      (wxTreeListMainWindow::OnSetFocus)
     EVT_KILL_FOCUS     (wxTreeListMainWindow::OnKillFocus)
     EVT_IDLE           (wxTreeListMainWindow::OnIdle)
-//?    EVT_SIZE           (wxTreeListMainWindow::OnSize)
     EVT_SCROLLWIN      (wxTreeListMainWindow::OnScroll)
 END_EVENT_TABLE()
 
     EVT_SCROLLWIN      (wxTreeListMainWindow::OnScroll)
 END_EVENT_TABLE()
 
@@ -1817,7 +1859,7 @@ void wxTreeListMainWindow::Init()
 
     m_hilightBrush = new wxBrush
                          (
 
     m_hilightBrush = new wxBrush
                          (
-                            wxSystemSettings::GetSystemColour
+                            wxSystemSettings::GetColour
                             (
                                 wxSYS_COLOUR_HIGHLIGHT
                             ),
                             (
                                 wxSYS_COLOUR_HIGHLIGHT
                             ),
@@ -1826,7 +1868,7 @@ void wxTreeListMainWindow::Init()
 
     m_hilightUnfocusedBrush = new wxBrush
                               (
 
     m_hilightUnfocusedBrush = new wxBrush
                               (
-                                 wxSystemSettings::GetSystemColour
+                                 wxSystemSettings::GetColour
                                  (
                                      wxSYS_COLOUR_BTNSHADOW
                                  ),
                                  (
                                      wxSYS_COLOUR_BTNSHADOW
                                  ),
@@ -1847,17 +1889,23 @@ void wxTreeListMainWindow::Init()
 
     m_findTimer = new wxTimer (this, -1);
 
 
     m_findTimer = new wxTimer (this, -1);
 
-    m_normalFont = wxSystemSettings::GetSystemFont( wxSYS_DEFAULT_GUI_FONT );
+    m_underMouse = NULL;
+
+#if defined( __WXMAC__ ) && defined(__WXMAC_CARBON__)
+    m_normalFont.MacCreateThemeFont( kThemeViewsFont ) ;
+#else
+    m_normalFont = wxSystemSettings::GetFont( wxSYS_DEFAULT_GUI_FONT );
+#endif
     m_boldFont = wxFont( m_normalFont.GetPointSize(),
                          m_normalFont.GetFamily(),
                          m_normalFont.GetStyle(),
                          wxBOLD,
     m_boldFont = wxFont( m_normalFont.GetPointSize(),
                          m_normalFont.GetFamily(),
                          m_normalFont.GetStyle(),
                          wxBOLD,
-                         m_normalFont.GetUnderlined());
+                         m_normalFont.GetUnderlined(),
+                         m_normalFont.GetFaceName(),
+                         m_normalFont.GetEncoding());
 }
 
 
 }
 
 
-static const int HEADER_HEIGHT = 23;
-
 bool wxTreeListMainWindow::Create(wxTreeListCtrl *parent,
                                   wxWindowID id,
                                   const wxPoint& pos,
 bool wxTreeListMainWindow::Create(wxTreeListCtrl *parent,
                                   wxWindowID id,
                                   const wxPoint& pos,
@@ -1867,17 +1915,20 @@ bool wxTreeListMainWindow::Create(wxTreeListCtrl *parent,
                                   const wxString& name )
 {
 #ifdef __WXMAC__
                                   const wxString& name )
 {
 #ifdef __WXMAC__
-    int major,minor;
-    wxGetOsVersion( &major, &minor );
-
-    if (style & wxTR_HAS_BUTTONS) style |= wxTR_MAC_BUTTONS;
-    if (style & wxTR_HAS_BUTTONS) style &= ~wxTR_HAS_BUTTONS;
-    style &= ~wxTR_LINES_AT_ROOT;
-    style |= wxTR_NO_LINES;
-    if (major < 10)
-        style |= wxTR_ROW_LINES;
+    if ( !(style & wxTR_DONT_ADJUST_MAC))
+    {
+        int major,minor;
+        wxGetOsVersion( &major, &minor );
+
+        if (style & wxTR_HAS_BUTTONS) style |= wxTR_TWIST_BUTTONS;
+        if (style & wxTR_HAS_BUTTONS) style &= ~wxTR_HAS_BUTTONS;
+        style &= ~wxTR_LINES_AT_ROOT;
+        style |= wxTR_NO_LINES;
+        if (major < 10)
+            style |= wxTR_ROW_LINES;
+    }
 #endif
 #endif
-
+    
     wxScrolledWindow::Create( parent, id, pos, size,
                               style|wxHSCROLL|wxVSCROLL, name );
 
     wxScrolledWindow::Create( parent, id, pos, size,
                               style|wxHSCROLL|wxVSCROLL, name );
 
@@ -1885,7 +1936,7 @@ bool wxTreeListMainWindow::Create(wxTreeListCtrl *parent,
     SetValidator( validator );
 #endif
 
     SetValidator( validator );
 #endif
 
-    SetBackgroundColour( wxSystemSettings::GetSystemColour( wxSYS_COLOUR_LISTBOX ) );
+    SetBackgroundColour( wxSystemSettings::GetColour( wxSYS_COLOUR_LISTBOX ) );
 
 #ifdef __WXMSW__
     {
 
 #ifdef __WXMSW__
     {
@@ -3263,7 +3314,7 @@ void wxTreeListMainWindow::PaintItem(wxTreeListItem *item, wxDC& dc)
     if (item->IsSelected() && HasFlag(wxTR_FULL_ROW_HIGHLIGHT)) {
             dc.SetBrush(*(m_hasFocus ? m_hilightBrush : m_hilightUnfocusedBrush));
             dc.SetPen(*wxBLACK_PEN);
     if (item->IsSelected() && HasFlag(wxTR_FULL_ROW_HIGHLIGHT)) {
             dc.SetBrush(*(m_hasFocus ? m_hilightBrush : m_hilightUnfocusedBrush));
             dc.SetPen(*wxBLACK_PEN);
-            colText = wxSystemSettings::GetSystemColour(wxSYS_COLOUR_HIGHLIGHTTEXT);
+            colText = wxSystemSettings::GetColour(wxSYS_COLOUR_HIGHLIGHTTEXT);
     } else {
         wxColour colBg;
         if (attr && attr->HasBackgroundColour()) {
     } else {
         wxColour colBg;
         if (attr && attr->HasBackgroundColour()) {
@@ -3329,7 +3380,7 @@ void wxTreeListMainWindow::PaintItem(wxTreeListItem *item, wxDC& dc)
             int width = wxMin(text_w+2, colwidth - text_x - x_colstart);
             dc.DrawRectangle(text_x-1, item->GetY() + offset, width, total_h-offset);
             dc.SetBackgroundMode(wxTRANSPARENT);
             int width = wxMin(text_w+2, colwidth - text_x - x_colstart);
             dc.DrawRectangle(text_x-1, item->GetY() + offset, width, total_h-offset);
             dc.SetBackgroundMode(wxTRANSPARENT);
-            dc.SetTextForeground(wxSystemSettings::GetSystemColour(wxSYS_COLOUR_HIGHLIGHTTEXT));
+            dc.SetTextForeground(wxSystemSettings::GetColour(wxSYS_COLOUR_HIGHLIGHTTEXT));
         }else{
             dc.SetTextForeground(colText);
         }
         }else{
             dc.SetTextForeground(colText);
         }
@@ -3428,16 +3479,17 @@ void wxTreeListMainWindow::PaintLevel (wxTreeListItem *item, wxDC &dc,
             // clip to the column width
             wxDCClipper clipper(dc, x_colstart, y_top, clip_width, 10000);
 
             // clip to the column width
             wxDCClipper clipper(dc, x_colstart, y_top, clip_width, 10000);
 
-            if (!HasFlag(wxTR_NO_LINES))
+            if ( !HasFlag(wxTR_NO_LINES) )
             {
             {
-                if (x > m_indent)
-                    dc.DrawLine(x - m_indent, y_mid, x - m_btnWidth2, y_mid);
+                // draw the horizontal line here
+                int x_start = x;
+                if (x > (signed)m_indent)
+                    x_start -= m_indent;
                 else if (HasFlag(wxTR_LINES_AT_ROOT))
                 else if (HasFlag(wxTR_LINES_AT_ROOT))
-                    dc.DrawLine(m_btnWidth2-2, y_mid,
-                                x - m_btnWidth2, y_mid);
-                dc.DrawLine(x + m_btnWidth2, y_mid, x /*+ m_spacing*/, y_mid);
+                    x_start = 3;
+                dc.DrawLine(x_start, y_mid, x /*+ m_spacing*/, y_mid);
             }
             }
-
+            
             if (m_imageListButtons != NULL)
             {
                 // draw the image button here
             if (m_imageListButtons != NULL)
             {
                 // draw the image button here
@@ -3452,54 +3504,25 @@ void wxTreeListMainWindow::PaintLevel (wxTreeListItem *item, wxDC &dc,
                                          wxIMAGELIST_DRAW_TRANSPARENT);
                 dc.DestroyClippingRegion();
             }
                                          wxIMAGELIST_DRAW_TRANSPARENT);
                 dc.DestroyClippingRegion();
             }
-            else if (HasFlag(wxTR_TWIST_BUTTONS))
+            else // no custom buttons
             {
             {
-                // draw the twisty button here
-                dc.SetPen(*wxBLACK_PEN);
-                dc.SetBrush(*m_hilightBrush);
-
-                wxPoint button[3];
+                static const int wImage = 9;
+                static const int hImage = 9;
 
 
+                int flag = 0;
                 if (item->IsExpanded())
                 if (item->IsExpanded())
-                {
-                    button[0].x = x - (m_btnWidth2+1);
-                    button[0].y = y_mid - (m_btnHeight/3);
-                    button[1].x = x + (m_btnWidth2+1);
-                    button[1].y = button[0].y;
-                    button[2].x = x;
-                    button[2].y = button[0].y + (m_btnHeight2+1);
-                }
-                else
-                {
-                    button[0].x = x - (m_btnWidth/3);
-                    button[0].y = y_mid - (m_btnHeight2+1);
-                    button[1].x = button[0].x;
-                    button[1].y = y_mid + (m_btnHeight2+1);
-                    button[2].x = button[0].x + (m_btnWidth2+1);
-                    button[2].y = y_mid;
-                }
-                dc.DrawPolygon(3, button);
-
-                dc.SetPen(m_dottedPen);
-            }
-            else // if (HasFlag(wxTR_HAS_BUTTONS))
-            {
-                // draw the plus sign here
-                dc.SetPen(*wxGREY_PEN);
-                dc.SetBrush(*wxWHITE_BRUSH);
-                dc.DrawRectangle (x-m_btnWidth2, y_mid-m_btnHeight2,
-                                  m_btnWidth, m_btnHeight);
-                dc.SetPen(*wxBLACK_PEN);
-                dc.DrawLine (x-(m_btnWidth2-3), y_mid,
-                             x+(m_btnWidth2-2), y_mid);
-                if (!item->IsExpanded())
-                    dc.DrawLine (x, y_mid-(m_btnHeight2-2),
-                                 x, y_mid+(m_btnHeight2-1));
-                dc.SetPen(m_dottedPen);
+                    flag |= wxCONTROL_EXPANDED;
+                if (item == m_underMouse)
+                    flag |= wxCONTROL_CURRENT;
+
+                wxRendererNative::Get().DrawTreeItemButton(
+                    this, dc,
+                    wxRect(x - wImage/2, y_mid - hImage/2, wImage, hImage),
+                    flag);
             }
 
             if (!HasFlag(wxTR_NO_LINES)) {
             }
 
             if (!HasFlag(wxTR_NO_LINES)) {
-                if (!(level == 0) && !((level == 1) && HasFlag(wxTR_HIDE_ROOT))) {
+                if (/*!(level == 0) &&*/ !((level == 1) && HasFlag(wxTR_HIDE_ROOT))) {
                     if (m_imgWidth > 0) {
                         dc.DrawLine(x+m_btnWidth2, y_mid, x+m_indent-m_imgWidth2, y_mid);
                     }else{
                     if (m_imgWidth > 0) {
                         dc.DrawLine(x+m_btnWidth2, y_mid, x+m_indent-m_imgWidth2, y_mid);
                     }else{
@@ -3514,7 +3537,7 @@ void wxTreeListMainWindow::PaintLevel (wxTreeListItem *item, wxDC &dc,
             wxDCClipper clipper(dc, x_colstart, y_top, clip_width, 10000);
 
             // draw the horizontal line here
             wxDCClipper clipper(dc, x_colstart, y_top, clip_width, 10000);
 
             // draw the horizontal line here
-            if (!(level == 0) && !((level == 1) && HasFlag(wxTR_HIDE_ROOT))) {
+            if (/*!(level == 0) &&*/ !((level == 1) && HasFlag(wxTR_HIDE_ROOT))) {
                 int x2 = x - m_indent;
                 if (m_imgWidth > 0) {
                     dc.DrawLine(x2, y_mid, x2+m_indent-m_imgWidth2, y_mid);
                 int x2 = x - m_indent;
                 if (m_imgWidth > 0) {
                     dc.DrawLine(x2, y_mid, x2+m_indent-m_imgWidth2, y_mid);
@@ -3534,7 +3557,7 @@ void wxTreeListMainWindow::PaintLevel (wxTreeListItem *item, wxDC &dc,
     {
         wxArrayTreeListItems& children = item->GetChildren();
         int count = children.Count();
     {
         wxArrayTreeListItems& children = item->GetChildren();
         int count = children.Count();
-        int n, oldY;
+        int n, oldY = 0;
 
         // paint sublevel items first
         for (n=0; n<count; ++n) {
 
         // paint sublevel items first
         for (n=0; n<count; ++n) {
@@ -3554,48 +3577,6 @@ void wxTreeListMainWindow::PaintLevel (wxTreeListItem *item, wxDC &dc,
             if (HasButtons()) y_mid += 5;
             dc.DrawLine(x, y_mid, x, oldY);
         }
             if (HasButtons()) y_mid += 5;
             dc.DrawLine(x, y_mid, x, oldY);
         }
-
-        
-//         // clip to the column width
-//         size_t clip_width = m_owner->GetHeaderWindow()->
-//                             GetColumn(m_main_column).GetWidth();
-//         wxDCClipper clipper(dc, x_colstart, y_top, clip_width, 10000);
-
-//         // process lower levels
-//         int oldY;
-//         if (m_imgWidth > 0) {
-//             oldY = y_mid + m_imgHeight2;
-//         }else{
-//             oldY = y_mid + h/2;
-//         }
-//         int y2;
-//         int n;
-//         for (n = 0; n < (int)children.Count(); ++n) {
-
-//             if (!HasFlag(wxTR_NO_LINES))
-//             {
-//                 // draw line down to last child
-//                 if (children[n]->HasPlus() && HasButtons()) {
-//                     y2 = y + h/2 - m_btnHeight2;
-//                     if (HasButtons()) {
-//                         dc.DrawLine(x+m_indent, oldY, x+m_indent, y2);
-//                     }else{
-//                         dc.DrawLine(x, oldY, x, y2);
-//                     }
-//                     oldY = y2 + m_btnHeight;
-//                 }else{
-//                     y2 = y + h/2;
-//                     if (HasButtons()) {
-//                         dc.DrawLine(x+m_indent, oldY, x+m_indent, y2);
-//                     }else{
-//                         dc.DrawLine(x, oldY, x, y2);
-//                     }
-//                     oldY = y2;
-//                 }
-//             }
-
-//             PaintLevel (children[n], dc, level+1, y, x_colstart);
-//         }
     }
 }
 
     }
 }
 
@@ -4146,6 +4127,60 @@ void wxTreeListMainWindow::OnMouse( wxMouseEvent &event )
 {
     if ( !m_anchor ) return;
 
 {
     if ( !m_anchor ) return;
 
+    wxPoint pt = CalcUnscrolledPosition(event.GetPosition());
+
+    // Is the mouse over a tree item button?
+    int flags = 0;
+    wxTreeListItem *item = m_anchor->HitTest(pt, this, flags, 0);
+    wxTreeListItem *underMouse = item;
+#if wxUSE_TOOLTIPS
+    bool underMouseChanged = (underMouse != m_underMouse) ;
+#endif // wxUSE_TOOLTIPS
+
+    if (underMouse && (flags & wxTREE_HITTEST_ONITEMBUTTON) &&
+        !event.LeftIsDown() && !m_isDragging &&
+        (!m_renameTimer || !m_renameTimer->IsRunning()))
+    {
+    }
+    else
+    {
+        underMouse = NULL;
+    }
+
+    if (underMouse != m_underMouse)
+    {
+         if (m_underMouse)
+         {
+            // unhighlight old item
+            wxTreeListItem *tmp = m_underMouse;
+            m_underMouse = NULL;
+            RefreshLine( tmp );
+         }
+
+         m_underMouse = underMouse;
+         if (m_underMouse)
+            RefreshLine( m_underMouse );
+    }
+
+#if wxUSE_TOOLTIPS
+    // Determines what item we are hovering over and need a tooltip for
+    wxTreeItemId hoverItem = item;
+
+    // We do not want a tooltip if we are dragging, or if the rename timer is running
+    if (underMouseChanged && hoverItem.IsOk() && !m_isDragging && (!m_renameTimer || !m_renameTimer->IsRunning()))
+    {
+        // Ask the tree control what tooltip (if any) should be shown
+        wxTreeEvent hevent(wxEVT_COMMAND_TREE_ITEM_GETTOOLTIP, GetId());
+        hevent.SetItem(hoverItem);
+        hevent.SetEventObject(this);
+
+        if ( GetEventHandler()->ProcessEvent(hevent) && hevent.IsAllowed() )
+        {
+            SetToolTip(hevent.GetLabel());
+        }
+    }
+#endif
+
     // we process left mouse up event (enables in-place edit), right down
     // (pass to the user code), left dbl click (activate item) and
     // dragging/moving events for items drag-and-drop
     // we process left mouse up event (enables in-place edit), right down
     // (pass to the user code), left dbl click (activate item) and
     // dragging/moving events for items drag-and-drop
@@ -4163,13 +4198,12 @@ void wxTreeListMainWindow::OnMouse( wxMouseEvent &event )
     if ( event.LeftDown() )
         SetFocus();
 
     if ( event.LeftDown() )
         SetFocus();
 
-    wxClientDC dc(this);
-    PrepareDC(dc);
-    wxCoord x = dc.DeviceToLogicalX( event.GetX() );
-    wxCoord y = dc.DeviceToLogicalY( event.GetY() );
-
-    int flags = 0;
-    wxTreeListItem *item = m_anchor->HitTest(wxPoint(x,y), this, flags, 0);
+//     wxClientDC dc(this);
+//     PrepareDC(dc);
+//     wxCoord x = dc.DeviceToLogicalX( event.GetX() );
+//     wxCoord y = dc.DeviceToLogicalY( event.GetY() );
+    wxCoord &x = pt.x;
+    wxCoord &y = pt.y;
 
     if ( event.Dragging() && !m_isDragging )
     {
 
     if ( event.Dragging() && !m_isDragging )
     {
@@ -4191,6 +4225,7 @@ void wxTreeListMainWindow::OnMouse( wxMouseEvent &event )
         wxTreeEvent nevent( command,/*ALB*/ m_owner->GetId() );
         nevent.SetItem( (long) m_current);
         nevent.SetEventObject(/*this*/m_owner); // ALB
         wxTreeEvent nevent( command,/*ALB*/ m_owner->GetId() );
         nevent.SetItem( (long) m_current);
         nevent.SetEventObject(/*this*/m_owner); // ALB
+        nevent.SetPoint(pt);
 
         // by default the dragging is not supported, the user code must
         // explicitly allow the event for it to take place
 
         // by default the dragging is not supported, the user code must
         // explicitly allow the event for it to take place
@@ -4380,13 +4415,6 @@ void wxTreeListMainWindow::OnIdle( wxIdleEvent &WXUNUSED(event) )
     AdjustMyScrollbars();
 }
 
     AdjustMyScrollbars();
 }
 
-void wxTreeListMainWindow::OnSize(wxSizeEvent& WXUNUSED(event))
-{
-//     int w, h;
-//     GetClientSize(&w, &h);
-//     m_header_win->SetSize(0, 0, w, HEADER_HEIGHT);
-}
-
 void wxTreeListMainWindow::OnScroll(wxScrollWinEvent& event)
 {
     // FIXME
 void wxTreeListMainWindow::OnScroll(wxScrollWinEvent& event)
 {
     // FIXME
@@ -4605,6 +4633,7 @@ IMPLEMENT_DYNAMIC_CLASS(wxTreeListCtrl, wxControl);
 
 BEGIN_EVENT_TABLE(wxTreeListCtrl, wxControl)
     EVT_SIZE(wxTreeListCtrl::OnSize)
 
 BEGIN_EVENT_TABLE(wxTreeListCtrl, wxControl)
     EVT_SIZE(wxTreeListCtrl::OnSize)
+    EVT_TREE_ITEM_GETTOOLTIP(wxID_ANY, wxTreeListCtrl::OnGetToolTip)
 END_EVENT_TABLE();
 
 bool wxTreeListCtrl::Create(wxWindow *parent, wxWindowID id,
 END_EVENT_TABLE();
 
 bool wxTreeListCtrl::Create(wxWindow *parent, wxWindowID id,
@@ -4626,17 +4655,44 @@ bool wxTreeListCtrl::Create(wxWindow *parent, wxWindowID id,
     m_header_win = new wxTreeListHeaderWindow(this, -1, m_main_win,
                                               wxPoint(0, 0), wxDefaultSize,
                                               wxTAB_TRAVERSAL);
     m_header_win = new wxTreeListHeaderWindow(this, -1, m_main_win,
                                               wxPoint(0, 0), wxDefaultSize,
                                               wxTAB_TRAVERSAL);
+    CalculateAndSetHeaderHeight();
     return TRUE;
 }
 
     return TRUE;
 }
 
-void wxTreeListCtrl::OnSize(wxSizeEvent& WXUNUSED(event))
+void wxTreeListCtrl::CalculateAndSetHeaderHeight()
+{
+    if ( m_header_win )
+    {
+        // we use 'g' to get the descent, too
+        int w, h, d;
+        m_header_win->GetTextExtent(wxT("Hg"), &w, &h, &d);
+        h += d + 2 * HEADER_OFFSET_Y + EXTRA_HEIGHT;
+
+        // only update if changed
+        if ( h != (int)m_headerHeight )
+        {
+            m_headerHeight = (size_t)h;
+            m_header_win->SetSize(m_header_win->GetSize().x, m_headerHeight);
+        }
+    }
+}
+
+void wxTreeListCtrl::DoHeaderLayout()
 {
     int w, h;
     GetClientSize(&w, &h);
 {
     int w, h;
     GetClientSize(&w, &h);
-    if(m_header_win)
-        m_header_win->SetSize(0, 0, w, HEADER_HEIGHT);
-    if(m_main_win)
-        m_main_win->SetSize(0, HEADER_HEIGHT + 1, w, h - HEADER_HEIGHT - 1);
+    if (m_header_win)
+    {
+        m_header_win->SetSize(0, 0, w, m_headerHeight);
+        m_header_win->Refresh(false);
+    }
+    if (m_main_win)
+        m_main_win->SetSize(0, m_headerHeight + 1, w, h - m_headerHeight - 1);
+}    
+
+void wxTreeListCtrl::OnSize(wxSizeEvent& WXUNUSED(event))
+{
+    DoHeaderLayout();
 }
 
 
 }
 
 
@@ -4740,8 +4796,12 @@ void wxTreeListCtrl::SetItemFont(const wxTreeItemId& item,
 
 bool wxTreeListCtrl::SetFont(const wxFont& font)
 {
 
 bool wxTreeListCtrl::SetFont(const wxFont& font)
 {
-    if(m_header_win) m_header_win->SetFont(font);
-    if(m_main_win)
+    if (m_header_win)
+    {
+        m_header_win->SetFont(font);
+        CalculateAndSetHeaderHeight();
+    }
+    if (m_main_win)
         return m_main_win->SetFont(font);
     else return FALSE;
 }
         return m_main_win->SetFont(font);
     else return FALSE;
 }
@@ -4947,10 +5007,16 @@ wxTreeItemId wxTreeListCtrl::FindItem (const wxTreeItemId& item, const wxString&
 { return m_main_win->FindItem (item, str, flags); }
 
 bool wxTreeListCtrl::SetBackgroundColour(const wxColour& colour)
 { return m_main_win->FindItem (item, str, flags); }
 
 bool wxTreeListCtrl::SetBackgroundColour(const wxColour& colour)
-{ return m_main_win->SetBackgroundColour(colour); }
+{ 
+    if (!m_main_win) return false;
+    return m_main_win->SetBackgroundColour(colour); 
+}
 
 bool wxTreeListCtrl::SetForegroundColour(const wxColour& colour)
 
 bool wxTreeListCtrl::SetForegroundColour(const wxColour& colour)
-{ return m_main_win->SetForegroundColour(colour); }
+{ 
+    if (!m_main_win) return false;
+    return m_main_win->SetForegroundColour(colour); 
+}
 
 size_t wxTreeListCtrl::GetColumnCount() const
 { return m_main_win->GetColumnCount(); }
 
 size_t wxTreeListCtrl::GetColumnCount() const
 { return m_main_win->GetColumnCount(); }
@@ -4977,7 +5043,10 @@ wxString wxTreeListCtrl::GetColumnText(size_t column) const
 { return m_header_win->GetColumnText(column); }
 
 void wxTreeListCtrl::AddColumn(const wxTreeListColumnInfo& col)
 { return m_header_win->GetColumnText(column); }
 
 void wxTreeListCtrl::AddColumn(const wxTreeListColumnInfo& col)
-{ m_header_win->AddColumn(col); }
+{
+    m_header_win->AddColumn(col);
+    DoHeaderLayout();
+}
 
 void wxTreeListCtrl::InsertColumn(size_t before,
                                   const wxTreeListColumnInfo& col)
 
 void wxTreeListCtrl::InsertColumn(size_t before,
                                   const wxTreeListColumnInfo& col)
@@ -5037,3 +5106,17 @@ void wxTreeListCtrl::Refresh(bool erase, const wxRect* rect)
 void wxTreeListCtrl::SetFocus()
 { m_main_win->SetFocus(); }
 
 void wxTreeListCtrl::SetFocus()
 { m_main_win->SetFocus(); }
 
+
+wxSize wxTreeListCtrl::DoGetBestSize() const
+{
+    // something is better than nothing...
+    return wxSize(100,80);
+}
+
+// Process the tooltip event, to speed up event processing.
+// Doesn't actually get a tooltip.
+void wxTreeListCtrl::OnGetToolTip( wxTreeEvent &event )
+{
+    event.Veto();
+}
+