📄 window.cpp
字号:
/////////////////////////////////////////////////////////////////////////////// Name: src/mac/carbon/window.cpp// Purpose: wxWindowMac// Author: Stefan Csomor// Modified by:// Created: 1998-01-01// RCS-ID: $Id: window.cpp,v 1.322 2006/10/31 08:49:45 RD Exp $// Copyright: (c) Stefan Csomor// Licence: wxWindows licence/////////////////////////////////////////////////////////////////////////////#include "wx/wxprec.h"#include "wx/window.h"#ifndef WX_PRECOMP #include "wx/log.h" #include "wx/app.h" #include "wx/utils.h" #include "wx/panel.h" #include "wx/frame.h" #include "wx/dc.h" #include "wx/dcclient.h" #include "wx/button.h" #include "wx/menu.h" #include "wx/dialog.h" #include "wx/settings.h" #include "wx/msgdlg.h" #include "wx/scrolbar.h" #include "wx/statbox.h" #include "wx/textctrl.h" #include "wx/toolbar.h" #include "wx/layout.h" #include "wx/statusbr.h" #include "wx/menuitem.h"#endif#include "wx/tooltip.h"#include "wx/spinctrl.h"#include "wx/geometry.h"#if wxUSE_CARET #include "wx/caret.h"#endif#if wxUSE_DRAG_AND_DROP#include "wx/dnd.h"#endif#include "wx/mac/uma.h"#define MAC_SCROLLBAR_SIZE 15#define MAC_SMALL_SCROLLBAR_SIZE 11#ifndef __DARWIN__#include <Windows.h>#include <ToolUtils.h>#include <Scrap.h>#include <MacTextEditor.h>#endif#if TARGET_API_MAC_OSX#ifndef __HIVIEW__ #include <HIToolbox/HIView.h>#endif#endif#include <string.h>#ifdef __WXUNIVERSAL__ IMPLEMENT_ABSTRACT_CLASS(wxWindowMac, wxWindowBase)#else IMPLEMENT_DYNAMIC_CLASS(wxWindow, wxWindowBase)#endifBEGIN_EVENT_TABLE(wxWindowMac, wxWindowBase) EVT_NC_PAINT(wxWindowMac::OnNcPaint) EVT_ERASE_BACKGROUND(wxWindowMac::OnEraseBackground)#if TARGET_API_MAC_OSX EVT_PAINT(wxWindowMac::OnPaint)#endif EVT_SET_FOCUS(wxWindowMac::OnSetFocus) EVT_KILL_FOCUS(wxWindowMac::OnSetFocus) EVT_MOUSE_EVENTS(wxWindowMac::OnMouseEvent)END_EVENT_TABLE()#define wxMAC_DEBUG_REDRAW 0#ifndef wxMAC_DEBUG_REDRAW#define wxMAC_DEBUG_REDRAW 0#endif// ---------------------------------------------------------------------------// Utility Routines to move between different coordinate systems// ---------------------------------------------------------------------------/* * Right now we have the following setup : * a border that is not part of the native control is always outside the * control's border (otherwise we loose all native intelligence, future ways * may be to have a second embedding control responsible for drawing borders * and backgrounds eventually) * so all this border calculations have to be taken into account when calling * native methods or getting native oriented data * so we have three coordinate systems here * wx client coordinates * wx window coordinates (including window frames) * native coordinates *///// originating from native control//void wxMacNativeToWindow( const wxWindow* window , RgnHandle handle ){ OffsetRgn( handle , window->MacGetLeftBorderSize() , window->MacGetTopBorderSize() ) ;}void wxMacNativeToWindow( const wxWindow* window , Rect *rect ){ OffsetRect( rect , window->MacGetLeftBorderSize() , window->MacGetTopBorderSize() ) ;}//// directed towards native control//void wxMacWindowToNative( const wxWindow* window , RgnHandle handle ){ OffsetRgn( handle , -window->MacGetLeftBorderSize() , -window->MacGetTopBorderSize() );}void wxMacWindowToNative( const wxWindow* window , Rect *rect ){ OffsetRect( rect , -window->MacGetLeftBorderSize() , -window->MacGetTopBorderSize() ) ;}// ---------------------------------------------------------------------------// Carbon Events// ---------------------------------------------------------------------------#if TARGET_API_MAC_OSX#if MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_3enum{ kEventControlVisibilityChanged = 157};#endif#endifstatic const EventTypeSpec eventList[] ={ { kEventClassCommand, kEventProcessCommand } , { kEventClassCommand, kEventCommandUpdateStatus } , { kEventClassControl , kEventControlHit } , { kEventClassTextInput, kEventTextInputUnicodeForKeyEvent } , { kEventClassTextInput, kEventTextInputUpdateActiveInputArea } , { kEventClassControl , kEventControlDraw } ,#if TARGET_API_MAC_OSX { kEventClassControl , kEventControlVisibilityChanged } , { kEventClassControl , kEventControlEnabledStateChanged } , { kEventClassControl , kEventControlHiliteChanged } ,#endif { kEventClassControl , kEventControlSetFocusPart } , { kEventClassService , kEventServiceGetTypes }, { kEventClassService , kEventServiceCopy }, { kEventClassService , kEventServicePaste },// { kEventClassControl , kEventControlInvalidateForSizeChange } , // 10.3 only// { kEventClassControl , kEventControlBoundsChanged } ,} ;static pascal OSStatus wxMacWindowControlEventHandler( EventHandlerCallRef handler , EventRef event , void *data ){ OSStatus result = eventNotHandledErr ; wxMacCarbonEvent cEvent( event ) ; ControlRef controlRef ; wxWindowMac* thisWindow = (wxWindowMac*) data ; cEvent.GetParameter( kEventParamDirectObject , &controlRef ) ; switch ( GetEventKind( event ) ) {#if TARGET_API_MAC_OSX case kEventControlDraw : { RgnHandle updateRgn = NULL ; RgnHandle allocatedRgn = NULL ; wxRegion visRegion = thisWindow->MacGetVisibleRegion() ; if ( cEvent.GetParameter<RgnHandle>(kEventParamRgnHandle, &updateRgn) != noErr ) { updateRgn = (RgnHandle) visRegion.GetWXHRGN() ; } else { if ( thisWindow->MacGetLeftBorderSize() != 0 || thisWindow->MacGetTopBorderSize() != 0 ) { // as this update region is in native window locals we must adapt it to wx window local allocatedRgn = NewRgn() ; CopyRgn( updateRgn , allocatedRgn ) ; // hide the given region by the new region that must be shifted wxMacNativeToWindow( thisWindow , allocatedRgn ) ; updateRgn = allocatedRgn ; } } Rect rgnBounds ; GetRegionBounds( updateRgn , &rgnBounds ) ;#if wxMAC_DEBUG_REDRAW if ( thisWindow->MacIsUserPane() ) { static float color = 0.5 ; static channel = 0 ; HIRect bounds; CGContextRef cgContext = cEvent.GetParameter<CGContextRef>(kEventParamCGContextRef) ; HIViewGetBounds( controlRef, &bounds ); CGContextSetRGBFillColor( cgContext, channel == 0 ? color : 0.5 , channel == 1 ? color : 0.5 , channel == 2 ? color : 0.5 , 1 ); CGContextFillRect( cgContext, bounds ); color += 0.1 ; if ( color > 0.9 ) { color = 0.5 ; channel++ ; if ( channel == 3 ) channel = 0 ; } }#endif {#if wxMAC_USE_CORE_GRAPHICS bool created = false ; CGContextRef cgContext = NULL ; OSStatus err = cEvent.GetParameter<CGContextRef>(kEventParamCGContextRef, &cgContext) ; wxASSERT_MSG( err == noErr , wxT("Unable to retrieve CGContextRef") ) ; thisWindow->MacSetCGContextRef( cgContext ) ; { wxMacCGContextStateSaver sg( cgContext ) ; float alpha = 1.0 ; { wxWindow* iter = thisWindow ; while ( iter ) { alpha *= (float) iter->GetTransparent()/255.0 ; if ( iter->IsTopLevel() ) iter = NULL ; else iter = iter->GetParent() ; } } CGContextSetAlpha( cgContext , alpha ) ;#endif if ( thisWindow->MacDoRedraw( updateRgn , cEvent.GetTicks() ) ) result = noErr ;#if wxMAC_USE_CORE_GRAPHICS thisWindow->MacSetCGContextRef( NULL ) ; } if ( created ) CGContextRelease( cgContext ) ;#endif } if ( allocatedRgn ) DisposeRgn( allocatedRgn ) ; } break ; case kEventControlVisibilityChanged : thisWindow->MacVisibilityChanged() ; break ; case kEventControlEnabledStateChanged : thisWindow->MacEnabledStateChanged() ; break ; case kEventControlHiliteChanged : thisWindow->MacHiliteChanged() ; break ;#endif // we emulate this event under Carbon CFM case kEventControlSetFocusPart : { Boolean focusEverything = false ; ControlPartCode controlPart = cEvent.GetParameter<ControlPartCode>(kEventParamControlPart , typeControlPartCode );#ifdef __WXMAC_OSX__ if ( cEvent.GetParameter<Boolean>(kEventParamControlFocusEverything , &focusEverything ) == noErr ) { }#endif if ( controlPart == kControlFocusNoPart ) {#if wxUSE_CARET if ( thisWindow->GetCaret() ) thisWindow->GetCaret()->OnKillFocus();#endif static bool inKillFocusEvent = false ; if ( !inKillFocusEvent ) { inKillFocusEvent = true ; wxFocusEvent event( wxEVT_KILL_FOCUS, thisWindow->GetId()); event.SetEventObject(thisWindow); thisWindow->GetEventHandler()->ProcessEvent(event) ; inKillFocusEvent = false ; } } else { // panel wants to track the window which was the last to have focus in it wxChildFocusEvent eventFocus(thisWindow); thisWindow->GetEventHandler()->ProcessEvent(eventFocus);#if wxUSE_CARET if ( thisWindow->GetCaret() ) thisWindow->GetCaret()->OnSetFocus();#endif wxFocusEvent event(wxEVT_SET_FOCUS, thisWindow->GetId()); event.SetEventObject(thisWindow); thisWindow->GetEventHandler()->ProcessEvent(event) ; } if ( thisWindow->MacIsUserPane() ) result = noErr ; } break ; case kEventControlHit : result = thisWindow->MacControlHit( handler , event ) ; break ; default : break ; } return result ;}static pascal OSStatus wxMacWindowServiceEventHandler( EventHandlerCallRef handler , EventRef event , void *data ){ OSStatus result = eventNotHandledErr ; wxMacCarbonEvent cEvent( event ) ; ControlRef controlRef ; wxWindowMac* thisWindow = (wxWindowMac*) data ; wxTextCtrl* textCtrl = wxDynamicCast( thisWindow , wxTextCtrl ) ; cEvent.GetParameter( kEventParamDirectObject , &controlRef ) ; switch ( GetEventKind( event ) ) { case kEventServiceGetTypes : if ( textCtrl ) { long from, to ; textCtrl->GetSelection( &from , &to ) ; CFMutableArrayRef copyTypes = 0 , pasteTypes = 0; if ( from != to ) copyTypes = cEvent.GetParameter< CFMutableArrayRef >( kEventParamServiceCopyTypes , typeCFMutableArrayRef ) ; if ( textCtrl->IsEditable() ) pasteTypes = cEvent.GetParameter< CFMutableArrayRef >( kEventParamServicePasteTypes , typeCFMutableArrayRef ) ; static const OSType textDataTypes[] = { kTXNTextData /* , 'utxt', 'PICT', 'MooV', 'AIFF' */ }; for ( size_t i = 0 ; i < WXSIZEOF(textDataTypes) ; ++i ) { CFStringRef typestring = CreateTypeStringWithOSType(textDataTypes[i]); if ( typestring ) { if ( copyTypes ) CFArrayAppendValue(copyTypes, typestring) ; if ( pasteTypes ) CFArrayAppendValue(pasteTypes, typestring) ; CFRelease( typestring ) ; } } result = noErr ; } break ; case kEventServiceCopy : if ( textCtrl ) { long from, to ; textCtrl->GetSelection( &from , &to ) ; wxString val = textCtrl->GetValue() ; val = val.Mid( from , to - from ) ; ScrapRef scrapRef = cEvent.GetParameter< ScrapRef > ( kEventParamScrapRef , typeScrapRef ) ; verify_noerr( ClearScrap( &scrapRef ) ) ; verify_noerr( PutScrapFlavor( scrapRef , kTXNTextData , 0 , val.length() , val.c_str() ) ) ; result = noErr ; } break ; case kEventServicePaste : if ( textCtrl ) { ScrapRef scrapRef = cEvent.GetParameter< ScrapRef > ( kEventParamScrapRef , typeScrapRef ) ; Size textSize, pastedSize ; verify_noerr( GetScrapFlavorSize(scrapRef, kTXNTextData, &textSize) ) ; textSize++ ; char *content = new char[textSize] ; GetScrapFlavorData(scrapRef, kTXNTextData, &pastedSize, content ); content[textSize - 1] = 0 ;#if wxUSE_UNICODE textCtrl->WriteText( wxString( content , wxConvLocal ) );#else textCtrl->WriteText( wxString( content ) ) ;#endif delete[] content ; result = noErr ; } break ; default: break ; } return result ;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -