]> git.saurik.com Git - wxWidgets.git/blame - src/mac/carbon/toolbar.cpp
guard code for mac / quickdraw
[wxWidgets.git] / src / mac / carbon / toolbar.cpp
CommitLineData
e9576ca5 1/////////////////////////////////////////////////////////////////////////////
3b6a1179 2// Name: src/mac/carbon/toolbar.cpp
e9576ca5 3// Purpose: wxToolBar
a31a5f85 4// Author: Stefan Csomor
e9576ca5
SC
5// Modified by:
6// Created: 04/01/98
7// RCS-ID: $Id$
84969af7 8// Copyright: (c) Stefan Csomor
991f71dc 9// Licence: wxWindows licence
e9576ca5
SC
10/////////////////////////////////////////////////////////////////////////////
11
3d1a4878 12#include "wx/wxprec.h"
519cb848
SC
13
14#if wxUSE_TOOLBAR
15
e56d2520 16#include "wx/toolbar.h"
e9576ca5 17
4e3e485b
WS
18#ifndef WX_PRECOMP
19 #include "wx/wx.h"
20#endif
21
83f787ba 22#include "wx/app.h"
d497dca4 23#include "wx/mac/uma.h"
bfe9ffbc 24#include "wx/geometry.h"
079b2f6b 25#include "wx/sysopt.h"
ee799df7 26
991f71dc 27
3b6a1179
DS
28const short kwxMacToolBarToolDefaultWidth = 16;
29const short kwxMacToolBarToolDefaultHeight = 16;
30const short kwxMacToolBarTopMargin = 4;
31const short kwxMacToolBarLeftMargin = 4;
32const short kwxMacToolBorder = 0;
33const short kwxMacToolSpacing = 6;
ee799df7 34
991f71dc
DS
35
36IMPLEMENT_DYNAMIC_CLASS(wxToolBar, wxControl)
37
38BEGIN_EVENT_TABLE(wxToolBar, wxToolBarBase)
39 EVT_PAINT( wxToolBar::OnPaint )
40END_EVENT_TABLE()
41
42
e56d2520
SC
43#pragma mark -
44#pragma mark Tool Implementation
45
46
37e2cb08
SC
47// ----------------------------------------------------------------------------
48// private classes
49// ----------------------------------------------------------------------------
50
e56d2520
SC
51// We have a dual implementation for each tool, ControlRef and HIToolbarItemRef
52
75c25a82
SC
53// when embedding native controls in the native toolbar we must make sure the
54// control does not get deleted behind our backs, so the retain count gets increased
55// (after creation it is 1), first be the creation of the custom HIToolbarItem wrapper
56// object, and second by the code 'creating' the custom HIView (which is the same as the
57// already existing native control, therefore we just increase the ref count)
58// when this view is removed from the native toolbar its count gets decremented again
59// and when the HITooolbarItem wrapper object gets destroyed it is decremented as well
60// so in the end the control lives with a refcount of one and can be disposed of by the
5cb78ae7
SC
61// wxControl code. For embedded controls on a non-native toolbar this ref count is less
62// so we can only test against a range, not a specific value of the refcount.
75c25a82 63
37e2cb08
SC
64class wxToolBarTool : public wxToolBarToolBase
65{
66public:
3025abca
DS
67 wxToolBarTool(
68 wxToolBar *tbar,
69 int id,
70 const wxString& label,
71 const wxBitmap& bmpNormal,
72 const wxBitmap& bmpDisabled,
73 wxItemKind kind,
74 wxObject *clientData,
75 const wxString& shortHelp,
76 const wxString& longHelp );
f3a65c3e 77
cdb11cb9
VZ
78 wxToolBarTool(wxToolBar *tbar, wxControl *control, const wxString& label)
79 : wxToolBarToolBase(tbar, control, label)
37e2cb08 80 {
3b6a1179 81 Init();
e56d2520 82 if (control != NULL)
3b6a1179 83 SetControlHandle( (ControlRef) control->GetHandle() );
37e2cb08 84 }
f3a65c3e 85
d3c7fc99 86 virtual ~wxToolBarTool()
bfe9ffbc 87 {
3b6a1179 88 ClearControl();
bfe9ffbc 89 }
f3a65c3e
VZ
90
91 WXWidget GetControlHandle()
92 {
3b6a1179 93 return (WXWidget) m_controlHandle;
e56d2520 94 }
f3a65c3e
VZ
95
96 void SetControlHandle( ControlRef handle )
97 {
3b6a1179 98 m_controlHandle = handle;
e56d2520 99 }
37e2cb08 100
3b6a1179 101 void SetPosition( const wxPoint& position );
f3a65c3e
VZ
102
103 void ClearControl()
104 {
8c07d8b3
SC
105 if ( m_controlHandle )
106 {
9d5ccdd3
SC
107 if ( !IsControl() )
108 DisposeControl( m_controlHandle );
109 else
110 {
75c25a82
SC
111 // the embedded control is not under the responsibility of the tool, it will be disposed of in the
112 // proper wxControl destructor
113 wxASSERT( IsValidControlHandle(GetControl()->GetPeer()->GetControlRef() )) ;
9d5ccdd3 114 }
8c07d8b3
SC
115 m_controlHandle = NULL ;
116 }
75c25a82 117 m_control = NULL;
991f71dc 118
e56d2520 119#if wxMAC_USE_NATIVE_TOOLBAR
507d5748
SC
120 if ( m_toolbarItemRef )
121 {
122 CFIndex count = CFGetRetainCount( m_toolbarItemRef ) ;
6239ee05
SC
123 // different behaviour under Leopard
124 if ( UMAGetSystemVersion() < 0x1050 )
125 {
126 wxASSERT_MSG( count == 1 , wxT("Reference Count of native tool was not 1 in wxToolBarTool destructor") );
127 }
83f787ba
SC
128 wxTheApp->MacAddToAutorelease(m_toolbarItemRef);
129 CFRelease(m_toolbarItemRef);
507d5748
SC
130 m_toolbarItemRef = NULL;
131 }
f3a65c3e 132#endif
e56d2520 133 }
f3a65c3e 134
bfe9ffbc
SC
135 wxSize GetSize() const
136 {
3025abca
DS
137 wxSize curSize;
138
bfe9ffbc
SC
139 if ( IsControl() )
140 {
3025abca 141 curSize = GetControl()->GetSize();
bfe9ffbc
SC
142 }
143 else if ( IsButton() )
144 {
3025abca 145 curSize = GetToolBar()->GetToolSize();
bfe9ffbc
SC
146 }
147 else
148 {
abbcdf3f 149 // separator size
3025abca 150 curSize = GetToolBar()->GetToolSize();
5a904a32 151 if ( GetToolBar()->GetWindowStyleFlag() & wxTB_VERTICAL )
3025abca 152 curSize.y /= 4;
5a904a32 153 else
3025abca 154 curSize.x /= 4;
bfe9ffbc 155 }
3025abca
DS
156
157 return curSize;
bfe9ffbc 158 }
991f71dc 159
bfe9ffbc
SC
160 wxPoint GetPosition() const
161 {
3b6a1179 162 return wxPoint( m_x, m_y );
f3a65c3e 163 }
991f71dc 164
3b6a1179 165 bool DoEnable( bool enable );
f3a65c3e 166
3b6a1179 167 void UpdateToggleImage( bool toggle );
f3a65c3e
VZ
168
169#if wxMAC_USE_NATIVE_TOOLBAR
170 void SetToolbarItemRef( HIToolbarItemRef ref )
171 {
e56d2520 172 if ( m_controlHandle )
3b6a1179 173 HideControl( m_controlHandle );
e56d2520 174 if ( m_toolbarItemRef )
3b6a1179 175 CFRelease( m_toolbarItemRef );
991f71dc 176
3b6a1179 177 m_toolbarItemRef = ref;
e56d2520
SC
178 if ( m_toolbarItemRef )
179 {
bbd321ff
RD
180 wxFont f;
181 wxFontEncoding enc;
182 if ( GetToolBar() )
183 f = GetToolBar()->GetFont();
184 if ( f.IsOk() )
185 enc = f.GetEncoding();
186 else
187 enc = wxFont::GetDefaultEncoding();
cdb11cb9 188
e56d2520 189 HIToolbarItemSetHelpText(
991f71dc 190 m_toolbarItemRef,
bbd321ff
RD
191 wxMacCFStringHolder( GetShortHelp(), enc ),
192 wxMacCFStringHolder( GetLongHelp(), enc ) );
e56d2520
SC
193 }
194 }
991f71dc 195
f3a65c3e
VZ
196 HIToolbarItemRef GetToolbarItemRef() const
197 {
3b6a1179 198 return m_toolbarItemRef;
e56d2520 199 }
df7998fc
VZ
200
201 void SetIndex( CFIndex idx )
2c1dbc95 202 {
3b6a1179 203 m_index = idx;
2c1dbc95
SC
204 }
205
df7998fc 206 CFIndex GetIndex() const
2c1dbc95 207 {
3b6a1179 208 return m_index;
2c1dbc95 209 }
e56d2520 210#endif
5d0bf05a 211
3b6a1179 212private:
f3a65c3e 213 void Init()
bfe9ffbc 214 {
3b6a1179 215 m_controlHandle = NULL;
991f71dc 216
e56d2520 217#if wxMAC_USE_NATIVE_TOOLBAR
3b6a1179
DS
218 m_toolbarItemRef = NULL;
219 m_index = -1;
e56d2520 220#endif
bfe9ffbc 221 }
991f71dc 222
3b6a1179 223 ControlRef m_controlHandle;
991f71dc
DS
224 wxCoord m_x;
225 wxCoord m_y;
226
e56d2520 227#if wxMAC_USE_NATIVE_TOOLBAR
3b6a1179 228 HIToolbarItemRef m_toolbarItemRef;
2c1dbc95 229 // position in its toolbar, -1 means not inserted
3b6a1179 230 CFIndex m_index;
e56d2520 231#endif
37e2cb08
SC
232};
233
facd6764
SC
234static const EventTypeSpec eventList[] =
235{
3b6a1179 236 { kEventClassControl, kEventControlHit },
3b6a1179 237 { kEventClassControl, kEventControlHitTest },
3b6a1179 238};
facd6764 239
89954433 240static pascal OSStatus wxMacToolBarToolControlEventHandler( EventHandlerCallRef WXUNUSED(handler), EventRef event, void *data )
facd6764 241{
3b6a1179
DS
242 OSStatus result = eventNotHandledErr;
243 ControlRef controlRef;
244 wxMacCarbonEvent cEvent( event );
facd6764 245
3b6a1179 246 cEvent.GetParameter( kEventParamDirectObject, &controlRef );
facd6764 247
991f71dc 248 switch ( GetEventKind( event ) )
facd6764 249 {
3b6a1179 250 case kEventControlHit:
facd6764 251 {
3b6a1179
DS
252 wxToolBarTool *tbartool = (wxToolBarTool*)data;
253 wxToolBar *tbar = tbartool != NULL ? (wxToolBar*) (tbartool->GetToolBar()) : NULL;
991f71dc 254 if ((tbartool != NULL) && tbartool->CanBeToggled())
facd6764 255 {
e56d2520 256 bool shouldToggle;
991f71dc 257
e56d2520 258 shouldToggle = !tbartool->IsToggled();
991f71dc 259
e56d2520 260 tbar->ToggleTool( tbartool->GetId(), shouldToggle );
facd6764 261 }
991f71dc 262
e56d2520
SC
263 if (tbartool != NULL)
264 tbar->OnLeftClick( tbartool->GetId(), tbartool->IsToggled() );
f3a65c3e 265 result = noErr;
facd6764 266 }
3b6a1179 267 break;
5d0bf05a 268
3b6a1179 269 case kEventControlHitTest:
73fd9428 270 {
3b6a1179
DS
271 HIPoint pt = cEvent.GetParameter<HIPoint>(kEventParamMouseLocation);
272 HIRect rect;
273 HIViewGetBounds( controlRef, &rect );
274
275 ControlPartCode pc = kControlNoPart;
276 if ( CGRectContainsPoint( rect, pt ) )
277 pc = kControlIconPart;
278 cEvent.SetParameter( kEventParamControlPart, typeControlPartCode, pc );
279 result = noErr;
73fd9428 280 }
3b6a1179 281 break;
5d0bf05a 282
3b6a1179
DS
283 default:
284 break;
facd6764 285 }
991f71dc 286
3b6a1179 287 return result;
facd6764
SC
288}
289
3b6a1179 290static pascal OSStatus wxMacToolBarToolEventHandler( EventHandlerCallRef handler, EventRef event, void *data )
facd6764 291{
3b6a1179 292 OSStatus result = eventNotHandledErr;
facd6764
SC
293
294 switch ( GetEventClass( event ) )
295 {
3b6a1179
DS
296 case kEventClassControl:
297 result = wxMacToolBarToolControlEventHandler( handler, event, data );
298 break;
5d0bf05a 299
3b6a1179
DS
300 default:
301 break;
facd6764 302 }
991f71dc 303
3b6a1179 304 return result;
facd6764
SC
305}
306
307DEFINE_ONE_SHOT_HANDLER_GETTER( wxMacToolBarToolEventHandler )
308
e56d2520
SC
309#if wxMAC_USE_NATIVE_TOOLBAR
310
e56d2520
SC
311static const EventTypeSpec toolBarEventList[] =
312{
3b6a1179
DS
313 { kEventClassToolbarItem, kEventToolbarItemPerformAction },
314};
e56d2520 315
89954433 316static pascal OSStatus wxMacToolBarCommandEventHandler( EventHandlerCallRef WXUNUSED(handler), EventRef event, void *data )
e56d2520 317{
3b6a1179 318 OSStatus result = eventNotHandledErr;
f3a65c3e 319
991f71dc 320 switch ( GetEventKind( event ) )
e56d2520 321 {
3b6a1179 322 case kEventToolbarItemPerformAction:
e56d2520 323 {
3b6a1179 324 wxToolBarTool* tbartool = (wxToolBarTool*) data;
e56d2520
SC
325 if ( tbartool != NULL )
326 {
991f71dc
DS
327 wxToolBar *tbar = (wxToolBar*)(tbartool->GetToolBar());
328 int toolID = tbartool->GetId();
329
e56d2520
SC
330 if ( tbartool->CanBeToggled() )
331 {
3025abca 332 if ( tbar != NULL )
2c1dbc95 333 tbar->ToggleTool(toolID, !tbartool->IsToggled() );
e56d2520 334 }
991f71dc 335
3025abca 336 if ( tbar != NULL )
3b6a1179 337 tbar->OnLeftClick( toolID, tbartool->IsToggled() );
f3a65c3e 338 result = noErr;
e56d2520
SC
339 }
340 }
3b6a1179 341 break;
5d0bf05a 342
3b6a1179
DS
343 default:
344 break;
e56d2520 345 }
991f71dc 346
3b6a1179 347 return result;
e56d2520
SC
348}
349
350static pascal OSStatus wxMacToolBarEventHandler( EventHandlerCallRef handler, EventRef event, void *data )
351{
3b6a1179 352 OSStatus result = eventNotHandledErr;
991f71dc
DS
353
354 switch ( GetEventClass( event ) )
e56d2520 355 {
3b6a1179
DS
356 case kEventClassToolbarItem:
357 result = wxMacToolBarCommandEventHandler( handler, event, data );
358 break;
5d0bf05a 359
3b6a1179
DS
360 default:
361 break;
e56d2520 362 }
991f71dc 363
3b6a1179 364 return result;
e56d2520
SC
365}
366
367DEFINE_ONE_SHOT_HANDLER_GETTER( wxMacToolBarEventHandler )
368
369#endif
370
3b6a1179 371bool wxToolBarTool::DoEnable( bool enable )
a2fe01c9
SC
372{
373 if ( IsControl() )
374 {
3b6a1179 375 GetControl()->Enable( enable );
a2fe01c9
SC
376 }
377 else if ( IsButton() )
378 {
f3a65c3e 379#if wxMAC_USE_NATIVE_TOOLBAR
3025abca 380 if ( m_toolbarItemRef != NULL )
3b6a1179 381 HIToolbarItemSetEnabled( m_toolbarItemRef, enable );
e56d2520
SC
382#endif
383
3025abca 384 if ( m_controlHandle != NULL )
e56d2520 385 {
e56d2520 386 if ( enable )
3b6a1179 387 EnableControl( m_controlHandle );
e56d2520 388 else
3b6a1179 389 DisableControl( m_controlHandle );
e56d2520 390 }
a2fe01c9 391 }
991f71dc 392
3b6a1179 393 return true;
a2fe01c9 394}
bfe9ffbc 395
3b6a1179 396void wxToolBarTool::SetPosition( const wxPoint& position )
bfe9ffbc
SC
397{
398 m_x = position.x;
399 m_y = position.y;
400
3b6a1179
DS
401 int mac_x = position.x;
402 int mac_y = position.y;
789ae0cf 403
789ae0cf
SC
404 if ( IsButton() )
405 {
3b6a1179
DS
406 Rect contrlRect;
407 GetControlBounds( m_controlHandle, &contrlRect );
408 int former_mac_x = contrlRect.left;
409 int former_mac_y = contrlRect.top;
410 GetToolBar()->GetToolSize();
f3a65c3e 411
bfe9ffbc
SC
412 if ( mac_x != former_mac_x || mac_y != former_mac_y )
413 {
3b6a1179 414 UMAMoveControl( m_controlHandle, mac_x, mac_y );
bfe9ffbc
SC
415 }
416 }
417 else if ( IsControl() )
418 {
9d5ccdd3
SC
419 // embedded native controls are moved by the OS
420#if wxMAC_USE_NATIVE_TOOLBAR
421 if ( ((wxToolBar*)GetToolBar())->MacWantsNativeToolbar() == false )
422#endif
423 {
424 GetControl()->Move( position );
425 }
bfe9ffbc 426 }
abbcdf3f
SC
427 else
428 {
f3a65c3e 429 // separator
3b6a1179
DS
430 Rect contrlRect;
431 GetControlBounds( m_controlHandle, &contrlRect );
432 int former_mac_x = contrlRect.left;
433 int former_mac_y = contrlRect.top;
f3a65c3e 434
abbcdf3f 435 if ( mac_x != former_mac_x || mac_y != former_mac_y )
3b6a1179 436 UMAMoveControl( m_controlHandle, mac_x, mac_y );
abbcdf3f 437 }
bfe9ffbc
SC
438}
439
f3a65c3e 440void wxToolBarTool::UpdateToggleImage( bool toggle )
73fd9428 441{
73fd9428
SC
442 if ( toggle )
443 {
3b6a1179
DS
444 int w = m_bmpNormal.GetWidth();
445 int h = m_bmpNormal.GetHeight();
446 wxBitmap bmp( w, h );
447 wxMemoryDC dc;
448
449 dc.SelectObject( bmp );
ce9da810
RD
450 dc.SetPen( wxPen(*wxBLACK) );
451 dc.SetBrush( wxBrush( *wxLIGHT_GREY ));
3b6a1179
DS
452 dc.DrawRectangle( 0, 0, w, h );
453 dc.DrawBitmap( m_bmpNormal, 0, 0, true );
454 dc.SelectObject( wxNullBitmap );
455 ControlButtonContentInfo info;
6239ee05 456 wxMacCreateBitmapButton( &info, bmp );
991f71dc 457 SetControlData( m_controlHandle, 0, kControlIconContentTag, sizeof(info), (Ptr)&info );
ce9da810
RD
458#if wxMAC_USE_NATIVE_TOOLBAR
459 if (m_toolbarItemRef != NULL)
460 {
6239ee05
SC
461 ControlButtonContentInfo info2;
462 wxMacCreateBitmapButton( &info2, bmp, kControlContentCGImageRef);
463 HIToolbarItemSetImage( m_toolbarItemRef, info2.u.imageRef );
464 wxMacReleaseBitmapButton( &info2 );
ce9da810
RD
465 }
466#endif
3b6a1179 467 wxMacReleaseBitmapButton( &info );
73fd9428
SC
468 }
469 else
470 {
3b6a1179 471 ControlButtonContentInfo info;
6239ee05 472 wxMacCreateBitmapButton( &info, m_bmpNormal );
3025abca 473 SetControlData( m_controlHandle, 0, kControlIconContentTag, sizeof(info), (Ptr)&info );
ce9da810
RD
474#if wxMAC_USE_NATIVE_TOOLBAR
475 if (m_toolbarItemRef != NULL)
476 {
6239ee05
SC
477 ControlButtonContentInfo info2;
478 wxMacCreateBitmapButton( &info2, m_bmpNormal, kControlContentCGImageRef);
479 HIToolbarItemSetImage( m_toolbarItemRef, info2.u.imageRef );
480 wxMacReleaseBitmapButton( &info2 );
ce9da810
RD
481 }
482#endif
3b6a1179 483 wxMacReleaseBitmapButton( &info );
73fd9428
SC
484 }
485
3b6a1179
DS
486 IconTransformType transform = toggle ? kTransformSelected : kTransformNone;
487 SetControlData(
488 m_controlHandle, 0, kControlIconTransformTag,
3025abca 489 sizeof(transform), (Ptr)&transform );
3b6a1179 490 HIViewSetNeedsDisplay( m_controlHandle, true );
73fd9428 491
73fd9428
SC
492}
493
3b6a1179
DS
494wxToolBarTool::wxToolBarTool(
495 wxToolBar *tbar,
496 int id,
497 const wxString& label,
498 const wxBitmap& bmpNormal,
499 const wxBitmap& bmpDisabled,
500 wxItemKind kind,
501 wxObject *clientData,
502 const wxString& shortHelp,
503 const wxString& longHelp )
504 :
505 wxToolBarToolBase(
506 tbar, id, label, bmpNormal, bmpDisabled, kind,
507 clientData, shortHelp, longHelp )
bfe9ffbc 508{
f4e0be4f 509 Init();
bfe9ffbc
SC
510}
511
e56d2520
SC
512#pragma mark -
513#pragma mark Toolbar Implementation
2f1ae414 514
3b6a1179
DS
515wxToolBarToolBase *wxToolBar::CreateTool(
516 int id,
517 const wxString& label,
518 const wxBitmap& bmpNormal,
519 const wxBitmap& bmpDisabled,
520 wxItemKind kind,
521 wxObject *clientData,
522 const wxString& shortHelp,
523 const wxString& longHelp )
37e2cb08 524{
3b6a1179
DS
525 return new wxToolBarTool(
526 this, id, label, bmpNormal, bmpDisabled, kind,
527 clientData, shortHelp, longHelp );
37e2cb08
SC
528}
529
cdb11cb9
VZ
530wxToolBarToolBase *
531wxToolBar::CreateTool(wxControl *control, const wxString& label)
37e2cb08 532{
cdb11cb9 533 return new wxToolBarTool(this, control, label);
37e2cb08
SC
534}
535
37e2cb08 536void wxToolBar::Init()
e9576ca5 537{
e40298d5
JS
538 m_maxWidth = -1;
539 m_maxHeight = -1;
540 m_defaultWidth = kwxMacToolBarToolDefaultWidth;
541 m_defaultHeight = kwxMacToolBarToolDefaultHeight;
991f71dc 542
e56d2520 543#if wxMAC_USE_NATIVE_TOOLBAR
3b6a1179
DS
544 m_macHIToolbarRef = NULL;
545 m_macUsesNativeToolbar = false;
e56d2520 546#endif
e9576ca5
SC
547}
548
0ac091ae 549#define kControlToolbarItemClassID CFSTR( "org.wxwidgets.controltoolbaritem" )
6d4835dc 550
cdb11cb9 551const EventTypeSpec kEvents[] =
6d4835dc 552{
0ac091ae
RD
553 { kEventClassHIObject, kEventHIObjectConstruct },
554 { kEventClassHIObject, kEventHIObjectInitialize },
555 { kEventClassHIObject, kEventHIObjectDestruct },
cdb11cb9 556
0ac091ae 557 { kEventClassToolbarItem, kEventToolbarItemCreateCustomView }
6d4835dc
SC
558};
559
cdb11cb9
VZ
560const EventTypeSpec kViewEvents[] =
561{
562 { kEventClassControl, kEventControlGetSizeConstraints }
6d4835dc
SC
563};
564
cdb11cb9
VZ
565struct ControlToolbarItem
566{
567 HIToolbarItemRef toolbarItem;
6d4835dc
SC
568 HIViewRef viewRef;
569 wxSize lastValidSize ;
cdb11cb9 570};
6d4835dc
SC
571
572static pascal OSStatus ControlToolbarItemHandler( EventHandlerCallRef inCallRef, EventRef inEvent, void* inUserData )
573{
0ac091ae
RD
574 OSStatus result = eventNotHandledErr;
575 ControlToolbarItem* object = (ControlToolbarItem*)inUserData;
576
577 switch ( GetEventClass( inEvent ) )
578 {
579 case kEventClassHIObject:
580 switch ( GetEventKind( inEvent ) )
581 {
582 case kEventHIObjectConstruct:
583 {
584 HIObjectRef toolbarItem;
585 ControlToolbarItem* item;
cdb11cb9 586
0ac091ae 587 GetEventParameter( inEvent, kEventParamHIObjectInstance, typeHIObjectRef, NULL,
6d4835dc 588 sizeof( HIObjectRef ), NULL, &toolbarItem );
cdb11cb9 589
6d4835dc
SC
590 item = (ControlToolbarItem*) malloc(sizeof(ControlToolbarItem)) ;
591 item->toolbarItem = toolbarItem ;
9154a136 592 item->lastValidSize = wxSize(-1,-1);
6d4835dc 593 item->viewRef = NULL ;
cdb11cb9 594
0ac091ae 595 SetEventParameter( inEvent, kEventParamHIObjectInstance, typeVoidPtr, sizeof( void * ), &item );
cdb11cb9 596
6d4835dc 597 result = noErr ;
0ac091ae
RD
598 }
599 break;
cdb11cb9 600
6d4835dc
SC
601 case kEventHIObjectInitialize:
602 result = CallNextEventHandler( inCallRef, inEvent );
0ac091ae 603 if ( result == noErr )
6d4835dc
SC
604 {
605 CFDataRef data;
606 GetEventParameter( inEvent, kEventParamToolbarItemConfigData, typeCFTypeRef, NULL,
607 sizeof( CFTypeRef ), NULL, &data );
cdb11cb9 608
6d4835dc 609 HIViewRef viewRef ;
cdb11cb9 610
6d4835dc
SC
611 wxASSERT_MSG( CFDataGetLength( data ) == sizeof( viewRef ) , wxT("Illegal Data passed") ) ;
612 memcpy( &viewRef , CFDataGetBytePtr( data ) , sizeof( viewRef ) ) ;
cdb11cb9 613
6d4835dc 614 object->viewRef = (HIViewRef) viewRef ;
75c25a82
SC
615 // make sure we keep that control during our lifetime
616 CFRetain( object->viewRef ) ;
6d4835dc 617
75c25a82
SC
618 verify_noerr(InstallEventHandler( GetControlEventTarget( viewRef ), ControlToolbarItemHandler,
619 GetEventTypeCount( kViewEvents ), kViewEvents, object, NULL ));
0ac091ae
RD
620 result = noErr ;
621 }
6d4835dc
SC
622 break;
623
0ac091ae 624 case kEventHIObjectDestruct:
507d5748 625 {
507d5748 626 HIViewRef viewRef = object->viewRef ;
83f787ba 627 if( viewRef && IsValidControlHandle( viewRef) )
507d5748 628 {
75c25a82
SC
629 // depending whether the wxControl corresponding to this HIView has already been destroyed or
630 // not, ref counts differ, so we cannot assert a special value
cdb11cb9 631 CFIndex count = CFGetRetainCount( viewRef ) ;
75c25a82 632 wxASSERT_MSG( count >=1 , wxT("Reference Count of native tool was illegal before removal") );
83f787ba
SC
633 if ( count >= 1 )
634 CFRelease( viewRef ) ;
507d5748
SC
635 }
636 free( object ) ;
637 result = noErr;
638 }
0ac091ae
RD
639 break;
640 }
641 break;
cdb11cb9 642
0ac091ae
RD
643 case kEventClassToolbarItem:
644 switch ( GetEventKind( inEvent ) )
cdb11cb9 645 {
0ac091ae
RD
646 case kEventToolbarItemCreateCustomView:
647 {
6d4835dc 648 HIViewRef viewRef = object->viewRef ;
6d4835dc
SC
649 HIViewRemoveFromSuperview( viewRef ) ;
650 HIViewSetVisible(viewRef, true) ;
75c25a82 651 CFRetain( viewRef ) ;
6d4835dc 652 result = SetEventParameter( inEvent, kEventParamControlRef, typeControlRef, sizeof( HIViewRef ), &viewRef );
0ac091ae
RD
653 }
654 break;
655 }
656 break;
cdb11cb9 657
0ac091ae
RD
658 case kEventClassControl:
659 switch ( GetEventKind( inEvent ) )
660 {
661 case kEventControlGetSizeConstraints:
662 {
6d4835dc
SC
663 wxWindow* wxwindow = wxFindControlFromMacControl(object->viewRef ) ;
664 if ( wxwindow )
665 {
9154a136
SC
666 // during toolbar layout the native window sometimes gets negative sizes,
667 // sometimes it just gets shrunk behind our back, so in order to avoid
668 // ever shrinking more, once a valid size is captured, we keep it
669
670 wxSize sz = object->lastValidSize;
671 if ( sz.x <= 0 || sz.y <= 0 )
672 {
673 sz = wxwindow->GetSize() ;
674 sz.x -= wxwindow->MacGetLeftBorderSize() + wxwindow->MacGetRightBorderSize();
675 sz.y -= wxwindow->MacGetTopBorderSize() + wxwindow->MacGetBottomBorderSize();
676 if ( sz.x > 0 && sz.y > 0 )
677 object->lastValidSize = sz ;
678 else
679 sz = wxSize(0,0) ;
680 }
cdb11cb9 681
9b7835a5
JS
682 // Extra width to avoid edge of combobox being cut off
683 sz.x += 3;
684
6d4835dc
SC
685 HISize min, max;
686 min.width = max.width = sz.x ;
687 min.height = max.height = sz.y ;
cdb11cb9 688
6d4835dc
SC
689 result = SetEventParameter( inEvent, kEventParamMinimumSize, typeHISize,
690 sizeof( HISize ), &min );
cdb11cb9 691
6d4835dc
SC
692 result = SetEventParameter( inEvent, kEventParamMaximumSize, typeHISize,
693 sizeof( HISize ), &max );
694 result = noErr ;
695 }
0ac091ae
RD
696 }
697 break;
698 }
699 break;
700 }
cdb11cb9 701
0ac091ae 702 return result;
6d4835dc
SC
703}
704
705void RegisterControlToolbarItemClass()
706{
0ac091ae 707 static bool sRegistered;
cdb11cb9 708
0ac091ae
RD
709 if ( !sRegistered )
710 {
711 HIObjectRegisterSubclass( kControlToolbarItemClassID, kHIToolbarItemClassID, 0,
712 ControlToolbarItemHandler, GetEventTypeCount( kEvents ), kEvents, 0, NULL );
cdb11cb9 713
0ac091ae
RD
714 sRegistered = true;
715 }
6d4835dc
SC
716}
717
718HIToolbarItemRef CreateControlToolbarItem(CFStringRef inIdentifier, CFTypeRef inConfigData)
719{
0ac091ae 720 RegisterControlToolbarItemClass();
cdb11cb9 721
0ac091ae
RD
722 OSStatus err;
723 EventRef event;
724 UInt32 options = kHIToolbarItemAllowDuplicates;
725 HIToolbarItemRef result = NULL;
cdb11cb9 726
0ac091ae
RD
727 err = CreateEvent( NULL, kEventClassHIObject, kEventHIObjectInitialize, GetCurrentEventTime(), 0, &event );
728 require_noerr( err, CantCreateEvent );
cdb11cb9 729
0ac091ae
RD
730 SetEventParameter( event, kEventParamAttributes, typeUInt32, sizeof( UInt32 ), &options );
731 SetEventParameter( event, kEventParamToolbarItemIdentifier, typeCFStringRef, sizeof( CFStringRef ), &inIdentifier );
cdb11cb9 732
0ac091ae
RD
733 if ( inConfigData )
734 SetEventParameter( event, kEventParamToolbarItemConfigData, typeCFTypeRef, sizeof( CFTypeRef ), &inConfigData );
cdb11cb9 735
0ac091ae
RD
736 err = HIObjectCreate( kControlToolbarItemClassID, event, (HIObjectRef*)&result );
737 check_noerr( err );
cdb11cb9 738
0ac091ae 739 ReleaseEvent( event );
cdb11cb9 740CantCreateEvent :
0ac091ae 741 return result ;
6d4835dc
SC
742}
743
716d0327 744#if wxMAC_USE_NATIVE_TOOLBAR
6d4835dc
SC
745static const EventTypeSpec kToolbarEvents[] =
746{
0ac091ae
RD
747 { kEventClassToolbar, kEventToolbarGetDefaultIdentifiers },
748 { kEventClassToolbar, kEventToolbarGetAllowedIdentifiers },
749 { kEventClassToolbar, kEventToolbarCreateItemWithIdentifier },
6d4835dc
SC
750};
751
89954433
VZ
752static OSStatus ToolbarDelegateHandler(EventHandlerCallRef WXUNUSED(inCallRef),
753 EventRef inEvent,
754 void* WXUNUSED(inUserData))
6d4835dc 755{
0ac091ae 756 OSStatus result = eventNotHandledErr;
9d5ccdd3
SC
757 // Not yet needed
758 // wxToolBar* toolbar = (wxToolBar*) inUserData ;
0ac091ae 759 CFMutableArrayRef array;
6d4835dc 760
0ac091ae
RD
761 switch ( GetEventKind( inEvent ) )
762 {
763 case kEventToolbarGetDefaultIdentifiers:
6d4835dc
SC
764 {
765 GetEventParameter( inEvent, kEventParamMutableArray, typeCFMutableArrayRef, NULL,
0ac091ae 766 sizeof( CFMutableArrayRef ), NULL, &array );
6d4835dc
SC
767 // not implemented yet
768 // GetToolbarDefaultItems( array );
769 result = noErr;
770 }
0ac091ae 771 break;
cdb11cb9 772
0ac091ae 773 case kEventToolbarGetAllowedIdentifiers:
6d4835dc
SC
774 {
775 GetEventParameter( inEvent, kEventParamMutableArray, typeCFMutableArrayRef, NULL,
0ac091ae 776 sizeof( CFMutableArrayRef ), NULL, &array );
6d4835dc
SC
777 // not implemented yet
778 // GetToolbarAllowedItems( array );
779 result = noErr;
780 }
0ac091ae
RD
781 break;
782 case kEventToolbarCreateItemWithIdentifier:
783 {
784 HIToolbarItemRef item = NULL;
785 CFTypeRef data = NULL;
6d4835dc 786 CFStringRef identifier = NULL ;
cdb11cb9 787
0ac091ae
RD
788 GetEventParameter( inEvent, kEventParamToolbarItemIdentifier, typeCFStringRef, NULL,
789 sizeof( CFStringRef ), NULL, &identifier );
cdb11cb9 790
0ac091ae
RD
791 GetEventParameter( inEvent, kEventParamToolbarItemConfigData, typeCFTypeRef, NULL,
792 sizeof( CFTypeRef ), NULL, &data );
cdb11cb9 793
6d4835dc
SC
794 if ( CFStringCompare( kControlToolbarItemClassID, identifier, kCFCompareBackwards ) == kCFCompareEqualTo )
795 {
796 item = CreateControlToolbarItem( kControlToolbarItemClassID, data );
797 if ( item )
798 {
799 SetEventParameter( inEvent, kEventParamToolbarItem, typeHIToolbarItemRef,
800 sizeof( HIToolbarItemRef ), &item );
801 result = noErr;
802 }
0ac091ae 803 }
cdb11cb9 804
0ac091ae
RD
805 }
806 break;
6d4835dc
SC
807 }
808 return result ;
809}
716d0327 810#endif // wxMAC_USE_NATIVE_TOOLBAR
6d4835dc 811
e56d2520
SC
812// also for the toolbar we have the dual implementation:
813// only when MacInstallNativeToolbar is called is the native toolbar set as the window toolbar
6d4835dc 814
3b6a1179
DS
815bool wxToolBar::Create(
816 wxWindow *parent,
991f71dc
DS
817 wxWindowID id,
818 const wxPoint& pos,
819 const wxSize& size,
820 long style,
3b6a1179 821 const wxString& name )
5d0bf05a 822{
3b6a1179
DS
823 if ( !wxToolBarBase::Create( parent, id, pos, size, style, wxDefaultValidator, name ) )
824 return false;
e56d2520 825
d408730c
VZ
826 FixupStyle();
827
991f71dc 828 OSStatus err = noErr;
e56d2520
SC
829
830#if wxMAC_USE_NATIVE_TOOLBAR
079b2f6b 831 if (parent->IsKindOf(CLASSINFO(wxFrame)) && wxSystemOptions::GetOptionInt(wxT("mac.toolbar.no-native")) != 1)
f3a65c3e 832 {
6239ee05 833 wxString labelStr = wxString::Format( wxT("%p"), this );
079b2f6b
JS
834 err = HIToolbarCreate(
835 wxMacCFStringHolder( labelStr, wxFont::GetDefaultEncoding() ), 0,
836 (HIToolbarRef*) &m_macHIToolbarRef );
6d4835dc 837
079b2f6b
JS
838 if (m_macHIToolbarRef != NULL)
839 {
840 InstallEventHandler( HIObjectGetEventTarget((HIToolbarRef)m_macHIToolbarRef ), ToolbarDelegateHandler,
841 GetEventTypeCount( kToolbarEvents ), kToolbarEvents, this, NULL );
e56d2520 842
079b2f6b
JS
843 HIToolbarDisplayMode mode = kHIToolbarDisplayModeDefault;
844 HIToolbarDisplaySize displaySize = kHIToolbarDisplaySizeSmall;
e56d2520 845
079b2f6b
JS
846 if ( style & wxTB_NOICONS )
847 mode = kHIToolbarDisplayModeLabelOnly;
848 else if ( style & wxTB_TEXT )
849 mode = kHIToolbarDisplayModeIconAndLabel;
850 else
851 mode = kHIToolbarDisplayModeIconOnly;
852
853 HIToolbarSetDisplayMode( (HIToolbarRef) m_macHIToolbarRef, mode );
854 HIToolbarSetDisplaySize( (HIToolbarRef) m_macHIToolbarRef, displaySize );
855 }
e56d2520 856 }
cdb11cb9 857#endif // wxMAC_USE_NATIVE_TOOLBAR
e56d2520 858
991f71dc 859 return (err == noErr);
e9576ca5
SC
860}
861
862wxToolBar::~wxToolBar()
f3a65c3e 863{
e56d2520 864#if wxMAC_USE_NATIVE_TOOLBAR
3025abca 865 if (m_macHIToolbarRef != NULL)
e56d2520
SC
866 {
867 // if this is the installed toolbar, then deinstall it
868 if (m_macUsesNativeToolbar)
869 MacInstallNativeToolbar( false );
870
507d5748 871 CFIndex count = CFGetRetainCount( m_macHIToolbarRef ) ;
6239ee05
SC
872 // Leopard seems to have one refcount more, so we cannot check reliably at the moment
873 if ( UMAGetSystemVersion() < 0x1050 )
874 {
875 wxASSERT_MSG( count == 1 , wxT("Reference Count of native control was not 1 in wxToolBar destructor") );
876 }
3025abca 877 CFRelease( (HIToolbarRef)m_macHIToolbarRef );
e56d2520
SC
878 m_macHIToolbarRef = NULL;
879 }
880#endif
881}
882
e56d2520
SC
883bool wxToolBar::Show( bool show )
884{
e56d2520 885 WindowRef tlw = MAC_WXHWND(MacGetTopLevelWindowRef());
3025abca 886 bool bResult = (tlw != NULL);
f3a65c3e 887
e56d2520
SC
888 if (bResult)
889 {
890#if wxMAC_USE_NATIVE_TOOLBAR
f3a65c3e 891 bool ownToolbarInstalled = false;
e56d2520
SC
892 MacTopLevelHasNativeToolbar( &ownToolbarInstalled );
893 if (ownToolbarInstalled)
894 {
3025abca 895 bResult = (IsWindowToolbarVisible( tlw ) != show);
a749a99f
SC
896 if ( bResult )
897 ShowHideWindowToolbar( tlw, show, false );
e56d2520
SC
898 }
899 else
e56d2520 900 bResult = wxToolBarBase::Show( show );
3025abca
DS
901#else
902
903 bResult = wxToolBarBase::Show( show );
904#endif
e56d2520 905 }
f3a65c3e 906
e56d2520
SC
907 return bResult;
908}
909
910bool wxToolBar::IsShown() const
911{
912 bool bResult;
913
914#if wxMAC_USE_NATIVE_TOOLBAR
3b6a1179 915 bool ownToolbarInstalled;
3025abca 916
e56d2520
SC
917 MacTopLevelHasNativeToolbar( &ownToolbarInstalled );
918 if (ownToolbarInstalled)
a749a99f
SC
919 {
920 WindowRef tlw = MAC_WXHWND(MacGetTopLevelWindowRef());
3b6a1179 921 bResult = IsWindowToolbarVisible( tlw );
a749a99f 922 }
e56d2520 923 else
e56d2520 924 bResult = wxToolBarBase::IsShown();
3025abca
DS
925#else
926
927 bResult = wxToolBarBase::IsShown();
928#endif
f3a65c3e 929
e56d2520
SC
930 return bResult;
931}
932
e56d2520
SC
933void wxToolBar::DoGetSize( int *width, int *height ) const
934{
935#if wxMAC_USE_NATIVE_TOOLBAR
936 Rect boundsR;
937 bool ownToolbarInstalled;
f3a65c3e 938
e56d2520
SC
939 MacTopLevelHasNativeToolbar( &ownToolbarInstalled );
940 if ( ownToolbarInstalled )
941 {
991f71dc 942 // TODO: is this really a control ?
e56d2520
SC
943 GetControlBounds( (ControlRef) m_macHIToolbarRef, &boundsR );
944 if ( width != NULL )
945 *width = boundsR.right - boundsR.left;
946 if ( height != NULL )
947 *height = boundsR.bottom - boundsR.top;
948 }
949 else
e56d2520 950 wxToolBarBase::DoGetSize( width, height );
3025abca
DS
951
952#else
953 wxToolBarBase::DoGetSize( width, height );
954#endif
e9576ca5
SC
955}
956
b13095df
SC
957wxSize wxToolBar::DoGetBestSize() const
958{
3b6a1179 959 int width, height;
991f71dc 960
3b6a1179 961 DoGetSize( &width, &height );
991f71dc 962
3b6a1179 963 return wxSize( width, height );
b13095df
SC
964}
965
f3a65c3e 966void wxToolBar::SetWindowStyleFlag( long style )
e56d2520
SC
967{
968 wxToolBarBase::SetWindowStyleFlag( style );
991f71dc 969
e56d2520
SC
970#if wxMAC_USE_NATIVE_TOOLBAR
971 if (m_macHIToolbarRef != NULL)
972 {
973 HIToolbarDisplayMode mode = kHIToolbarDisplayModeDefault;
974
975 if ( style & wxTB_NOICONS )
976 mode = kHIToolbarDisplayModeLabelOnly;
977 else if ( style & wxTB_TEXT )
978 mode = kHIToolbarDisplayModeIconAndLabel;
979 else
980 mode = kHIToolbarDisplayModeIconOnly;
f3a65c3e 981
e56d2520
SC
982 HIToolbarSetDisplayMode( (HIToolbarRef) m_macHIToolbarRef, mode );
983 }
984#endif
985}
986
987#if wxMAC_USE_NATIVE_TOOLBAR
988bool wxToolBar::MacWantsNativeToolbar()
989{
990 return m_macUsesNativeToolbar;
991}
992
993bool wxToolBar::MacTopLevelHasNativeToolbar(bool *ownToolbarInstalled) const
994{
995 bool bResultV = false;
996
997 if (ownToolbarInstalled != NULL)
998 *ownToolbarInstalled = false;
999
1000 WindowRef tlw = MAC_WXHWND(MacGetTopLevelWindowRef());
1001 if (tlw != NULL)
1002 {
1003 HIToolbarRef curToolbarRef = NULL;
1004 OSStatus err = GetWindowToolbar( tlw, &curToolbarRef );
3025abca 1005 bResultV = ((err == noErr) && (curToolbarRef != NULL));
e56d2520
SC
1006 if (bResultV && (ownToolbarInstalled != NULL))
1007 *ownToolbarInstalled = (curToolbarRef == m_macHIToolbarRef);
1008 }
1009
1010 return bResultV;
1011}
1012
f3a65c3e 1013bool wxToolBar::MacInstallNativeToolbar(bool usesNative)
e56d2520 1014{
df7998fc 1015 bool bResult = false;
e56d2520 1016
e56d2520
SC
1017 if (usesNative && (m_macHIToolbarRef == NULL))
1018 return bResult;
f3a65c3e 1019
e56d2520
SC
1020 if (usesNative && ((GetWindowStyleFlag() & wxTB_VERTICAL) != 0))
1021 return bResult;
f3a65c3e 1022
3025abca
DS
1023 WindowRef tlw = MAC_WXHWND(MacGetTopLevelWindowRef());
1024 if (tlw == NULL)
1025 return bResult;
1026
e56d2520
SC
1027 // check the existing toolbar
1028 HIToolbarRef curToolbarRef = NULL;
1029 OSStatus err = GetWindowToolbar( tlw, &curToolbarRef );
991f71dc 1030 if (err != noErr)
e56d2520
SC
1031 curToolbarRef = NULL;
1032
1033 m_macUsesNativeToolbar = usesNative;
1034
1035 if (m_macUsesNativeToolbar)
1036 {
1037 // only install toolbar if there isn't one installed already
1038 if (curToolbarRef == NULL)
1039 {
1040 bResult = true;
1041
1042 SetWindowToolbar( tlw, (HIToolbarRef) m_macHIToolbarRef );
1043 ShowHideWindowToolbar( tlw, true, false );
1044 ChangeWindowAttributes( tlw, kWindowToolbarButtonAttribute, 0 );
1045 SetAutomaticControlDragTrackingEnabledForWindow( tlw, true );
f3a65c3e 1046
3b6a1179 1047 Rect r = { 0, 0, 0, 0 };
e56d2520 1048 m_peer->SetRect( &r );
e56d2520 1049 SetSize( wxSIZE_AUTO_WIDTH, 0 );
e56d2520
SC
1050 m_peer->SetVisibility( false, true );
1051 wxToolBarBase::Show( false );
1052 }
1053 }
1054 else
1055 {
1056 // only deinstall toolbar if this is the installed one
1057 if (m_macHIToolbarRef == curToolbarRef)
1058 {
1059 bResult = true;
1060
1061 ShowHideWindowToolbar( tlw, false, false );
3b6a1179 1062 ChangeWindowAttributes( tlw, 0, kWindowToolbarButtonAttribute );
e56d2520 1063 SetWindowToolbar( tlw, NULL );
f3a65c3e 1064
e56d2520 1065 m_peer->SetVisibility( true, true );
e56d2520
SC
1066 }
1067 }
1068
1069 if (bResult)
1070 InvalidateBestSize();
1071
1072// wxLogDebug( wxT(" --> [%lx] - result [%s]"), (long)this, bResult ? wxT("T") : wxT("F") );
1073 return bResult;
1074}
1075#endif
1076
37e2cb08 1077bool wxToolBar::Realize()
e9576ca5 1078{
eb22f2a6 1079 if (m_tools.GetCount() == 0)
3803c372 1080 return false;
0b7a8cd3 1081
e56d2520
SC
1082 int maxWidth = 0;
1083 int maxHeight = 0;
f3a65c3e 1084
bfe9ffbc
SC
1085 int maxToolWidth = 0;
1086 int maxToolHeight = 0;
f3a65c3e 1087
991f71dc
DS
1088 int x = m_xMargin + kwxMacToolBarLeftMargin;
1089 int y = m_yMargin + kwxMacToolBarTopMargin;
1090
1091 int tw, th;
1092 GetSize( &tw, &th );
1093
e56d2520 1094 // find the maximum tool width and height
3025abca
DS
1095 wxToolBarTool *tool;
1096 wxToolBarToolsList::compatibility_iterator node = m_tools.GetFirst();
35f94ffd 1097 while ( node )
bfe9ffbc 1098 {
3025abca 1099 tool = (wxToolBarTool *) node->GetData();
e56d2520
SC
1100 if ( tool != NULL )
1101 {
1102 wxSize sz = tool->GetSize();
f3a65c3e 1103
e56d2520
SC
1104 if ( sz.x > maxToolWidth )
1105 maxToolWidth = sz.x;
1106 if ( sz.y > maxToolHeight )
1107 maxToolHeight = sz.y;
1108 }
f3a65c3e 1109
bfe9ffbc
SC
1110 node = node->GetNext();
1111 }
f3a65c3e 1112
991f71dc
DS
1113 bool lastIsRadio = false;
1114 bool curIsRadio = false;
df7998fc
VZ
1115
1116#if wxMAC_USE_NATIVE_TOOLBAR
3b6a1179
DS
1117 CFIndex currentPosition = 0;
1118 bool insertAll = false;
58862dfa
VZ
1119
1120 HIToolbarRef refTB = (HIToolbarRef)m_macHIToolbarRef;
991f71dc 1121#endif
df7998fc 1122
991f71dc 1123 node = m_tools.GetFirst();
35f94ffd 1124 while ( node )
7810c95b 1125 {
3025abca 1126 tool = (wxToolBarTool*) node->GetData();
e56d2520 1127 if ( tool == NULL )
214b9484 1128 {
e56d2520
SC
1129 node = node->GetNext();
1130 continue;
214b9484 1131 }
f3a65c3e 1132
991f71dc 1133 // set tool position:
e56d2520
SC
1134 // for the moment just perform a single row/column alignment
1135 wxSize cursize = tool->GetSize();
bfe9ffbc 1136 if ( x + cursize.x > maxWidth )
e56d2520 1137 maxWidth = x + cursize.x;
bfe9ffbc 1138 if ( y + cursize.y > maxHeight )
e56d2520 1139 maxHeight = y + cursize.y;
f3a65c3e 1140
73fd9428
SC
1141 if ( GetWindowStyleFlag() & wxTB_VERTICAL )
1142 {
e56d2520
SC
1143 int x1 = x + ( maxToolWidth - cursize.x ) / 2;
1144 tool->SetPosition( wxPoint(x1, y) );
73fd9428
SC
1145 }
1146 else
1147 {
e56d2520
SC
1148 int y1 = y + ( maxToolHeight - cursize.y ) / 2;
1149 tool->SetPosition( wxPoint(x, y1) );
1150 }
f3a65c3e 1151
e56d2520 1152 // update the item positioning state
bfe9ffbc 1153 if ( GetWindowStyleFlag() & wxTB_VERTICAL )
e56d2520
SC
1154 y += cursize.y + kwxMacToolSpacing;
1155 else
1156 x += cursize.x + kwxMacToolSpacing;
f3a65c3e 1157
e56d2520
SC
1158#if wxMAC_USE_NATIVE_TOOLBAR
1159 // install in native HIToolbar
58862dfa 1160 if ( refTB )
bfe9ffbc 1161 {
58862dfa 1162 HIToolbarItemRef hiItemRef = tool->GetToolbarItemRef();
e56d2520
SC
1163 if ( hiItemRef != NULL )
1164 {
991f71dc 1165 if ( insertAll || (tool->GetIndex() != currentPosition) )
e56d2520 1166 {
dcae64c2 1167 OSStatus err = noErr;
8138cfec
SC
1168 if ( !insertAll )
1169 {
dcae64c2
DS
1170 insertAll = true;
1171
8138cfec
SC
1172 // if this is the first tool that gets newly inserted or repositioned
1173 // first remove all 'old' tools from here to the right, because of this
58862dfa
VZ
1174 // all following tools will have to be reinserted (insertAll).
1175 for ( wxToolBarToolsList::compatibility_iterator node2 = m_tools.GetLast();
1176 node2 != node;
1177 node2 = node2->GetPrevious() )
dcae64c2 1178 {
58862dfa
VZ
1179 wxToolBarTool *tool2 = (wxToolBarTool*) node2->GetData();
1180
1181 const long idx = tool2->GetIndex();
1182 if ( idx != -1 )
1183 {
75c25a82
SC
1184 if ( tool2->IsControl() )
1185 {
1186 CFIndex count = CFGetRetainCount( tool2->GetControl()->GetPeer()->GetControlRef() ) ;
5cb78ae7 1187 wxASSERT_MSG( count == 3 || count == 2 , wxT("Reference Count of native tool was illegal before removal") );
75c25a82
SC
1188 wxASSERT( IsValidControlHandle(tool2->GetControl()->GetPeer()->GetControlRef() )) ;
1189 }
58862dfa
VZ
1190 err = HIToolbarRemoveItemAtIndex(refTB, idx);
1191 if ( err != noErr )
1192 {
1193 wxLogDebug(wxT("HIToolbarRemoveItemAtIndex(%ld) failed [%ld]"),
1194 idx, (long)err);
1195 }
75c25a82
SC
1196 if ( tool2->IsControl() )
1197 {
1198 CFIndex count = CFGetRetainCount( tool2->GetControl()->GetPeer()->GetControlRef() ) ;
1199 wxASSERT_MSG( count == 2 , wxT("Reference Count of native tool was not 2 after removal") );
1200 wxASSERT( IsValidControlHandle(tool2->GetControl()->GetPeer()->GetControlRef() )) ;
1201 }
58862dfa
VZ
1202
1203 tool2->SetIndex(-1);
1204 }
dcae64c2
DS
1205 }
1206 }
991f71dc 1207
58862dfa 1208 err = HIToolbarInsertItemAtIndex( refTB, hiItemRef, currentPosition );
dcae64c2
DS
1209 if (err != noErr)
1210 {
58862dfa 1211 wxLogDebug( wxT("HIToolbarInsertItemAtIndex failed [%ld]"), (long)err );
dcae64c2 1212 }
3b6a1179 1213
dcae64c2 1214 tool->SetIndex( currentPosition );
75c25a82
SC
1215 if ( tool->IsControl() )
1216 {
1217 CFIndex count = CFGetRetainCount( tool->GetControl()->GetPeer()->GetControlRef() ) ;
5cb78ae7 1218 wxASSERT_MSG( count == 3 || count == 2, wxT("Reference Count of native tool was illegal after insertion") );
75c25a82
SC
1219 wxASSERT( IsValidControlHandle(tool->GetControl()->GetPeer()->GetControlRef() )) ;
1220 }
e56d2520 1221 }
991f71dc 1222
dcae64c2 1223 currentPosition++;
e56d2520
SC
1224 }
1225 }
dcae64c2 1226#endif
f3a65c3e 1227
e56d2520
SC
1228 // update radio button (and group) state
1229 lastIsRadio = curIsRadio;
1230 curIsRadio = ( tool->IsButton() && (tool->GetKind() == wxITEM_RADIO) );
f3a65c3e 1231
e56d2520
SC
1232 if ( !curIsRadio )
1233 {
1234 if ( tool->IsToggled() )
1235 DoToggleTool( tool, true );
0b7a8cd3
GD
1236 }
1237 else
1238 {
e56d2520
SC
1239 if ( !lastIsRadio )
1240 {
dcae64c2 1241 if ( tool->Toggle( true ) )
e56d2520
SC
1242 {
1243 DoToggleTool( tool, true );
e56d2520
SC
1244 }
1245 }
1246 else if ( tool->IsToggled() )
1247 {
1248 if ( tool->IsToggled() )
1249 DoToggleTool( tool, true );
f3a65c3e 1250
e56d2520 1251 wxToolBarToolsList::compatibility_iterator nodePrev = node->GetPrevious();
35f94ffd 1252 while ( nodePrev )
e56d2520
SC
1253 {
1254 wxToolBarToolBase *toggleTool = nodePrev->GetData();
1255 if ( (toggleTool == NULL) || !toggleTool->IsButton() || (toggleTool->GetKind() != wxITEM_RADIO) )
1256 break;
f3a65c3e 1257
dcae64c2 1258 if ( toggleTool->Toggle( false ) )
e56d2520 1259 DoToggleTool( toggleTool, false );
f3a65c3e 1260
e56d2520
SC
1261 nodePrev = nodePrev->GetPrevious();
1262 }
1263 }
0b7a8cd3 1264 }
f3a65c3e 1265
eb22f2a6 1266 node = node->GetNext();
7810c95b 1267 }
f3a65c3e 1268
0b7a8cd3 1269 if ( GetWindowStyleFlag() & wxTB_HORIZONTAL )
7810c95b 1270 {
e56d2520
SC
1271 // if not set yet, only one row
1272 if ( m_maxRows <= 0 )
1273 SetRows( 1 );
f3a65c3e 1274
90d3f91a 1275 m_minWidth = maxWidth;
e56d2520 1276 maxWidth = tw;
0b7a8cd3 1277 maxHeight += m_yMargin + kwxMacToolBarTopMargin;
e56d2520 1278 m_minHeight = m_maxHeight = maxHeight;
7810c95b 1279 }
0b7a8cd3
GD
1280 else
1281 {
e56d2520
SC
1282 // if not set yet, have one column
1283 if ( (GetToolsCount() > 0) && (m_maxRows <= 0) )
1284 SetRows( GetToolsCount() );
f3a65c3e 1285
90d3f91a 1286 m_minHeight = maxHeight;
e56d2520 1287 maxHeight = th;
0b7a8cd3 1288 maxWidth += m_xMargin + kwxMacToolBarLeftMargin;
e56d2520 1289 m_minWidth = m_maxWidth = maxWidth;
0b7a8cd3 1290 }
e56d2520 1291
f3a65c3e 1292#if 0
e56d2520
SC
1293 // FIXME: should this be OSX-only?
1294 {
1295 bool wantNativeToolbar, ownToolbarInstalled;
1296
1297 // attempt to install the native toolbar
1298 wantNativeToolbar = ((GetWindowStyleFlag() & wxTB_VERTICAL) == 0);
1299 MacInstallNativeToolbar( wantNativeToolbar );
1300 (void)MacTopLevelHasNativeToolbar( &ownToolbarInstalled );
1301 if (!ownToolbarInstalled)
1302 {
1303 SetSize( maxWidth, maxHeight );
1304 InvalidateBestSize();
1305 }
1306 }
f3a65c3e 1307#else
facd6764 1308 SetSize( maxWidth, maxHeight );
9f884528 1309 InvalidateBestSize();
e56d2520 1310#endif
2c1dbc95 1311
170acdc9 1312 SetInitialSize();
2c1dbc95 1313
3803c372 1314 return true;
e9576ca5
SC
1315}
1316
1317void wxToolBar::SetToolBitmapSize(const wxSize& size)
1318{
e56d2520
SC
1319 m_defaultWidth = size.x + kwxMacToolBorder;
1320 m_defaultHeight = size.y + kwxMacToolBorder;
f3a65c3e 1321
e56d2520
SC
1322#if wxMAC_USE_NATIVE_TOOLBAR
1323 if (m_macHIToolbarRef != NULL)
1324 {
1325 int maxs = wxMax( size.x, size.y );
3b6a1179 1326 HIToolbarDisplaySize sizeSpec;
328f4fee 1327 if ( maxs > 32 )
3b6a1179 1328 sizeSpec = kHIToolbarDisplaySizeNormal;
00a7bd85 1329 else if ( maxs > 24 )
3b6a1179 1330 sizeSpec = kHIToolbarDisplaySizeDefault;
328f4fee 1331 else
3b6a1179 1332 sizeSpec = kHIToolbarDisplaySizeSmall;
f3a65c3e 1333
e56d2520
SC
1334 HIToolbarSetDisplaySize( (HIToolbarRef) m_macHIToolbarRef, sizeSpec );
1335 }
1336#endif
e9576ca5
SC
1337}
1338
e9576ca5
SC
1339// The button size is bigger than the bitmap size
1340wxSize wxToolBar::GetToolSize() const
1341{
ee799df7 1342 return wxSize(m_defaultWidth + kwxMacToolBorder, m_defaultHeight + kwxMacToolBorder);
e9576ca5
SC
1343}
1344
37e2cb08 1345void wxToolBar::SetRows(int nRows)
e9576ca5 1346{
e56d2520
SC
1347 // avoid resizing the frame uselessly
1348 if ( nRows != m_maxRows )
e56d2520 1349 m_maxRows = nRows;
e9576ca5
SC
1350}
1351
f3a65c3e 1352void wxToolBar::MacSuperChangedPosition()
c257d44d 1353{
e56d2520 1354 wxWindow::MacSuperChangedPosition();
991f71dc 1355
e56d2520
SC
1356#if wxMAC_USE_NATIVE_TOOLBAR
1357 if (! m_macUsesNativeToolbar )
e56d2520 1358 Realize();
991f71dc 1359#else
3025abca 1360
991f71dc
DS
1361 Realize();
1362#endif
c257d44d
SC
1363}
1364
bbd321ff
RD
1365void wxToolBar::SetToolNormalBitmap( int id, const wxBitmap& bitmap )
1366{
1367 wxToolBarTool* tool = wx_static_cast(wxToolBarTool*, FindById(id));
1368 if ( tool )
1369 {
1370 wxCHECK_RET( tool->IsButton(), wxT("Can only set bitmap on button tools."));
1371
1372 tool->SetNormalBitmap(bitmap);
1373
1374 // a side-effect of the UpdateToggleImage function is that it always changes the bitmap used on the button.
1375 tool->UpdateToggleImage( tool->CanBeToggled() && tool->IsToggled() );
cdb11cb9 1376 }
bbd321ff
RD
1377}
1378
1379void wxToolBar::SetToolDisabledBitmap( int id, const wxBitmap& bitmap )
1380{
1381 wxToolBarTool* tool = wx_static_cast(wxToolBarTool*, FindById(id));
1382 if ( tool )
1383 {
1384 wxCHECK_RET( tool->IsButton(), wxT("Can only set bitmap on button tools."));
1385
1386 tool->SetDisabledBitmap(bitmap);
cdb11cb9 1387
bbd321ff 1388 // TODO: what to do for this one?
cdb11cb9 1389 }
bbd321ff
RD
1390}
1391
37e2cb08 1392wxToolBarToolBase *wxToolBar::FindToolForPosition(wxCoord x, wxCoord y) const
e9576ca5 1393{
3025abca 1394 wxToolBarTool *tool;
affd2611 1395 wxToolBarToolsList::compatibility_iterator node = m_tools.GetFirst();
35f94ffd 1396 while ( node )
e044f600 1397 {
3025abca 1398 tool = (wxToolBarTool *)node->GetData();
e56d2520 1399 if (tool != NULL)
e044f600 1400 {
e56d2520
SC
1401 wxRect2DInt r( tool->GetPosition(), tool->GetSize() );
1402 if ( r.Contains( wxPoint( x, y ) ) )
1403 return tool;
e044f600 1404 }
bfe9ffbc
SC
1405
1406 node = node->GetNext();
e044f600 1407 }
37e2cb08 1408
3025abca 1409 return (wxToolBarToolBase*)NULL;
e9576ca5
SC
1410}
1411
2f1ae414
SC
1412wxString wxToolBar::MacGetToolTipString( wxPoint &pt )
1413{
3b6a1179 1414 wxToolBarToolBase *tool = FindToolForPosition( pt.x, pt.y );
e56d2520 1415 if ( tool != NULL )
3b6a1179 1416 return tool->GetShortHelp();
e56d2520 1417
3b6a1179 1418 return wxEmptyString;
2f1ae414
SC
1419}
1420
37e2cb08 1421void wxToolBar::DoEnableTool(wxToolBarToolBase *t, bool enable)
e9576ca5 1422{
e56d2520 1423 if ( t != NULL )
3b6a1179 1424 ((wxToolBarTool*)t)->DoEnable( enable );
e9576ca5
SC
1425}
1426
37e2cb08 1427void wxToolBar::DoToggleTool(wxToolBarToolBase *t, bool toggle)
e9576ca5 1428{
e044f600 1429 wxToolBarTool *tool = (wxToolBarTool *)t;
e56d2520
SC
1430 if ( ( tool != NULL ) && tool->IsButton() )
1431 tool->UpdateToggleImage( toggle );
37e2cb08 1432}
7c551d95 1433
3b6a1179 1434bool wxToolBar::DoInsertTool(size_t WXUNUSED(pos), wxToolBarToolBase *toolBase)
37e2cb08 1435{
3b6a1179 1436 wxToolBarTool *tool = wx_static_cast( wxToolBarTool*, toolBase );
e56d2520
SC
1437 if (tool == NULL)
1438 return false;
1439
1440 WindowRef window = (WindowRef) MacGetTopLevelWindowRef();
1441 wxSize toolSize = GetToolSize();
3b6a1179 1442 Rect toolrect = { 0, 0, toolSize.y, toolSize.x };
e56d2520
SC
1443 ControlRef controlHandle = NULL;
1444 OSStatus err = 0;
bbd321ff 1445 tool->Attach( this );
be5fe3aa 1446
cdb11cb9 1447#if wxMAC_USE_NATIVE_TOOLBAR
6239ee05
SC
1448 wxString label = tool->GetLabel();
1449 if (m_macHIToolbarRef && !label.empty() )
1450 {
1451 // strip mnemonics from the label for compatibility
1452 // with the usual labels in wxStaticText sense
1453 label = wxStripMenuCodes(label);
1454 }
1455#endif // wxMAC_USE_NATIVE_TOOLBAR
cdb11cb9 1456
e56d2520 1457 switch (tool->GetStyle())
be5fe3aa 1458 {
3b6a1179 1459 case wxTOOL_STYLE_SEPARATOR:
be5fe3aa 1460 {
e56d2520
SC
1461 wxASSERT( tool->GetControlHandle() == NULL );
1462 toolSize.x /= 4;
1463 toolSize.y /= 4;
be5fe3aa 1464 if ( GetWindowStyleFlag() & wxTB_VERTICAL )
e56d2520 1465 toolrect.bottom = toolSize.y;
be5fe3aa 1466 else
e56d2520
SC
1467 toolrect.right = toolSize.x;
1468
be5fe3aa 1469 // in flat style we need a visual separator
991f71dc 1470#if wxMAC_USE_NATIVE_TOOLBAR
079b2f6b
JS
1471 if (m_macHIToolbarRef != NULL)
1472 {
980807d1 1473 HIToolbarItemRef item;
079b2f6b
JS
1474 err = HIToolbarItemCreate(
1475 kHIToolbarSeparatorIdentifier,
1476 kHIToolbarItemCantBeRemoved | kHIToolbarItemIsSeparator | kHIToolbarItemAllowDuplicates,
1477 &item );
1478 if (err == noErr)
1479 tool->SetToolbarItemRef( item );
1480 }
1481 else
1482 err = noErr;
cdb11cb9 1483#endif // wxMAC_USE_NATIVE_TOOLBAR
991f71dc 1484
e56d2520
SC
1485 CreateSeparatorControl( window, &toolrect, &controlHandle );
1486 tool->SetControlHandle( controlHandle );
be5fe3aa 1487 }
e56d2520
SC
1488 break;
1489
3b6a1179 1490 case wxTOOL_STYLE_BUTTON:
be5fe3aa 1491 {
3b6a1179
DS
1492 wxASSERT( tool->GetControlHandle() == NULL );
1493 ControlButtonContentInfo info;
6239ee05 1494 wxMacCreateBitmapButton( &info, tool->GetNormalBitmap() );
f3a65c3e 1495
df7998fc 1496 if ( UMAGetSystemVersion() >= 0x1000)
3b6a1179 1497 {
6239ee05
SC
1498 // contrary to the docs this control only works with iconrefs
1499 ControlButtonContentInfo info;
1500 wxMacCreateBitmapButton( &info, tool->GetNormalBitmap(), kControlContentIconRef );
3b6a1179 1501 CreateIconControl( window, &toolrect, &info, false, &controlHandle );
6239ee05 1502 wxMacReleaseBitmapButton( &info );
3b6a1179 1503 }
df7998fc
VZ
1504 else
1505 {
3b6a1179 1506 SInt16 behaviour = kControlBehaviorOffsetContents;
df7998fc 1507 if ( tool->CanBeToggled() )
3b6a1179
DS
1508 behaviour |= kControlBehaviorToggles;
1509 err = CreateBevelButtonControl( window,
1510 &toolrect, CFSTR(""), kControlBevelButtonNormalBevel,
1511 behaviour, &info, 0, 0, 0, &controlHandle );
df7998fc 1512 }
e56d2520
SC
1513
1514#if wxMAC_USE_NATIVE_TOOLBAR
079b2f6b 1515 if (m_macHIToolbarRef != NULL)
e56d2520 1516 {
6239ee05
SC
1517 HIToolbarItemRef item;
1518 wxString labelStr = wxString::Format(wxT("%p"), tool);
079b2f6b
JS
1519 err = HIToolbarItemCreate(
1520 wxMacCFStringHolder(labelStr, wxFont::GetDefaultEncoding()),
1521 kHIToolbarItemCantBeRemoved | kHIToolbarItemAnchoredLeft | kHIToolbarItemAllowDuplicates, &item );
1522 if (err == noErr)
1523 {
6239ee05
SC
1524 ControlButtonContentInfo info2;
1525 wxMacCreateBitmapButton( &info2, tool->GetNormalBitmap(), kControlContentCGImageRef);
1526
079b2f6b
JS
1527 InstallEventHandler(
1528 HIObjectGetEventTarget(item), GetwxMacToolBarEventHandlerUPP(),
1529 GetEventTypeCount(toolBarEventList), toolBarEventList, tool, NULL );
6239ee05
SC
1530 HIToolbarItemSetLabel( item, wxMacCFStringHolder(label, m_font.GetEncoding()) );
1531 HIToolbarItemSetImage( item, info2.u.imageRef );
079b2f6b
JS
1532 HIToolbarItemSetCommandID( item, kHIToolbarCommandPressAction );
1533 tool->SetToolbarItemRef( item );
6239ee05
SC
1534
1535 wxMacReleaseBitmapButton( &info2 );
079b2f6b 1536 }
e56d2520 1537 }
079b2f6b
JS
1538 else
1539 err = noErr;
cdb11cb9 1540#endif // wxMAC_USE_NATIVE_TOOLBAR
e56d2520 1541
3b6a1179 1542 wxMacReleaseBitmapButton( &info );
3025abca 1543
991f71dc 1544#if 0
3b6a1179
DS
1545 SetBevelButtonTextPlacement( m_controlHandle, kControlBevelButtonPlaceBelowGraphic );
1546 UMASetControlTitle( m_controlHandle, label, wxFont::GetDefaultEncoding() );
991f71dc 1547#endif
f3a65c3e 1548
3b6a1179
DS
1549 InstallControlEventHandler(
1550 (ControlRef) controlHandle, GetwxMacToolBarToolEventHandlerUPP(),
e56d2520 1551 GetEventTypeCount(eventList), eventList, tool, NULL );
be5fe3aa 1552
e56d2520 1553 tool->SetControlHandle( controlHandle );
be5fe3aa 1554 }
e56d2520
SC
1555 break;
1556
3b6a1179 1557 case wxTOOL_STYLE_CONTROL:
3b6a1179 1558
6d4835dc 1559#if wxMAC_USE_NATIVE_TOOLBAR
079b2f6b 1560 if (m_macHIToolbarRef != NULL)
e56d2520 1561 {
d5c87edd 1562 wxCHECK_MSG( tool->GetControl(), false, _T("control must be non-NULL") );
6239ee05 1563 HIToolbarItemRef item;
6d4835dc
SC
1564 HIViewRef viewRef = (HIViewRef) tool->GetControl()->GetHandle() ;
1565 CFDataRef data = CFDataCreate( kCFAllocatorDefault , (UInt8*) &viewRef , sizeof(viewRef) ) ;
cdb11cb9
VZ
1566 err = HIToolbarCreateItemWithIdentifier((HIToolbarRef) m_macHIToolbarRef,kControlToolbarItemClassID,
1567 data , &item ) ;
6d4835dc
SC
1568
1569 if (err == noErr)
e56d2520 1570 {
e56d2520 1571 tool->SetToolbarItemRef( item );
e56d2520 1572 }
6d4835dc
SC
1573 CFRelease( data ) ;
1574 }
079b2f6b
JS
1575 else
1576 {
1577 err = noErr;
1578 break;
1579 }
e56d2520 1580#else
6d4835dc 1581 // right now there's nothing to do here
e56d2520
SC
1582#endif
1583 break;
1584
3b6a1179 1585 default:
e56d2520 1586 break;
be5fe3aa 1587 }
f3a65c3e 1588
991f71dc 1589 if ( err == noErr )
be5fe3aa 1590 {
e56d2520
SC
1591 if ( controlHandle )
1592 {
1593 ControlRef container = (ControlRef) GetHandle();
3b6a1179 1594 wxASSERT_MSG( container != NULL, wxT("No valid Mac container control") );
be5fe3aa 1595
e56d2520
SC
1596 UMAShowControl( controlHandle );
1597 ::EmbedControl( controlHandle, container );
1598 }
1599
1600 if ( tool->CanBeToggled() && tool->IsToggled() )
1601 tool->UpdateToggleImage( true );
be5fe3aa 1602
e56d2520 1603 // nothing special to do here - we relayout in Realize() later
e56d2520
SC
1604 InvalidateBestSize();
1605 }
1606 else
be5fe3aa 1607 {
767e0835 1608 wxFAIL_MSG( wxString::Format( wxT("wxToolBar::DoInsertTool - failure [%ld]"), (long)err ) );
be5fe3aa 1609 }
f3a65c3e 1610
991f71dc 1611 return (err == noErr);
37e2cb08 1612}
e9576ca5 1613
5115c51a 1614void wxToolBar::DoSetToggle(wxToolBarToolBase *WXUNUSED(tool), bool WXUNUSED(toggle))
37e2cb08 1615{
3b6a1179 1616 wxFAIL_MSG( wxT("not implemented") );
e9576ca5
SC
1617}
1618
be5fe3aa 1619bool wxToolBar::DoDeleteTool(size_t WXUNUSED(pos), wxToolBarToolBase *toolbase)
37e2cb08 1620{
3b6a1179 1621 wxToolBarTool* tool = wx_static_cast( wxToolBarTool*, toolbase );
affd2611 1622 wxToolBarToolsList::compatibility_iterator node;
bfe9ffbc
SC
1623 for ( node = m_tools.GetFirst(); node; node = node->GetNext() )
1624 {
1625 wxToolBarToolBase *tool2 = node->GetData();
1626 if ( tool2 == tool )
1627 {
1628 // let node point to the next node in the list
1629 node = node->GetNext();
1630
1631 break;
1632 }
1633 }
1634
3b6a1179 1635 wxSize sz = ((wxToolBarTool*)tool)->GetSize();
bfe9ffbc
SC
1636
1637 tool->Detach();
df7998fc
VZ
1638
1639#if wxMAC_USE_NATIVE_TOOLBAR
1640 CFIndex removeIndex = tool->GetIndex();
dcae64c2 1641#endif
bfe9ffbc 1642
507d5748 1643#if wxMAC_USE_NATIVE_TOOLBAR
079b2f6b 1644 if (m_macHIToolbarRef != NULL)
507d5748 1645 {
079b2f6b
JS
1646 if ( removeIndex != -1 && m_macHIToolbarRef )
1647 {
1648 HIToolbarRemoveItemAtIndex( (HIToolbarRef) m_macHIToolbarRef, removeIndex );
1649 tool->SetIndex( -1 );
1650 }
507d5748
SC
1651 }
1652#endif
488b2c29
SC
1653 switch ( tool->GetStyle() )
1654 {
1655 case wxTOOL_STYLE_CONTROL:
507d5748 1656 if ( tool->GetControl() )
be5fe3aa 1657 tool->GetControl()->Destroy();
488b2c29
SC
1658 break;
1659
1660 case wxTOOL_STYLE_BUTTON:
1661 case wxTOOL_STYLE_SEPARATOR:
507d5748 1662 // nothing special
488b2c29 1663 break;
e56d2520
SC
1664
1665 default:
1666 break;
488b2c29 1667 }
507d5748 1668 tool->ClearControl();
488b2c29 1669
bfe9ffbc 1670 // and finally reposition all the controls after this one
f3a65c3e 1671
3b6a1179 1672 for ( /* node -> first after deleted */; node; node = node->GetNext() )
bfe9ffbc
SC
1673 {
1674 wxToolBarTool *tool2 = (wxToolBarTool*) node->GetData();
3b6a1179 1675 wxPoint pt = tool2->GetPosition();
bfe9ffbc
SC
1676
1677 if ( GetWindowStyleFlag() & wxTB_VERTICAL )
3b6a1179 1678 pt.y -= sz.y;
bfe9ffbc 1679 else
3b6a1179 1680 pt.x -= sz.x;
e56d2520 1681
3b6a1179 1682 tool2->SetPosition( pt );
df7998fc 1683
2c1dbc95 1684#if wxMAC_USE_NATIVE_TOOLBAR
079b2f6b
JS
1685 if (m_macHIToolbarRef != NULL)
1686 {
1687 if ( removeIndex != -1 && tool2->GetIndex() > removeIndex )
1688 tool2->SetIndex( tool2->GetIndex() - 1 );
1689 }
2c1dbc95 1690#endif
bfe9ffbc 1691 }
f3a65c3e 1692
9f884528 1693 InvalidateBestSize();
991f71dc 1694
3b6a1179 1695 return true;
37e2cb08 1696}
2f1ae414
SC
1697
1698void wxToolBar::OnPaint(wxPaintEvent& event)
1699{
e56d2520
SC
1700#if wxMAC_USE_NATIVE_TOOLBAR
1701 if ( m_macUsesNativeToolbar )
1702 {
dcae64c2
DS
1703 event.Skip(true);
1704 return;
e56d2520
SC
1705 }
1706#endif
f3a65c3e 1707
3b6a1179 1708 wxPaintDC dc(this);
ddc548ec 1709
3b6a1179
DS
1710 int w, h;
1711 GetSize( &w, &h );
991f71dc 1712
dcae64c2 1713 bool drawMetalTheme = MacGetTopLevelWindow()->MacGetMetalAppearance();
dcae64c2 1714
9d463591 1715 if ( !drawMetalTheme )
ddc548ec 1716 {
dcae64c2
DS
1717 HIThemePlacardDrawInfo info;
1718 memset( &info, 0, sizeof(info) );
1719 info.version = 0;
1720 info.state = IsEnabled() ? kThemeStateActive : kThemeStateInactive;
1721
1722 CGContextRef cgContext = (CGContextRef) MacGetCGContextRef();
1723 HIRect rect = CGRectMake( 0, 0, w, h );
1724 HIThemeDrawPlacard( &rect, &info, cgContext, kHIThemeOrientationNormal );
ddc548ec
SC
1725 }
1726 else
1727 {
1728 // leave the background as it is (striped or metal)
1729 }
991f71dc 1730
dcae64c2 1731 event.Skip();
2f1ae414 1732}
895f5af7 1733
519cb848 1734#endif // wxUSE_TOOLBAR