1 ///////////////////////////////////////////////////////////////////////////////
3 // Name: src/aui/auibar.cpp
4 // Purpose: wxaui: wx advanced user interface - docking window manager
5 // Author: Benjamin I. Williams
9 // Copyright: (C) Copyright 2005-2006, Kirix Corporation, All Rights Reserved
10 // Licence: wxWindows Library Licence, Version 3.1
11 ///////////////////////////////////////////////////////////////////////////////
13 // ============================================================================
15 // ============================================================================
17 // ----------------------------------------------------------------------------
19 // ----------------------------------------------------------------------------
21 #include "wx/wxprec.h"
29 #include "wx/statline.h"
30 #include "wx/dcbuffer.h"
33 #include "wx/settings.h"
36 #include "wx/aui/auibar.h"
37 #include "wx/aui/framemanager.h"
40 #include "wx/osx/private.h"
43 #include "wx/arrimpl.cpp"
44 WX_DEFINE_OBJARRAY(wxAuiToolBarItemArray
)
47 wxDEFINE_EVENT( wxEVT_COMMAND_AUITOOLBAR_TOOL_DROPDOWN
, wxAuiToolBarEvent
);
48 wxDEFINE_EVENT( wxEVT_COMMAND_AUITOOLBAR_OVERFLOW_CLICK
, wxAuiToolBarEvent
);
49 wxDEFINE_EVENT( wxEVT_COMMAND_AUITOOLBAR_RIGHT_CLICK
, wxAuiToolBarEvent
);
50 wxDEFINE_EVENT( wxEVT_COMMAND_AUITOOLBAR_MIDDLE_CLICK
, wxAuiToolBarEvent
);
51 wxDEFINE_EVENT( wxEVT_COMMAND_AUITOOLBAR_BEGIN_DRAG
, wxAuiToolBarEvent
);
54 IMPLEMENT_CLASS(wxAuiToolBar
, wxControl
)
55 IMPLEMENT_DYNAMIC_CLASS(wxAuiToolBarEvent
, wxEvent
)
58 // missing wxITEM_* items
61 wxITEM_CONTROL
= wxITEM_MAX
,
66 const int BUTTON_DROPDOWN_WIDTH
= 10;
69 wxBitmap
wxAuiBitmapFromBits(const unsigned char bits
[], int w
, int h
,
70 const wxColour
& color
);
72 static wxBitmap
MakeDisabledBitmap(wxBitmap
& bmp
)
74 wxImage image
= bmp
.ConvertToImage();
77 mr
= image
.GetMaskRed();
78 mg
= image
.GetMaskGreen();
79 mb
= image
.GetMaskBlue();
81 unsigned char* data
= image
.GetData();
82 int width
= image
.GetWidth();
83 int height
= image
.GetHeight();
84 bool has_mask
= image
.HasMask();
86 for (int y
= height
-1; y
>= 0; --y
)
88 for (int x
= width
-1; x
>= 0; --x
)
90 data
= image
.GetData() + (y
*(width
*3))+(x
*3);
91 unsigned char* r
= data
;
92 unsigned char* g
= data
+1;
93 unsigned char* b
= data
+2;
95 if (has_mask
&& *r
== mr
&& *g
== mg
&& *b
== mb
)
98 *r
= wxColour::AlphaBlend(*r
, 255, 0.4);
99 *g
= wxColour::AlphaBlend(*g
, 255, 0.4);
100 *b
= wxColour::AlphaBlend(*b
, 255, 0.4);
104 return wxBitmap(image
);
107 static wxColor
GetBaseColor()
110 #if defined( __WXMAC__ ) && wxOSX_USE_COCOA_OR_CARBON
111 wxColor base_colour
= wxColour( wxMacCreateCGColorFromHITheme(kThemeBrushToolbarBackground
));
113 wxColor base_colour
= wxSystemSettings::GetColour(wxSYS_COLOUR_3DFACE
);
116 // the base_colour is too pale to use as our base colour,
117 // so darken it a bit --
118 if ((255-base_colour
.Red()) +
119 (255-base_colour
.Green()) +
120 (255-base_colour
.Blue()) < 60)
122 base_colour
= base_colour
.ChangeLightness(92);
130 class ToolbarCommandCapture
: public wxEvtHandler
134 ToolbarCommandCapture() { m_last_id
= 0; }
135 int GetCommandId() const { return m_last_id
; }
137 bool ProcessEvent(wxEvent
& evt
)
139 if (evt
.GetEventType() == wxEVT_COMMAND_MENU_SELECTED
)
141 m_last_id
= evt
.GetId();
145 if (GetNextHandler())
146 return GetNextHandler()->ProcessEvent(evt
);
157 static const unsigned char
158 DISABLED_TEXT_GREY_HUE
= wxColour::AlphaBlend(0, 255, 0.4);
159 const wxColour
DISABLED_TEXT_COLOR(DISABLED_TEXT_GREY_HUE
,
160 DISABLED_TEXT_GREY_HUE
,
161 DISABLED_TEXT_GREY_HUE
);
163 wxAuiDefaultToolBarArt::wxAuiDefaultToolBarArt()
165 m_base_colour
= GetBaseColor();
168 m_text_orientation
= wxAUI_TBTOOL_TEXT_BOTTOM
;
169 m_highlight_colour
= wxSystemSettings::GetColour(wxSYS_COLOUR_HIGHLIGHT
);
171 m_separator_size
= 7;
173 m_overflow_size
= 16;
175 wxColor darker1_colour
= m_base_colour
.ChangeLightness(85);
176 wxColor darker2_colour
= m_base_colour
.ChangeLightness(75);
177 wxColor darker3_colour
= m_base_colour
.ChangeLightness(60);
178 wxColor darker4_colour
= m_base_colour
.ChangeLightness(50);
179 wxColor darker5_colour
= m_base_colour
.ChangeLightness(40);
181 m_gripper_pen1
= wxPen(darker5_colour
);
182 m_gripper_pen2
= wxPen(darker3_colour
);
183 m_gripper_pen3
= *wxWHITE_PEN
;
185 static const unsigned char button_dropdown_bits
[] = { 0xe0, 0xf1, 0xfb };
186 static const unsigned char overflow_bits
[] = { 0x80, 0xff, 0x80, 0xc1, 0xe3, 0xf7 };
188 m_button_dropdown_bmp
= wxAuiBitmapFromBits(button_dropdown_bits
, 5, 3,
190 m_disabled_button_dropdown_bmp
= wxAuiBitmapFromBits(
191 button_dropdown_bits
, 5, 3,
192 wxColor(128,128,128));
193 m_overflow_bmp
= wxAuiBitmapFromBits(overflow_bits
, 7, 6, *wxBLACK
);
194 m_disabled_overflow_bmp
= wxAuiBitmapFromBits(overflow_bits
, 7, 6, wxColor(128,128,128));
196 m_font
= *wxNORMAL_FONT
;
199 wxAuiDefaultToolBarArt::~wxAuiDefaultToolBarArt()
201 m_font
= *wxNORMAL_FONT
;
205 wxAuiToolBarArt
* wxAuiDefaultToolBarArt::Clone()
207 return static_cast<wxAuiToolBarArt
*>(new wxAuiDefaultToolBarArt
);
210 void wxAuiDefaultToolBarArt::SetFlags(unsigned int flags
)
215 void wxAuiDefaultToolBarArt::SetFont(const wxFont
& font
)
220 void wxAuiDefaultToolBarArt::SetTextOrientation(int orientation
)
222 m_text_orientation
= orientation
;
225 unsigned int wxAuiDefaultToolBarArt::GetFlags()
230 wxFont
wxAuiDefaultToolBarArt::GetFont()
235 int wxAuiDefaultToolBarArt::GetTextOrientation()
237 return m_text_orientation
;
240 void wxAuiDefaultToolBarArt::DrawBackground(
242 wxWindow
* WXUNUSED(wnd
),
247 wxColour start_colour
= m_base_colour
.ChangeLightness(150);
248 wxColour end_colour
= m_base_colour
.ChangeLightness(90);
249 dc
.GradientFillLinear(rect
, start_colour
, end_colour
, wxSOUTH
);
252 void wxAuiDefaultToolBarArt::DrawLabel(
254 wxWindow
* WXUNUSED(wnd
),
255 const wxAuiToolBarItem
& item
,
259 dc
.SetTextForeground(*wxBLACK
);
261 // we only care about the text height here since the text
262 // will get cropped based on the width of the item
263 int text_width
= 0, text_height
= 0;
264 dc
.GetTextExtent(wxT("ABCDHgj"), &text_width
, &text_height
);
266 // set the clipping region
267 wxRect clip_rect
= rect
;
268 clip_rect
.width
-= 1;
269 dc
.SetClippingRegion(clip_rect
);
273 text_y
= rect
.y
+ (rect
.height
-text_height
)/2;
274 dc
.DrawText(item
.GetLabel(), text_x
, text_y
);
275 dc
.DestroyClippingRegion();
279 void wxAuiDefaultToolBarArt::DrawButton(
281 wxWindow
* WXUNUSED(wnd
),
282 const wxAuiToolBarItem
& item
,
285 int text_width
= 0, text_height
= 0;
287 if (m_flags
& wxAUI_TB_TEXT
)
293 dc
.GetTextExtent(wxT("ABCDHgj"), &tx
, &text_height
);
295 dc
.GetTextExtent(item
.GetLabel(), &text_width
, &ty
);
298 int bmp_x
= 0, bmp_y
= 0;
299 int text_x
= 0, text_y
= 0;
301 if (m_text_orientation
== wxAUI_TBTOOL_TEXT_BOTTOM
)
305 (item
.GetBitmap().GetWidth()/2);
308 ((rect
.height
-text_height
)/2) -
309 (item
.GetBitmap().GetHeight()/2);
311 text_x
= rect
.x
+ (rect
.width
/2) - (text_width
/2) + 1;
312 text_y
= rect
.y
+ rect
.height
- text_height
- 1;
314 else if (m_text_orientation
== wxAUI_TBTOOL_TEXT_RIGHT
)
320 (item
.GetBitmap().GetHeight()/2);
322 text_x
= bmp_x
+ 3 + item
.GetBitmap().GetWidth();
329 if (!(item
.GetState() & wxAUI_BUTTON_STATE_DISABLED
))
331 if (item
.GetState() & wxAUI_BUTTON_STATE_PRESSED
)
333 dc
.SetPen(wxPen(m_highlight_colour
));
334 dc
.SetBrush(wxBrush(m_highlight_colour
.ChangeLightness(150)));
335 dc
.DrawRectangle(rect
);
337 else if ((item
.GetState() & wxAUI_BUTTON_STATE_HOVER
) || item
.IsSticky())
339 dc
.SetPen(wxPen(m_highlight_colour
));
340 dc
.SetBrush(wxBrush(m_highlight_colour
.ChangeLightness(170)));
342 // draw an even lighter background for checked item hovers (since
343 // the hover background is the same color as the check background)
344 if (item
.GetState() & wxAUI_BUTTON_STATE_CHECKED
)
345 dc
.SetBrush(wxBrush(m_highlight_colour
.ChangeLightness(180)));
347 dc
.DrawRectangle(rect
);
349 else if (item
.GetState() & wxAUI_BUTTON_STATE_CHECKED
)
351 // it's important to put this code in an else statment after the
352 // hover, otherwise hovers won't draw properly for checked items
353 dc
.SetPen(wxPen(m_highlight_colour
));
354 dc
.SetBrush(wxBrush(m_highlight_colour
.ChangeLightness(170)));
355 dc
.DrawRectangle(rect
);
360 if (item
.GetState() & wxAUI_BUTTON_STATE_DISABLED
)
361 bmp
= item
.GetDisabledBitmap();
363 bmp
= item
.GetBitmap();
366 dc
.DrawBitmap(bmp
, bmp_x
, bmp_y
, true);
368 // set the item's text color based on if it is disabled
369 dc
.SetTextForeground(*wxBLACK
);
370 if (item
.GetState() & wxAUI_BUTTON_STATE_DISABLED
)
371 dc
.SetTextForeground(DISABLED_TEXT_COLOR
);
373 if ( (m_flags
& wxAUI_TB_TEXT
) && !item
.GetLabel().empty() )
375 dc
.DrawText(item
.GetLabel(), text_x
, text_y
);
380 void wxAuiDefaultToolBarArt::DrawDropDownButton(
382 wxWindow
* WXUNUSED(wnd
),
383 const wxAuiToolBarItem
& item
,
386 int text_width
= 0, text_height
= 0, text_x
= 0, text_y
= 0;
387 int bmp_x
= 0, bmp_y
= 0, dropbmp_x
= 0, dropbmp_y
= 0;
389 wxRect button_rect
= wxRect(rect
.x
,
391 rect
.width
-BUTTON_DROPDOWN_WIDTH
,
393 wxRect dropdown_rect
= wxRect(rect
.x
+rect
.width
-BUTTON_DROPDOWN_WIDTH
-1,
395 BUTTON_DROPDOWN_WIDTH
+1,
398 if (m_flags
& wxAUI_TB_TEXT
)
403 if (m_flags
& wxAUI_TB_TEXT
)
405 dc
.GetTextExtent(wxT("ABCDHgj"), &tx
, &text_height
);
409 dc
.GetTextExtent(item
.GetLabel(), &text_width
, &ty
);
414 dropbmp_x
= dropdown_rect
.x
+
415 (dropdown_rect
.width
/2) -
416 (m_button_dropdown_bmp
.GetWidth()/2);
417 dropbmp_y
= dropdown_rect
.y
+
418 (dropdown_rect
.height
/2) -
419 (m_button_dropdown_bmp
.GetHeight()/2);
422 if (m_text_orientation
== wxAUI_TBTOOL_TEXT_BOTTOM
)
424 bmp_x
= button_rect
.x
+
425 (button_rect
.width
/2) -
426 (item
.GetBitmap().GetWidth()/2);
427 bmp_y
= button_rect
.y
+
428 ((button_rect
.height
-text_height
)/2) -
429 (item
.GetBitmap().GetHeight()/2);
431 text_x
= rect
.x
+ (rect
.width
/2) - (text_width
/2) + 1;
432 text_y
= rect
.y
+ rect
.height
- text_height
- 1;
434 else if (m_text_orientation
== wxAUI_TBTOOL_TEXT_RIGHT
)
440 (item
.GetBitmap().GetHeight()/2);
442 text_x
= bmp_x
+ 3 + item
.GetBitmap().GetWidth();
449 if (item
.GetState() & wxAUI_BUTTON_STATE_PRESSED
)
451 dc
.SetPen(wxPen(m_highlight_colour
));
452 dc
.SetBrush(wxBrush(m_highlight_colour
.ChangeLightness(140)));
453 dc
.DrawRectangle(button_rect
);
455 dc
.SetBrush(wxBrush(m_highlight_colour
.ChangeLightness(170)));
456 dc
.DrawRectangle(dropdown_rect
);
458 else if (item
.GetState() & wxAUI_BUTTON_STATE_HOVER
||
461 dc
.SetPen(wxPen(m_highlight_colour
));
462 dc
.SetBrush(wxBrush(m_highlight_colour
.ChangeLightness(170)));
463 dc
.DrawRectangle(button_rect
);
464 dc
.DrawRectangle(dropdown_rect
);
466 else if (item
.GetState() & wxAUI_BUTTON_STATE_CHECKED
)
468 // Notice that this branch must come after the hover one to ensure the
469 // correct appearance when the mouse hovers over a checked item.
470 dc
.SetPen(wxPen(m_highlight_colour
));
471 dc
.SetBrush(wxBrush(m_highlight_colour
.ChangeLightness(170)));
472 dc
.DrawRectangle(button_rect
);
473 dc
.DrawRectangle(dropdown_rect
);
478 if (item
.GetState() & wxAUI_BUTTON_STATE_DISABLED
)
480 bmp
= item
.GetDisabledBitmap();
481 dropbmp
= m_disabled_button_dropdown_bmp
;
485 bmp
= item
.GetBitmap();
486 dropbmp
= m_button_dropdown_bmp
;
492 dc
.DrawBitmap(bmp
, bmp_x
, bmp_y
, true);
493 dc
.DrawBitmap(dropbmp
, dropbmp_x
, dropbmp_y
, true);
495 // set the item's text color based on if it is disabled
496 dc
.SetTextForeground(*wxBLACK
);
497 if (item
.GetState() & wxAUI_BUTTON_STATE_DISABLED
)
498 dc
.SetTextForeground(DISABLED_TEXT_COLOR
);
500 if ( (m_flags
& wxAUI_TB_TEXT
) && !item
.GetLabel().empty() )
502 dc
.DrawText(item
.GetLabel(), text_x
, text_y
);
506 void wxAuiDefaultToolBarArt::DrawControlLabel(
508 wxWindow
* WXUNUSED(wnd
),
509 const wxAuiToolBarItem
& item
,
512 if (!(m_flags
& wxAUI_TB_TEXT
))
515 if (m_text_orientation
!= wxAUI_TBTOOL_TEXT_BOTTOM
)
518 int text_x
= 0, text_y
= 0;
519 int text_width
= 0, text_height
= 0;
524 if (m_flags
& wxAUI_TB_TEXT
)
526 dc
.GetTextExtent(wxT("ABCDHgj"), &tx
, &text_height
);
530 dc
.GetTextExtent(item
.GetLabel(), &text_width
, &ty
);
532 // don't draw the label if it is wider than the item width
533 if (text_width
> rect
.width
)
536 // set the label's text color
537 dc
.SetTextForeground(*wxBLACK
);
539 text_x
= rect
.x
+ (rect
.width
/2) - (text_width
/2) + 1;
540 text_y
= rect
.y
+ rect
.height
- text_height
- 1;
542 if ( (m_flags
& wxAUI_TB_TEXT
) && !item
.GetLabel().empty() )
544 dc
.DrawText(item
.GetLabel(), text_x
, text_y
);
548 wxSize
wxAuiDefaultToolBarArt::GetLabelSize(
550 wxWindow
* WXUNUSED(wnd
),
551 const wxAuiToolBarItem
& item
)
555 // get label's height
556 int width
= 0, height
= 0;
557 dc
.GetTextExtent(wxT("ABCDHgj"), &width
, &height
);
560 width
= item
.GetMinSize().GetWidth();
564 // no width specified, measure the text ourselves
565 width
= dc
.GetTextExtent(item
.GetLabel()).GetX();
568 return wxSize(width
, height
);
571 wxSize
wxAuiDefaultToolBarArt::GetToolSize(
573 wxWindow
* WXUNUSED(wnd
),
574 const wxAuiToolBarItem
& item
)
576 if (!item
.GetBitmap().IsOk() && !(m_flags
& wxAUI_TB_TEXT
))
577 return wxSize(16,16);
579 int width
= item
.GetBitmap().GetWidth();
580 int height
= item
.GetBitmap().GetHeight();
582 if (m_flags
& wxAUI_TB_TEXT
)
587 if (m_text_orientation
== wxAUI_TBTOOL_TEXT_BOTTOM
)
589 dc
.GetTextExtent(wxT("ABCDHgj"), &tx
, &ty
);
592 if ( !item
.GetLabel().empty() )
594 dc
.GetTextExtent(item
.GetLabel(), &tx
, &ty
);
595 width
= wxMax(width
, tx
+6);
598 else if ( m_text_orientation
== wxAUI_TBTOOL_TEXT_RIGHT
&&
599 !item
.GetLabel().empty() )
601 width
+= 3; // space between left border and bitmap
602 width
+= 3; // space between bitmap and text
604 if ( !item
.GetLabel().empty() )
606 dc
.GetTextExtent(item
.GetLabel(), &tx
, &ty
);
608 height
= wxMax(height
, ty
);
613 // if the tool has a dropdown button, add it to the width
614 if (item
.HasDropDown())
615 width
+= (BUTTON_DROPDOWN_WIDTH
+4);
617 return wxSize(width
, height
);
620 void wxAuiDefaultToolBarArt::DrawSeparator(
622 wxWindow
* WXUNUSED(wnd
),
625 bool horizontal
= true;
626 if (m_flags
& wxAUI_TB_VERTICAL
)
633 rect
.x
+= (rect
.width
/2);
635 int new_height
= (rect
.height
*3)/4;
636 rect
.y
+= (rect
.height
/2) - (new_height
/2);
637 rect
.height
= new_height
;
641 rect
.y
+= (rect
.height
/2);
643 int new_width
= (rect
.width
*3)/4;
644 rect
.x
+= (rect
.width
/2) - (new_width
/2);
645 rect
.width
= new_width
;
648 wxColour start_colour
= m_base_colour
.ChangeLightness(80);
649 wxColour end_colour
= m_base_colour
.ChangeLightness(80);
650 dc
.GradientFillLinear(rect
, start_colour
, end_colour
, horizontal
? wxSOUTH
: wxEAST
);
653 void wxAuiDefaultToolBarArt::DrawGripper(wxDC
& dc
,
654 wxWindow
* WXUNUSED(wnd
),
662 if (m_flags
& wxAUI_TB_VERTICAL
)
664 x
= rect
.x
+ (i
*4) + 5;
666 if (x
> rect
.GetWidth()-5)
672 y
= rect
.y
+ (i
*4) + 5;
673 if (y
> rect
.GetHeight()-5)
677 dc
.SetPen(m_gripper_pen1
);
679 dc
.SetPen(m_gripper_pen2
);
680 dc
.DrawPoint(x
, y
+1);
681 dc
.DrawPoint(x
+1, y
);
682 dc
.SetPen(m_gripper_pen3
);
683 dc
.DrawPoint(x
+2, y
+1);
684 dc
.DrawPoint(x
+2, y
+2);
685 dc
.DrawPoint(x
+1, y
+2);
692 void wxAuiDefaultToolBarArt::DrawOverflowButton(wxDC
& dc
,
697 if (state
& wxAUI_BUTTON_STATE_HOVER
||
698 state
& wxAUI_BUTTON_STATE_PRESSED
)
700 wxRect cli_rect
= wnd
->GetClientRect();
701 wxColor light_gray_bg
= m_highlight_colour
.ChangeLightness(170);
703 if (m_flags
& wxAUI_TB_VERTICAL
)
705 dc
.SetPen(wxPen(m_highlight_colour
));
706 dc
.DrawLine(rect
.x
, rect
.y
, rect
.x
+rect
.width
, rect
.y
);
707 dc
.SetPen(wxPen(light_gray_bg
));
708 dc
.SetBrush(wxBrush(light_gray_bg
));
709 dc
.DrawRectangle(rect
.x
, rect
.y
+1, rect
.width
, rect
.height
);
713 dc
.SetPen(wxPen(m_highlight_colour
));
714 dc
.DrawLine(rect
.x
, rect
.y
, rect
.x
, rect
.y
+rect
.height
);
715 dc
.SetPen(wxPen(light_gray_bg
));
716 dc
.SetBrush(wxBrush(light_gray_bg
));
717 dc
.DrawRectangle(rect
.x
+1, rect
.y
, rect
.width
, rect
.height
);
721 int x
= rect
.x
+1+(rect
.width
-m_overflow_bmp
.GetWidth())/2;
722 int y
= rect
.y
+1+(rect
.height
-m_overflow_bmp
.GetHeight())/2;
723 dc
.DrawBitmap(m_overflow_bmp
, x
, y
, true);
726 int wxAuiDefaultToolBarArt::GetElementSize(int element_id
)
730 case wxAUI_TBART_SEPARATOR_SIZE
: return m_separator_size
;
731 case wxAUI_TBART_GRIPPER_SIZE
: return m_gripper_size
;
732 case wxAUI_TBART_OVERFLOW_SIZE
: return m_overflow_size
;
737 void wxAuiDefaultToolBarArt::SetElementSize(int element_id
, int size
)
741 case wxAUI_TBART_SEPARATOR_SIZE
: m_separator_size
= size
; break;
742 case wxAUI_TBART_GRIPPER_SIZE
: m_gripper_size
= size
; break;
743 case wxAUI_TBART_OVERFLOW_SIZE
: m_overflow_size
= size
; break;
747 int wxAuiDefaultToolBarArt::ShowDropDown(wxWindow
* wnd
,
748 const wxAuiToolBarItemArray
& items
)
752 size_t items_added
= 0;
754 size_t i
, count
= items
.GetCount();
755 for (i
= 0; i
< count
; ++i
)
757 wxAuiToolBarItem
& item
= items
.Item(i
);
759 if (item
.GetKind() == wxITEM_NORMAL
)
761 wxString text
= item
.GetShortHelp();
763 text
= item
.GetLabel();
768 wxMenuItem
* m
= new wxMenuItem(&menuPopup
, item
.GetId(), text
, item
.GetShortHelp());
770 m
->SetBitmap(item
.GetBitmap());
774 else if (item
.GetKind() == wxITEM_SEPARATOR
)
777 menuPopup
.AppendSeparator();
781 // find out where to put the popup menu of window items
782 wxPoint pt
= ::wxGetMousePosition();
783 pt
= wnd
->ScreenToClient(pt
);
785 // find out the screen coordinate at the bottom of the tab ctrl
786 wxRect cli_rect
= wnd
->GetClientRect();
787 pt
.y
= cli_rect
.y
+ cli_rect
.height
;
789 ToolbarCommandCapture
* cc
= new ToolbarCommandCapture
;
790 wnd
->PushEventHandler(cc
);
791 wnd
->PopupMenu(&menuPopup
, pt
);
792 int command
= cc
->GetCommandId();
793 wnd
->PopEventHandler(true);
801 static wxOrientation
GetOrientation(long& style
)
803 switch (style
& wxAUI_ORIENTATION_MASK
)
805 case wxAUI_TB_HORIZONTAL
:
807 case wxAUI_TB_VERTICAL
:
810 wxFAIL_MSG("toolbar cannot be locked in both horizontal and vertical orientations (maybe no lock was intended?)");
817 BEGIN_EVENT_TABLE(wxAuiToolBar
, wxControl
)
818 EVT_SIZE(wxAuiToolBar::OnSize
)
819 EVT_IDLE(wxAuiToolBar::OnIdle
)
820 EVT_ERASE_BACKGROUND(wxAuiToolBar::OnEraseBackground
)
821 EVT_PAINT(wxAuiToolBar::OnPaint
)
822 EVT_LEFT_DOWN(wxAuiToolBar::OnLeftDown
)
823 EVT_LEFT_DCLICK(wxAuiToolBar::OnLeftDown
)
824 EVT_LEFT_UP(wxAuiToolBar::OnLeftUp
)
825 EVT_RIGHT_DOWN(wxAuiToolBar::OnRightDown
)
826 EVT_RIGHT_DCLICK(wxAuiToolBar::OnRightDown
)
827 EVT_RIGHT_UP(wxAuiToolBar::OnRightUp
)
828 EVT_MIDDLE_DOWN(wxAuiToolBar::OnMiddleDown
)
829 EVT_MIDDLE_DCLICK(wxAuiToolBar::OnMiddleDown
)
830 EVT_MIDDLE_UP(wxAuiToolBar::OnMiddleUp
)
831 EVT_MOTION(wxAuiToolBar::OnMotion
)
832 EVT_LEAVE_WINDOW(wxAuiToolBar::OnLeaveWindow
)
833 EVT_MOUSE_CAPTURE_LOST(wxAuiToolBar::OnCaptureLost
)
834 EVT_SET_CURSOR(wxAuiToolBar::OnSetCursor
)
838 wxAuiToolBar::wxAuiToolBar(wxWindow
* parent
,
840 const wxPoint
& position
,
847 style
| wxBORDER_NONE
)
849 m_sizer
= new wxBoxSizer(wxHORIZONTAL
);
851 m_button_height
= -1;
852 m_sizer_element_count
= 0;
853 m_action_pos
= wxPoint(-1,-1);
854 m_action_item
= NULL
;
856 m_art
= new wxAuiDefaultToolBarArt
;
858 m_tool_border_padding
= 3;
859 m_tool_text_orientation
= wxAUI_TBTOOL_TEXT_BOTTOM
;
860 m_gripper_sizer_item
= NULL
;
861 m_overflow_sizer_item
= NULL
;
863 m_orientation
= GetOrientation(style
);
864 if (m_orientation
== wxBOTH
)
866 m_orientation
= wxHORIZONTAL
;
868 m_style
= style
| wxBORDER_NONE
;
869 m_gripper_visible
= (m_style
& wxAUI_TB_GRIPPER
) ? true : false;
870 m_overflow_visible
= (m_style
& wxAUI_TB_OVERFLOW
) ? true : false;
871 m_overflow_state
= 0;
872 SetMargins(5, 5, 2, 2);
873 SetFont(*wxNORMAL_FONT
);
875 SetExtraStyle(wxWS_EX_PROCESS_IDLE
);
876 if (style
& wxAUI_TB_HORZ_LAYOUT
)
877 SetToolTextOrientation(wxAUI_TBTOOL_TEXT_RIGHT
);
878 SetBackgroundStyle(wxBG_STYLE_CUSTOM
);
882 wxAuiToolBar::~wxAuiToolBar()
888 void wxAuiToolBar::SetWindowStyleFlag(long style
)
890 GetOrientation(style
); // assert if style is invalid
891 wxCHECK_RET(IsPaneValid(style
),
892 "window settings and pane settings are incompatible");
894 wxControl::SetWindowStyleFlag(style
);
903 if (m_style
& wxAUI_TB_GRIPPER
)
904 m_gripper_visible
= true;
906 m_gripper_visible
= false;
909 if (m_style
& wxAUI_TB_OVERFLOW
)
910 m_overflow_visible
= true;
912 m_overflow_visible
= false;
914 if (style
& wxAUI_TB_HORZ_LAYOUT
)
915 SetToolTextOrientation(wxAUI_TBTOOL_TEXT_RIGHT
);
917 SetToolTextOrientation(wxAUI_TBTOOL_TEXT_BOTTOM
);
920 long wxAuiToolBar::GetWindowStyleFlag() const
925 void wxAuiToolBar::SetArtProvider(wxAuiToolBarArt
* art
)
934 m_art
->SetTextOrientation(m_tool_text_orientation
);
938 wxAuiToolBarArt
* wxAuiToolBar::GetArtProvider() const
946 wxAuiToolBarItem
* wxAuiToolBar::AddTool(int tool_id
,
947 const wxString
& label
,
948 const wxBitmap
& bitmap
,
949 const wxString
& short_help_string
,
952 return AddTool(tool_id
,
963 wxAuiToolBarItem
* wxAuiToolBar::AddTool(int tool_id
,
964 const wxString
& label
,
965 const wxBitmap
& bitmap
,
966 const wxBitmap
& disabled_bitmap
,
968 const wxString
& short_help_string
,
969 const wxString
& long_help_string
,
970 wxObject
* WXUNUSED(client_data
))
972 wxAuiToolBarItem item
;
975 item
.bitmap
= bitmap
;
976 item
.disabled_bitmap
= disabled_bitmap
;
977 item
.short_help
= short_help_string
;
978 item
.long_help
= long_help_string
;
980 item
.dropdown
= false;
981 item
.spacer_pixels
= 0;
982 item
.toolid
= tool_id
;
986 item
.sizer_item
= NULL
;
987 item
.min_size
= wxDefaultSize
;
991 if (item
.toolid
== wxID_ANY
)
992 item
.toolid
= wxNewId();
994 if (!item
.disabled_bitmap
.IsOk())
996 // no disabled bitmap specified, we need to make one
997 if (item
.bitmap
.IsOk())
999 //wxImage img = item.bitmap.ConvertToImage();
1000 //wxImage grey_version = img.ConvertToGreyscale();
1001 //item.disabled_bitmap = wxBitmap(grey_version);
1002 item
.disabled_bitmap
= MakeDisabledBitmap(item
.bitmap
);
1006 return &m_items
.Last();
1009 wxAuiToolBarItem
* wxAuiToolBar::AddControl(wxControl
* control
,
1010 const wxString
& label
)
1012 wxAuiToolBarItem item
;
1013 item
.window
= (wxWindow
*)control
;
1015 item
.bitmap
= wxNullBitmap
;
1016 item
.disabled_bitmap
= wxNullBitmap
;
1018 item
.dropdown
= false;
1019 item
.spacer_pixels
= 0;
1020 item
.toolid
= control
->GetId();
1022 item
.proportion
= 0;
1023 item
.kind
= wxITEM_CONTROL
;
1024 item
.sizer_item
= NULL
;
1025 item
.min_size
= control
->GetEffectiveMinSize();
1027 item
.sticky
= false;
1030 return &m_items
.Last();
1033 wxAuiToolBarItem
* wxAuiToolBar::AddLabel(int tool_id
,
1034 const wxString
& label
,
1037 wxSize min_size
= wxDefaultSize
;
1041 wxAuiToolBarItem item
;
1044 item
.bitmap
= wxNullBitmap
;
1045 item
.disabled_bitmap
= wxNullBitmap
;
1047 item
.dropdown
= false;
1048 item
.spacer_pixels
= 0;
1049 item
.toolid
= tool_id
;
1051 item
.proportion
= 0;
1052 item
.kind
= wxITEM_LABEL
;
1053 item
.sizer_item
= NULL
;
1054 item
.min_size
= min_size
;
1056 item
.sticky
= false;
1058 if (item
.toolid
== wxID_ANY
)
1059 item
.toolid
= wxNewId();
1062 return &m_items
.Last();
1065 wxAuiToolBarItem
* wxAuiToolBar::AddSeparator()
1067 wxAuiToolBarItem item
;
1069 item
.label
= wxEmptyString
;
1070 item
.bitmap
= wxNullBitmap
;
1071 item
.disabled_bitmap
= wxNullBitmap
;
1073 item
.dropdown
= false;
1076 item
.proportion
= 0;
1077 item
.kind
= wxITEM_SEPARATOR
;
1078 item
.sizer_item
= NULL
;
1079 item
.min_size
= wxDefaultSize
;
1081 item
.sticky
= false;
1084 return &m_items
.Last();
1087 wxAuiToolBarItem
* wxAuiToolBar::AddSpacer(int pixels
)
1089 wxAuiToolBarItem item
;
1091 item
.label
= wxEmptyString
;
1092 item
.bitmap
= wxNullBitmap
;
1093 item
.disabled_bitmap
= wxNullBitmap
;
1095 item
.dropdown
= false;
1096 item
.spacer_pixels
= pixels
;
1099 item
.proportion
= 0;
1100 item
.kind
= wxITEM_SPACER
;
1101 item
.sizer_item
= NULL
;
1102 item
.min_size
= wxDefaultSize
;
1104 item
.sticky
= false;
1107 return &m_items
.Last();
1110 wxAuiToolBarItem
* wxAuiToolBar::AddStretchSpacer(int proportion
)
1112 wxAuiToolBarItem item
;
1114 item
.label
= wxEmptyString
;
1115 item
.bitmap
= wxNullBitmap
;
1116 item
.disabled_bitmap
= wxNullBitmap
;
1118 item
.dropdown
= false;
1119 item
.spacer_pixels
= 0;
1122 item
.proportion
= proportion
;
1123 item
.kind
= wxITEM_SPACER
;
1124 item
.sizer_item
= NULL
;
1125 item
.min_size
= wxDefaultSize
;
1127 item
.sticky
= false;
1130 return &m_items
.Last();
1133 void wxAuiToolBar::Clear()
1136 m_sizer_element_count
= 0;
1139 bool wxAuiToolBar::DeleteTool(int tool_id
)
1141 int idx
= GetToolIndex(tool_id
);
1142 if (idx
>= 0 && idx
< (int)m_items
.GetCount())
1144 m_items
.RemoveAt(idx
);
1152 bool wxAuiToolBar::DeleteByIndex(int idx
)
1154 if (idx
>= 0 && idx
< (int)m_items
.GetCount())
1156 m_items
.RemoveAt(idx
);
1165 wxControl
* wxAuiToolBar::FindControl(int id
)
1167 wxWindow
* wnd
= FindWindow(id
);
1168 return (wxControl
*)wnd
;
1171 wxAuiToolBarItem
* wxAuiToolBar::FindTool(int tool_id
) const
1174 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
1176 wxAuiToolBarItem
& item
= m_items
.Item(i
);
1177 if (item
.toolid
== tool_id
)
1184 wxAuiToolBarItem
* wxAuiToolBar::FindToolByPosition(wxCoord x
, wxCoord y
) const
1187 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
1189 wxAuiToolBarItem
& item
= m_items
.Item(i
);
1191 if (!item
.sizer_item
)
1194 wxRect rect
= item
.sizer_item
->GetRect();
1195 if (rect
.Contains(x
,y
))
1197 // if the item doesn't fit on the toolbar, return NULL
1198 if (!GetToolFitsByIndex(i
))
1208 wxAuiToolBarItem
* wxAuiToolBar::FindToolByPositionWithPacking(wxCoord x
, wxCoord y
) const
1211 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
1213 wxAuiToolBarItem
& item
= m_items
.Item(i
);
1215 if (!item
.sizer_item
)
1218 wxRect rect
= item
.sizer_item
->GetRect();
1220 // apply tool packing
1222 rect
.width
+= m_tool_packing
;
1224 if (rect
.Contains(x
,y
))
1226 // if the item doesn't fit on the toolbar, return NULL
1227 if (!GetToolFitsByIndex(i
))
1237 wxAuiToolBarItem
* wxAuiToolBar::FindToolByIndex(int idx
) const
1242 if (idx
>= (int)m_items
.size())
1245 return &(m_items
[idx
]);
1248 void wxAuiToolBar::SetToolBitmapSize(const wxSize
& WXUNUSED(size
))
1250 // TODO: wxToolBar compatibility
1253 wxSize
wxAuiToolBar::GetToolBitmapSize() const
1255 // TODO: wxToolBar compatibility
1256 return wxSize(16,15);
1259 void wxAuiToolBar::SetToolProportion(int tool_id
, int proportion
)
1261 wxAuiToolBarItem
* item
= FindTool(tool_id
);
1265 item
->proportion
= proportion
;
1268 int wxAuiToolBar::GetToolProportion(int tool_id
) const
1270 wxAuiToolBarItem
* item
= FindTool(tool_id
);
1274 return item
->proportion
;
1277 void wxAuiToolBar::SetToolSeparation(int separation
)
1280 m_art
->SetElementSize(wxAUI_TBART_SEPARATOR_SIZE
, separation
);
1283 int wxAuiToolBar::GetToolSeparation() const
1286 return m_art
->GetElementSize(wxAUI_TBART_SEPARATOR_SIZE
);
1292 void wxAuiToolBar::SetToolDropDown(int tool_id
, bool dropdown
)
1294 wxAuiToolBarItem
* item
= FindTool(tool_id
);
1298 item
->dropdown
= dropdown
;
1301 bool wxAuiToolBar::GetToolDropDown(int tool_id
) const
1303 wxAuiToolBarItem
* item
= FindTool(tool_id
);
1307 return item
->dropdown
;
1310 void wxAuiToolBar::SetToolSticky(int tool_id
, bool sticky
)
1312 // ignore separators
1316 wxAuiToolBarItem
* item
= FindTool(tool_id
);
1320 if (item
->sticky
== sticky
)
1323 item
->sticky
= sticky
;
1329 bool wxAuiToolBar::GetToolSticky(int tool_id
) const
1331 wxAuiToolBarItem
* item
= FindTool(tool_id
);
1335 return item
->sticky
;
1341 void wxAuiToolBar::SetToolBorderPadding(int padding
)
1343 m_tool_border_padding
= padding
;
1346 int wxAuiToolBar::GetToolBorderPadding() const
1348 return m_tool_border_padding
;
1351 void wxAuiToolBar::SetToolTextOrientation(int orientation
)
1353 m_tool_text_orientation
= orientation
;
1357 m_art
->SetTextOrientation(orientation
);
1361 int wxAuiToolBar::GetToolTextOrientation() const
1363 return m_tool_text_orientation
;
1366 void wxAuiToolBar::SetToolPacking(int packing
)
1368 m_tool_packing
= packing
;
1371 int wxAuiToolBar::GetToolPacking() const
1373 return m_tool_packing
;
1377 void wxAuiToolBar::SetOrientation(int orientation
)
1379 wxCHECK_RET(orientation
== wxHORIZONTAL
||
1380 orientation
== wxVERTICAL
,
1381 "invalid orientation value");
1382 if (orientation
!= m_orientation
)
1384 m_orientation
= wxOrientation(orientation
);
1389 void wxAuiToolBar::SetMargins(int left
, int right
, int top
, int bottom
)
1392 m_left_padding
= left
;
1394 m_right_padding
= right
;
1396 m_top_padding
= top
;
1398 m_bottom_padding
= bottom
;
1401 bool wxAuiToolBar::GetGripperVisible() const
1403 return m_gripper_visible
;
1406 void wxAuiToolBar::SetGripperVisible(bool visible
)
1408 m_gripper_visible
= visible
;
1410 m_style
|= wxAUI_TB_GRIPPER
;
1412 m_style
&= ~wxAUI_TB_GRIPPER
;
1418 bool wxAuiToolBar::GetOverflowVisible() const
1420 return m_overflow_visible
;
1423 void wxAuiToolBar::SetOverflowVisible(bool visible
)
1425 m_overflow_visible
= visible
;
1427 m_style
|= wxAUI_TB_OVERFLOW
;
1429 m_style
&= ~wxAUI_TB_OVERFLOW
;
1433 bool wxAuiToolBar::SetFont(const wxFont
& font
)
1435 bool res
= wxWindow::SetFont(font
);
1439 m_art
->SetFont(font
);
1446 void wxAuiToolBar::SetHoverItem(wxAuiToolBarItem
* pitem
)
1448 wxAuiToolBarItem
* former_hover
= NULL
;
1451 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
1453 wxAuiToolBarItem
& item
= m_items
.Item(i
);
1454 if (item
.state
& wxAUI_BUTTON_STATE_HOVER
)
1455 former_hover
= &item
;
1456 item
.state
&= ~wxAUI_BUTTON_STATE_HOVER
;
1461 pitem
->state
|= wxAUI_BUTTON_STATE_HOVER
;
1464 if (former_hover
!= pitem
)
1471 void wxAuiToolBar::SetPressedItem(wxAuiToolBarItem
* pitem
)
1473 wxAuiToolBarItem
* former_item
= NULL
;
1476 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
1478 wxAuiToolBarItem
& item
= m_items
.Item(i
);
1479 if (item
.state
& wxAUI_BUTTON_STATE_PRESSED
)
1480 former_item
= &item
;
1481 item
.state
&= ~wxAUI_BUTTON_STATE_PRESSED
;
1486 pitem
->state
&= ~wxAUI_BUTTON_STATE_HOVER
;
1487 pitem
->state
|= wxAUI_BUTTON_STATE_PRESSED
;
1490 if (former_item
!= pitem
)
1497 void wxAuiToolBar::RefreshOverflowState()
1499 if (!m_overflow_sizer_item
)
1501 m_overflow_state
= 0;
1505 int overflow_state
= 0;
1507 wxRect overflow_rect
= GetOverflowRect();
1510 // find out the mouse's current position
1511 wxPoint pt
= ::wxGetMousePosition();
1512 pt
= this->ScreenToClient(pt
);
1514 // find out if the mouse cursor is inside the dropdown rectangle
1515 if (overflow_rect
.Contains(pt
.x
, pt
.y
))
1517 if (::wxGetMouseState().LeftIsDown())
1518 overflow_state
= wxAUI_BUTTON_STATE_PRESSED
;
1520 overflow_state
= wxAUI_BUTTON_STATE_HOVER
;
1523 if (overflow_state
!= m_overflow_state
)
1525 m_overflow_state
= overflow_state
;
1530 m_overflow_state
= overflow_state
;
1533 void wxAuiToolBar::ToggleTool(int tool_id
, bool state
)
1535 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1537 if (tool
&& (tool
->kind
== wxITEM_CHECK
|| tool
->kind
== wxITEM_RADIO
))
1539 if (tool
->kind
== wxITEM_RADIO
)
1542 idx
= GetToolIndex(tool_id
);
1543 count
= (int)m_items
.GetCount();
1545 if (idx
>= 0 && idx
< count
)
1547 for (i
= idx
+ 1; i
< count
; ++i
)
1549 if (m_items
[i
].kind
!= wxITEM_RADIO
)
1551 m_items
[i
].state
&= ~wxAUI_BUTTON_STATE_CHECKED
;
1553 for (i
= idx
- 1; i
>= 0; i
--)
1555 if (m_items
[i
].kind
!= wxITEM_RADIO
)
1557 m_items
[i
].state
&= ~wxAUI_BUTTON_STATE_CHECKED
;
1561 tool
->state
|= wxAUI_BUTTON_STATE_CHECKED
;
1563 else if (tool
->kind
== wxITEM_CHECK
)
1566 tool
->state
|= wxAUI_BUTTON_STATE_CHECKED
;
1568 tool
->state
&= ~wxAUI_BUTTON_STATE_CHECKED
;
1573 bool wxAuiToolBar::GetToolToggled(int tool_id
) const
1575 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1579 if ( (tool
->kind
!= wxITEM_CHECK
) && (tool
->kind
!= wxITEM_RADIO
) )
1582 return (tool
->state
& wxAUI_BUTTON_STATE_CHECKED
) ? true : false;
1588 void wxAuiToolBar::EnableTool(int tool_id
, bool state
)
1590 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1595 tool
->state
&= ~wxAUI_BUTTON_STATE_DISABLED
;
1597 tool
->state
|= wxAUI_BUTTON_STATE_DISABLED
;
1601 bool wxAuiToolBar::GetToolEnabled(int tool_id
) const
1603 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1606 return (tool
->state
& wxAUI_BUTTON_STATE_DISABLED
) ? false : true;
1611 wxString
wxAuiToolBar::GetToolLabel(int tool_id
) const
1613 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1614 wxASSERT_MSG(tool
, wxT("can't find tool in toolbar item array"));
1616 return wxEmptyString
;
1621 void wxAuiToolBar::SetToolLabel(int tool_id
, const wxString
& label
)
1623 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1626 tool
->label
= label
;
1630 wxBitmap
wxAuiToolBar::GetToolBitmap(int tool_id
) const
1632 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1633 wxASSERT_MSG(tool
, wxT("can't find tool in toolbar item array"));
1635 return wxNullBitmap
;
1637 return tool
->bitmap
;
1640 void wxAuiToolBar::SetToolBitmap(int tool_id
, const wxBitmap
& bitmap
)
1642 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1645 tool
->bitmap
= bitmap
;
1649 wxString
wxAuiToolBar::GetToolShortHelp(int tool_id
) const
1651 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1652 wxASSERT_MSG(tool
, wxT("can't find tool in toolbar item array"));
1654 return wxEmptyString
;
1656 return tool
->short_help
;
1659 void wxAuiToolBar::SetToolShortHelp(int tool_id
, const wxString
& help_string
)
1661 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1664 tool
->short_help
= help_string
;
1668 wxString
wxAuiToolBar::GetToolLongHelp(int tool_id
) const
1670 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1671 wxASSERT_MSG(tool
, wxT("can't find tool in toolbar item array"));
1673 return wxEmptyString
;
1675 return tool
->long_help
;
1678 void wxAuiToolBar::SetToolLongHelp(int tool_id
, const wxString
& help_string
)
1680 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1683 tool
->long_help
= help_string
;
1687 void wxAuiToolBar::SetCustomOverflowItems(const wxAuiToolBarItemArray
& prepend
,
1688 const wxAuiToolBarItemArray
& append
)
1690 m_custom_overflow_prepend
= prepend
;
1691 m_custom_overflow_append
= append
;
1694 // get size of hint rectangle for a particular dock location
1695 wxSize
wxAuiToolBar::GetHintSize(int dock_direction
) const
1697 switch (dock_direction
)
1699 case wxAUI_DOCK_TOP
:
1700 case wxAUI_DOCK_BOTTOM
:
1701 return m_horzHintSize
;
1702 case wxAUI_DOCK_RIGHT
:
1703 case wxAUI_DOCK_LEFT
:
1704 return m_vertHintSize
;
1706 wxCHECK_MSG(false, wxDefaultSize
, "invalid dock location value");
1710 bool wxAuiToolBar::IsPaneValid(const wxAuiPaneInfo
& pane
) const
1712 return IsPaneValid(m_style
, pane
);
1715 bool wxAuiToolBar::IsPaneValid(long style
, const wxAuiPaneInfo
& pane
)
1717 if (style
& wxAUI_TB_HORIZONTAL
)
1719 if (pane
.IsLeftDockable() || pane
.IsRightDockable())
1724 else if (style
& wxAUI_TB_VERTICAL
)
1726 if (pane
.IsTopDockable() || pane
.IsBottomDockable())
1734 bool wxAuiToolBar::IsPaneValid(long style
) const
1736 wxAuiManager
* manager
= wxAuiManager::GetManager(const_cast<wxAuiToolBar
*>(this));
1739 return IsPaneValid(style
, manager
->GetPane(const_cast<wxAuiToolBar
*>(this)));
1744 void wxAuiToolBar::SetArtFlags() const
1746 unsigned int artflags
= m_style
& ~wxAUI_ORIENTATION_MASK
;
1747 if (m_orientation
== wxVERTICAL
)
1749 artflags
|= wxAUI_TB_VERTICAL
;
1751 m_art
->SetFlags(artflags
);
1754 size_t wxAuiToolBar::GetToolCount() const
1756 return m_items
.size();
1759 int wxAuiToolBar::GetToolIndex(int tool_id
) const
1761 // this will prevent us from returning the index of the
1762 // first separator in the toolbar since its id is equal to -1
1766 size_t i
, count
= m_items
.GetCount();
1767 for (i
= 0; i
< count
; ++i
)
1769 wxAuiToolBarItem
& item
= m_items
.Item(i
);
1770 if (item
.toolid
== tool_id
)
1777 bool wxAuiToolBar::GetToolFitsByIndex(int tool_idx
) const
1779 if (tool_idx
< 0 || tool_idx
>= (int)m_items
.GetCount())
1782 if (!m_items
[tool_idx
].sizer_item
)
1786 GetClientSize(&cli_w
, &cli_h
);
1788 wxRect rect
= m_items
[tool_idx
].sizer_item
->GetRect();
1790 if (m_orientation
== wxVERTICAL
)
1792 // take the dropdown size into account
1793 if (m_overflow_visible
)
1794 cli_h
-= m_overflow_sizer_item
->GetSize().y
;
1796 if (rect
.y
+rect
.height
< cli_h
)
1801 // take the dropdown size into account
1802 if (m_overflow_visible
)
1803 cli_w
-= m_overflow_sizer_item
->GetSize().x
;
1805 if (rect
.x
+rect
.width
< cli_w
)
1813 bool wxAuiToolBar::GetToolFits(int tool_id
) const
1815 return GetToolFitsByIndex(GetToolIndex(tool_id
));
1818 wxRect
wxAuiToolBar::GetToolRect(int tool_id
) const
1820 wxAuiToolBarItem
* tool
= FindTool(tool_id
);
1821 if (tool
&& tool
->sizer_item
)
1823 return tool
->sizer_item
->GetRect();
1829 bool wxAuiToolBar::GetToolBarFits() const
1831 if (m_items
.GetCount() == 0)
1833 // empty toolbar always 'fits'
1837 // entire toolbar content fits if the last tool fits
1838 return GetToolFitsByIndex(m_items
.GetCount() - 1);
1841 bool wxAuiToolBar::Realize()
1843 wxClientDC
dc(this);
1847 // calculate hint sizes for both horizontal and vertical
1848 // in the order that leaves toolbar in correct final state
1849 bool retval
= false;
1850 if (m_orientation
== wxHORIZONTAL
)
1852 if (RealizeHelper(dc
, false))
1854 m_vertHintSize
= GetSize();
1855 if (RealizeHelper(dc
, true))
1857 m_horzHintSize
= GetSize();
1864 if (RealizeHelper(dc
, true))
1866 m_horzHintSize
= GetSize();
1867 if (RealizeHelper(dc
, false))
1869 m_vertHintSize
= GetSize();
1879 bool wxAuiToolBar::RealizeHelper(wxClientDC
& dc
, bool horizontal
)
1881 // create the new sizer to add toolbar elements to
1882 wxBoxSizer
* sizer
= new wxBoxSizer(horizontal
? wxHORIZONTAL
: wxVERTICAL
);
1885 int separator_size
= m_art
->GetElementSize(wxAUI_TBART_SEPARATOR_SIZE
);
1886 int gripper_size
= m_art
->GetElementSize(wxAUI_TBART_GRIPPER_SIZE
);
1887 if (gripper_size
> 0 && m_gripper_visible
)
1890 m_gripper_sizer_item
= sizer
->Add(gripper_size
, 1, 0, wxEXPAND
);
1892 m_gripper_sizer_item
= sizer
->Add(1, gripper_size
, 0, wxEXPAND
);
1896 m_gripper_sizer_item
= NULL
;
1899 // add "left" padding
1900 if (m_left_padding
> 0)
1903 sizer
->Add(m_left_padding
, 1);
1905 sizer
->Add(1, m_left_padding
);
1909 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
1911 wxAuiToolBarItem
& item
= m_items
.Item(i
);
1912 wxSizerItem
* sizer_item
= NULL
;
1918 wxSize size
= m_art
->GetLabelSize(dc
, this, item
);
1919 sizer_item
= sizer
->Add(size
.x
+ (m_tool_border_padding
*2),
1920 size
.y
+ (m_tool_border_padding
*2),
1925 sizer
->AddSpacer(m_tool_packing
);
1935 wxSize size
= m_art
->GetToolSize(dc
, this, item
);
1936 sizer_item
= sizer
->Add(size
.x
+ (m_tool_border_padding
*2),
1937 size
.y
+ (m_tool_border_padding
*2),
1943 sizer
->AddSpacer(m_tool_packing
);
1949 case wxITEM_SEPARATOR
:
1952 sizer_item
= sizer
->Add(separator_size
, 1, 0, wxEXPAND
);
1954 sizer_item
= sizer
->Add(1, separator_size
, 0, wxEXPAND
);
1959 sizer
->AddSpacer(m_tool_packing
);
1966 if (item
.proportion
> 0)
1967 sizer_item
= sizer
->AddStretchSpacer(item
.proportion
);
1969 sizer_item
= sizer
->Add(item
.spacer_pixels
, 1);
1972 case wxITEM_CONTROL
:
1974 //sizer_item = sizer->Add(item.window, item.proportion, wxEXPAND);
1975 wxSizerItem
* ctrl_sizer_item
;
1977 wxBoxSizer
* vert_sizer
= new wxBoxSizer(wxVERTICAL
);
1978 vert_sizer
->AddStretchSpacer(1);
1979 ctrl_sizer_item
= vert_sizer
->Add(item
.window
, 0, wxEXPAND
);
1980 vert_sizer
->AddStretchSpacer(1);
1981 if ( (m_style
& wxAUI_TB_TEXT
) &&
1982 m_tool_text_orientation
== wxAUI_TBTOOL_TEXT_BOTTOM
&&
1983 !item
.GetLabel().empty() )
1985 wxSize s
= GetLabelSize(item
.GetLabel());
1986 vert_sizer
->Add(1, s
.y
);
1990 sizer_item
= sizer
->Add(vert_sizer
, item
.proportion
, wxEXPAND
);
1992 wxSize min_size
= item
.min_size
;
1995 // proportional items will disappear from the toolbar if
1996 // their min width is not set to something really small
1997 if (item
.proportion
!= 0)
2002 if (min_size
.IsFullySpecified())
2004 sizer_item
->SetMinSize(min_size
);
2005 ctrl_sizer_item
->SetMinSize(min_size
);
2011 sizer
->AddSpacer(m_tool_packing
);
2016 item
.sizer_item
= sizer_item
;
2019 // add "right" padding
2020 if (m_right_padding
> 0)
2023 sizer
->Add(m_right_padding
, 1);
2025 sizer
->Add(1, m_right_padding
);
2028 // add drop down area
2029 m_overflow_sizer_item
= NULL
;
2031 if (m_style
& wxAUI_TB_OVERFLOW
)
2033 int overflow_size
= m_art
->GetElementSize(wxAUI_TBART_OVERFLOW_SIZE
);
2034 if (overflow_size
> 0 && m_overflow_visible
)
2037 m_overflow_sizer_item
= sizer
->Add(overflow_size
, 1, 0, wxEXPAND
);
2039 m_overflow_sizer_item
= sizer
->Add(1, overflow_size
, 0, wxEXPAND
);
2043 m_overflow_sizer_item
= NULL
;
2048 // the outside sizer helps us apply the "top" and "bottom" padding
2049 wxBoxSizer
* outside_sizer
= new wxBoxSizer(horizontal
? wxVERTICAL
: wxHORIZONTAL
);
2051 // add "top" padding
2052 if (m_top_padding
> 0)
2055 outside_sizer
->Add(1, m_top_padding
);
2057 outside_sizer
->Add(m_top_padding
, 1);
2060 // add the sizer that contains all of the toolbar elements
2061 outside_sizer
->Add(sizer
, 1, wxEXPAND
);
2063 // add "bottom" padding
2064 if (m_bottom_padding
> 0)
2067 outside_sizer
->Add(1, m_bottom_padding
);
2069 outside_sizer
->Add(m_bottom_padding
, 1);
2072 delete m_sizer
; // remove old sizer
2073 m_sizer
= outside_sizer
;
2075 // calculate the rock-bottom minimum size
2076 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
2078 wxAuiToolBarItem
& item
= m_items
.Item(i
);
2079 if (item
.sizer_item
&& item
.proportion
> 0 && item
.min_size
.IsFullySpecified())
2080 item
.sizer_item
->SetMinSize(0,0);
2083 m_absolute_min_size
= m_sizer
->GetMinSize();
2085 // reset the min sizes to what they were
2086 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
2088 wxAuiToolBarItem
& item
= m_items
.Item(i
);
2089 if (item
.sizer_item
&& item
.proportion
> 0 && item
.min_size
.IsFullySpecified())
2090 item
.sizer_item
->SetMinSize(item
.min_size
);
2094 wxSize size
= m_sizer
->GetMinSize();
2095 m_minWidth
= size
.x
;
2096 m_minHeight
= size
.y
;
2098 if ((m_style
& wxAUI_TB_NO_AUTORESIZE
) == 0)
2100 wxSize cur_size
= GetClientSize();
2101 wxSize new_size
= GetMinSize();
2102 if (new_size
!= cur_size
)
2104 SetClientSize(new_size
);
2108 m_sizer
->SetDimension(0, 0, cur_size
.x
, cur_size
.y
);
2113 wxSize cur_size
= GetClientSize();
2114 m_sizer
->SetDimension(0, 0, cur_size
.x
, cur_size
.y
);
2120 int wxAuiToolBar::GetOverflowState() const
2122 return m_overflow_state
;
2125 wxRect
wxAuiToolBar::GetOverflowRect() const
2127 wxRect
cli_rect(wxPoint(0,0), GetClientSize());
2128 wxRect overflow_rect
= m_overflow_sizer_item
->GetRect();
2129 int overflow_size
= m_art
->GetElementSize(wxAUI_TBART_OVERFLOW_SIZE
);
2131 if (m_orientation
== wxVERTICAL
)
2133 overflow_rect
.y
= cli_rect
.height
- overflow_size
;
2134 overflow_rect
.x
= 0;
2135 overflow_rect
.width
= cli_rect
.width
;
2136 overflow_rect
.height
= overflow_size
;
2140 overflow_rect
.x
= cli_rect
.width
- overflow_size
;
2141 overflow_rect
.y
= 0;
2142 overflow_rect
.width
= overflow_size
;
2143 overflow_rect
.height
= cli_rect
.height
;
2146 return overflow_rect
;
2149 wxSize
wxAuiToolBar::GetLabelSize(const wxString
& label
)
2151 wxClientDC
dc(this);
2154 int text_width
= 0, text_height
= 0;
2158 // get the text height
2159 dc
.GetTextExtent(wxT("ABCDHgj"), &tx
, &text_height
);
2161 // get the text width
2162 dc
.GetTextExtent(label
, &text_width
, &ty
);
2164 return wxSize(text_width
, text_height
);
2168 void wxAuiToolBar::DoIdleUpdate()
2170 wxEvtHandler
* handler
= GetEventHandler();
2172 bool need_refresh
= false;
2175 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
2177 wxAuiToolBarItem
& item
= m_items
.Item(i
);
2179 if (item
.toolid
== -1)
2182 wxUpdateUIEvent
evt(item
.toolid
);
2183 evt
.SetEventObject(this);
2185 if (handler
->ProcessEvent(evt
))
2187 if (evt
.GetSetEnabled())
2191 is_enabled
= item
.window
->IsEnabled();
2193 is_enabled
= (item
.state
& wxAUI_BUTTON_STATE_DISABLED
) ? false : true;
2195 bool new_enabled
= evt
.GetEnabled();
2196 if (new_enabled
!= is_enabled
)
2200 item
.window
->Enable(new_enabled
);
2205 item
.state
&= ~wxAUI_BUTTON_STATE_DISABLED
;
2207 item
.state
|= wxAUI_BUTTON_STATE_DISABLED
;
2209 need_refresh
= true;
2213 if (evt
.GetSetChecked())
2215 // make sure we aren't checking an item that can't be
2216 if (item
.kind
!= wxITEM_CHECK
&& item
.kind
!= wxITEM_RADIO
)
2219 bool is_checked
= (item
.state
& wxAUI_BUTTON_STATE_CHECKED
) ? true : false;
2220 bool new_checked
= evt
.GetChecked();
2222 if (new_checked
!= is_checked
)
2225 item
.state
|= wxAUI_BUTTON_STATE_CHECKED
;
2227 item
.state
&= ~wxAUI_BUTTON_STATE_CHECKED
;
2229 need_refresh
= true;
2244 void wxAuiToolBar::OnSize(wxSizeEvent
& WXUNUSED(evt
))
2247 GetClientSize(&x
, &y
);
2249 if (((x
>= y
) && m_absolute_min_size
.x
> x
) ||
2250 ((y
> x
) && m_absolute_min_size
.y
> y
))
2252 // hide all flexible items
2254 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
2256 wxAuiToolBarItem
& item
= m_items
.Item(i
);
2257 if (item
.sizer_item
&& item
.proportion
> 0 && item
.sizer_item
->IsShown())
2259 item
.sizer_item
->Show(false);
2260 item
.sizer_item
->SetProportion(0);
2266 // show all flexible items
2268 for (i
= 0, count
= m_items
.GetCount(); i
< count
; ++i
)
2270 wxAuiToolBarItem
& item
= m_items
.Item(i
);
2271 if (item
.sizer_item
&& item
.proportion
> 0 && !item
.sizer_item
->IsShown())
2273 item
.sizer_item
->Show(true);
2274 item
.sizer_item
->SetProportion(item
.proportion
);
2279 m_sizer
->SetDimension(0, 0, x
, y
);
2284 // idle events aren't sent while user is resizing frame (why?),
2285 // but resizing toolbar here causes havoc,
2286 // so force idle handler to run after size handling complete
2287 QueueEvent(new wxIdleEvent
);
2292 void wxAuiToolBar::DoSetSize(int x
,
2298 wxSize parent_size
= GetParent()->GetClientSize();
2299 if (x
+ width
> parent_size
.x
)
2300 width
= wxMax(0, parent_size
.x
- x
);
2301 if (y
+ height
> parent_size
.y
)
2302 height
= wxMax(0, parent_size
.y
- y
);
2304 wxWindow::DoSetSize(x
, y
, width
, height
, sizeFlags
);
2308 void wxAuiToolBar::OnIdle(wxIdleEvent
& evt
)
2310 // if orientation doesn't match dock, fix it
2311 wxAuiManager
* manager
= wxAuiManager::GetManager(this);
2314 wxAuiPaneInfo
& pane
= manager
->GetPane(this);
2315 // pane state member is public, so it might have been changed
2316 // without going through wxPaneInfo::SetFlag() check
2317 bool ok
= pane
.IsOk();
2318 wxCHECK2_MSG(!ok
|| IsPaneValid(m_style
, pane
), ok
= false,
2319 "window settings and pane settings are incompatible");
2322 wxOrientation newOrientation
= m_orientation
;
2323 if (pane
.IsDocked())
2325 switch (pane
.dock_direction
)
2327 case wxAUI_DOCK_TOP
:
2328 case wxAUI_DOCK_BOTTOM
:
2329 newOrientation
= wxHORIZONTAL
;
2331 case wxAUI_DOCK_LEFT
:
2332 case wxAUI_DOCK_RIGHT
:
2333 newOrientation
= wxVERTICAL
;
2336 wxFAIL_MSG("invalid dock location value");
2339 else if (pane
.IsResizable() &&
2340 GetOrientation(m_style
) == wxBOTH
)
2342 // changing orientation in OnSize causes havoc
2344 GetClientSize(&x
, &y
);
2348 newOrientation
= wxHORIZONTAL
;
2352 newOrientation
= wxVERTICAL
;
2355 if (newOrientation
!= m_orientation
)
2357 SetOrientation(newOrientation
);
2359 if (newOrientation
== wxHORIZONTAL
)
2361 pane
.best_size
= GetHintSize(wxAUI_DOCK_TOP
);
2365 pane
.best_size
= GetHintSize(wxAUI_DOCK_LEFT
);
2367 if (pane
.IsDocked())
2369 pane
.floating_size
= wxDefaultSize
;
2373 SetSize(GetParent()->GetClientSize());
2384 void wxAuiToolBar::OnPaint(wxPaintEvent
& WXUNUSED(evt
))
2386 wxAutoBufferedPaintDC
dc(this);
2387 wxRect
cli_rect(wxPoint(0,0), GetClientSize());
2390 bool horizontal
= m_orientation
== wxHORIZONTAL
;
2393 m_art
->DrawBackground(dc
, this, cli_rect
);
2395 int gripper_size
= m_art
->GetElementSize(wxAUI_TBART_GRIPPER_SIZE
);
2396 int dropdown_size
= m_art
->GetElementSize(wxAUI_TBART_OVERFLOW_SIZE
);
2398 // paint the gripper
2399 if (gripper_size
> 0 && m_gripper_sizer_item
)
2401 wxRect gripper_rect
= m_gripper_sizer_item
->GetRect();
2403 gripper_rect
.width
= gripper_size
;
2405 gripper_rect
.height
= gripper_size
;
2406 m_art
->DrawGripper(dc
, this, gripper_rect
);
2409 // calculated how far we can draw items
2412 last_extent
= cli_rect
.width
;
2414 last_extent
= cli_rect
.height
;
2415 if (m_overflow_visible
)
2416 last_extent
-= dropdown_size
;
2418 // paint each individual tool
2419 size_t i
, count
= m_items
.GetCount();
2420 for (i
= 0; i
< count
; ++i
)
2422 wxAuiToolBarItem
& item
= m_items
.Item(i
);
2424 if (!item
.sizer_item
)
2427 wxRect item_rect
= item
.sizer_item
->GetRect();
2430 if ((horizontal
&& item_rect
.x
+ item_rect
.width
>= last_extent
) ||
2431 (!horizontal
&& item_rect
.y
+ item_rect
.height
>= last_extent
))
2436 if (item
.kind
== wxITEM_SEPARATOR
)
2439 m_art
->DrawSeparator(dc
, this, item_rect
);
2441 else if (item
.kind
== wxITEM_LABEL
)
2443 // draw a text label only
2444 m_art
->DrawLabel(dc
, this, item
, item_rect
);
2446 else if (item
.kind
== wxITEM_NORMAL
)
2448 // draw a regular button or dropdown button
2450 m_art
->DrawButton(dc
, this, item
, item_rect
);
2452 m_art
->DrawDropDownButton(dc
, this, item
, item_rect
);
2454 else if (item
.kind
== wxITEM_CHECK
)
2456 // draw either a regular or dropdown toggle button
2458 m_art
->DrawButton(dc
, this, item
, item_rect
);
2460 m_art
->DrawDropDownButton(dc
, this, item
, item_rect
);
2462 else if (item
.kind
== wxITEM_RADIO
)
2464 // draw a toggle button
2465 m_art
->DrawButton(dc
, this, item
, item_rect
);
2467 else if (item
.kind
== wxITEM_CONTROL
)
2469 // draw the control's label
2470 m_art
->DrawControlLabel(dc
, this, item
, item_rect
);
2473 // fire a signal to see if the item wants to be custom-rendered
2474 OnCustomRender(dc
, item
, item_rect
);
2477 // paint the overflow button
2478 if (dropdown_size
> 0 && m_overflow_sizer_item
)
2480 wxRect dropdown_rect
= GetOverflowRect();
2481 m_art
->DrawOverflowButton(dc
, this, dropdown_rect
, m_overflow_state
);
2485 void wxAuiToolBar::OnEraseBackground(wxEraseEvent
& WXUNUSED(evt
))
2490 void wxAuiToolBar::OnLeftDown(wxMouseEvent
& evt
)
2492 wxRect
cli_rect(wxPoint(0,0), GetClientSize());
2494 if (m_gripper_sizer_item
)
2496 wxRect gripper_rect
= m_gripper_sizer_item
->GetRect();
2497 if (gripper_rect
.Contains(evt
.GetX(), evt
.GetY()))
2500 wxAuiManager
* manager
= wxAuiManager::GetManager(this);
2504 int x_drag_offset
= evt
.GetX() - gripper_rect
.GetX();
2505 int y_drag_offset
= evt
.GetY() - gripper_rect
.GetY();
2507 // gripper was clicked
2508 manager
->StartPaneDrag(this, wxPoint(x_drag_offset
, y_drag_offset
));
2513 if (m_overflow_sizer_item
)
2515 wxRect overflow_rect
= GetOverflowRect();
2518 m_overflow_visible
&&
2519 overflow_rect
.Contains(evt
.m_x
, evt
.m_y
))
2521 wxAuiToolBarEvent
e(wxEVT_COMMAND_AUITOOLBAR_OVERFLOW_CLICK
, -1);
2522 e
.SetEventObject(this);
2524 e
.SetClickPoint(wxPoint(evt
.GetX(), evt
.GetY()));
2525 bool processed
= GetEventHandler()->ProcessEvent(e
);
2534 wxAuiToolBarItemArray overflow_items
;
2537 // add custom overflow prepend items, if any
2538 count
= m_custom_overflow_prepend
.GetCount();
2539 for (i
= 0; i
< count
; ++i
)
2540 overflow_items
.Add(m_custom_overflow_prepend
[i
]);
2542 // only show items that don't fit in the dropdown
2543 count
= m_items
.GetCount();
2544 for (i
= 0; i
< count
; ++i
)
2546 if (!GetToolFitsByIndex(i
))
2547 overflow_items
.Add(m_items
[i
]);
2550 // add custom overflow append items, if any
2551 count
= m_custom_overflow_append
.GetCount();
2552 for (i
= 0; i
< count
; ++i
)
2553 overflow_items
.Add(m_custom_overflow_append
[i
]);
2555 int res
= m_art
->ShowDropDown(this, overflow_items
);
2556 m_overflow_state
= 0;
2560 wxCommandEvent
e(wxEVT_COMMAND_MENU_SELECTED
, res
);
2561 e
.SetEventObject(this);
2562 GetParent()->GetEventHandler()->ProcessEvent(e
);
2571 m_action_pos
= wxPoint(evt
.GetX(), evt
.GetY());
2572 m_action_item
= FindToolByPosition(evt
.GetX(), evt
.GetY());
2576 if (m_action_item
->state
& wxAUI_BUTTON_STATE_DISABLED
)
2578 m_action_pos
= wxPoint(-1,-1);
2579 m_action_item
= NULL
;
2585 // fire the tool dropdown event
2586 wxAuiToolBarEvent
e(wxEVT_COMMAND_AUITOOLBAR_TOOL_DROPDOWN
, m_action_item
->toolid
);
2587 e
.SetEventObject(this);
2588 e
.SetToolId(m_action_item
->toolid
);
2590 int mouse_x
= evt
.GetX();
2591 wxRect rect
= m_action_item
->sizer_item
->GetRect();
2592 const bool dropDownHit
= m_action_item
->dropdown
&&
2593 mouse_x
>= (rect
.x
+rect
.width
-BUTTON_DROPDOWN_WIDTH
-1) &&
2594 mouse_x
< (rect
.x
+rect
.width
);
2595 e
.SetDropDownClicked(dropDownHit
);
2597 e
.SetClickPoint(evt
.GetPosition());
2598 e
.SetItemRect(rect
);
2600 // we only set the 'pressed button' state if we hit the actual button
2601 // and not just the drop-down
2602 SetPressedItem(dropDownHit
? 0 : m_action_item
);
2606 m_action_pos
= wxPoint(-1,-1);
2607 m_action_item
= NULL
;
2610 if(!GetEventHandler()->ProcessEvent(e
) || e
.GetSkipped())
2617 void wxAuiToolBar::OnLeftUp(wxMouseEvent
& evt
)
2622 SetPressedItem(NULL
);
2624 wxAuiToolBarItem
* hit_item
= FindToolByPosition(evt
.GetX(), evt
.GetY());
2625 if (hit_item
&& !(hit_item
->state
& wxAUI_BUTTON_STATE_DISABLED
))
2627 SetHoverItem(hit_item
);
2632 // TODO: it would make sense to send out an 'END_DRAG' event here,
2633 // otherwise a client would never know what to do with the 'BEGIN_DRAG'
2636 // OnCaptureLost() will be called now and this will reset all our state
2637 // tracking variables
2642 wxAuiToolBarItem
* hit_item
;
2643 hit_item
= FindToolByPosition(evt
.GetX(), evt
.GetY());
2645 if (m_action_item
&& hit_item
== m_action_item
)
2649 wxCommandEvent
e(wxEVT_COMMAND_MENU_SELECTED
, m_action_item
->toolid
);
2650 e
.SetEventObject(this);
2652 if (hit_item
->kind
== wxITEM_CHECK
|| hit_item
->kind
== wxITEM_RADIO
)
2654 const bool toggle
= !(m_action_item
->state
& wxAUI_BUTTON_STATE_CHECKED
);
2656 ToggleTool(m_action_item
->toolid
, toggle
);
2658 // repaint immediately
2665 // we have to release the mouse *before* sending the event, because
2666 // we don't know what a handler might do. It could open up a popup
2667 // menu for example and that would make us lose our capture anyway.
2671 GetEventHandler()->ProcessEvent(e
);
2679 void wxAuiToolBar::OnRightDown(wxMouseEvent
& evt
)
2681 wxRect
cli_rect(wxPoint(0,0), GetClientSize());
2683 if (m_gripper_sizer_item
)
2685 wxRect gripper_rect
= m_gripper_sizer_item
->GetRect();
2686 if (gripper_rect
.Contains(evt
.GetX(), evt
.GetY()))
2690 if (m_overflow_sizer_item
)
2692 int dropdown_size
= m_art
->GetElementSize(wxAUI_TBART_OVERFLOW_SIZE
);
2693 if (dropdown_size
> 0 &&
2694 evt
.m_x
> cli_rect
.width
- dropdown_size
&&
2696 evt
.m_y
< cli_rect
.height
&&
2703 m_action_pos
= wxPoint(evt
.GetX(), evt
.GetY());
2704 m_action_item
= FindToolByPosition(evt
.GetX(), evt
.GetY());
2706 if (m_action_item
&& m_action_item
->state
& wxAUI_BUTTON_STATE_DISABLED
)
2708 m_action_pos
= wxPoint(-1,-1);
2709 m_action_item
= NULL
;
2716 void wxAuiToolBar::OnRightUp(wxMouseEvent
& evt
)
2718 wxAuiToolBarItem
* hit_item
;
2719 hit_item
= FindToolByPosition(evt
.GetX(), evt
.GetY());
2721 if (m_action_item
&& hit_item
== m_action_item
)
2723 if (hit_item
->kind
== wxITEM_NORMAL
)
2725 wxAuiToolBarEvent
e(wxEVT_COMMAND_AUITOOLBAR_RIGHT_CLICK
, m_action_item
->toolid
);
2726 e
.SetEventObject(this);
2727 e
.SetToolId(m_action_item
->toolid
);
2728 e
.SetClickPoint(m_action_pos
);
2729 GetEventHandler()->ProcessEvent(e
);
2735 // right-clicked on the invalid area of the toolbar
2736 wxAuiToolBarEvent
e(wxEVT_COMMAND_AUITOOLBAR_RIGHT_CLICK
, -1);
2737 e
.SetEventObject(this);
2739 e
.SetClickPoint(m_action_pos
);
2740 GetEventHandler()->ProcessEvent(e
);
2744 // reset member variables
2745 m_action_pos
= wxPoint(-1,-1);
2746 m_action_item
= NULL
;
2749 void wxAuiToolBar::OnMiddleDown(wxMouseEvent
& evt
)
2751 wxRect
cli_rect(wxPoint(0,0), GetClientSize());
2753 if (m_gripper_sizer_item
)
2755 wxRect gripper_rect
= m_gripper_sizer_item
->GetRect();
2756 if (gripper_rect
.Contains(evt
.GetX(), evt
.GetY()))
2760 if (m_overflow_sizer_item
)
2762 int dropdown_size
= m_art
->GetElementSize(wxAUI_TBART_OVERFLOW_SIZE
);
2763 if (dropdown_size
> 0 &&
2764 evt
.m_x
> cli_rect
.width
- dropdown_size
&&
2766 evt
.m_y
< cli_rect
.height
&&
2773 m_action_pos
= wxPoint(evt
.GetX(), evt
.GetY());
2774 m_action_item
= FindToolByPosition(evt
.GetX(), evt
.GetY());
2778 if (m_action_item
->state
& wxAUI_BUTTON_STATE_DISABLED
)
2780 m_action_pos
= wxPoint(-1,-1);
2781 m_action_item
= NULL
;
2789 void wxAuiToolBar::OnMiddleUp(wxMouseEvent
& evt
)
2791 wxAuiToolBarItem
* hit_item
;
2792 hit_item
= FindToolByPosition(evt
.GetX(), evt
.GetY());
2794 if (m_action_item
&& hit_item
== m_action_item
)
2796 if (hit_item
->kind
== wxITEM_NORMAL
)
2798 wxAuiToolBarEvent
e(wxEVT_COMMAND_AUITOOLBAR_MIDDLE_CLICK
, m_action_item
->toolid
);
2799 e
.SetEventObject(this);
2800 e
.SetToolId(m_action_item
->toolid
);
2801 e
.SetClickPoint(m_action_pos
);
2802 GetEventHandler()->ProcessEvent(e
);
2807 // reset member variables
2808 m_action_pos
= wxPoint(-1,-1);
2809 m_action_item
= NULL
;
2812 void wxAuiToolBar::OnMotion(wxMouseEvent
& evt
)
2814 const bool button_pressed
= HasCapture();
2816 // start a drag event
2817 if (!m_dragging
&& button_pressed
&&
2818 abs(evt
.GetX() - m_action_pos
.x
) + abs(evt
.GetY() - m_action_pos
.y
) > 5)
2820 // TODO: sending this event only makes sense if there is an 'END_DRAG'
2821 // event sent sometime in the future (see OnLeftUp())
2822 wxAuiToolBarEvent
e(wxEVT_COMMAND_AUITOOLBAR_BEGIN_DRAG
, GetId());
2823 e
.SetEventObject(this);
2824 e
.SetToolId(m_action_item
->toolid
);
2825 m_dragging
= GetEventHandler()->ProcessEvent(e
) && !e
.GetSkipped();
2833 wxAuiToolBarItem
* hit_item
= FindToolByPosition(evt
.GetX(), evt
.GetY());
2836 // if we have a button pressed we want it to be shown in 'depressed'
2837 // state unless we move the mouse outside the button, then we want it
2838 // to show as just 'highlighted'
2839 if (hit_item
== m_action_item
)
2840 SetPressedItem(m_action_item
);
2843 SetPressedItem(NULL
);
2844 SetHoverItem(m_action_item
);
2849 if (hit_item
&& (hit_item
->state
& wxAUI_BUTTON_STATE_DISABLED
))
2852 SetHoverItem(hit_item
);
2854 // tooltips handling
2855 wxAuiToolBarItem
* packing_hit_item
;
2856 packing_hit_item
= FindToolByPositionWithPacking(evt
.GetX(), evt
.GetY());
2857 if (packing_hit_item
)
2859 if (packing_hit_item
!= m_tip_item
)
2861 m_tip_item
= packing_hit_item
;
2863 if ( !packing_hit_item
->short_help
.empty() )
2864 SetToolTip(packing_hit_item
->short_help
);
2875 // figure out the dropdown button state (are we hovering or pressing it?)
2876 RefreshOverflowState();
2880 void wxAuiToolBar::DoResetMouseState()
2882 RefreshOverflowState();
2884 SetPressedItem(NULL
);
2888 // we have to reset those here, because the mouse-up handlers which do
2889 // it usually won't be called if we let go of a mouse button while we
2890 // are outside of the window
2891 m_action_pos
= wxPoint(-1,-1);
2892 m_action_item
= NULL
;
2895 void wxAuiToolBar::OnLeaveWindow(wxMouseEvent
& evt
)
2903 DoResetMouseState();
2906 void wxAuiToolBar::OnCaptureLost(wxMouseCaptureLostEvent
& WXUNUSED(evt
))
2910 DoResetMouseState();
2913 void wxAuiToolBar::OnSetCursor(wxSetCursorEvent
& evt
)
2915 wxCursor cursor
= wxNullCursor
;
2917 if (m_gripper_sizer_item
)
2919 wxRect gripper_rect
= m_gripper_sizer_item
->GetRect();
2920 if (gripper_rect
.Contains(evt
.GetX(), evt
.GetY()))
2922 cursor
= wxCursor(wxCURSOR_SIZING
);
2926 evt
.SetCursor(cursor
);