1 /////////////////////////////////////////////////////////////////////////////
2 // Name: src/mac/carbon/window.cpp
3 // Purpose: wxWindowMac
4 // Author: Stefan Csomor
8 // Copyright: (c) Stefan Csomor
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
12 #include "wx/wxprec.h"
14 #include "wx/window.h"
23 #include "wx/dcclient.h"
24 #include "wx/button.h"
26 #include "wx/dialog.h"
27 #include "wx/settings.h"
28 #include "wx/msgdlg.h"
29 #include "wx/scrolbar.h"
30 #include "wx/statbox.h"
31 #include "wx/textctrl.h"
32 #include "wx/toolbar.h"
33 #include "wx/layout.h"
34 #include "wx/statusbr.h"
35 #include "wx/menuitem.h"
36 #include "wx/treectrl.h"
37 #include "wx/listctrl.h"
40 #include "wx/tooltip.h"
41 #include "wx/spinctrl.h"
42 #include "wx/geometry.h"
45 #include "wx/listctrl.h"
49 #include "wx/treectrl.h"
56 #if wxUSE_DRAG_AND_DROP
60 #include "wx/mac/uma.h"
62 #define MAC_SCROLLBAR_SIZE 15
63 #define MAC_SMALL_SCROLLBAR_SIZE 11
67 #include <ToolUtils.h>
69 #include <MacTextEditor.h>
72 #if TARGET_API_MAC_OSX
74 #include <HIToolbox/HIView.h>
80 #ifdef __WXUNIVERSAL__
81 IMPLEMENT_ABSTRACT_CLASS(wxWindowMac
, wxWindowBase
)
83 IMPLEMENT_DYNAMIC_CLASS(wxWindow
, wxWindowBase
)
86 BEGIN_EVENT_TABLE(wxWindowMac
, wxWindowBase
)
87 EVT_NC_PAINT(wxWindowMac::OnNcPaint
)
88 EVT_ERASE_BACKGROUND(wxWindowMac::OnEraseBackground
)
89 #if TARGET_API_MAC_OSX
90 EVT_PAINT(wxWindowMac::OnPaint
)
92 EVT_SET_FOCUS(wxWindowMac::OnSetFocus
)
93 EVT_KILL_FOCUS(wxWindowMac::OnSetFocus
)
94 EVT_MOUSE_EVENTS(wxWindowMac::OnMouseEvent
)
97 #define wxMAC_DEBUG_REDRAW 0
98 #ifndef wxMAC_DEBUG_REDRAW
99 #define wxMAC_DEBUG_REDRAW 0
102 // ---------------------------------------------------------------------------
103 // Utility Routines to move between different coordinate systems
104 // ---------------------------------------------------------------------------
107 * Right now we have the following setup :
108 * a border that is not part of the native control is always outside the
109 * control's border (otherwise we loose all native intelligence, future ways
110 * may be to have a second embedding control responsible for drawing borders
111 * and backgrounds eventually)
112 * so all this border calculations have to be taken into account when calling
113 * native methods or getting native oriented data
114 * so we have three coordinate systems here
115 * wx client coordinates
116 * wx window coordinates (including window frames)
121 // originating from native control
125 void wxMacNativeToWindow( const wxWindow
* window
, RgnHandle handle
)
127 OffsetRgn( handle
, window
->MacGetLeftBorderSize() , window
->MacGetTopBorderSize() ) ;
130 void wxMacNativeToWindow( const wxWindow
* window
, Rect
*rect
)
132 OffsetRect( rect
, window
->MacGetLeftBorderSize() , window
->MacGetTopBorderSize() ) ;
136 // directed towards native control
139 void wxMacWindowToNative( const wxWindow
* window
, RgnHandle handle
)
141 OffsetRgn( handle
, -window
->MacGetLeftBorderSize() , -window
->MacGetTopBorderSize() );
144 void wxMacWindowToNative( const wxWindow
* window
, Rect
*rect
)
146 OffsetRect( rect
, -window
->MacGetLeftBorderSize() , -window
->MacGetTopBorderSize() ) ;
149 // ---------------------------------------------------------------------------
151 // ---------------------------------------------------------------------------
153 #if TARGET_API_MAC_OSX
155 #if MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_3
158 kEventControlVisibilityChanged
= 157
164 static const EventTypeSpec eventList
[] =
166 { kEventClassCommand
, kEventProcessCommand
} ,
167 { kEventClassCommand
, kEventCommandUpdateStatus
} ,
169 { kEventClassControl
, kEventControlGetClickActivation
} ,
170 { kEventClassControl
, kEventControlHit
} ,
172 { kEventClassTextInput
, kEventTextInputUnicodeForKeyEvent
} ,
173 { kEventClassTextInput
, kEventTextInputUpdateActiveInputArea
} ,
175 { kEventClassControl
, kEventControlDraw
} ,
176 #if TARGET_API_MAC_OSX
177 { kEventClassControl
, kEventControlVisibilityChanged
} ,
178 { kEventClassControl
, kEventControlEnabledStateChanged
} ,
179 { kEventClassControl
, kEventControlHiliteChanged
} ,
181 { kEventClassControl
, kEventControlActivate
} ,
182 { kEventClassControl
, kEventControlDeactivate
} ,
184 { kEventClassControl
, kEventControlSetFocusPart
} ,
186 { kEventClassService
, kEventServiceGetTypes
},
187 { kEventClassService
, kEventServiceCopy
},
188 { kEventClassService
, kEventServicePaste
},
190 // { kEventClassControl , kEventControlInvalidateForSizeChange } , // 10.3 only
191 // { kEventClassControl , kEventControlBoundsChanged } ,
194 static pascal OSStatus
wxMacWindowControlEventHandler( EventHandlerCallRef handler
, EventRef event
, void *data
)
196 OSStatus result
= eventNotHandledErr
;
198 wxMacCarbonEvent
cEvent( event
) ;
200 ControlRef controlRef
;
201 wxWindowMac
* thisWindow
= (wxWindowMac
*) data
;
203 cEvent
.GetParameter( kEventParamDirectObject
, &controlRef
) ;
205 switch ( GetEventKind( event
) )
207 #if TARGET_API_MAC_OSX
208 case kEventControlDraw
:
210 RgnHandle updateRgn
= NULL
;
211 RgnHandle allocatedRgn
= NULL
;
212 wxRegion visRegion
= thisWindow
->MacGetVisibleRegion() ;
214 if ( cEvent
.GetParameter
<RgnHandle
>(kEventParamRgnHandle
, &updateRgn
) != noErr
)
216 updateRgn
= (RgnHandle
) visRegion
.GetWXHRGN() ;
220 if ( thisWindow
->MacGetLeftBorderSize() != 0 || thisWindow
->MacGetTopBorderSize() != 0 )
222 // as this update region is in native window locals we must adapt it to wx window local
223 allocatedRgn
= NewRgn() ;
224 CopyRgn( updateRgn
, allocatedRgn
) ;
226 // hide the given region by the new region that must be shifted
227 wxMacNativeToWindow( thisWindow
, allocatedRgn
) ;
228 updateRgn
= allocatedRgn
;
233 GetRegionBounds( updateRgn
, &rgnBounds
) ;
235 #if wxMAC_DEBUG_REDRAW
236 if ( thisWindow
->MacIsUserPane() )
238 static float color
= 0.5 ;
241 CGContextRef cgContext
= cEvent
.GetParameter
<CGContextRef
>(kEventParamCGContextRef
) ;
243 HIViewGetBounds( controlRef
, &bounds
);
244 CGContextSetRGBFillColor( cgContext
, channel
== 0 ? color
: 0.5 ,
245 channel
== 1 ? color
: 0.5 , channel
== 2 ? color
: 0.5 , 1 );
246 CGContextFillRect( cgContext
, bounds
);
259 #if wxMAC_USE_CORE_GRAPHICS
260 bool created
= false ;
261 CGContextRef cgContext
= NULL
;
262 OSStatus err
= cEvent
.GetParameter
<CGContextRef
>(kEventParamCGContextRef
, &cgContext
) ;
263 wxASSERT_MSG( err
== noErr
, wxT("Unable to retrieve CGContextRef") ) ;
264 thisWindow
->MacSetCGContextRef( cgContext
) ;
267 wxMacCGContextStateSaver
sg( cgContext
) ;
270 wxWindow
* iter
= thisWindow
;
273 alpha
*= (float) iter
->GetTransparent()/255.0 ;
274 if ( iter
->IsTopLevel() )
277 iter
= iter
->GetParent() ;
280 CGContextSetAlpha( cgContext
, alpha
) ;
282 if ( thisWindow
->MacDoRedraw( updateRgn
, cEvent
.GetTicks() ) )
285 #if wxMAC_USE_CORE_GRAPHICS
286 thisWindow
->MacSetCGContextRef( NULL
) ;
290 CGContextRelease( cgContext
) ;
295 DisposeRgn( allocatedRgn
) ;
299 case kEventControlVisibilityChanged
:
300 thisWindow
->MacVisibilityChanged() ;
303 case kEventControlEnabledStateChanged
:
304 thisWindow
->MacEnabledStateChanged() ;
307 case kEventControlHiliteChanged
:
308 thisWindow
->MacHiliteChanged() ;
311 case kEventControlActivate
:
312 case kEventControlDeactivate
:
313 // FIXME: we should have a virtual function for this!
315 if ( thisWindow
->IsKindOf( CLASSINFO( wxTreeCtrl
) ) )
316 thisWindow
->Refresh();
319 if ( thisWindow
->IsKindOf( CLASSINFO( wxListCtrl
) ) )
320 thisWindow
->Refresh();
323 #endif // TARGET_API_MAC_OSX
325 // we emulate this event under Carbon CFM
326 case kEventControlSetFocusPart
:
328 Boolean focusEverything
= false ;
329 ControlPartCode controlPart
= cEvent
.GetParameter
<ControlPartCode
>(kEventParamControlPart
, typeControlPartCode
);
332 if ( cEvent
.GetParameter
<Boolean
>(kEventParamControlFocusEverything
, &focusEverything
) == noErr
)
337 if ( thisWindow
->MacIsUserPane() )
340 if ( controlPart
== kControlFocusNoPart
)
343 if ( thisWindow
->GetCaret() )
344 thisWindow
->GetCaret()->OnKillFocus();
347 static bool inKillFocusEvent
= false ;
349 if ( !inKillFocusEvent
)
351 inKillFocusEvent
= true ;
352 wxFocusEvent
event( wxEVT_KILL_FOCUS
, thisWindow
->GetId());
353 event
.SetEventObject(thisWindow
);
354 thisWindow
->GetEventHandler()->ProcessEvent(event
) ;
355 inKillFocusEvent
= false ;
360 // panel wants to track the window which was the last to have focus in it
361 wxChildFocusEvent
eventFocus(thisWindow
);
362 thisWindow
->GetEventHandler()->ProcessEvent(eventFocus
);
365 if ( thisWindow
->GetCaret() )
366 thisWindow
->GetCaret()->OnSetFocus();
369 wxFocusEvent
event(wxEVT_SET_FOCUS
, thisWindow
->GetId());
370 event
.SetEventObject(thisWindow
);
371 thisWindow
->GetEventHandler()->ProcessEvent(event
) ;
376 case kEventControlHit
:
377 result
= thisWindow
->MacControlHit( handler
, event
) ;
380 case kEventControlGetClickActivation
:
382 // fix to always have a proper activation for DataBrowser controls (stay in bkgnd otherwise)
383 WindowRef owner
= cEvent
.GetParameter
<WindowRef
>(kEventParamWindowRef
);
384 if ( !IsWindowActive(owner
) )
386 cEvent
.SetParameter(kEventParamClickActivation
,(UInt32
) kActivateAndIgnoreClick
) ;
399 static pascal OSStatus
wxMacWindowServiceEventHandler( EventHandlerCallRef handler
, EventRef event
, void *data
)
401 OSStatus result
= eventNotHandledErr
;
403 wxMacCarbonEvent
cEvent( event
) ;
405 ControlRef controlRef
;
406 wxWindowMac
* thisWindow
= (wxWindowMac
*) data
;
407 wxTextCtrl
* textCtrl
= wxDynamicCast( thisWindow
, wxTextCtrl
) ;
408 cEvent
.GetParameter( kEventParamDirectObject
, &controlRef
) ;
410 switch ( GetEventKind( event
) )
412 case kEventServiceGetTypes
:
416 textCtrl
->GetSelection( &from
, &to
) ;
418 CFMutableArrayRef copyTypes
= 0 , pasteTypes
= 0;
420 copyTypes
= cEvent
.GetParameter
< CFMutableArrayRef
>( kEventParamServiceCopyTypes
, typeCFMutableArrayRef
) ;
421 if ( textCtrl
->IsEditable() )
422 pasteTypes
= cEvent
.GetParameter
< CFMutableArrayRef
>( kEventParamServicePasteTypes
, typeCFMutableArrayRef
) ;
424 static const OSType textDataTypes
[] = { kTXNTextData
/* , 'utxt', 'PICT', 'MooV', 'AIFF' */ };
425 for ( size_t i
= 0 ; i
< WXSIZEOF(textDataTypes
) ; ++i
)
427 CFStringRef typestring
= CreateTypeStringWithOSType(textDataTypes
[i
]);
431 CFArrayAppendValue(copyTypes
, typestring
) ;
433 CFArrayAppendValue(pasteTypes
, typestring
) ;
435 CFRelease( typestring
) ;
443 case kEventServiceCopy
:
448 textCtrl
->GetSelection( &from
, &to
) ;
449 wxString val
= textCtrl
->GetValue() ;
450 val
= val
.Mid( from
, to
- from
) ;
451 ScrapRef scrapRef
= cEvent
.GetParameter
< ScrapRef
> ( kEventParamScrapRef
, typeScrapRef
) ;
452 verify_noerr( ClearScrap( &scrapRef
) ) ;
453 verify_noerr( PutScrapFlavor( scrapRef
, kTXNTextData
, 0 , val
.length() , val
.c_str() ) ) ;
458 case kEventServicePaste
:
461 ScrapRef scrapRef
= cEvent
.GetParameter
< ScrapRef
> ( kEventParamScrapRef
, typeScrapRef
) ;
462 Size textSize
, pastedSize
;
463 verify_noerr( GetScrapFlavorSize(scrapRef
, kTXNTextData
, &textSize
) ) ;
465 char *content
= new char[textSize
] ;
466 GetScrapFlavorData(scrapRef
, kTXNTextData
, &pastedSize
, content
);
467 content
[textSize
- 1] = 0 ;
470 textCtrl
->WriteText( wxString( content
, wxConvLocal
) );
472 textCtrl
->WriteText( wxString( content
) ) ;
487 pascal OSStatus
wxMacUnicodeTextEventHandler( EventHandlerCallRef handler
, EventRef event
, void *data
)
489 OSStatus result
= eventNotHandledErr
;
490 wxWindowMac
* focus
= (wxWindowMac
*) data
;
492 wchar_t* uniChars
= NULL
;
493 UInt32 when
= EventTimeToTicks( GetEventTime( event
) ) ;
495 UniChar
* charBuf
= NULL
;
496 ByteCount dataSize
= 0 ;
499 if ( GetEventParameter( event
, kEventParamTextInputSendText
, typeUnicodeText
, NULL
, 0 , &dataSize
, NULL
) == noErr
)
501 numChars
= dataSize
/ sizeof( UniChar
) + 1;
504 if ( (size_t) numChars
* 2 > sizeof(buf
) )
505 charBuf
= new UniChar
[ numChars
] ;
509 uniChars
= new wchar_t[ numChars
] ;
510 GetEventParameter( event
, kEventParamTextInputSendText
, typeUnicodeText
, NULL
, dataSize
, NULL
, charBuf
) ;
511 charBuf
[ numChars
- 1 ] = 0;
512 #if SIZEOF_WCHAR_T == 2
513 uniChars
= (wchar_t*) charBuf
;
514 /* memcpy( uniChars , charBuf , numChars * 2 ) ;*/ // is there any point in copying charBuf over itself? (in fact, memcpy isn't even guaranteed to work correctly if the source and destination ranges overlap...)
516 // the resulting string will never have more chars than the utf16 version, so this is safe
517 wxMBConvUTF16 converter
;
518 numChars
= converter
.MB2WC( uniChars
, (const char*)charBuf
, numChars
) ;
522 switch ( GetEventKind( event
) )
524 case kEventTextInputUpdateActiveInputArea
:
526 // An IME input event may return several characters, but we need to send one char at a time to
528 for (int pos
=0 ; pos
< numChars
; pos
++)
530 WXEVENTREF formerEvent
= wxTheApp
->MacGetCurrentEvent() ;
531 WXEVENTHANDLERCALLREF formerHandler
= wxTheApp
->MacGetCurrentEventHandlerCallRef() ;
532 wxTheApp
->MacSetCurrentEvent( event
, handler
) ;
534 UInt32 message
= uniChars
[pos
] < 128 ? (char)uniChars
[pos
] : '?';
536 NB: faking a charcode here is problematic. The kEventTextInputUpdateActiveInputArea event is sent
537 multiple times to update the active range during inline input, so this handler will often receive
538 uncommited text, which should usually not trigger side effects. It might be a good idea to check the
539 kEventParamTextInputSendFixLen parameter and verify if input is being confirmed (see CarbonEvents.h).
540 On the other hand, it can be useful for some applications to react to uncommitted text (for example,
541 to update a status display), as long as it does not disrupt the inline input session. Ideally, wx
542 should add new event types to support advanced text input. For now, I would keep things as they are.
544 However, the code that was being used caused additional problems:
545 UInt32 message = (0 << 8) + ((char)uniChars[pos] );
546 Since it simply truncated the unichar to the last byte, it ended up causing weird bugs with inline
547 input, such as switching to another field when one attempted to insert the character U+4E09 (the kanji
548 for "three"), because it was truncated to 09 (kTabCharCode), which was later "converted" to WXK_TAB
549 (still 09) in wxMacTranslateKey; or triggering the default button when one attempted to insert U+840D
550 (the kanji for "name"), which got truncated to 0D and interpreted as a carriage return keypress.
551 Note that even single-byte characters could have been misinterpreted, since MacRoman charcodes only
552 overlap with Unicode within the (7-bit) ASCII range.
553 But simply passing a NUL charcode would disable text updated events, because wxTextCtrl::OnChar checks
554 for codes within a specific range. Therefore I went for the solution seen above, which keeps ASCII
555 characters as they are and replaces the rest with '?', ensuring that update events are triggered.
556 It would be better to change wxTextCtrl::OnChar to look at the actual unicode character instead, but
557 I don't have time to look into that right now.
560 if ( wxTheApp
->MacSendCharEvent(
561 focus
, message
, 0 , when
, 0 , 0 , uniChars
[pos
] ) )
566 wxTheApp
->MacSetCurrentEvent( formerEvent
, formerHandler
) ;
570 case kEventTextInputUnicodeForKeyEvent
:
572 UInt32 keyCode
, modifiers
;
575 unsigned char charCode
;
577 GetEventParameter( event
, kEventParamTextInputSendKeyboardEvent
, typeEventRef
, NULL
, sizeof(rawEvent
), NULL
, &rawEvent
) ;
578 GetEventParameter( rawEvent
, kEventParamKeyMacCharCodes
, typeChar
, NULL
, sizeof(char), NULL
, &charCode
);
579 GetEventParameter( rawEvent
, kEventParamKeyCode
, typeUInt32
, NULL
, sizeof(UInt32
), NULL
, &keyCode
);
580 GetEventParameter( rawEvent
, kEventParamKeyModifiers
, typeUInt32
, NULL
, sizeof(UInt32
), NULL
, &modifiers
);
581 GetEventParameter( rawEvent
, kEventParamMouseLocation
, typeQDPoint
, NULL
, sizeof(Point
), NULL
, &point
);
583 UInt32 message
= (keyCode
<< 8) + charCode
;
585 // An IME input event may return several characters, but we need to send one char at a time to
587 for (int pos
=0 ; pos
< numChars
; pos
++)
589 WXEVENTREF formerEvent
= wxTheApp
->MacGetCurrentEvent() ;
590 WXEVENTHANDLERCALLREF formerHandler
= wxTheApp
->MacGetCurrentEventHandlerCallRef() ;
591 wxTheApp
->MacSetCurrentEvent( event
, handler
) ;
593 if ( wxTheApp
->MacSendCharEvent(
594 focus
, message
, modifiers
, when
, point
.h
, point
.v
, uniChars
[pos
] ) )
599 wxTheApp
->MacSetCurrentEvent( formerEvent
, formerHandler
) ;
608 if ( charBuf
!= buf
)
614 static pascal OSStatus
wxMacWindowCommandEventHandler( EventHandlerCallRef handler
, EventRef event
, void *data
)
616 OSStatus result
= eventNotHandledErr
;
617 wxWindowMac
* focus
= (wxWindowMac
*) data
;
621 wxMacCarbonEvent
cEvent( event
) ;
622 cEvent
.GetParameter
<HICommand
>(kEventParamDirectObject
,typeHICommand
,&command
) ;
624 wxMenuItem
* item
= NULL
;
625 wxMenu
* itemMenu
= wxFindMenuFromMacCommand( command
, item
) ;
626 int id
= wxMacCommandToId( command
.commandID
) ;
630 wxASSERT( itemMenu
!= NULL
) ;
632 switch ( cEvent
.GetKind() )
634 case kEventProcessCommand
:
636 if (item
->IsCheckable())
637 item
->Check( !item
->IsChecked() ) ;
639 if ( itemMenu
->SendEvent( id
, item
->IsCheckable() ? item
->IsChecked() : -1 ) )
643 wxCommandEvent
event(wxEVT_COMMAND_MENU_SELECTED
, id
);
644 event
.SetEventObject(focus
);
645 event
.SetInt(item
->IsCheckable() ? item
->IsChecked() : -1);
647 if ( focus
->GetEventHandler()->ProcessEvent(event
) )
653 case kEventCommandUpdateStatus
:
655 wxUpdateUIEvent
event(id
);
656 event
.SetEventObject( itemMenu
);
658 bool processed
= false;
660 // Try the menu's event handler
662 wxEvtHandler
*handler
= itemMenu
->GetEventHandler();
664 processed
= handler
->ProcessEvent(event
);
667 // Try the window the menu was popped up from
668 // (and up through the hierarchy)
671 const wxMenuBase
*menu
= itemMenu
;
674 wxWindow
*win
= menu
->GetInvokingWindow();
677 processed
= win
->GetEventHandler()->ProcessEvent(event
);
681 menu
= menu
->GetParent();
687 processed
= focus
->GetEventHandler()->ProcessEvent(event
);
692 // if anything changed, update the changed attribute
693 if (event
.GetSetText())
694 itemMenu
->SetLabel(id
, event
.GetText());
695 if (event
.GetSetChecked())
696 itemMenu
->Check(id
, event
.GetChecked());
697 if (event
.GetSetEnabled())
698 itemMenu
->Enable(id
, event
.GetEnabled());
712 pascal OSStatus
wxMacWindowEventHandler( EventHandlerCallRef handler
, EventRef event
, void *data
)
714 EventRef formerEvent
= (EventRef
) wxTheApp
->MacGetCurrentEvent() ;
715 EventHandlerCallRef formerEventHandlerCallRef
= (EventHandlerCallRef
) wxTheApp
->MacGetCurrentEventHandlerCallRef() ;
716 wxTheApp
->MacSetCurrentEvent( event
, handler
) ;
717 OSStatus result
= eventNotHandledErr
;
719 switch ( GetEventClass( event
) )
721 case kEventClassCommand
:
722 result
= wxMacWindowCommandEventHandler( handler
, event
, data
) ;
725 case kEventClassControl
:
726 result
= wxMacWindowControlEventHandler( handler
, event
, data
) ;
729 case kEventClassService
:
730 result
= wxMacWindowServiceEventHandler( handler
, event
, data
) ;
733 case kEventClassTextInput
:
734 result
= wxMacUnicodeTextEventHandler( handler
, event
, data
) ;
741 wxTheApp
->MacSetCurrentEvent( formerEvent
, formerEventHandlerCallRef
) ;
746 DEFINE_ONE_SHOT_HANDLER_GETTER( wxMacWindowEventHandler
)
748 #if !TARGET_API_MAC_OSX
750 // ---------------------------------------------------------------------------
751 // UserPane events for non OSX builds
752 // ---------------------------------------------------------------------------
754 static pascal void wxMacControlUserPaneDrawProc(ControlRef control
, SInt16 part
)
756 wxWindow
* win
= wxFindControlFromMacControl(control
) ;
758 win
->MacControlUserPaneDrawProc(part
) ;
760 wxMAC_DEFINE_PROC_GETTER( ControlUserPaneDrawUPP
, wxMacControlUserPaneDrawProc
) ;
762 static pascal ControlPartCode
wxMacControlUserPaneHitTestProc(ControlRef control
, Point where
)
764 wxWindow
* win
= wxFindControlFromMacControl(control
) ;
766 return win
->MacControlUserPaneHitTestProc(where
.h
, where
.v
) ;
768 return kControlNoPart
;
770 wxMAC_DEFINE_PROC_GETTER( ControlUserPaneHitTestUPP
, wxMacControlUserPaneHitTestProc
) ;
772 static pascal ControlPartCode
wxMacControlUserPaneTrackingProc(ControlRef control
, Point startPt
, ControlActionUPP actionProc
)
774 wxWindow
* win
= wxFindControlFromMacControl(control
) ;
776 return win
->MacControlUserPaneTrackingProc( startPt
.h
, startPt
.v
, (void*) actionProc
) ;
778 return kControlNoPart
;
780 wxMAC_DEFINE_PROC_GETTER( ControlUserPaneTrackingUPP
, wxMacControlUserPaneTrackingProc
) ;
782 static pascal void wxMacControlUserPaneIdleProc(ControlRef control
)
784 wxWindow
* win
= wxFindControlFromMacControl(control
) ;
786 win
->MacControlUserPaneIdleProc() ;
788 wxMAC_DEFINE_PROC_GETTER( ControlUserPaneIdleUPP
, wxMacControlUserPaneIdleProc
) ;
790 static pascal ControlPartCode
wxMacControlUserPaneKeyDownProc(ControlRef control
, SInt16 keyCode
, SInt16 charCode
, SInt16 modifiers
)
792 wxWindow
* win
= wxFindControlFromMacControl(control
) ;
794 return win
->MacControlUserPaneKeyDownProc(keyCode
,charCode
,modifiers
) ;
796 return kControlNoPart
;
798 wxMAC_DEFINE_PROC_GETTER( ControlUserPaneKeyDownUPP
, wxMacControlUserPaneKeyDownProc
) ;
800 static pascal void wxMacControlUserPaneActivateProc(ControlRef control
, Boolean activating
)
802 wxWindow
* win
= wxFindControlFromMacControl(control
) ;
804 win
->MacControlUserPaneActivateProc(activating
) ;
806 wxMAC_DEFINE_PROC_GETTER( ControlUserPaneActivateUPP
, wxMacControlUserPaneActivateProc
) ;
808 static pascal ControlPartCode
wxMacControlUserPaneFocusProc(ControlRef control
, ControlFocusPart action
)
810 wxWindow
* win
= wxFindControlFromMacControl(control
) ;
812 return win
->MacControlUserPaneFocusProc(action
) ;
814 return kControlNoPart
;
816 wxMAC_DEFINE_PROC_GETTER( ControlUserPaneFocusUPP
, wxMacControlUserPaneFocusProc
) ;
818 static pascal void wxMacControlUserPaneBackgroundProc(ControlRef control
, ControlBackgroundPtr info
)
820 wxWindow
* win
= wxFindControlFromMacControl(control
) ;
822 win
->MacControlUserPaneBackgroundProc(info
) ;
824 wxMAC_DEFINE_PROC_GETTER( ControlUserPaneBackgroundUPP
, wxMacControlUserPaneBackgroundProc
) ;
826 void wxWindowMac::MacControlUserPaneDrawProc(wxInt16 part
)
829 RgnHandle rgn
= NewRgn() ;
831 MacWindowToRootWindow( &x
, &y
) ;
832 OffsetRgn( rgn
, -x
, -y
) ;
833 wxMacWindowStateSaver
sv( this ) ;
834 SectRgn( rgn
, (RgnHandle
) MacGetVisibleRegion().GetWXHRGN() , rgn
) ;
835 MacDoRedraw( rgn
, 0 ) ;
839 wxInt16
wxWindowMac::MacControlUserPaneHitTestProc(wxInt16 x
, wxInt16 y
)
841 return kControlNoPart
;
844 wxInt16
wxWindowMac::MacControlUserPaneTrackingProc(wxInt16 x
, wxInt16 y
, void* actionProc
)
846 return kControlNoPart
;
849 void wxWindowMac::MacControlUserPaneIdleProc()
853 wxInt16
wxWindowMac::MacControlUserPaneKeyDownProc(wxInt16 keyCode
, wxInt16 charCode
, wxInt16 modifiers
)
855 return kControlNoPart
;
858 void wxWindowMac::MacControlUserPaneActivateProc(bool activating
)
862 wxInt16
wxWindowMac::MacControlUserPaneFocusProc(wxInt16 action
)
864 if ( AcceptsFocus() )
867 return kControlNoPart
;
870 void wxWindowMac::MacControlUserPaneBackgroundProc(void* info
)
876 // ---------------------------------------------------------------------------
877 // Scrollbar Tracking for all
878 // ---------------------------------------------------------------------------
880 pascal void wxMacLiveScrollbarActionProc( ControlRef control
, ControlPartCode partCode
) ;
881 pascal void wxMacLiveScrollbarActionProc( ControlRef control
, ControlPartCode partCode
)
885 wxWindow
* wx
= wxFindControlFromMacControl( control
) ;
887 wx
->MacHandleControlClick( (WXWidget
) control
, partCode
, true /* stillDown */ ) ;
890 wxMAC_DEFINE_PROC_GETTER( ControlActionUPP
, wxMacLiveScrollbarActionProc
) ;
892 // ===========================================================================
894 // ===========================================================================
896 WX_DECLARE_HASH_MAP(ControlRef
, wxWindow
*, wxPointerHash
, wxPointerEqual
, MacControlMap
);
898 static MacControlMap wxWinMacControlList
;
900 wxWindow
*wxFindControlFromMacControl(ControlRef inControl
)
902 MacControlMap::iterator node
= wxWinMacControlList
.find(inControl
);
904 return (node
== wxWinMacControlList
.end()) ? NULL
: node
->second
;
907 void wxAssociateControlWithMacControl(ControlRef inControl
, wxWindow
*control
)
909 // adding NULL ControlRef is (first) surely a result of an error and
910 // (secondly) breaks native event processing
911 wxCHECK_RET( inControl
!= (ControlRef
) NULL
, wxT("attempt to add a NULL WindowRef to window list") );
913 wxWinMacControlList
[inControl
] = control
;
916 void wxRemoveMacControlAssociation(wxWindow
*control
)
918 // iterate over all the elements in the class
919 // is the iterator stable ? as we might have two associations pointing to the same wxWindow
920 // we should go on...
926 MacControlMap::iterator it
;
927 for ( it
= wxWinMacControlList
.begin(); it
!= wxWinMacControlList
.end(); ++it
)
929 if ( it
->second
== control
)
931 wxWinMacControlList
.erase(it
);
939 // ----------------------------------------------------------------------------
940 // constructors and such
941 // ----------------------------------------------------------------------------
943 wxWindowMac::wxWindowMac()
948 wxWindowMac::wxWindowMac(wxWindowMac
*parent
,
953 const wxString
& name
)
956 Create(parent
, id
, pos
, size
, style
, name
);
959 void wxWindowMac::Init()
965 #if wxMAC_USE_CORE_GRAPHICS
966 m_cgContextRef
= NULL
;
969 // as all windows are created with WS_VISIBLE style...
972 m_hScrollBar
= NULL
;
973 m_vScrollBar
= NULL
;
974 m_macBackgroundBrush
= wxNullBrush
;
976 m_macIsUserPane
= true;
977 m_clipChildren
= false ;
978 m_cachedClippedRectValid
= false ;
980 // we need a valid font for the encodings
981 wxWindowBase::SetFont(wxSystemSettings::GetFont(wxSYS_DEFAULT_GUI_FONT
));
984 wxWindowMac::~wxWindowMac()
988 m_isBeingDeleted
= true;
990 MacInvalidateBorders() ;
992 #ifndef __WXUNIVERSAL__
993 // VS: make sure there's no wxFrame with last focus set to us:
994 for ( wxWindow
*win
= GetParent(); win
; win
= win
->GetParent() )
996 wxFrame
*frame
= wxDynamicCast(win
, wxFrame
);
999 if ( frame
->GetLastFocus() == this )
1000 frame
->SetLastFocus((wxWindow
*)NULL
);
1006 // destroy children before destroying this window itself
1009 // wxRemoveMacControlAssociation( this ) ;
1010 // If we delete an item, we should initialize the parent panel,
1011 // because it could now be invalid.
1012 wxTopLevelWindow
*tlw
= wxDynamicCast(wxGetTopLevelParent(this), wxTopLevelWindow
);
1015 if ( tlw
->GetDefaultItem() == (wxButton
*) this)
1016 tlw
->SetDefaultItem(NULL
);
1019 if ( m_peer
&& m_peer
->Ok() )
1021 // in case the callback might be called during destruction
1022 wxRemoveMacControlAssociation( this) ;
1023 ::RemoveEventHandler( (EventHandlerRef
) m_macControlEventHandler
) ;
1024 // we currently are not using this hook
1025 // ::SetControlColorProc( *m_peer , NULL ) ;
1029 if ( g_MacLastWindow
== this )
1030 g_MacLastWindow
= NULL
;
1032 wxFrame
* frame
= wxDynamicCast( wxGetTopLevelParent( this ) , wxFrame
) ;
1035 if ( frame
->GetLastFocus() == this )
1036 frame
->SetLastFocus( NULL
) ;
1039 // delete our drop target if we've got one
1040 #if wxUSE_DRAG_AND_DROP
1041 if ( m_dropTarget
!= NULL
)
1043 delete m_dropTarget
;
1044 m_dropTarget
= NULL
;
1051 WXWidget
wxWindowMac::GetHandle() const
1053 return (WXWidget
) m_peer
->GetControlRef() ;
1056 void wxWindowMac::MacInstallEventHandler( WXWidget control
)
1058 wxAssociateControlWithMacControl( (ControlRef
) control
, this ) ;
1059 InstallControlEventHandler( (ControlRef
)control
, GetwxMacWindowEventHandlerUPP(),
1060 GetEventTypeCount(eventList
), eventList
, this,
1061 (EventHandlerRef
*)&m_macControlEventHandler
);
1063 #if !TARGET_API_MAC_OSX
1064 if ( (ControlRef
) control
== m_peer
->GetControlRef() )
1066 m_peer
->SetData
<ControlUserPaneDrawUPP
>(kControlEntireControl
, kControlUserPaneDrawProcTag
, GetwxMacControlUserPaneDrawProc()) ;
1067 m_peer
->SetData
<ControlUserPaneHitTestUPP
>(kControlEntireControl
, kControlUserPaneHitTestProcTag
, GetwxMacControlUserPaneHitTestProc()) ;
1068 m_peer
->SetData
<ControlUserPaneTrackingUPP
>(kControlEntireControl
, kControlUserPaneTrackingProcTag
, GetwxMacControlUserPaneTrackingProc()) ;
1069 m_peer
->SetData
<ControlUserPaneIdleUPP
>(kControlEntireControl
, kControlUserPaneIdleProcTag
, GetwxMacControlUserPaneIdleProc()) ;
1070 m_peer
->SetData
<ControlUserPaneKeyDownUPP
>(kControlEntireControl
, kControlUserPaneKeyDownProcTag
, GetwxMacControlUserPaneKeyDownProc()) ;
1071 m_peer
->SetData
<ControlUserPaneActivateUPP
>(kControlEntireControl
, kControlUserPaneActivateProcTag
, GetwxMacControlUserPaneActivateProc()) ;
1072 m_peer
->SetData
<ControlUserPaneFocusUPP
>(kControlEntireControl
, kControlUserPaneFocusProcTag
, GetwxMacControlUserPaneFocusProc()) ;
1073 m_peer
->SetData
<ControlUserPaneBackgroundUPP
>(kControlEntireControl
, kControlUserPaneBackgroundProcTag
, GetwxMacControlUserPaneBackgroundProc()) ;
1079 bool wxWindowMac::Create(wxWindowMac
*parent
,
1084 const wxString
& name
)
1086 wxCHECK_MSG( parent
, false, wxT("can't create wxWindowMac without parent") );
1088 if ( !CreateBase(parent
, id
, pos
, size
, style
, wxDefaultValidator
, name
) )
1091 m_windowVariant
= parent
->GetWindowVariant() ;
1093 if ( m_macIsUserPane
)
1095 Rect bounds
= wxMacGetBoundsForControl( this , pos
, size
) ;
1098 | kControlSupportsEmbedding
1099 | kControlSupportsLiveFeedback
1100 | kControlGetsFocusOnClick
1101 // | kControlHasSpecialBackground
1102 // | kControlSupportsCalcBestRect
1103 | kControlHandlesTracking
1104 | kControlSupportsFocus
1105 | kControlWantsActivate
1106 | kControlWantsIdle
;
1108 m_peer
= new wxMacControl(this) ;
1109 OSStatus err
=::CreateUserPaneControl( MAC_WXHWND(GetParent()->MacGetTopLevelWindowRef()) , &bounds
, features
, m_peer
->GetControlRefAddr() );
1110 verify_noerr( err
);
1112 MacPostControlCreate(pos
, size
) ;
1115 #ifndef __WXUNIVERSAL__
1116 // Don't give scrollbars to wxControls unless they ask for them
1117 if ( (! IsKindOf(CLASSINFO(wxControl
)) && ! IsKindOf(CLASSINFO(wxStatusBar
)))
1118 || (IsKindOf(CLASSINFO(wxControl
)) && ((style
& wxHSCROLL
) || (style
& wxVSCROLL
))))
1120 MacCreateScrollBars( style
) ;
1124 wxWindowCreateEvent
event(this);
1125 GetEventHandler()->AddPendingEvent(event
);
1130 void wxWindowMac::MacChildAdded()
1133 m_vScrollBar
->Raise() ;
1135 m_hScrollBar
->Raise() ;
1138 void wxWindowMac::MacPostControlCreate(const wxPoint
& pos
, const wxSize
& size
)
1140 wxASSERT_MSG( m_peer
!= NULL
&& m_peer
->Ok() , wxT("No valid mac control") ) ;
1142 m_peer
->SetReference( (URefCon
) this ) ;
1143 GetParent()->AddChild( this );
1145 MacInstallEventHandler( (WXWidget
) m_peer
->GetControlRef() );
1147 ControlRef container
= (ControlRef
) GetParent()->GetHandle() ;
1148 wxASSERT_MSG( container
!= NULL
, wxT("No valid mac container control") ) ;
1149 ::EmbedControl( m_peer
->GetControlRef() , container
) ;
1150 GetParent()->MacChildAdded() ;
1152 // adjust font, controlsize etc
1153 DoSetWindowVariant( m_windowVariant
) ;
1155 m_peer
->SetLabel( wxStripMenuCodes(m_label
, wxStrip_Mnemonics
) ) ;
1157 if (!m_macIsUserPane
)
1158 SetInitialSize(size
);
1160 SetCursor( *wxSTANDARD_CURSOR
) ;
1163 void wxWindowMac::DoSetWindowVariant( wxWindowVariant variant
)
1165 // Don't assert, in case we set the window variant before
1166 // the window is created
1167 // wxASSERT( m_peer->Ok() ) ;
1169 m_windowVariant
= variant
;
1171 if (m_peer
== NULL
|| !m_peer
->Ok())
1175 ThemeFontID themeFont
= kThemeSystemFont
;
1177 // we will get that from the settings later
1178 // and make this NORMAL later, but first
1179 // we have a few calculations that we must fix
1183 case wxWINDOW_VARIANT_NORMAL
:
1184 size
= kControlSizeNormal
;
1185 themeFont
= kThemeSystemFont
;
1188 case wxWINDOW_VARIANT_SMALL
:
1189 size
= kControlSizeSmall
;
1190 themeFont
= kThemeSmallSystemFont
;
1193 case wxWINDOW_VARIANT_MINI
:
1194 if (UMAGetSystemVersion() >= 0x1030 )
1196 // not always defined in the headers
1202 size
= kControlSizeSmall
;
1203 themeFont
= kThemeSmallSystemFont
;
1207 case wxWINDOW_VARIANT_LARGE
:
1208 size
= kControlSizeLarge
;
1209 themeFont
= kThemeSystemFont
;
1213 wxFAIL_MSG(_T("unexpected window variant"));
1217 m_peer
->SetData
<ControlSize
>(kControlEntireControl
, kControlSizeTag
, &size
) ;
1220 font
.MacCreateThemeFont( themeFont
) ;
1224 void wxWindowMac::MacUpdateControlFont()
1226 m_peer
->SetFont( GetFont() , GetForegroundColour() , GetWindowStyle() ) ;
1230 bool wxWindowMac::SetFont(const wxFont
& font
)
1232 bool retval
= wxWindowBase::SetFont( font
);
1234 MacUpdateControlFont() ;
1239 bool wxWindowMac::SetForegroundColour(const wxColour
& col
)
1241 bool retval
= wxWindowBase::SetForegroundColour( col
);
1244 MacUpdateControlFont();
1249 bool wxWindowMac::SetBackgroundColour(const wxColour
& col
)
1251 if ( !wxWindowBase::SetBackgroundColour(col
) && m_hasBgCol
)
1255 wxColour
newCol(GetBackgroundColour());
1257 if ( newCol
== wxSystemSettings::GetColour( wxSYS_COLOUR_WINDOW
) )
1258 brush
.MacSetTheme( kThemeBrushDocumentWindowBackground
) ;
1259 else if ( newCol
== wxSystemSettings::GetColour( wxSYS_COLOUR_3DFACE
) )
1260 brush
.MacSetTheme( kThemeBrushDialogBackgroundActive
) ;
1262 brush
.SetColour( newCol
) ;
1264 MacSetBackgroundBrush( brush
) ;
1265 MacUpdateControlFont() ;
1270 void wxWindowMac::MacSetBackgroundBrush( const wxBrush
&brush
)
1272 m_macBackgroundBrush
= brush
;
1273 m_peer
->SetBackground( brush
) ;
1276 bool wxWindowMac::MacCanFocus() const
1278 // TODO : evaluate performance hits by looking up this value, eventually cache the results for a 1 sec or so
1279 // CAUTION : the value returned currently is 0 or 2, I've also found values of 1 having the same meaning,
1280 // but the value range is nowhere documented
1281 Boolean keyExistsAndHasValidFormat
;
1282 CFIndex fullKeyboardAccess
= CFPreferencesGetAppIntegerValue( CFSTR("AppleKeyboardUIMode" ) ,
1283 kCFPreferencesCurrentApplication
, &keyExistsAndHasValidFormat
);
1285 if ( keyExistsAndHasValidFormat
&& fullKeyboardAccess
> 0 )
1291 UInt32 features
= 0 ;
1292 m_peer
->GetFeatures( &features
) ;
1294 return features
& ( kControlSupportsFocus
| kControlGetsFocusOnClick
) ;
1298 void wxWindowMac::SetFocus()
1300 if ( !AcceptsFocus() )
1303 wxWindow
* former
= FindFocus() ;
1304 if ( former
== this )
1307 // as we cannot rely on the control features to find out whether we are in full keyboard mode,
1308 // we can only leave in case of an error
1309 OSStatus err
= m_peer
->SetFocus( kControlFocusNextPart
) ;
1310 if ( err
== errCouldntSetFocus
)
1313 SetUserFocusWindow( (WindowRef
)MacGetTopLevelWindowRef() );
1315 #if !TARGET_API_MAC_OSX
1316 // emulate carbon events when running under CarbonLib where they are not natively available
1319 EventRef evRef
= NULL
;
1321 err
= MacCreateEvent(
1322 NULL
, kEventClassControl
, kEventControlSetFocusPart
, TicksToEventTime( TickCount() ) ,
1323 kEventAttributeUserEvent
, &evRef
);
1324 verify_noerr( err
);
1326 wxMacCarbonEvent
cEvent( evRef
) ;
1327 cEvent
.SetParameter
<ControlRef
>( kEventParamDirectObject
, (ControlRef
) former
->GetHandle() ) ;
1328 cEvent
.SetParameter
<ControlPartCode
>(kEventParamControlPart
, typeControlPartCode
, kControlFocusNoPart
) ;
1330 wxMacWindowEventHandler( NULL
, evRef
, former
) ;
1331 ReleaseEvent( evRef
) ;
1334 // send new focus event
1336 EventRef evRef
= NULL
;
1338 err
= MacCreateEvent(
1339 NULL
, kEventClassControl
, kEventControlSetFocusPart
, TicksToEventTime( TickCount() ) ,
1340 kEventAttributeUserEvent
, &evRef
);
1341 verify_noerr( err
);
1343 wxMacCarbonEvent
cEvent( evRef
) ;
1344 cEvent
.SetParameter
<ControlRef
>( kEventParamDirectObject
, (ControlRef
) GetHandle() ) ;
1345 cEvent
.SetParameter
<ControlPartCode
>(kEventParamControlPart
, typeControlPartCode
, kControlFocusNextPart
) ;
1347 wxMacWindowEventHandler( NULL
, evRef
, this ) ;
1348 ReleaseEvent( evRef
) ;
1353 void wxWindowMac::DoCaptureMouse()
1355 wxApp::s_captureWindow
= this ;
1358 wxWindow
* wxWindowBase::GetCapture()
1360 return wxApp::s_captureWindow
;
1363 void wxWindowMac::DoReleaseMouse()
1365 wxApp::s_captureWindow
= NULL
;
1368 #if wxUSE_DRAG_AND_DROP
1370 void wxWindowMac::SetDropTarget(wxDropTarget
*pDropTarget
)
1372 if ( m_dropTarget
!= NULL
)
1373 delete m_dropTarget
;
1375 m_dropTarget
= pDropTarget
;
1376 if ( m_dropTarget
!= NULL
)
1384 // Old-style File Manager Drag & Drop
1385 void wxWindowMac::DragAcceptFiles(bool accept
)
1390 // Returns the size of the native control. In the case of the toplevel window
1391 // this is the content area root control
1393 void wxWindowMac::MacGetPositionAndSizeFromControl(int& x
, int& y
,
1394 int& w
, int& h
) const
1396 wxFAIL_MSG( wxT("Not currently supported") ) ;
1399 // From a wx position / size calculate the appropriate size of the native control
1401 bool wxWindowMac::MacGetBoundsForControl(
1405 int& w
, int& h
, bool adjustOrigin
) const
1407 // the desired size, minus the border pixels gives the correct size of the control
1411 // TODO: the default calls may be used as soon as PostCreateControl Is moved here
1412 w
= wxMax(size
.x
, 0) ; // WidthDefault( size.x );
1413 h
= wxMax(size
.y
, 0) ; // HeightDefault( size.y ) ;
1415 x
+= MacGetLeftBorderSize() ;
1416 y
+= MacGetTopBorderSize() ;
1417 w
-= MacGetLeftBorderSize() + MacGetRightBorderSize() ;
1418 h
-= MacGetTopBorderSize() + MacGetBottomBorderSize() ;
1421 AdjustForParentClientOrigin( x
, y
) ;
1423 // this is in window relative coordinate, as this parent may have a border, its physical position is offset by this border
1424 if ( !GetParent()->IsTopLevel() )
1426 x
-= GetParent()->MacGetLeftBorderSize() ;
1427 y
-= GetParent()->MacGetTopBorderSize() ;
1433 // Get window size (not client size)
1434 void wxWindowMac::DoGetSize(int *x
, int *y
) const
1437 m_peer
->GetRect( &bounds
) ;
1440 *x
= bounds
.right
- bounds
.left
+ MacGetLeftBorderSize() + MacGetRightBorderSize() ;
1442 *y
= bounds
.bottom
- bounds
.top
+ MacGetTopBorderSize() + MacGetBottomBorderSize() ;
1445 // get the position of the bounds of this window in client coordinates of its parent
1446 void wxWindowMac::DoGetPosition(int *x
, int *y
) const
1449 m_peer
->GetRect( &bounds
) ;
1451 int x1
= bounds
.left
;
1452 int y1
= bounds
.top
;
1454 // get the wx window position from the native one
1455 x1
-= MacGetLeftBorderSize() ;
1456 y1
-= MacGetTopBorderSize() ;
1458 if ( !IsTopLevel() )
1460 wxWindow
*parent
= GetParent();
1463 // we must first adjust it to be in window coordinates of the parent,
1464 // as otherwise it gets lost by the ClientAreaOrigin fix
1465 x1
+= parent
->MacGetLeftBorderSize() ;
1466 y1
+= parent
->MacGetTopBorderSize() ;
1468 // and now to client coordinates
1469 wxPoint
pt(parent
->GetClientAreaOrigin());
1481 void wxWindowMac::DoScreenToClient(int *x
, int *y
) const
1483 WindowRef window
= (WindowRef
) MacGetTopLevelWindowRef() ;
1484 wxCHECK_RET( window
, wxT("TopLevel Window missing") ) ;
1486 Point localwhere
= { 0, 0 } ;
1493 wxMacGlobalToLocal( window
, &localwhere
) ;
1500 MacRootWindowToWindow( x
, y
) ;
1502 wxPoint origin
= GetClientAreaOrigin() ;
1509 void wxWindowMac::DoClientToScreen(int *x
, int *y
) const
1511 WindowRef window
= (WindowRef
) MacGetTopLevelWindowRef() ;
1512 wxCHECK_RET( window
, wxT("TopLevel window missing") ) ;
1514 wxPoint origin
= GetClientAreaOrigin() ;
1520 MacWindowToRootWindow( x
, y
) ;
1522 Point localwhere
= { 0, 0 };
1528 wxMacLocalToGlobal( window
, &localwhere
) ;
1536 void wxWindowMac::MacClientToRootWindow( int *x
, int *y
) const
1538 wxPoint origin
= GetClientAreaOrigin() ;
1544 MacWindowToRootWindow( x
, y
) ;
1547 void wxWindowMac::MacRootWindowToClient( int *x
, int *y
) const
1549 MacRootWindowToWindow( x
, y
) ;
1551 wxPoint origin
= GetClientAreaOrigin() ;
1558 void wxWindowMac::MacWindowToRootWindow( int *x
, int *y
) const
1567 if ( !IsTopLevel() )
1569 wxTopLevelWindowMac
* top
= MacGetTopLevelWindow();
1572 pt
.x
-= MacGetLeftBorderSize() ;
1573 pt
.y
-= MacGetTopBorderSize() ;
1574 wxMacControl::Convert( &pt
, m_peer
, top
->m_peer
) ;
1584 void wxWindowMac::MacWindowToRootWindow( short *x
, short *y
) const
1593 MacWindowToRootWindow( &x1
, &y1
) ;
1601 void wxWindowMac::MacRootWindowToWindow( int *x
, int *y
) const
1610 if ( !IsTopLevel() )
1612 wxTopLevelWindowMac
* top
= MacGetTopLevelWindow();
1615 wxMacControl::Convert( &pt
, top
->m_peer
, m_peer
) ;
1616 pt
.x
+= MacGetLeftBorderSize() ;
1617 pt
.y
+= MacGetTopBorderSize() ;
1627 void wxWindowMac::MacRootWindowToWindow( short *x
, short *y
) const
1636 MacRootWindowToWindow( &x1
, &y1
) ;
1644 void wxWindowMac::MacGetContentAreaInset( int &left
, int &top
, int &right
, int &bottom
)
1646 RgnHandle rgn
= NewRgn() ;
1648 if ( m_peer
->GetRegion( kControlContentMetaPart
, rgn
) == noErr
)
1650 Rect structure
, content
;
1652 GetRegionBounds( rgn
, &content
) ;
1653 m_peer
->GetRect( &structure
) ;
1654 OffsetRect( &structure
, -structure
.left
, -structure
.top
) ;
1656 left
= content
.left
- structure
.left
;
1657 top
= content
.top
- structure
.top
;
1658 right
= structure
.right
- content
.right
;
1659 bottom
= structure
.bottom
- content
.bottom
;
1663 left
= top
= right
= bottom
= 0 ;
1669 wxSize
wxWindowMac::DoGetSizeFromClientSize( const wxSize
& size
) const
1671 wxSize sizeTotal
= size
;
1673 RgnHandle rgn
= NewRgn() ;
1674 if ( m_peer
->GetRegion( kControlContentMetaPart
, rgn
) == noErr
)
1676 Rect content
, structure
;
1677 GetRegionBounds( rgn
, &content
) ;
1678 m_peer
->GetRect( &structure
) ;
1680 // structure is in parent coordinates, but we only need width and height, so it's ok
1682 sizeTotal
.x
+= (structure
.right
- structure
.left
) - (content
.right
- content
.left
) ;
1683 sizeTotal
.y
+= (structure
.bottom
- structure
.top
) - (content
.bottom
- content
.top
) ;
1688 sizeTotal
.x
+= MacGetLeftBorderSize() + MacGetRightBorderSize() ;
1689 sizeTotal
.y
+= MacGetTopBorderSize() + MacGetBottomBorderSize() ;
1694 // Get size *available for subwindows* i.e. excluding menu bar etc.
1695 void wxWindowMac::DoGetClientSize( int *x
, int *y
) const
1699 RgnHandle rgn
= NewRgn() ;
1701 if ( m_peer
->GetRegion( kControlContentMetaPart
, rgn
) == noErr
)
1702 GetRegionBounds( rgn
, &content
) ;
1704 m_peer
->GetRect( &content
) ;
1707 ww
= content
.right
- content
.left
;
1708 hh
= content
.bottom
- content
.top
;
1710 if (m_hScrollBar
&& m_hScrollBar
->IsShown() )
1711 hh
-= m_hScrollBar
->GetSize().y
;
1713 if (m_vScrollBar
&& m_vScrollBar
->IsShown() )
1714 ww
-= m_vScrollBar
->GetSize().x
;
1722 bool wxWindowMac::SetCursor(const wxCursor
& cursor
)
1724 if (m_cursor
.IsSameAs(cursor
))
1729 if ( ! wxWindowBase::SetCursor( *wxSTANDARD_CURSOR
) )
1734 if ( ! wxWindowBase::SetCursor( cursor
) )
1738 wxASSERT_MSG( m_cursor
.Ok(),
1739 wxT("cursor must be valid after call to the base version"));
1741 wxWindowMac
*mouseWin
= 0 ;
1743 wxTopLevelWindowMac
*tlw
= MacGetTopLevelWindow() ;
1744 WindowRef window
= (WindowRef
) ( tlw
? tlw
->MacGetWindowRef() : 0 ) ;
1746 ControlPartCode part
;
1747 ControlRef control
;
1749 #if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
1751 HIGetMousePosition(kHICoordSpaceWindow
, window
, &hiPoint
);
1756 Boolean swapped
= QDSwapPort( GetWindowPort( window
) , &savePort
) ;
1758 // TODO: If we ever get a GetCurrentEvent... replacement
1759 // for the mouse position, use it...
1764 control
= wxMacFindControlUnderMouse( tlw
, pt
, window
, &part
) ;
1766 mouseWin
= wxFindControlFromMacControl( control
) ;
1768 #if MAC_OS_X_VERSION_MIN_REQUIRED < MAC_OS_X_VERSION_10_5
1770 QDSwapPort( savePort
, NULL
) ;
1774 if ( mouseWin
== this && !wxIsBusy() )
1775 m_cursor
.MacInstall() ;
1781 bool wxWindowMac::DoPopupMenu(wxMenu
*menu
, int x
, int y
)
1783 menu
->SetInvokingWindow(this);
1786 if ( x
== wxDefaultCoord
&& y
== wxDefaultCoord
)
1788 wxPoint mouse
= wxGetMousePosition();
1794 ClientToScreen( &x
, &y
) ;
1797 menu
->MacBeforeDisplay( true ) ;
1798 long menuResult
= ::PopUpMenuSelect((MenuHandle
) menu
->GetHMenu() , y
, x
, 0) ;
1799 if ( HiWord(menuResult
) != 0 )
1802 GetMenuItemCommandID( GetMenuHandle(HiWord(menuResult
)) , LoWord(menuResult
) , &macid
);
1803 int id
= wxMacCommandToId( macid
);
1804 wxMenuItem
* item
= NULL
;
1806 item
= menu
->FindItem( id
, &realmenu
) ;
1809 if (item
->IsCheckable())
1810 item
->Check( !item
->IsChecked() ) ;
1812 menu
->SendEvent( id
, item
->IsCheckable() ? item
->IsChecked() : -1 ) ;
1816 menu
->MacAfterDisplay( true ) ;
1817 menu
->SetInvokingWindow( NULL
);
1823 // ----------------------------------------------------------------------------
1825 // ----------------------------------------------------------------------------
1829 void wxWindowMac::DoSetToolTip(wxToolTip
*tooltip
)
1831 wxWindowBase::DoSetToolTip(tooltip
);
1834 m_tooltip
->SetWindow(this);
1839 void wxWindowMac::MacInvalidateBorders()
1841 if ( m_peer
== NULL
)
1844 bool vis
= MacIsReallyShown() ;
1848 int outerBorder
= MacGetLeftBorderSize() ;
1849 if ( m_peer
->NeedsFocusRect() && m_peer
->HasFocus() )
1852 if ( outerBorder
== 0 )
1855 // now we know that we have something to do at all
1857 // as the borders are drawn on the parent we have to properly invalidate all these areas
1858 RgnHandle updateInner
, updateOuter
;
1861 // this rectangle is in HIViewCoordinates under OSX and in Window Coordinates under Carbon
1862 updateInner
= NewRgn() ;
1863 updateOuter
= NewRgn() ;
1865 m_peer
->GetRect( &rect
) ;
1866 RectRgn( updateInner
, &rect
) ;
1867 InsetRect( &rect
, -outerBorder
, -outerBorder
) ;
1868 RectRgn( updateOuter
, &rect
) ;
1869 DiffRgn( updateOuter
, updateInner
, updateOuter
) ;
1871 #ifdef __WXMAC_OSX__
1872 GetParent()->m_peer
->SetNeedsDisplay( updateOuter
) ;
1874 WindowRef tlw
= (WindowRef
) MacGetTopLevelWindowRef() ;
1876 InvalWindowRgn( tlw
, updateOuter
) ;
1879 DisposeRgn( updateOuter
) ;
1880 DisposeRgn( updateInner
) ;
1883 void wxWindowMac::DoMoveWindow(int x
, int y
, int width
, int height
)
1885 // this is never called for a toplevel window, so we know we have a parent
1886 int former_x
, former_y
, former_w
, former_h
;
1888 // Get true coordinates of former position
1889 DoGetPosition( &former_x
, &former_y
) ;
1890 DoGetSize( &former_w
, &former_h
) ;
1892 wxWindow
*parent
= GetParent();
1895 wxPoint
pt(parent
->GetClientAreaOrigin());
1900 int actualWidth
= width
;
1901 int actualHeight
= height
;
1905 if ((m_minWidth
!= -1) && (actualWidth
< m_minWidth
))
1906 actualWidth
= m_minWidth
;
1907 if ((m_minHeight
!= -1) && (actualHeight
< m_minHeight
))
1908 actualHeight
= m_minHeight
;
1909 if ((m_maxWidth
!= -1) && (actualWidth
> m_maxWidth
))
1910 actualWidth
= m_maxWidth
;
1911 if ((m_maxHeight
!= -1) && (actualHeight
> m_maxHeight
))
1912 actualHeight
= m_maxHeight
;
1914 bool doMove
= false, doResize
= false ;
1916 if ( actualX
!= former_x
|| actualY
!= former_y
)
1919 if ( actualWidth
!= former_w
|| actualHeight
!= former_h
)
1922 if ( doMove
|| doResize
)
1924 // as the borders are drawn outside the native control, we adjust now
1926 wxRect
bounds( wxPoint( actualX
+ MacGetLeftBorderSize() ,actualY
+ MacGetTopBorderSize() ),
1927 wxSize( actualWidth
- (MacGetLeftBorderSize() + MacGetRightBorderSize()) ,
1928 actualHeight
- (MacGetTopBorderSize() + MacGetBottomBorderSize()) ) ) ;
1931 wxMacRectToNative( &bounds
, &r
) ;
1933 if ( !GetParent()->IsTopLevel() )
1934 wxMacWindowToNative( GetParent() , &r
) ;
1936 MacInvalidateBorders() ;
1938 m_cachedClippedRectValid
= false ;
1939 m_peer
->SetRect( &r
) ;
1941 wxWindowMac::MacSuperChangedPosition() ; // like this only children will be notified
1943 MacInvalidateBorders() ;
1945 MacRepositionScrollBars() ;
1948 wxPoint
point(actualX
, actualY
);
1949 wxMoveEvent
event(point
, m_windowId
);
1950 event
.SetEventObject(this);
1951 GetEventHandler()->ProcessEvent(event
) ;
1956 MacRepositionScrollBars() ;
1957 wxSize
size(actualWidth
, actualHeight
);
1958 wxSizeEvent
event(size
, m_windowId
);
1959 event
.SetEventObject(this);
1960 GetEventHandler()->ProcessEvent(event
);
1965 wxSize
wxWindowMac::DoGetBestSize() const
1967 if ( m_macIsUserPane
|| IsTopLevel() )
1968 return wxWindowBase::DoGetBestSize() ;
1970 Rect bestsize
= { 0 , 0 , 0 , 0 } ;
1971 int bestWidth
, bestHeight
;
1973 m_peer
->GetBestRect( &bestsize
) ;
1974 if ( EmptyRect( &bestsize
) )
1979 bestsize
.bottom
= 16 ;
1981 if ( IsKindOf( CLASSINFO( wxScrollBar
) ) )
1983 bestsize
.bottom
= 16 ;
1986 else if ( IsKindOf( CLASSINFO( wxSpinButton
) ) )
1988 bestsize
.bottom
= 24 ;
1993 // return wxWindowBase::DoGetBestSize() ;
1997 bestWidth
= bestsize
.right
- bestsize
.left
;
1998 bestHeight
= bestsize
.bottom
- bestsize
.top
;
1999 if ( bestHeight
< 10 )
2002 return wxSize(bestWidth
, bestHeight
);
2005 // set the size of the window: if the dimensions are positive, just use them,
2006 // but if any of them is equal to -1, it means that we must find the value for
2007 // it ourselves (unless sizeFlags contains wxSIZE_ALLOW_MINUS_ONE flag, in
2008 // which case -1 is a valid value for x and y)
2010 // If sizeFlags contains wxSIZE_AUTO_WIDTH/HEIGHT flags (default), we calculate
2011 // the width/height to best suit our contents, otherwise we reuse the current
2013 void wxWindowMac::DoSetSize(int x
, int y
, int width
, int height
, int sizeFlags
)
2015 // get the current size and position...
2016 int currentX
, currentY
;
2017 int currentW
, currentH
;
2019 GetPosition(¤tX
, ¤tY
);
2020 GetSize(¤tW
, ¤tH
);
2022 // ... and don't do anything (avoiding flicker) if it's already ok
2023 if ( x
== currentX
&& y
== currentY
&&
2024 width
== currentW
&& height
== currentH
&& ( height
!= -1 && width
!= -1 ) )
2027 MacRepositionScrollBars() ; // we might have a real position shift
2032 if ( !(sizeFlags
& wxSIZE_ALLOW_MINUS_ONE
) )
2034 if ( x
== wxDefaultCoord
)
2036 if ( y
== wxDefaultCoord
)
2040 AdjustForParentClientOrigin( x
, y
, sizeFlags
);
2042 wxSize size
= wxDefaultSize
;
2043 if ( width
== wxDefaultCoord
)
2045 if ( sizeFlags
& wxSIZE_AUTO_WIDTH
)
2047 size
= DoGetBestSize();
2052 // just take the current one
2057 if ( height
== wxDefaultCoord
)
2059 if ( sizeFlags
& wxSIZE_AUTO_HEIGHT
)
2061 if ( size
.x
== wxDefaultCoord
)
2062 size
= DoGetBestSize();
2063 // else: already called DoGetBestSize() above
2069 // just take the current one
2074 DoMoveWindow( x
, y
, width
, height
);
2077 wxPoint
wxWindowMac::GetClientAreaOrigin() const
2079 RgnHandle rgn
= NewRgn() ;
2081 if ( m_peer
->GetRegion( kControlContentMetaPart
, rgn
) == noErr
)
2083 GetRegionBounds( rgn
, &content
) ;
2093 return wxPoint( content
.left
+ MacGetLeftBorderSize() , content
.top
+ MacGetTopBorderSize() );
2096 void wxWindowMac::DoSetClientSize(int clientwidth
, int clientheight
)
2098 if ( clientwidth
!= wxDefaultCoord
|| clientheight
!= wxDefaultCoord
)
2100 int currentclientwidth
, currentclientheight
;
2101 int currentwidth
, currentheight
;
2103 GetClientSize( ¤tclientwidth
, ¤tclientheight
) ;
2104 GetSize( ¤twidth
, ¤theight
) ;
2106 DoSetSize( wxDefaultCoord
, wxDefaultCoord
, currentwidth
+ clientwidth
- currentclientwidth
,
2107 currentheight
+ clientheight
- currentclientheight
, wxSIZE_USE_EXISTING
) ;
2111 void wxWindowMac::SetLabel(const wxString
& title
)
2113 m_label
= wxStripMenuCodes(title
, wxStrip_Mnemonics
) ;
2115 if ( m_peer
&& m_peer
->Ok() )
2116 m_peer
->SetLabel( m_label
) ;
2121 wxString
wxWindowMac::GetLabel() const
2126 bool wxWindowMac::Show(bool show
)
2128 bool former
= MacIsReallyShown() ;
2129 if ( !wxWindowBase::Show(show
) )
2132 // TODO: use visibilityChanged Carbon Event for OSX
2134 m_peer
->SetVisibility( show
, true ) ;
2136 if ( former
!= MacIsReallyShown() )
2137 MacPropagateVisibilityChanged() ;
2142 void wxWindowMac::DoEnable(bool enable
)
2144 m_peer
->Enable( enable
) ;
2148 // status change propagations (will be not necessary for OSX later )
2151 void wxWindowMac::MacPropagateVisibilityChanged()
2153 #if !TARGET_API_MAC_OSX
2154 MacVisibilityChanged() ;
2157 wxWindowList::compatibility_iterator node
= GetChildren().GetFirst();
2160 child
= node
->GetData();
2161 if ( child
->IsShown() )
2162 child
->MacPropagateVisibilityChanged() ;
2164 node
= node
->GetNext();
2169 void wxWindowMac::OnEnabled(bool enabled
)
2171 #if !TARGET_API_MAC_OSX
2172 MacEnabledStateChanged() ;
2176 void wxWindowMac::MacPropagateHiliteChanged()
2178 #if !TARGET_API_MAC_OSX
2179 MacHiliteChanged() ;
2182 wxWindowList::compatibility_iterator node
= GetChildren().GetFirst();
2185 child
= node
->GetData();
2186 if (child
/* && child->IsEnabled() */)
2187 child
->MacPropagateHiliteChanged() ;
2189 node
= node
->GetNext();
2195 // status change notifications
2198 void wxWindowMac::MacVisibilityChanged()
2202 void wxWindowMac::MacHiliteChanged()
2206 void wxWindowMac::MacEnabledStateChanged()
2211 // status queries on the inherited window's state
2214 bool wxWindowMac::MacIsReallyShown()
2216 // only under OSX the visibility of the TLW is taken into account
2217 if ( m_isBeingDeleted
)
2220 #if TARGET_API_MAC_OSX
2221 if ( m_peer
&& m_peer
->Ok() )
2222 return m_peer
->IsVisible();
2225 wxWindow
* win
= this ;
2226 while ( win
->IsShown() )
2228 if ( win
->IsTopLevel() )
2231 win
= win
->GetParent() ;
2239 bool wxWindowMac::MacIsReallyEnabled()
2241 return m_peer
->IsEnabled() ;
2244 bool wxWindowMac::MacIsReallyHilited()
2246 return m_peer
->IsActive();
2249 void wxWindowMac::MacFlashInvalidAreas()
2251 #if TARGET_API_MAC_OSX
2252 HIViewFlashDirtyArea( (WindowRef
) MacGetTopLevelWindowRef() ) ;
2256 int wxWindowMac::GetCharHeight() const
2258 wxClientDC
dc( (wxWindowMac
*)this ) ;
2260 return dc
.GetCharHeight() ;
2263 int wxWindowMac::GetCharWidth() const
2265 wxClientDC
dc( (wxWindowMac
*)this ) ;
2267 return dc
.GetCharWidth() ;
2270 void wxWindowMac::GetTextExtent(const wxString
& string
, int *x
, int *y
,
2271 int *descent
, int *externalLeading
, const wxFont
*theFont
) const
2273 const wxFont
*fontToUse
= theFont
;
2275 fontToUse
= &m_font
;
2277 wxClientDC
dc( (wxWindowMac
*) this ) ;
2279 dc
.GetTextExtent( string
, &lx
, &ly
, &ld
, &le
, (wxFont
*)fontToUse
) ;
2280 if ( externalLeading
)
2281 *externalLeading
= le
;
2291 * Rect is given in client coordinates, for further reading, read wxTopLevelWindowMac::InvalidateRect
2292 * we always intersect with the entire window, not only with the client area
2295 void wxWindowMac::Refresh(bool eraseBack
, const wxRect
*rect
)
2297 if ( m_peer
== NULL
)
2300 if ( !MacIsReallyShown() )
2307 wxMacRectToNative( rect
, &r
) ;
2308 m_peer
->SetNeedsDisplay( &r
) ;
2312 m_peer
->SetNeedsDisplay() ;
2316 void wxWindowMac::Freeze()
2318 #if TARGET_API_MAC_OSX
2319 if ( !m_frozenness
++ )
2321 if ( m_peer
&& m_peer
->Ok() )
2322 m_peer
->SetDrawingEnabled( false ) ;
2327 void wxWindowMac::Thaw()
2329 #if TARGET_API_MAC_OSX
2330 wxASSERT_MSG( m_frozenness
> 0, wxT("Thaw() without matching Freeze()") );
2332 if ( !--m_frozenness
)
2334 if ( m_peer
&& m_peer
->Ok() )
2336 m_peer
->SetDrawingEnabled( true ) ;
2337 m_peer
->InvalidateWithChildren() ;
2343 bool wxWindowMac::IsFrozen() const
2345 return m_frozenness
!= 0;
2348 wxWindowMac
*wxGetActiveWindow()
2350 // actually this is a windows-only concept
2354 // Coordinates relative to the window
2355 void wxWindowMac::WarpPointer(int x_pos
, int y_pos
)
2357 // We really don't move the mouse programmatically under Mac.
2360 void wxWindowMac::OnEraseBackground(wxEraseEvent
& event
)
2362 if ( MacGetTopLevelWindow() == NULL
)
2365 #if TARGET_API_MAC_OSX
2366 if ( !m_macBackgroundBrush
.Ok() || m_macBackgroundBrush
.GetStyle() == wxTRANSPARENT
)
2373 event
.GetDC()->Clear() ;
2377 void wxWindowMac::OnNcPaint( wxNcPaintEvent
& event
)
2382 int wxWindowMac::GetScrollPos(int orient
) const
2384 if ( orient
== wxHORIZONTAL
)
2387 return m_hScrollBar
->GetThumbPosition() ;
2392 return m_vScrollBar
->GetThumbPosition() ;
2398 // This now returns the whole range, not just the number
2399 // of positions that we can scroll.
2400 int wxWindowMac::GetScrollRange(int orient
) const
2402 if ( orient
== wxHORIZONTAL
)
2405 return m_hScrollBar
->GetRange() ;
2410 return m_vScrollBar
->GetRange() ;
2416 int wxWindowMac::GetScrollThumb(int orient
) const
2418 if ( orient
== wxHORIZONTAL
)
2421 return m_hScrollBar
->GetThumbSize() ;
2426 return m_vScrollBar
->GetThumbSize() ;
2432 void wxWindowMac::SetScrollPos(int orient
, int pos
, bool refresh
)
2434 if ( orient
== wxHORIZONTAL
)
2437 m_hScrollBar
->SetThumbPosition( pos
) ;
2442 m_vScrollBar
->SetThumbPosition( pos
) ;
2447 // we draw borders and grow boxes, are already set up and clipped in the current port / cgContextRef
2448 // our own window origin is at leftOrigin/rightOrigin
2451 void wxWindowMac::MacPaintBorders( int leftOrigin
, int rightOrigin
)
2457 bool hasFocus
= m_peer
->NeedsFocusRect() && m_peer
->HasFocus() ;
2458 bool hasBothScrollbars
= (m_hScrollBar
&& m_hScrollBar
->IsShown()) && (m_vScrollBar
&& m_vScrollBar
->IsShown()) ;
2460 // back to the surrounding frame rectangle
2461 m_peer
->GetRect( &rect
) ;
2462 InsetRect( &rect
, -1 , -1 ) ;
2464 #if wxMAC_USE_CORE_GRAPHICS
2466 CGRect cgrect
= CGRectMake( rect
.left
, rect
.top
, rect
.right
- rect
.left
,
2467 rect
.bottom
- rect
.top
) ;
2469 HIThemeFrameDrawInfo info
;
2470 memset( &info
, 0 , sizeof(info
) ) ;
2474 info
.state
= IsEnabled() ? kThemeStateActive
: kThemeStateInactive
;
2475 info
.isFocused
= hasFocus
;
2477 CGContextRef cgContext
= (CGContextRef
) GetParent()->MacGetCGContextRef() ;
2478 wxASSERT( cgContext
) ;
2480 if ( HasFlag(wxRAISED_BORDER
) || HasFlag(wxSUNKEN_BORDER
) || HasFlag(wxDOUBLE_BORDER
) )
2482 info
.kind
= kHIThemeFrameTextFieldSquare
;
2483 HIThemeDrawFrame( &cgrect
, &info
, cgContext
, kHIThemeOrientationNormal
) ;
2485 else if ( HasFlag(wxSIMPLE_BORDER
) )
2487 info
.kind
= kHIThemeFrameListBox
;
2488 HIThemeDrawFrame( &cgrect
, &info
, cgContext
, kHIThemeOrientationNormal
) ;
2490 else if ( hasFocus
)
2492 HIThemeDrawFocusRect( &cgrect
, true , cgContext
, kHIThemeOrientationNormal
) ;
2495 m_peer
->GetRect( &rect
) ;
2496 if ( hasBothScrollbars
)
2498 int size
= m_hScrollBar
->GetWindowVariant() == wxWINDOW_VARIANT_NORMAL
? 16 : 12 ;
2499 CGRect cgrect
= CGRectMake( rect
.right
- size
, rect
.bottom
- size
, size
, size
) ;
2500 CGPoint cgpoint
= CGPointMake( rect
.right
- size
, rect
.bottom
- size
) ;
2501 HIThemeGrowBoxDrawInfo info
;
2502 memset( &info
, 0, sizeof(info
) ) ;
2504 info
.state
= IsEnabled() ? kThemeStateActive
: kThemeStateInactive
;
2505 info
.kind
= kHIThemeGrowBoxKindNone
;
2506 info
.size
= kHIThemeGrowBoxSizeNormal
;
2507 info
.direction
= kThemeGrowRight
| kThemeGrowDown
;
2508 HIThemeDrawGrowBox( &cgpoint
, &info
, cgContext
, kHIThemeOrientationNormal
) ;
2513 wxTopLevelWindowMac
* top
= MacGetTopLevelWindow();
2517 wxMacControl::Convert( &pt
, GetParent()->m_peer
, top
->m_peer
) ;
2518 OffsetRect( &rect
, pt
.x
, pt
.y
) ;
2521 if ( HasFlag(wxRAISED_BORDER
) || HasFlag( wxSUNKEN_BORDER
) || HasFlag(wxDOUBLE_BORDER
) )
2522 DrawThemeEditTextFrame( &rect
, IsEnabled() ? kThemeStateActive
: kThemeStateInactive
) ;
2523 else if ( HasFlag(wxSIMPLE_BORDER
) )
2524 DrawThemeListBoxFrame( &rect
, IsEnabled() ? kThemeStateActive
: kThemeStateInactive
) ;
2527 DrawThemeFocusRect( &rect
, true ) ;
2529 if ( hasBothScrollbars
)
2531 // GetThemeStandaloneGrowBoxBounds
2532 // DrawThemeStandaloneNoGrowBox
2538 void wxWindowMac::RemoveChild( wxWindowBase
*child
)
2540 if ( child
== m_hScrollBar
)
2541 m_hScrollBar
= NULL
;
2542 if ( child
== m_vScrollBar
)
2543 m_vScrollBar
= NULL
;
2545 wxWindowBase::RemoveChild( child
) ;
2548 // New function that will replace some of the above.
2549 void wxWindowMac::SetScrollbar(int orient
, int pos
, int thumbVisible
,
2550 int range
, bool refresh
)
2553 bool triggerSizeEvent
= false;
2555 if ( orient
== wxHORIZONTAL
)
2559 showScroller
= ((range
!= 0) && (range
> thumbVisible
));
2560 if ( m_hScrollBar
->IsShown() != showScroller
)
2562 m_hScrollBar
->Show( showScroller
);
2563 triggerSizeEvent
= true;
2566 m_hScrollBar
->SetScrollbar( pos
, thumbVisible
, range
, thumbVisible
, refresh
) ;
2573 showScroller
= ((range
!= 0) && (range
> thumbVisible
));
2574 if ( m_vScrollBar
->IsShown() != showScroller
)
2576 m_vScrollBar
->Show( showScroller
) ;
2577 triggerSizeEvent
= true;
2580 m_vScrollBar
->SetScrollbar( pos
, thumbVisible
, range
, thumbVisible
, refresh
) ;
2584 MacRepositionScrollBars() ;
2585 if ( triggerSizeEvent
)
2587 wxSizeEvent
event(GetSize(), m_windowId
);
2588 event
.SetEventObject(this);
2589 GetEventHandler()->ProcessEvent(event
);
2593 // Does a physical scroll
2594 void wxWindowMac::ScrollWindow(int dx
, int dy
, const wxRect
*rect
)
2596 if ( dx
== 0 && dy
== 0 )
2599 int width
, height
;
2600 GetClientSize( &width
, &height
) ;
2603 // note there currently is a bug in OSX which makes inefficient refreshes in case an entire control
2604 // area is scrolled, this does not occur if width and height are 2 pixels less,
2605 // TODO: write optimal workaround
2606 wxRect
scrollrect( MacGetLeftBorderSize() , MacGetTopBorderSize() , width
, height
) ;
2608 scrollrect
.Intersect( *rect
) ;
2610 if ( m_peer
->GetNeedsDisplay() )
2612 // because HIViewScrollRect does not scroll the already invalidated area we have two options:
2613 // either immediate redraw or full invalidate
2615 // is the better overall solution, as it does not slow down scrolling
2616 m_peer
->SetNeedsDisplay() ;
2618 // this would be the preferred version for fast drawing controls
2620 #if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_3
2621 if ( UMAGetSystemVersion() >= 0x1030 )
2622 HIViewRender(m_peer
->GetControlRef()) ;
2629 // as the native control might be not a 0/0 wx window coordinates, we have to offset
2630 scrollrect
.Offset( -MacGetLeftBorderSize() , -MacGetTopBorderSize() ) ;
2631 m_peer
->ScrollRect( &scrollrect
, dx
, dy
) ;
2633 // becuase HIViewScrollRect does not scroll the already invalidated area we have two options
2634 // either immediate redraw or full invalidate
2636 // is the better overall solution, as it does not slow down scrolling
2637 m_peer
->SetNeedsDisplay() ;
2639 // this would be the preferred version for fast drawing controls
2641 HIViewRender(m_peer
->GetControlRef()) ;
2647 for (wxWindowList::compatibility_iterator node
= GetChildren().GetFirst(); node
; node
= node
->GetNext())
2649 child
= node
->GetData();
2652 if (child
== m_vScrollBar
)
2654 if (child
== m_hScrollBar
)
2656 if (child
->IsTopLevel())
2659 child
->GetPosition( &x
, &y
);
2660 child
->GetSize( &w
, &h
);
2663 wxRect
rc( x
, y
, w
, h
);
2664 if (rect
->Intersects( rc
))
2665 child
->SetSize( x
+ dx
, y
+ dy
, w
, h
);
2669 child
->SetSize( x
+ dx
, y
+ dy
, w
, h
);
2674 void wxWindowMac::MacOnScroll( wxScrollEvent
&event
)
2676 if ( event
.GetEventObject() == m_vScrollBar
|| event
.GetEventObject() == m_hScrollBar
)
2678 wxScrollWinEvent wevent
;
2679 wevent
.SetPosition(event
.GetPosition());
2680 wevent
.SetOrientation(event
.GetOrientation());
2681 wevent
.SetEventObject(this);
2683 if (event
.GetEventType() == wxEVT_SCROLL_TOP
)
2684 wevent
.SetEventType( wxEVT_SCROLLWIN_TOP
);
2685 else if (event
.GetEventType() == wxEVT_SCROLL_BOTTOM
)
2686 wevent
.SetEventType( wxEVT_SCROLLWIN_BOTTOM
);
2687 else if (event
.GetEventType() == wxEVT_SCROLL_LINEUP
)
2688 wevent
.SetEventType( wxEVT_SCROLLWIN_LINEUP
);
2689 else if (event
.GetEventType() == wxEVT_SCROLL_LINEDOWN
)
2690 wevent
.SetEventType( wxEVT_SCROLLWIN_LINEDOWN
);
2691 else if (event
.GetEventType() == wxEVT_SCROLL_PAGEUP
)
2692 wevent
.SetEventType( wxEVT_SCROLLWIN_PAGEUP
);
2693 else if (event
.GetEventType() == wxEVT_SCROLL_PAGEDOWN
)
2694 wevent
.SetEventType( wxEVT_SCROLLWIN_PAGEDOWN
);
2695 else if (event
.GetEventType() == wxEVT_SCROLL_THUMBTRACK
)
2696 wevent
.SetEventType( wxEVT_SCROLLWIN_THUMBTRACK
);
2697 else if (event
.GetEventType() == wxEVT_SCROLL_THUMBRELEASE
)
2698 wevent
.SetEventType( wxEVT_SCROLLWIN_THUMBRELEASE
);
2700 GetEventHandler()->ProcessEvent(wevent
);
2704 // Get the window with the focus
2705 wxWindowMac
*wxWindowBase::DoFindFocus()
2707 ControlRef control
;
2708 GetKeyboardFocus( GetUserFocusWindow() , &control
) ;
2709 return wxFindControlFromMacControl( control
) ;
2712 void wxWindowMac::OnSetFocus( wxFocusEvent
& event
)
2714 // panel wants to track the window which was the last to have focus in it,
2715 // so we want to set ourselves as the window which last had focus
2717 // notice that it's also important to do it upwards the tree because
2718 // otherwise when the top level panel gets focus, it won't set it back to
2719 // us, but to some other sibling
2721 // CS: don't know if this is still needed:
2722 //wxChildFocusEvent eventFocus(this);
2723 //(void)GetEventHandler()->ProcessEvent(eventFocus);
2725 if ( MacGetTopLevelWindow() && m_peer
->NeedsFocusRect() )
2727 #if wxMAC_USE_CORE_GRAPHICS
2728 GetParent()->Refresh() ;
2730 wxMacWindowStateSaver
sv( this ) ;
2733 m_peer
->GetRect( &rect
) ;
2734 // auf den umgebenden Rahmen zur\9fck
2735 InsetRect( &rect
, -1 , -1 ) ;
2737 wxTopLevelWindowMac
* top
= MacGetTopLevelWindow();
2741 wxMacControl::Convert( &pt
, GetParent()->m_peer
, top
->m_peer
) ;
2743 rect
.right
+= pt
.x
;
2745 rect
.bottom
+= pt
.y
;
2748 bool bIsFocusEvent
= (event
.GetEventType() == wxEVT_SET_FOCUS
);
2749 DrawThemeFocusRect( &rect
, bIsFocusEvent
) ;
2750 if ( !bIsFocusEvent
)
2752 // as this erases part of the frame we have to redraw borders
2753 // and because our z-ordering is not always correct (staticboxes)
2754 // we have to invalidate things, we cannot simple redraw
2755 MacInvalidateBorders() ;
2763 void wxWindowMac::OnInternalIdle()
2765 // This calls the UI-update mechanism (querying windows for
2766 // menu/toolbar/control state information)
2767 if (wxUpdateUIEvent::CanUpdate(this))
2768 UpdateWindowUI(wxUPDATE_UI_FROMIDLE
);
2771 // Raise the window to the top of the Z order
2772 void wxWindowMac::Raise()
2774 m_peer
->SetZOrder( true , NULL
) ;
2777 // Lower the window to the bottom of the Z order
2778 void wxWindowMac::Lower()
2780 m_peer
->SetZOrder( false , NULL
) ;
2783 // static wxWindow *gs_lastWhich = NULL;
2785 bool wxWindowMac::MacSetupCursor( const wxPoint
& pt
)
2787 // first trigger a set cursor event
2789 wxPoint clientorigin
= GetClientAreaOrigin() ;
2790 wxSize clientsize
= GetClientSize() ;
2792 if ( wxRect2DInt( clientorigin
.x
, clientorigin
.y
, clientsize
.x
, clientsize
.y
).Contains( wxPoint2DInt( pt
) ) )
2794 wxSetCursorEvent
event( pt
.x
, pt
.y
);
2796 bool processedEvtSetCursor
= GetEventHandler()->ProcessEvent(event
);
2797 if ( processedEvtSetCursor
&& event
.HasCursor() )
2799 cursor
= event
.GetCursor() ;
2803 // the test for processedEvtSetCursor is here to prevent using m_cursor
2804 // if the user code caught EVT_SET_CURSOR() and returned nothing from
2805 // it - this is a way to say that our cursor shouldn't be used for this
2807 if ( !processedEvtSetCursor
&& m_cursor
.Ok() )
2810 if ( !wxIsBusy() && !GetParent() )
2811 cursor
= *wxSTANDARD_CURSOR
;
2815 cursor
.MacInstall() ;
2818 return cursor
.Ok() ;
2821 wxString
wxWindowMac::MacGetToolTipString( wxPoint
&pt
)
2825 return m_tooltip
->GetTip() ;
2828 return wxEmptyString
;
2831 void wxWindowMac::ClearBackground()
2837 void wxWindowMac::Update()
2839 #if TARGET_API_MAC_OSX
2840 MacGetTopLevelWindow()->MacPerformUpdates() ;
2842 ::Draw1Control( m_peer
->GetControlRef() ) ;
2846 wxTopLevelWindowMac
* wxWindowMac::MacGetTopLevelWindow() const
2848 wxTopLevelWindowMac
* win
= NULL
;
2849 WindowRef window
= (WindowRef
) MacGetTopLevelWindowRef() ;
2851 win
= wxFindWinFromMacWindow( window
) ;
2856 const wxRect
& wxWindowMac::MacGetClippedClientRect() const
2858 MacUpdateClippedRects() ;
2860 return m_cachedClippedClientRect
;
2863 const wxRect
& wxWindowMac::MacGetClippedRect() const
2865 MacUpdateClippedRects() ;
2867 return m_cachedClippedRect
;
2870 const wxRect
&wxWindowMac:: MacGetClippedRectWithOuterStructure() const
2872 MacUpdateClippedRects() ;
2874 return m_cachedClippedRectWithOuterStructure
;
2877 const wxRegion
& wxWindowMac::MacGetVisibleRegion( bool includeOuterStructures
)
2879 static wxRegion emptyrgn
;
2881 if ( !m_isBeingDeleted
&& MacIsReallyShown() /*m_peer->IsVisible() */ )
2883 MacUpdateClippedRects() ;
2884 if ( includeOuterStructures
)
2885 return m_cachedClippedRegionWithOuterStructure
;
2887 return m_cachedClippedRegion
;
2895 void wxWindowMac::MacUpdateClippedRects() const
2897 if ( m_cachedClippedRectValid
)
2900 // includeOuterStructures is true if we try to draw somthing like a focus ring etc.
2901 // also a window dc uses this, in this case we only clip in the hierarchy for hard
2902 // borders like a scrollwindow, splitter etc otherwise we end up in a paranoia having
2903 // to add focus borders everywhere
2905 Rect r
, rIncludingOuterStructures
;
2907 m_peer
->GetRect( &r
) ;
2908 r
.left
-= MacGetLeftBorderSize() ;
2909 r
.top
-= MacGetTopBorderSize() ;
2910 r
.bottom
+= MacGetBottomBorderSize() ;
2911 r
.right
+= MacGetRightBorderSize() ;
2918 rIncludingOuterStructures
= r
;
2919 InsetRect( &rIncludingOuterStructures
, -4 , -4 ) ;
2921 wxRect cl
= GetClientRect() ;
2922 Rect rClient
= { cl
.y
, cl
.x
, cl
.y
+ cl
.height
, cl
.x
+ cl
.width
} ;
2926 const wxWindow
* child
= this ;
2927 const wxWindow
* parent
= NULL
;
2929 while ( !child
->IsTopLevel() && ( parent
= child
->GetParent() ) != NULL
)
2931 if ( parent
->MacIsChildOfClientArea(child
) )
2933 size
= parent
->GetClientSize() ;
2934 wxPoint origin
= parent
->GetClientAreaOrigin() ;
2940 // this will be true for scrollbars, toolbars etc.
2941 size
= parent
->GetSize() ;
2942 y
= parent
->MacGetTopBorderSize() ;
2943 x
= parent
->MacGetLeftBorderSize() ;
2944 size
.x
-= parent
->MacGetLeftBorderSize() + parent
->MacGetRightBorderSize() ;
2945 size
.y
-= parent
->MacGetTopBorderSize() + parent
->MacGetBottomBorderSize() ;
2948 parent
->MacWindowToRootWindow( &x
, &y
) ;
2949 MacRootWindowToWindow( &x
, &y
) ;
2951 Rect rparent
= { y
, x
, y
+ size
.y
, x
+ size
.x
} ;
2953 // the wxwindow and client rects will always be clipped
2954 SectRect( &r
, &rparent
, &r
) ;
2955 SectRect( &rClient
, &rparent
, &rClient
) ;
2957 // the structure only at 'hard' borders
2958 if ( parent
->MacClipChildren() ||
2959 ( parent
->GetParent() && parent
->GetParent()->MacClipGrandChildren() ) )
2961 SectRect( &rIncludingOuterStructures
, &rparent
, &rIncludingOuterStructures
) ;
2967 m_cachedClippedRect
= wxRect( r
.left
, r
.top
, r
.right
- r
.left
, r
.bottom
- r
.top
) ;
2968 m_cachedClippedClientRect
= wxRect( rClient
.left
, rClient
.top
,
2969 rClient
.right
- rClient
.left
, rClient
.bottom
- rClient
.top
) ;
2970 m_cachedClippedRectWithOuterStructure
= wxRect(
2971 rIncludingOuterStructures
.left
, rIncludingOuterStructures
.top
,
2972 rIncludingOuterStructures
.right
- rIncludingOuterStructures
.left
,
2973 rIncludingOuterStructures
.bottom
- rIncludingOuterStructures
.top
) ;
2975 m_cachedClippedRegionWithOuterStructure
= wxRegion( m_cachedClippedRectWithOuterStructure
) ;
2976 m_cachedClippedRegion
= wxRegion( m_cachedClippedRect
) ;
2977 m_cachedClippedClientRegion
= wxRegion( m_cachedClippedClientRect
) ;
2979 m_cachedClippedRectValid
= true ;
2983 This function must not change the updatergn !
2985 bool wxWindowMac::MacDoRedraw( WXHRGN updatergnr
, long time
)
2987 bool handled
= false ;
2989 RgnHandle updatergn
= (RgnHandle
) updatergnr
;
2990 GetRegionBounds( updatergn
, &updatebounds
) ;
2992 // wxLogDebug(wxT("update for %s bounds %d, %d, %d, %d"), wxString(GetClassInfo()->GetClassName()).c_str(), updatebounds.left, updatebounds.top , updatebounds.right , updatebounds.bottom ) ;
2994 if ( !EmptyRgn(updatergn
) )
2996 RgnHandle newupdate
= NewRgn() ;
2997 wxSize point
= GetClientSize() ;
2998 wxPoint origin
= GetClientAreaOrigin() ;
2999 SetRectRgn( newupdate
, origin
.x
, origin
.y
, origin
.x
+ point
.x
, origin
.y
+ point
.y
) ;
3000 SectRgn( newupdate
, updatergn
, newupdate
) ;
3002 // first send an erase event to the entire update area
3004 // for the toplevel window this really is the entire area
3005 // for all the others only their client area, otherwise they
3006 // might be drawing with full alpha and eg put blue into
3007 // the grow-box area of a scrolled window (scroll sample)
3008 wxDC
* dc
= new wxWindowDC(this);
3010 dc
->SetClippingRegion(wxRegion(updatergn
));
3012 dc
->SetClippingRegion(wxRegion(newupdate
));
3014 wxEraseEvent
eevent( GetId(), dc
);
3015 eevent
.SetEventObject( this );
3016 GetEventHandler()->ProcessEvent( eevent
);
3020 // calculate a client-origin version of the update rgn and set m_updateRegion to that
3021 OffsetRgn( newupdate
, -origin
.x
, -origin
.y
) ;
3022 m_updateRegion
= newupdate
;
3023 DisposeRgn( newupdate
) ;
3025 if ( !m_updateRegion
.Empty() )
3027 // paint the window itself
3030 event
.SetTimestamp(time
);
3031 event
.SetEventObject(this);
3032 GetEventHandler()->ProcessEvent(event
);
3036 // now we cannot rely on having its borders drawn by a window itself, as it does not
3037 // get the updateRgn wide enough to always do so, so we do it from the parent
3038 // this would also be the place to draw any custom backgrounds for native controls
3039 // in Composited windowing
3040 wxPoint clientOrigin
= GetClientAreaOrigin() ;
3044 for (wxWindowList::compatibility_iterator node
= GetChildren().GetFirst(); node
; node
= node
->GetNext())
3046 child
= node
->GetData();
3049 if (child
== m_vScrollBar
)
3051 if (child
== m_hScrollBar
)
3053 if (child
->IsTopLevel())
3055 if (!child
->IsShown())
3058 // only draw those in the update region (add a safety margin of 10 pixels for shadow effects
3060 child
->GetPosition( &x
, &y
);
3061 child
->GetSize( &w
, &h
);
3062 Rect childRect
= { y
, x
, y
+ h
, x
+ w
} ;
3063 OffsetRect( &childRect
, clientOrigin
.x
, clientOrigin
.y
) ;
3064 InsetRect( &childRect
, -10 , -10) ;
3066 if ( RectInRgn( &childRect
, updatergn
) )
3068 // paint custom borders
3069 wxNcPaintEvent
eventNc( child
->GetId() );
3070 eventNc
.SetEventObject( child
);
3071 if ( !child
->GetEventHandler()->ProcessEvent( eventNc
) )
3073 #if wxMAC_USE_CORE_GRAPHICS
3074 child
->MacPaintBorders(0, 0) ;
3077 wxWindowDC
dc(this) ;
3078 dc
.SetClippingRegion(wxRegion(updatergn
));
3079 wxMacPortSetter
helper(&dc
) ;
3080 child
->MacPaintBorders(0, 0) ;
3092 WXWindow
wxWindowMac::MacGetTopLevelWindowRef() const
3094 wxWindowMac
*iter
= (wxWindowMac
*)this ;
3098 if ( iter
->IsTopLevel() )
3099 return ((wxTopLevelWindow
*)iter
)->MacGetWindowRef() ;
3101 iter
= iter
->GetParent() ;
3107 void wxWindowMac::MacCreateScrollBars( long style
)
3109 wxASSERT_MSG( m_vScrollBar
== NULL
&& m_hScrollBar
== NULL
, wxT("attempt to create window twice") ) ;
3111 if ( style
& ( wxVSCROLL
| wxHSCROLL
) )
3113 bool hasBoth
= ( style
& wxVSCROLL
) && ( style
& wxHSCROLL
) ;
3114 int scrlsize
= MAC_SCROLLBAR_SIZE
;
3115 if ( GetWindowVariant() == wxWINDOW_VARIANT_SMALL
|| GetWindowVariant() == wxWINDOW_VARIANT_MINI
)
3117 scrlsize
= MAC_SMALL_SCROLLBAR_SIZE
;
3120 int adjust
= hasBoth
? scrlsize
- 1: 0 ;
3122 GetClientSize( &width
, &height
) ;
3124 wxPoint
vPoint(width
- scrlsize
, 0) ;
3125 wxSize
vSize(scrlsize
, height
- adjust
) ;
3126 wxPoint
hPoint(0, height
- scrlsize
) ;
3127 wxSize
hSize(width
- adjust
, scrlsize
) ;
3129 if ( style
& wxVSCROLL
)
3130 m_vScrollBar
= new wxScrollBar(this, wxID_ANY
, vPoint
, vSize
, wxVERTICAL
);
3132 if ( style
& wxHSCROLL
)
3133 m_hScrollBar
= new wxScrollBar(this, wxID_ANY
, hPoint
, hSize
, wxHORIZONTAL
);
3136 // because the create does not take into account the client area origin
3137 // we might have a real position shift
3138 MacRepositionScrollBars() ;
3141 bool wxWindowMac::MacIsChildOfClientArea( const wxWindow
* child
) const
3143 bool result
= ((child
== NULL
) || ((child
!= m_hScrollBar
) && (child
!= m_vScrollBar
)));
3148 void wxWindowMac::MacRepositionScrollBars()
3150 if ( !m_hScrollBar
&& !m_vScrollBar
)
3153 bool hasBoth
= (m_hScrollBar
&& m_hScrollBar
->IsShown()) && ( m_vScrollBar
&& m_vScrollBar
->IsShown()) ;
3154 int scrlsize
= m_hScrollBar
? m_hScrollBar
->GetSize().y
: ( m_vScrollBar
? m_vScrollBar
->GetSize().x
: MAC_SCROLLBAR_SIZE
) ;
3155 int adjust
= hasBoth
? scrlsize
- 1 : 0 ;
3157 // get real client area
3159 GetSize( &width
, &height
);
3161 width
-= MacGetLeftBorderSize() + MacGetRightBorderSize();
3162 height
-= MacGetTopBorderSize() + MacGetBottomBorderSize();
3164 wxPoint
vPoint( width
- scrlsize
, 0 ) ;
3165 wxSize
vSize( scrlsize
, height
- adjust
) ;
3166 wxPoint
hPoint( 0 , height
- scrlsize
) ;
3167 wxSize
hSize( width
- adjust
, scrlsize
) ;
3170 int x
= 0, y
= 0, w
, h
;
3171 GetSize( &w
, &h
) ;
3173 MacClientToRootWindow( &x
, &y
) ;
3174 MacClientToRootWindow( &w
, &h
) ;
3176 wxWindowMac
*iter
= (wxWindowMac
*)this ;
3178 int totW
= 10000 , totH
= 10000;
3181 if ( iter
->IsTopLevel() )
3183 iter
->GetSize( &totW
, &totH
) ;
3187 iter
= iter
->GetParent() ;
3201 if ( w
- x
>= totW
)
3206 if ( h
- y
>= totH
)
3214 m_vScrollBar
->SetSize( vPoint
.x
, vPoint
.y
, vSize
.x
, vSize
.y
, wxSIZE_ALLOW_MINUS_ONE
);
3216 m_hScrollBar
->SetSize( hPoint
.x
, hPoint
.y
, hSize
.x
, hSize
.y
, wxSIZE_ALLOW_MINUS_ONE
);
3219 bool wxWindowMac::AcceptsFocus() const
3221 return MacCanFocus() && wxWindowBase::AcceptsFocus();
3224 void wxWindowMac::MacSuperChangedPosition()
3226 // only window-absolute structures have to be moved i.e. controls
3228 m_cachedClippedRectValid
= false ;
3231 wxWindowList::compatibility_iterator node
= GetChildren().GetFirst();
3234 child
= node
->GetData();
3235 child
->MacSuperChangedPosition() ;
3237 node
= node
->GetNext();
3241 void wxWindowMac::MacTopLevelWindowChangedPosition()
3243 // only screen-absolute structures have to be moved i.e. glcanvas
3246 wxWindowList::compatibility_iterator node
= GetChildren().GetFirst();
3249 child
= node
->GetData();
3250 child
->MacTopLevelWindowChangedPosition() ;
3252 node
= node
->GetNext();
3256 long wxWindowMac::MacGetLeftBorderSize() const
3263 if (HasFlag(wxRAISED_BORDER
) || HasFlag( wxSUNKEN_BORDER
) || HasFlag(wxDOUBLE_BORDER
))
3265 // this metric is only the 'outset' outside the simple frame rect
3266 GetThemeMetric( kThemeMetricEditTextFrameOutset
, &border
) ;
3269 else if (HasFlag(wxSIMPLE_BORDER
))
3271 // this metric is only the 'outset' outside the simple frame rect
3272 GetThemeMetric( kThemeMetricListBoxFrameOutset
, &border
) ;
3279 long wxWindowMac::MacGetRightBorderSize() const
3281 // they are all symmetric in mac themes
3282 return MacGetLeftBorderSize() ;
3285 long wxWindowMac::MacGetTopBorderSize() const
3287 // they are all symmetric in mac themes
3288 return MacGetLeftBorderSize() ;
3291 long wxWindowMac::MacGetBottomBorderSize() const
3293 // they are all symmetric in mac themes
3294 return MacGetLeftBorderSize() ;
3297 long wxWindowMac::MacRemoveBordersFromStyle( long style
)
3299 return style
& ~wxBORDER_MASK
;
3302 // Find the wxWindowMac at the current mouse position, returning the mouse
3304 wxWindowMac
* wxFindWindowAtPointer( wxPoint
& pt
)
3306 pt
= wxGetMousePosition();
3307 wxWindowMac
* found
= wxFindWindowAtPoint(pt
);
3312 // Get the current mouse position.
3313 wxPoint
wxGetMousePosition()
3317 wxGetMousePosition( &x
, &y
);
3319 return wxPoint(x
, y
);
3322 void wxWindowMac::OnMouseEvent( wxMouseEvent
&event
)
3324 if ( event
.GetEventType() == wxEVT_RIGHT_DOWN
)
3326 // copied from wxGTK : CS
3327 // VZ: shouldn't we move this to base class then?
3329 // generate a "context menu" event: this is similar to wxEVT_RIGHT_DOWN
3332 // (a) it's a command event and so is propagated to the parent
3333 // (b) under MSW it can be generated from kbd too
3334 // (c) it uses screen coords (because of (a))
3335 wxContextMenuEvent
evtCtx(wxEVT_CONTEXT_MENU
,
3337 this->ClientToScreen(event
.GetPosition()));
3338 if ( ! GetEventHandler()->ProcessEvent(evtCtx
) )
3347 void wxWindowMac::OnPaint( wxPaintEvent
& event
)
3349 if ( wxTheApp
->MacGetCurrentEvent() != NULL
&& wxTheApp
->MacGetCurrentEventHandlerCallRef() != NULL
)
3350 CallNextEventHandler(
3351 (EventHandlerCallRef
)wxTheApp
->MacGetCurrentEventHandlerCallRef() ,
3352 (EventRef
) wxTheApp
->MacGetCurrentEvent() ) ;
3355 void wxWindowMac::MacHandleControlClick( WXWidget control
, wxInt16 controlpart
, bool WXUNUSED( mouseStillDown
) )
3359 Rect
wxMacGetBoundsForControl( wxWindow
* window
, const wxPoint
& pos
, const wxSize
&size
, bool adjustForOrigin
)
3363 window
->MacGetBoundsForControl( pos
, size
, x
, y
, w
, h
, adjustForOrigin
) ;
3364 Rect bounds
= { y
, x
, y
+ h
, x
+ w
};
3369 wxInt32
wxWindowMac::MacControlHit(WXEVENTHANDLERREF
WXUNUSED(handler
) , WXEVENTREF
WXUNUSED(event
) )
3371 return eventNotHandledErr
;
3374 bool wxWindowMac::Reparent(wxWindowBase
*newParentBase
)
3376 wxWindowMac
*newParent
= (wxWindowMac
*)newParentBase
;
3377 if ( !wxWindowBase::Reparent(newParent
) )
3380 // copied from MacPostControlCreate
3381 ControlRef container
= (ControlRef
) GetParent()->GetHandle() ;
3383 wxASSERT_MSG( container
!= NULL
, wxT("No valid mac container control") ) ;
3385 ::EmbedControl( m_peer
->GetControlRef() , container
) ;
3390 bool wxWindowMac::SetTransparent(wxByte alpha
)
3392 #if wxMAC_USE_CORE_GRAPHICS
3393 if ( alpha
!= m_macAlpha
)
3395 m_macAlpha
= alpha
;
3405 bool wxWindowMac::CanSetTransparent()
3407 #if wxMAC_USE_CORE_GRAPHICS
3414 wxByte
wxWindowMac::GetTransparent() const