X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/8bebc229c7aa9a57fdb4b4955bbe23cd1a44f54a..8471ea90331c42693823ede04ded5fd4d5bf008b:/src/mac/dc.cpp diff --git a/src/mac/dc.cpp b/src/mac/dc.cpp index edfaa69506..d906bac5a4 100644 --- a/src/mac/dc.cpp +++ b/src/mac/dc.cpp @@ -28,10 +28,10 @@ using namespace std ; #endif #include "wx/mac/private.h" -#include "ATSUnicode.h" -#include "TextCommon.h" -#include "TextEncodingConverter.h" -#include "FixMath.h" +#include +#include +#include +#include #if !USE_SHARED_LIBRARY IMPLEMENT_ABSTRACT_CLASS(wxDC, wxObject) #endif @@ -55,6 +55,8 @@ const double RAD2DEG = 180.0 / M_PI; const short kEmulatedMode = -1 ; const short kUnsupportedMode = -2 ; +extern TECObjectRef s_TECNativeCToUnicode ; + // set to 0 if problems arise #define wxMAC_EXPERIMENTAL_DC 1 @@ -79,15 +81,21 @@ public : wxASSERT( dc->Ok() ) ; GetPort( &m_oldPort ) ; SetPort( (GrafPtr) dc->m_macPort ) ; + m_clipRgn = NewRgn() ; + GetClip( m_clipRgn ) ; m_dc = dc ; dc->MacSetupPort( NULL ) ; } ~wxMacFastPortSetter() { + SetPort( (GrafPtr) m_dc->m_macPort ) ; + SetClip( m_clipRgn ) ; SetPort( m_oldPort ) ; m_dc->MacCleanupPort( NULL ) ; + DisposeRgn( m_clipRgn ) ; } private : + RgnHandle m_clipRgn ; GrafPtr m_oldPort ; const wxDC* m_dc ; } ; @@ -96,6 +104,30 @@ private : typedef wxMacPortSetter wxMacFastPortSetter ; #endif +#if 0 + +// start moving to a dual implementation for QD and CGContextRef + +class wxMacGraphicsContext +{ +public : + void DrawBitmap( const wxBitmap &bmp, wxCoord x, wxCoord y, bool useMask ) = 0 ; + void SetClippingRegion( wxCoord x, wxCoord y, wxCoord width, wxCoord height ) = 0 ; + void SetClippingRegion( const wxRegion ®ion ) = 0 ; + void DestroyClippingRegion() = 0 ; + void SetTextForeground( const wxColour &col ) = 0 ; + void SetTextBackground( const wxColour &col ) = 0 ; + void SetLogicalScale( double x , double y ) = 0 ; + void SetUserScale( double x , double y ) = 0; +} ; + +class wxMacQuickDrawContext : public wxMacGraphicsContext +{ +public : +} ; + +#endif + wxMacWindowClipper::wxMacWindowClipper( const wxWindow* win ) { m_formerClip = NewRgn() ; @@ -1339,11 +1371,10 @@ void wxDC::DoDrawRotatedText(const wxString& str, wxCoord x, wxCoord y, wxMacFastPortSetter helper(this) ; MacInstallFont() ; - wxFontRefData * font = (wxFontRefData*) m_font.GetRefData() ; if ( 0 ) { m_macFormerAliasState = IsAntiAliasedTextEnabled(&m_macFormerAliasSize); - SetAntiAliasedTextEnabled(true, SInt16(m_scaleY * font->m_macFontSize)); + SetAntiAliasedTextEnabled(true, SInt16(m_scaleY * m_font.GetMacFontSize())); m_macAliasWasEnabled = true ; } OSStatus status = noErr ; @@ -1353,24 +1384,9 @@ void wxDC::DoDrawRotatedText(const wxString& str, wxCoord x, wxCoord y, status = ::ATSUCreateTextLayoutWithTextPtr( (UniCharArrayPtr) (const wxChar*) str , 0 , str.Length() , str.Length() , 1 , &chars , (ATSUStyle*) &m_macATSUIStyle , &atsuLayout ) ; #else - TECObjectRef ec; - status = TECCreateConverter(&ec, - wxApp::s_macDefaultEncodingIsPC - ? (int)kTextEncodingWindowsLatin1 - : (int)kTextEncodingMacRoman, - kTextEncodingUnicodeDefault); - - wxASSERT_MSG( status == noErr , wxT("couldn't start converter") ) ; - ByteCount byteOutLen ; - ByteCount byteInLen = str.Length() ; - ByteCount byteBufferLen = byteInLen *2 ; - char* buf = new char[byteBufferLen] ; - status = TECConvertText(ec, (ConstTextPtr)str.c_str() , byteInLen, &byteInLen, - (TextPtr)buf, byteBufferLen, &byteOutLen); - wxASSERT_MSG( status == noErr , wxT("couldn't convert text") ) ; - status = TECDisposeConverter(ec); - wxASSERT_MSG( status == noErr , wxT("couldn't dispose converter") ) ; - status = ::ATSUCreateTextLayoutWithTextPtr( (UniCharArrayPtr) buf , 0 , byteOutLen / 2 , byteOutLen / 2 , 1 , + wxWCharBuffer wchar = str.wc_str( wxConvLocal ) ; + int wlen = wxWcslen( wchar.data() ) ; + status = ::ATSUCreateTextLayoutWithTextPtr( (UniCharArrayPtr) wchar.data() , 0 , wlen , wlen , 1 , &chars , (ATSUStyle*) &m_macATSUIStyle , &atsuLayout ) ; #endif wxASSERT_MSG( status == noErr , wxT("couldn't create the layout of the rotated text") ); @@ -1418,10 +1434,6 @@ void wxDC::DoDrawRotatedText(const wxString& str, wxCoord x, wxCoord y, CalcBoundingBox(XDEV2LOG(rect.left), YDEV2LOG(rect.top) ); CalcBoundingBox(XDEV2LOG(rect.right), YDEV2LOG(rect.bottom) ); ::ATSUDisposeTextLayout(atsuLayout); -#if wxUSE_UNICODE -#else - delete[] buf ; -#endif } void wxDC::DoDrawText(const wxString& strtext, wxCoord x, wxCoord y) @@ -1464,6 +1476,7 @@ void wxDC::DoDrawText(const wxString& strtext, wxCoord x, wxCoord y) int i = 0 ; int line = 0 ; { +#if 0 // we don't have to do all that here while( i < length ) { if( strtext[i] == 13 || strtext[i] == 10) @@ -1473,7 +1486,7 @@ void wxDC::DoDrawText(const wxString& strtext, wxCoord x, wxCoord y) if ( useDrawThemeText ) { Rect frame = { yy + line*(fi.descent + fi.ascent + fi.leading) ,xx , yy + (line+1)*(fi.descent + fi.ascent + fi.leading) , xx + 10000 } ; - wxMacCFStringHolder mString( linetext ) ; + wxMacCFStringHolder mString( linetext , m_font.GetEncoding() ) ; if ( m_backgroundMode != wxTRANSPARENT ) { Point bounds={0,0} ; @@ -1501,8 +1514,23 @@ void wxDC::DoDrawText(const wxString& strtext, wxCoord x, wxCoord y) else #endif { - wxCharBuffer text = wxMacStringToCString(linetext) ; + wxCharBuffer text = linetext.mb_str(wxConvLocal) ; ::DrawText( text , 0 , strlen(text) ) ; + if ( m_backgroundMode != wxTRANSPARENT ) + { + Point bounds={0,0} ; + Rect background = frame ; + SInt16 baseline ; + ::GetThemeTextDimensions( mString, + kThemeCurrentPortFont, + kThemeStateActive, + false, + &bounds, + &baseline ); + background.right = background.left + bounds.h ; + background.bottom = background.top + bounds.v ; + ::EraseRect( &background ) ; + } line++ ; ::MoveTo( xx , yy + line*(fi.descent + fi.ascent + fi.leading) ); } @@ -1511,11 +1539,13 @@ void wxDC::DoDrawText(const wxString& strtext, wxCoord x, wxCoord y) i++ ; } wxString linetext = strtext.Mid( laststop , i - laststop ) ; +#endif // 0 + wxString linetext = strtext ; #if TARGET_CARBON if ( useDrawThemeText ) { Rect frame = { yy + line*(fi.descent + fi.ascent + fi.leading) ,xx , yy + (line+1)*(fi.descent + fi.ascent + fi.leading) , xx + 10000 } ; - wxMacCFStringHolder mString( linetext ) ; + wxMacCFStringHolder mString( linetext , m_font.GetEncoding()) ; if ( m_backgroundMode != wxTRANSPARENT ) { @@ -1543,7 +1573,15 @@ void wxDC::DoDrawText(const wxString& strtext, wxCoord x, wxCoord y) else #endif { - wxCharBuffer text = wxMacStringToCString(linetext) ; + wxCharBuffer text = linetext.mb_str(wxConvLocal) ; + if ( m_backgroundMode != wxTRANSPARENT ) + { + Rect frame = { yy - fi.ascent + line*(fi.descent + fi.ascent + fi.leading) ,xx , yy - fi.ascent + (line+1)*(fi.descent + fi.ascent + fi.leading) , xx + 10000 } ; + short width = ::TextWidth( text , 0 , strlen(text) ) ; + frame.right = frame.left + width ; + + ::EraseRect( &frame ) ; + } ::DrawText( text , 0 , strlen(text) ) ; } } @@ -1583,27 +1621,14 @@ void wxDC::DoGetTextExtent( const wxString &strtext, wxCoord *width, wxCoord *h if ( externalLeading ) *externalLeading = YDEV2LOGREL( fi.leading ) ; int length = strtext.Length() ; - /* - const char *text = NULL ; - wxString macText ; - if ( wxApp::s_macDefaultEncodingIsPC ) - { - macText = wxMacMakeMacStringFromPC( string ) ; - text = macText ; - length = macText.Length() ; - } - else - { - text = string ; - length = string.Length() ; - } - */ + int laststop = 0 ; int i = 0 ; int curwidth = 0 ; if ( width ) { *width = 0 ; +#if 0 // apparently we don't have to do all that while( i < length ) { if( strtext[i] == 13 || strtext[i] == 10) @@ -1616,7 +1641,7 @@ void wxDC::DoGetTextExtent( const wxString &strtext, wxCoord *width, wxCoord *h { Point bounds={0,0} ; SInt16 baseline ; - wxMacCFStringHolder mString( linetext ) ; + wxMacCFStringHolder mString( linetext , m_font.GetEncoding() ) ; ::GetThemeTextDimensions( mString, kThemeCurrentPortFont, kThemeStateActive, @@ -1628,7 +1653,7 @@ void wxDC::DoGetTextExtent( const wxString &strtext, wxCoord *width, wxCoord *h else #endif { - wxCharBuffer text = wxMacStringToCString(linetext) ; + wxCharBuffer text = linetext.mb_str(wxConvLocal) ; curwidth = ::TextWidth( text , 0 , strlen(text) ) ; } if ( curwidth > *width ) @@ -1639,12 +1664,14 @@ void wxDC::DoGetTextExtent( const wxString &strtext, wxCoord *width, wxCoord *h } wxString linetext = strtext.Mid( laststop , i - laststop ) ; +#endif // 0 + wxString linetext = strtext ; #if TARGET_CARBON if ( useGetThemeText ) { Point bounds={0,0} ; SInt16 baseline ; - wxMacCFStringHolder mString( linetext ) ; + wxMacCFStringHolder mString( linetext , m_font.GetEncoding() ) ; ::GetThemeTextDimensions( mString, kThemeCurrentPortFont, kThemeStateActive, @@ -1656,7 +1683,7 @@ void wxDC::DoGetTextExtent( const wxString &strtext, wxCoord *width, wxCoord *h else #endif { - wxCharBuffer text = wxMacStringToCString(linetext) ; + wxCharBuffer text = linetext.mb_str(wxConvLocal) ; curwidth = ::TextWidth( text , 0 , strlen(text) ) ; } if ( curwidth > *width ) @@ -1670,6 +1697,68 @@ void wxDC::DoGetTextExtent( const wxString &strtext, wxCoord *width, wxCoord *h } } + +bool wxDC::DoGetPartialTextExtents(const wxString& text, wxArrayInt& widths) const +{ + wxCHECK_MSG(Ok(), false, wxT("Invalid DC")); + + widths.Empty(); + widths.Add(0, text.Length()); + + if (text.Length() == 0) + return false; + + wxMacFastPortSetter helper(this) ; + MacInstallFont() ; +#if TARGET_CARBON + bool useGetThemeText = ( GetThemeTextDimensions != (void*) kUnresolvedCFragSymbolAddress ) ; + if ( UMAGetSystemVersion() < 0x1000 || IsKindOf(CLASSINFO( wxPrinterDC ) ) || ((wxFont*)&m_font)->GetNoAntiAliasing() ) + useGetThemeText = false ; + + if ( useGetThemeText ) + { + // If anybody knows how to do this more efficiently yet still handle + // the fractional glyph widths that may be present when using AA + // fonts, please change it. Currently it is measuring from the + // begining of the string for each succeding substring, which is much + // slower than this should be. + for (size_t i=0; iGetNoAntiAliasing() ) useGetThemeText = false ; #endif - char text[] = "H" ; + char text[] = "g" ; #if TARGET_CARBON if ( useGetThemeText ) { @@ -1736,12 +1825,11 @@ void wxDC::MacInstallFont() const // return ; Pattern blackColor ; MacSetupBackgroundForCurrentPort(m_backgroundBrush) ; - wxFontRefData * font = (wxFontRefData*) m_font.GetRefData() ; - if ( font ) + if ( m_font.Ok() ) { - ::TextFont( font->m_macFontNum ) ; - ::TextSize( short(m_scaleY * font->m_macFontSize) ) ; - ::TextFace( font->m_macFontStyle ) ; + ::TextFont( m_font.GetMacFontNum() ) ; + ::TextSize( (short)(m_scaleY * m_font.GetMacFontSize()) ) ; + ::TextFace( m_font.GetMacFontStyle() ) ; m_macFontInstalled = true ; m_macBrushInstalled = false ; m_macPenInstalled = false ; @@ -1810,9 +1898,9 @@ void wxDC::MacInstallFont() const } ::PenMode( mode ) ; OSStatus status = noErr ; - Fixed atsuSize = IntToFixed( int(m_scaleY * font->m_macFontSize) ) ; - Style qdStyle = font->m_macFontStyle ; - ATSUFontID atsuFont = font->m_macATSUFontID ; + Fixed atsuSize = IntToFixed( int(m_scaleY * m_font.GetMacFontSize()) ) ; + Style qdStyle = m_font.GetMacFontStyle() ; + ATSUFontID atsuFont = m_font.GetMacATSUFontID() ; status = ::ATSUCreateStyle((ATSUStyle *)&m_macATSUIStyle) ; wxASSERT_MSG( status == noErr , wxT("couldn't create ATSU style") ) ; ATSUAttributeTag atsuTags[] = @@ -1865,18 +1953,18 @@ void wxDC::MacInstallFont() const Pattern gPatterns[] = { // hatch patterns - { 0xFF , 0xFF , 0xFF , 0xFF , 0xFF , 0xFF , 0xFF , 0xFF } , - { 0x01 , 0x02 , 0x04 , 0x08 , 0x10 , 0x20 , 0x40 , 0x80 } , - { 0x80 , 0x40 , 0x20 , 0x10 , 0x08 , 0x04 , 0x02 , 0x01 } , - { 0x10 , 0x10 , 0x10 , 0xFF , 0x10 , 0x10 , 0x10 , 0x10 } , - { 0x00 , 0x00 , 0x00 , 0xFF , 0x00 , 0x00 , 0x00 , 0x00 } , - { 0x10 , 0x10 , 0x10 , 0x10 , 0x10 , 0x10 , 0x10 , 0x10 } , - { 0x81 , 0x42 , 0x24 , 0x18 , 0x18 , 0x24 , 0x42 , 0x81 } , + { { 0xFF , 0xFF , 0xFF , 0xFF , 0xFF , 0xFF , 0xFF , 0xFF } } , + { { 0x01 , 0x02 , 0x04 , 0x08 , 0x10 , 0x20 , 0x40 , 0x80 } } , + { { 0x80 , 0x40 , 0x20 , 0x10 , 0x08 , 0x04 , 0x02 , 0x01 } } , + { { 0x10 , 0x10 , 0x10 , 0xFF , 0x10 , 0x10 , 0x10 , 0x10 } } , + { { 0x00 , 0x00 , 0x00 , 0xFF , 0x00 , 0x00 , 0x00 , 0x00 } } , + { { 0x10 , 0x10 , 0x10 , 0x10 , 0x10 , 0x10 , 0x10 , 0x10 } } , + { { 0x81 , 0x42 , 0x24 , 0x18 , 0x18 , 0x24 , 0x42 , 0x81 } } , // dash patterns - { 0xCC , 0x99 , 0x33 , 0x66 , 0xCC , 0x99 , 0x33 , 0x66 } , // DOT - { 0xFE , 0xFD , 0xFB , 0xF7 , 0xEF , 0xDF , 0xBF , 0x7F } , // LONG_DASH - { 0xEE , 0xDD , 0xBB , 0x77 , 0xEE , 0xDD , 0xBB , 0x77 } , // SHORT_DASH - { 0xDE , 0xBD , 0x7B , 0xF6 , 0xED , 0xDB , 0xB7 , 0x6F } , // DOT_DASH + { { 0xCC , 0x99 , 0x33 , 0x66 , 0xCC , 0x99 , 0x33 , 0x66 } } , // DOT + { { 0xFE , 0xFD , 0xFB , 0xF7 , 0xEF , 0xDF , 0xBF , 0x7F } } , // LONG_DASH + { { 0xEE , 0xDD , 0xBB , 0x77 , 0xEE , 0xDD , 0xBB , 0x77 } } , // SHORT_DASH + { { 0xDE , 0xBD , 0x7B , 0xF6 , 0xED , 0xDB , 0xB7 , 0x6F } } , // DOT_DASH } ; static void wxMacGetPattern(int penStyle, Pattern *pattern) @@ -1903,7 +1991,7 @@ static void wxMacGetPattern(int penStyle, Pattern *pattern) void wxDC::MacInstallPen() const { wxCHECK_RET(Ok(), wxT("Invalid DC")); - Pattern blackColor; + //Pattern blackColor; // if ( m_macPenInstalled ) // return ; RGBColor forecolor = MAC_WXCOLORREF( m_pen.GetColour().GetPixel());