]> git.saurik.com Git - wxWidgets.git/blame - src/osx/carbon/font.cpp
copying native cursor under cocoa
[wxWidgets.git] / src / osx / carbon / font.cpp
CommitLineData
489468fe 1/////////////////////////////////////////////////////////////////////////////
524c47aa 2// Name: src/osx/carbon/font.cpp
489468fe
SC
3// Purpose: wxFont class
4// Author: Stefan Csomor
5// Modified by:
6// Created: 1998-01-01
7// RCS-ID: $Id$
8// Copyright: (c) Stefan Csomor
9// Licence: wxWindows licence
10/////////////////////////////////////////////////////////////////////////////
11
12#include "wx/wxprec.h"
13
14#include "wx/font.h"
15
16#ifndef WX_PRECOMP
17 #include "wx/string.h"
18 #include "wx/utils.h"
19 #include "wx/intl.h"
20 #include "wx/gdicmn.h"
21 #include "wx/log.h"
22#endif
23
24#include "wx/fontutil.h"
25#include "wx/graphics.h"
26#include "wx/settings.h"
f1c40652 27#include "wx/tokenzr.h"
489468fe 28
b2680ced 29#include "wx/osx/private.h"
29e32b7f 30
489468fe
SC
31#include <map>
32#include <string>
33
34IMPLEMENT_DYNAMIC_CLASS(wxFont, wxGDIObject)
35
489468fe
SC
36class WXDLLEXPORT wxFontRefData: public wxGDIRefData
37{
38public:
489468fe 39
f1c40652 40 wxFontRefData()
489468fe 41 {
f1c40652
SC
42 Init();
43 m_info.Init(10, wxFONTFAMILY_DEFAULT, wxFONTSTYLE_NORMAL, wxFONTWEIGHT_NORMAL,
44 false, wxEmptyString, wxFONTENCODING_DEFAULT);
489468fe
SC
45 }
46
f1c40652 47 wxFontRefData(const wxFontRefData& data);
03647350 48
f1c40652 49 wxFontRefData( const wxNativeFontInfo& info ) : m_info(info)
489468fe 50 {
f1c40652 51 Init();
489468fe
SC
52 }
53
f1c40652 54 wxFontRefData(wxOSXSystemFont font, int size);
03647350 55
292e5e1f 56#if wxOSX_USE_CORE_TEXT
489468fe
SC
57 wxFontRefData( wxUint32 coreTextFontType );
58 wxFontRefData( CTFontRef font );
59 wxFontRefData( CTFontDescriptorRef fontdescriptor, int size );
60#endif
61
62 virtual ~wxFontRefData();
63
489468fe
SC
64 void SetPointSize( int size )
65 {
f1c40652
SC
66 if( GetPointSize() != size )
67 {
68 m_info.SetPointSize(size);
69 Free();
70 }
489468fe
SC
71 }
72
f1c40652 73 int GetPointSize() const { return m_info.GetPointSize(); }
489468fe 74
0c14b6c3 75 void SetFamily( wxFontFamily family )
489468fe 76 {
f1c40652
SC
77 if ( m_info.m_family != family )
78 {
79 m_info.SetFamily( family );
80 Free();
81 }
489468fe
SC
82 }
83
f1c40652 84 wxFontFamily GetFamily() const { return m_info.GetFamily(); }
489468fe 85
0c14b6c3 86 void SetStyle( wxFontStyle style )
489468fe 87 {
f1c40652
SC
88 if ( m_info.m_style != style )
89 {
90 m_info.SetStyle( style );
91 Free();
92 }
489468fe
SC
93 }
94
95
f1c40652 96 wxFontStyle GetStyle() const { return m_info.GetStyle(); }
489468fe 97
0c14b6c3 98 void SetWeight( wxFontWeight weight )
489468fe 99 {
f1c40652
SC
100 if ( m_info.m_weight != weight )
101 {
102 m_info.SetWeight( weight );
103 Free();
104 }
489468fe
SC
105 }
106
107
f1c40652 108 wxFontWeight GetWeight() const { return m_info.GetWeight(); }
489468fe
SC
109
110 void SetUnderlined( bool u )
111 {
f1c40652
SC
112 if ( m_info.m_underlined != u )
113 {
114 m_info.SetUnderlined( u );
115 Free();
116 }
489468fe
SC
117 }
118
f1c40652 119 bool GetUnderlined() const { return m_info.GetUnderlined(); }
489468fe
SC
120
121 void SetFaceName( const wxString& facename )
122 {
f1c40652
SC
123 if ( m_info.m_faceName != facename )
124 {
125 m_info.SetFaceName( facename );
126 Free();
127 }
489468fe
SC
128 }
129
f1c40652 130 wxString GetFaceName() const { return m_info.GetFaceName(); }
489468fe
SC
131
132 void SetEncoding( wxFontEncoding encoding )
133 {
f1c40652
SC
134 if ( m_info.m_encoding != encoding )
135 {
136 m_info.SetEncoding( encoding );
137 Free();
138 }
489468fe
SC
139 }
140
f1c40652 141 wxFontEncoding GetEncoding() const { return m_info.GetEncoding(); }
489468fe 142
f1c40652 143 void Free();
489468fe
SC
144
145 void MacFindFont();
146
147protected:
148 // common part of all ctors
f1c40652 149 void Init();
292e5e1f 150#if wxOSX_USE_CORE_TEXT
f1c40652 151 // void Init( CTFontRef font );
489468fe 152#endif
489468fe 153public:
f1c40652
SC
154 bool m_fontValid;
155#if wxOSX_USE_CARBON && wxOSX_USE_ATSU_TEXT
b3b17ee7 156 // for true theming support we must store the correct font
489468fe
SC
157 // information here, as this speeds up and optimizes rendering
158 ThemeFontID m_macThemeFontID ;
159#endif
292e5e1f 160#if wxOSX_USE_CORE_TEXT
489468fe 161 wxCFRef<CTFontRef> m_ctFont;
489468fe 162#endif
beb2638a 163#if wxOSX_USE_ATSU_TEXT
03c28161
SC
164 void CreateATSUFont();
165
489468fe 166 ATSUStyle m_macATSUStyle ;
f1c40652 167#endif
9445de1e 168 wxCFRef<CGFontRef> m_cgFont;
f1c40652
SC
169#if wxOSX_USE_COCOA
170 WX_NSFont m_nsFont;
171#endif
172#if wxOSX_USE_IPHONE
173 WX_UIFont m_uiFont;
489468fe
SC
174#endif
175 wxNativeFontInfo m_info;
176};
177
178#define M_FONTDATA ((wxFontRefData*)m_refData)
179
f1c40652
SC
180wxFontRefData::wxFontRefData(const wxFontRefData& data)
181{
182 Init();
183 m_info = data.m_info;
f1c40652
SC
184 m_fontValid = data.m_fontValid;
185#if wxOSX_USE_CARBON && wxOSX_USE_ATSU_TEXT
186 m_macThemeFontID = data.m_macThemeFontID;
187#endif
188#if wxOSX_USE_CORE_TEXT
189 m_ctFont = data.m_ctFont;
03647350 190#endif
9445de1e 191 m_cgFont = data.m_cgFont;
beb2638a 192#if wxOSX_USE_ATSU_TEXT
f1c40652
SC
193 if ( data.m_macATSUStyle != NULL )
194 {
195 ATSUCreateStyle(&m_macATSUStyle) ;
196 ATSUCopyAttributes(data.m_macATSUStyle, m_macATSUStyle);
197 }
198#endif
199#if wxOSX_USE_COCOA
200 m_nsFont = (NSFont*) wxMacCocoaRetain(data.m_nsFont);
201#endif
202#if wxOSX_USE_IPHONE
b4ff8b3e 203 m_uiFont = (UIFont*) wxMacCocoaRetain(data.m_uiFont);
f1c40652 204#endif
03647350 205
f1c40652 206}
489468fe
SC
207
208// ============================================================================
209// implementation
210// ============================================================================
211
212// ----------------------------------------------------------------------------
213// wxFontRefData
214// ----------------------------------------------------------------------------
215
f1c40652 216void wxFontRefData::Init()
489468fe 217{
f1c40652 218#if wxOSX_USE_CARBON && wxOSX_USE_ATSU_TEXT
489468fe
SC
219 m_macThemeFontID = kThemeCurrentPortFont ;
220#endif
beb2638a 221#if wxOSX_USE_ATSU_TEXT
489468fe
SC
222 m_macATSUStyle = NULL ;
223#endif
f1c40652
SC
224#if wxOSX_USE_COCOA
225 m_nsFont = NULL;
226#endif
227#if wxOSX_USE_IPHONE
228 m_uiFont = NULL;
229#endif
230 m_fontValid = false;
489468fe
SC
231}
232
233wxFontRefData::~wxFontRefData()
234{
f1c40652 235 Free();
489468fe
SC
236}
237
f1c40652 238void wxFontRefData::Free()
489468fe 239{
292e5e1f 240#if wxOSX_USE_CORE_TEXT
489468fe 241 m_ctFont.reset();
489468fe 242#endif
9445de1e 243 m_cgFont.reset();
beb2638a 244#if wxOSX_USE_ATSU_TEXT
9581362b
SC
245#if wxOSX_USE_CARBON
246 m_macThemeFontID = kThemeCurrentPortFont ;
247#endif
489468fe
SC
248 if ( m_macATSUStyle )
249 {
250 ::ATSUDisposeStyle((ATSUStyle)m_macATSUStyle);
251 m_macATSUStyle = NULL ;
252 }
253#endif
f1c40652
SC
254#if wxOSX_USE_COCOA
255 if (m_nsFont != NULL)
256 {
257 wxMacCocoaRelease(m_nsFont);
258 m_nsFont = NULL;
489468fe 259 }
f1c40652
SC
260#endif
261#if wxOSX_USE_IPHONE
262 if (m_uiFont != NULL)
489468fe 263 {
f1c40652
SC
264 wxMacCocoaRelease(m_uiFont);
265 m_uiFont = NULL;
489468fe 266 }
f1c40652
SC
267#endif
268 m_fontValid = false;
489468fe
SC
269}
270
f1c40652 271wxFontRefData::wxFontRefData(wxOSXSystemFont font, int size)
489468fe 272{
f1c40652
SC
273 wxASSERT( font != wxOSX_SYSTEM_FONT_NONE );
274 Init();
03647350 275
f1c40652
SC
276#if wxOSX_USE_CORE_TEXT
277 if ( UMAGetSystemVersion() >= 0x1050 )
489468fe 278 {
de0d2095 279 CTFontUIFontType uifont = kCTFontSystemFontType;
f1c40652 280 switch( font )
489468fe 281 {
f1c40652
SC
282 case wxOSX_SYSTEM_FONT_NORMAL:
283 uifont = kCTFontSystemFontType;
284 break;
285 case wxOSX_SYSTEM_FONT_BOLD:
286 uifont = kCTFontEmphasizedSystemFontType;
287 break;
288 case wxOSX_SYSTEM_FONT_SMALL:
289 uifont = kCTFontSmallSystemFontType;
290 break;
291 case wxOSX_SYSTEM_FONT_SMALL_BOLD:
292 uifont = kCTFontSmallEmphasizedSystemFontType;
293 break;
294 case wxOSX_SYSTEM_FONT_MINI:
295 uifont = kCTFontMiniSystemFontType;
296 break;
297 case wxOSX_SYSTEM_FONT_MINI_BOLD:
298 uifont = kCTFontMiniEmphasizedSystemFontType;
299 break;
300 case wxOSX_SYSTEM_FONT_LABELS:
301 uifont = kCTFontLabelFontType;
302 break;
303 case wxOSX_SYSTEM_FONT_VIEWS:
304 uifont = kCTFontViewsFontType;
305 break;
306 default:
307 break;
489468fe 308 }
f1c40652
SC
309 m_ctFont.reset(CTFontCreateUIFontForLanguage( uifont, (CGFloat) size, NULL ));
310 wxCFRef<CTFontDescriptorRef> descr;
311 descr.reset( CTFontCopyFontDescriptor( m_ctFont ) );
312 m_info.Init(descr);
313 }
314#endif
315#if wxOSX_USE_ATSU_TEXT
316 {
9a672c75
SC
317#if !wxOSX_USE_CARBON
318 // not needed outside
de0d2095 319 ThemeFontID m_macThemeFontID = kThemeSystemFont;
9a672c75 320#endif
f1c40652
SC
321 switch( font )
322 {
323 case wxOSX_SYSTEM_FONT_NORMAL:
324 m_macThemeFontID = kThemeSystemFont;
325 break;
326 case wxOSX_SYSTEM_FONT_BOLD:
327 m_macThemeFontID = kThemeEmphasizedSystemFont;
328 break;
329 case wxOSX_SYSTEM_FONT_SMALL:
330 m_macThemeFontID = kThemeSmallSystemFont;
331 break;
332 case wxOSX_SYSTEM_FONT_SMALL_BOLD:
333 m_macThemeFontID = kThemeSmallEmphasizedSystemFont;
334 break;
335 case wxOSX_SYSTEM_FONT_MINI:
336 m_macThemeFontID = kThemeMiniSystemFont;
337 break;
338 case wxOSX_SYSTEM_FONT_MINI_BOLD:
b3b17ee7 339 // bold not available under theming
f1c40652
SC
340 m_macThemeFontID = kThemeMiniSystemFont;
341 break;
342 case wxOSX_SYSTEM_FONT_LABELS:
343 m_macThemeFontID = kThemeLabelFont;
344 break;
345 case wxOSX_SYSTEM_FONT_VIEWS:
346 m_macThemeFontID = kThemeViewsFont;
347 break;
348 default:
03647350 349 break;
f1c40652
SC
350 }
351 if ( m_info.m_faceName.empty() )
352 {
353 Style style ;
354 FMFontSize fontSize;
355 Str255 qdFontName ;
03647350 356
f1c40652
SC
357 GetThemeFont( m_macThemeFontID, GetApplicationScript(), qdFontName, &fontSize, &style );
358 if ( size != 0 )
359 fontSize = size;
360
361 wxFontStyle fontstyle = wxFONTSTYLE_NORMAL;
362 wxFontWeight fontweight = wxFONTWEIGHT_NORMAL;
363 bool underlined = false;
03647350 364
f1c40652
SC
365 if ( style & bold )
366 fontweight = wxFONTWEIGHT_BOLD ;
367 else
368 fontweight = wxFONTWEIGHT_NORMAL ;
369 if ( style & italic )
370 fontstyle = wxFONTSTYLE_ITALIC ;
371 if ( style & underline )
372 underlined = true ;
03647350 373
2ff0354a 374 m_info.Init(fontSize,wxFONTFAMILY_DEFAULT,fontstyle,fontweight,underlined,
f1c40652
SC
375 wxMacMakeStringFromPascal( qdFontName ), wxFONTENCODING_DEFAULT);
376 }
489468fe 377 }
489468fe 378#endif
f1c40652 379#if wxOSX_USE_COCOA
aa6208d9 380 m_nsFont = wxFont::OSXCreateNSFont( font, &m_info );
f1c40652
SC
381#endif
382#if wxOSX_USE_IPHONE
aa6208d9 383 m_uiFont = wxFont::OSXCreateUIFont( font, &m_info );
f1c40652 384#endif
03c28161
SC
385 m_info.EnsureValid();
386#if wxOSX_USE_ATSU_TEXT
387 CreateATSUFont();
388#endif
389
390 m_fontValid = true;
f1c40652 391}
489468fe 392
03c28161
SC
393#if wxOSX_USE_ATSU_TEXT
394void wxFontRefData::CreateATSUFont()
395{
396 // we try to get as much styles as possible into ATSU
397
398 OSStatus status = ::ATSUCreateStyle(&m_macATSUStyle);
399 wxASSERT_MSG( status == noErr , wxT("couldn't create ATSU style") );
400
401 ATSUAttributeTag atsuTags[] =
402 {
403 kATSUFontTag ,
404 kATSUSizeTag ,
405 kATSUVerticalCharacterTag,
406 kATSUQDBoldfaceTag ,
407 kATSUQDItalicTag ,
408 kATSUQDUnderlineTag ,
409 kATSUQDCondensedTag ,
410 kATSUQDExtendedTag ,
411 };
412 ByteCount atsuSizes[WXSIZEOF(atsuTags)] =
413 {
414 sizeof( ATSUFontID ) ,
415 sizeof( Fixed ) ,
416 sizeof( ATSUVerticalCharacterType),
417 sizeof( Boolean ) ,
418 sizeof( Boolean ) ,
419 sizeof( Boolean ) ,
420 sizeof( Boolean ) ,
421 sizeof( Boolean ) ,
422 };
423
424 Boolean kTrue = true ;
425 Boolean kFalse = false ;
426
427 Fixed atsuSize = IntToFixed( m_info.m_pointSize );
428 ATSUVerticalCharacterType kHorizontal = kATSUStronglyHorizontal;
429 FMFontStyle addQDStyle = m_info.m_atsuAdditionalQDStyles;
430 ATSUAttributeValuePtr atsuValues[WXSIZEOF(atsuTags)] =
431 {
432 &m_info.m_atsuFontID ,
433 &atsuSize ,
434 &kHorizontal,
435 (addQDStyle & bold) ? &kTrue : &kFalse ,
436 (addQDStyle & italic) ? &kTrue : &kFalse ,
437 (addQDStyle & underline) ? &kTrue : &kFalse ,
438 (addQDStyle & condense) ? &kTrue : &kFalse ,
439 (addQDStyle & extend) ? &kTrue : &kFalse ,
440 };
441
442 status = ::ATSUSetAttributes(
443 (ATSUStyle)m_macATSUStyle,
444 WXSIZEOF(atsuTags),
445 atsuTags, atsuSizes, atsuValues);
446
447 wxASSERT_MSG( status == noErr , wxString::Format(wxT("couldn't modify ATSU style. Status was %d"), (int) status).c_str() );
448
449 if ( m_cgFont.get() == NULL )
450 {
451 ATSFontRef fontRef = FMGetATSFontRefFromFont(m_info.m_atsuFontID);
452 m_cgFont.reset( CGFontCreateWithPlatformFont( &fontRef ) );
453 }
454}
455#endif
456
489468fe
SC
457void wxFontRefData::MacFindFont()
458{
f1c40652
SC
459 if ( m_fontValid )
460 return;
03647350 461
72912228
JS
462 wxCHECK_RET( m_info.m_pointSize > 0, wxT("Point size should not be zero.") );
463
f1c40652 464 m_info.EnsureValid();
03647350 465
292e5e1f 466#if wxOSX_USE_CORE_TEXT
489468fe
SC
467 if ( UMAGetSystemVersion() >= 0x1050 )
468 {
f1c40652 469 CTFontSymbolicTraits traits = 0;
0c14b6c3 470
f1c40652
SC
471 if (m_info.m_weight == wxFONTWEIGHT_BOLD)
472 traits |= kCTFontBoldTrait;
473 if (m_info.m_style == wxFONTSTYLE_ITALIC || m_info.m_style == wxFONTSTYLE_SLANT)
474 traits |= kCTFontItalicTrait;
489468fe 475
f1c40652
SC
476 // use font caching
477 wxString lookupnameWithSize = wxString::Format( "%s_%ld_%ld", m_info.m_faceName.c_str(), traits, m_info.m_pointSize );
489468fe 478
f1c40652
SC
479 static std::map< std::wstring , wxCFRef< CTFontRef > > fontcache ;
480 m_ctFont = fontcache[ std::wstring(lookupnameWithSize.wc_str()) ];
481 if ( !m_ctFont )
489468fe 482 {
03c28161
SC
483 m_ctFont.reset(CTFontCreateWithName( wxCFStringRef(m_info.m_faceName), m_info.m_pointSize , NULL ));
484 if ( traits != 0 )
485 {
486 m_ctFont.reset(CTFontCreateCopyWithSymbolicTraits( m_ctFont, 0, NULL, traits, traits ));
487 }
489468fe 488 }
03c28161 489
9445de1e 490 m_cgFont.reset(CTFontCopyGraphicsFont(m_ctFont, NULL));
489468fe 491 }
f1c40652 492
489468fe 493#endif
292e5e1f 494#if wxOSX_USE_ATSU_TEXT
03c28161 495 CreateATSUFont();
489468fe 496#endif
f1c40652 497#if wxOSX_USE_COCOA
aa6208d9 498 m_nsFont = wxFont::OSXCreateNSFont( &m_info );
f1c40652
SC
499#endif
500#if wxOSX_USE_IPHONE
aa6208d9 501 m_uiFont = wxFont::OSXCreateUIFont( &m_info );
f1c40652
SC
502#endif
503 m_fontValid = true;
489468fe
SC
504}
505
506// ----------------------------------------------------------------------------
507// wxFont
508// ----------------------------------------------------------------------------
509
510bool wxFont::Create(const wxNativeFontInfo& info)
511{
f1c40652 512 UnRef();
03647350 513
f1c40652
SC
514 m_refData = new wxFontRefData( info );
515 RealizeResource();
03647350 516
f1c40652 517 return true;
489468fe
SC
518}
519
7eb8aeb8
SC
520wxFont::wxFont(wxOSXSystemFont font)
521{
522 m_refData = new wxFontRefData( font, 0 );
523}
524
489468fe
SC
525wxFont::wxFont(const wxString& fontdesc)
526{
527 wxNativeFontInfo info;
528 if ( info.FromString(fontdesc) )
529 (void)Create(info);
530}
531
532bool wxFont::Create(int pointSize,
0c14b6c3
FM
533 wxFontFamily family,
534 wxFontStyle style,
535 wxFontWeight weight,
536 bool underlined,
f1c40652 537 const wxString& faceNameParam,
0c14b6c3 538 wxFontEncoding encoding)
489468fe
SC
539{
540 UnRef();
03647350 541
f1c40652 542 wxString faceName = faceNameParam;
489468fe 543
f1c40652
SC
544 if ( faceName.empty() )
545 {
546 switch ( family )
547 {
548 case wxFONTFAMILY_DEFAULT :
549 faceName = wxT("Lucida Grande");
550 break;
03647350 551
f1c40652
SC
552 case wxFONTFAMILY_SCRIPT :
553 case wxFONTFAMILY_ROMAN :
554 case wxFONTFAMILY_DECORATIVE :
555 faceName = wxT("Times");
556 break ;
557
558 case wxFONTFAMILY_SWISS :
559 faceName = wxT("Helvetica");
560 break ;
561
562 case wxFONTFAMILY_MODERN :
563 case wxFONTFAMILY_TELETYPE:
564 faceName = wxT("Courier");
565 break ;
566
567 default:
568 faceName = wxT("Times");
569 break ;
570 }
571 }
03647350 572
f1c40652 573 wxNativeFontInfo info;
03647350 574
f1c40652 575 info.Init(pointSize, family, style, weight,
489468fe
SC
576 underlined, faceName, encoding);
577
f1c40652 578 m_refData = new wxFontRefData(info);
489468fe
SC
579
580 return true;
581}
582
f1c40652 583wxFont::~wxFont()
489468fe 584{
f1c40652 585}
489468fe 586
c443ff6f
SC
587void wxFont::DoSetNativeFontInfo(const wxNativeFontInfo& info)
588{
589 UnRef();
03647350 590
c443ff6f
SC
591 m_refData = new wxFontRefData( info);
592}
593
594
f1c40652
SC
595bool wxFont::RealizeResource()
596{
597 M_FONTDATA->MacFindFont();
489468fe
SC
598
599 return true;
600}
601
f1c40652
SC
602void wxFont::SetEncoding(wxFontEncoding encoding)
603{
604 AllocExclusive();
489468fe
SC
605
606 M_FONTDATA->SetEncoding( encoding );
489468fe
SC
607}
608
609wxGDIRefData *wxFont::CreateGDIRefData() const
610{
611 return new wxFontRefData;
612}
613
614wxGDIRefData *wxFont::CloneGDIRefData(const wxGDIRefData *data) const
615{
5c33522f 616 return new wxFontRefData(*static_cast<const wxFontRefData *>(data));
489468fe
SC
617}
618
619void wxFont::SetPointSize(int pointSize)
620{
621 if ( M_FONTDATA->GetPointSize() == pointSize )
622 return;
623
f1c40652 624 AllocExclusive();
489468fe
SC
625
626 M_FONTDATA->SetPointSize( pointSize );
489468fe
SC
627}
628
0c14b6c3 629void wxFont::SetFamily(wxFontFamily family)
489468fe 630{
f1c40652 631 AllocExclusive();
489468fe
SC
632
633 M_FONTDATA->SetFamily( family );
489468fe
SC
634}
635
0c14b6c3 636void wxFont::SetStyle(wxFontStyle style)
489468fe 637{
f1c40652 638 AllocExclusive();
489468fe
SC
639
640 M_FONTDATA->SetStyle( style );
489468fe
SC
641}
642
0c14b6c3 643void wxFont::SetWeight(wxFontWeight weight)
489468fe 644{
f1c40652 645 AllocExclusive();
489468fe
SC
646
647 M_FONTDATA->SetWeight( weight );
489468fe
SC
648}
649
650bool wxFont::SetFaceName(const wxString& faceName)
651{
f1c40652 652 AllocExclusive();
489468fe
SC
653
654 M_FONTDATA->SetFaceName( faceName );
655
489468fe
SC
656 return wxFontBase::SetFaceName(faceName);
657}
658
659void wxFont::SetUnderlined(bool underlined)
660{
f1c40652 661 AllocExclusive();
489468fe
SC
662
663 M_FONTDATA->SetUnderlined( underlined );
489468fe
SC
664}
665
489468fe
SC
666// ----------------------------------------------------------------------------
667// accessors
668// ----------------------------------------------------------------------------
669
670// TODO: insert checks everywhere for M_FONTDATA == NULL!
671
672int wxFont::GetPointSize() const
673{
674 wxCHECK_MSG( M_FONTDATA != NULL , 0, wxT("invalid font") );
675
676 return M_FONTDATA->GetPointSize();
677}
678
679wxSize wxFont::GetPixelSize() const
680{
681#if wxUSE_GRAPHICS_CONTEXT
682 // TODO: consider caching the value
683 wxGraphicsContext* dc = wxGraphicsContext::CreateFromNative((CGContextRef) NULL);
684 dc->SetFont(*(wxFont *)this,*wxBLACK);
685 wxDouble width, height = 0;
686 dc->GetTextExtent( wxT("g"), &width, &height, NULL, NULL);
687 delete dc;
688 return wxSize((int)width, (int)height);
689#else
690 return wxFontBase::GetPixelSize();
691#endif
692}
693
0c14b6c3 694wxFontFamily wxFont::GetFamily() const
489468fe 695{
0c14b6c3 696 wxCHECK_MSG( M_FONTDATA != NULL , wxFONTFAMILY_MAX, wxT("invalid font") );
489468fe
SC
697
698 return M_FONTDATA->GetFamily();
699}
700
0c14b6c3 701wxFontStyle wxFont::GetStyle() const
489468fe 702{
0c14b6c3 703 wxCHECK_MSG( M_FONTDATA != NULL , wxFONTSTYLE_MAX, wxT("invalid font") );
489468fe
SC
704
705 return M_FONTDATA->GetStyle() ;
706}
707
0c14b6c3 708wxFontWeight wxFont::GetWeight() const
489468fe 709{
0c14b6c3 710 wxCHECK_MSG( M_FONTDATA != NULL , wxFONTWEIGHT_MAX, wxT("invalid font") );
489468fe
SC
711
712 return M_FONTDATA->GetWeight();
713}
714
715bool wxFont::GetUnderlined() const
716{
717 wxCHECK_MSG( M_FONTDATA != NULL , false, wxT("invalid font") );
718
719 return M_FONTDATA->GetUnderlined();
720}
721
722wxString wxFont::GetFaceName() const
723{
724 wxCHECK_MSG( M_FONTDATA != NULL , wxEmptyString , wxT("invalid font") );
725
726 return M_FONTDATA->GetFaceName() ;
727}
728
729wxFontEncoding wxFont::GetEncoding() const
730{
731 wxCHECK_MSG( M_FONTDATA != NULL , wxFONTENCODING_DEFAULT , wxT("invalid font") );
732
733 return M_FONTDATA->GetEncoding() ;
734}
735
f1c40652 736#if wxOSX_USE_ATSU_TEXT && wxOSX_USE_CARBON
489468fe
SC
737
738short wxFont::MacGetFontNum() const
739{
740 wxCHECK_MSG( M_FONTDATA != NULL , 0, wxT("invalid font") );
741
f1c40652
SC
742 // cast away constness otherwise lazy font resolution is not possible
743 const_cast<wxFont *>(this)->RealizeResource();
03647350 744
f1c40652 745 return M_FONTDATA->m_info.m_qdFontFamily;
489468fe
SC
746}
747
f1c40652 748wxByte wxFont::MacGetFontStyle() const
489468fe
SC
749{
750 wxCHECK_MSG( M_FONTDATA != NULL , 0, wxT("invalid font") );
751
f1c40652
SC
752 // cast away constness otherwise lazy font resolution is not possible
753 const_cast<wxFont *>(this)->RealizeResource();
03647350 754
f1c40652 755 return M_FONTDATA->m_info.m_qdFontStyle;
489468fe
SC
756}
757
f1c40652 758wxUint16 wxFont::MacGetThemeFontID() const
489468fe
SC
759{
760 wxCHECK_MSG( M_FONTDATA != NULL , 0, wxT("invalid font") );
761
f1c40652 762 return M_FONTDATA->m_macThemeFontID;
489468fe
SC
763}
764
f1c40652
SC
765#endif
766
beb2638a 767#if wxOSX_USE_ATSU_TEXT
f1c40652 768void * wxFont::MacGetATSUStyle() const
489468fe 769{
f1c40652 770 wxCHECK_MSG( M_FONTDATA != NULL , NULL, wxT("invalid font") );
489468fe 771
f1c40652
SC
772 // cast away constness otherwise lazy font resolution is not possible
773 const_cast<wxFont *>(this)->RealizeResource();
03647350 774
f1c40652 775 return M_FONTDATA->m_macATSUStyle;
489468fe 776}
6f283573
SC
777
778#if WXWIN_COMPATIBILITY_2_8
03647350 779wxUint32 wxFont::MacGetATSUFontID() const
6f283573 780{
c22ace4d 781 wxCHECK_MSG( M_FONTDATA != NULL, 0, wxT("invalid font") );
6f283573
SC
782
783 // cast away constness otherwise lazy font resolution is not possible
784 const_cast<wxFont *>(this)->RealizeResource();
03647350 785
6f283573
SC
786 return M_FONTDATA->m_info.m_atsuFontID;
787}
788
789wxUint32 wxFont::MacGetATSUAdditionalQDStyles() const
790{
c22ace4d 791 wxCHECK_MSG( M_FONTDATA != NULL, 0, wxT("invalid font") );
6f283573
SC
792
793 // cast away constness otherwise lazy font resolution is not possible
794 const_cast<wxFont *>(this)->RealizeResource();
03647350 795
6f283573
SC
796 return M_FONTDATA->m_info.m_atsuAdditionalQDStyles;
797}
798#endif
799
f1c40652
SC
800#endif
801
802#if wxOSX_USE_CORE_TEXT
489468fe 803
aa6208d9 804CTFontRef wxFont::OSXGetCTFont() const
489468fe
SC
805{
806 wxCHECK_MSG( M_FONTDATA != NULL , 0, wxT("invalid font") );
807
f1c40652
SC
808 // cast away constness otherwise lazy font resolution is not possible
809 const_cast<wxFont *>(this)->RealizeResource();
03647350 810
f1c40652 811 return (CTFontRef)(M_FONTDATA->m_ctFont);
489468fe
SC
812}
813
f1c40652
SC
814#endif
815
9445de1e
SC
816#if wxOSX_USE_COCOA_OR_CARBON
817
aa6208d9 818CGFontRef wxFont::OSXGetCGFont() const
9445de1e
SC
819{
820 wxCHECK_MSG( M_FONTDATA != NULL , 0, wxT("invalid font") );
821
822 // cast away constness otherwise lazy font resolution is not possible
823 const_cast<wxFont *>(this)->RealizeResource();
03647350 824
9445de1e
SC
825 return (M_FONTDATA->m_cgFont);
826}
827
828#endif
829
830
f1c40652
SC
831#if wxOSX_USE_COCOA
832
aa6208d9 833NSFont* wxFont::OSXGetNSFont() const
489468fe
SC
834{
835 wxCHECK_MSG( M_FONTDATA != NULL , 0, wxT("invalid font") );
836
f1c40652
SC
837 // cast away constness otherwise lazy font resolution is not possible
838 const_cast<wxFont *>(this)->RealizeResource();
03647350 839
f1c40652 840 return (M_FONTDATA->m_nsFont);
489468fe 841}
f1c40652 842
489468fe
SC
843#endif
844
f1c40652 845const wxNativeFontInfo * wxFont::GetNativeFontInfo() const
489468fe
SC
846{
847 wxCHECK_MSG( M_FONTDATA != NULL , NULL, wxT("invalid font") );
f1c40652 848 wxCHECK_MSG( Ok(), NULL, wxT("invalid font") );
489468fe 849
f1c40652
SC
850 // cast away constness otherwise lazy font resolution is not possible
851 const_cast<wxFont *>(this)->RealizeResource();
03647350 852
f1c40652
SC
853 // M_FONTDATA->m_info.InitFromFont(*this);
854
855 return &(M_FONTDATA->m_info);
856}
857
858// ----------------------------------------------------------------------------
859// wxNativeFontInfo
860// ----------------------------------------------------------------------------
861
862#if wxOSX_USE_CORE_TEXT
863
864/* from Core Text Manual Common Operations */
865
866static CTFontDescriptorRef wxMacCreateCTFontDescriptor(CFStringRef iFamilyName, CTFontSymbolicTraits iTraits )
867{
868 CTFontDescriptorRef descriptor = NULL;
869 CFMutableDictionaryRef attributes;
870
2e587bb9 871 wxASSERT(iFamilyName != NULL);
f1c40652
SC
872 // Create a mutable dictionary to hold our attributes.
873 attributes = CFDictionaryCreateMutable(kCFAllocatorDefault, 0,
874 &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks);
2e587bb9 875 wxASSERT(attributes != NULL);
f1c40652
SC
876
877 if (attributes != NULL) {
878 // Add a family name to our attributes.
879 CFDictionaryAddValue(attributes, kCTFontFamilyNameAttribute, iFamilyName);
880
881
882 if ( iTraits ) {
883 CFMutableDictionaryRef traits;
884 CFNumberRef symTraits;
885
886 // Create the traits dictionary.
887 symTraits = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type,
888 &iTraits);
2e587bb9 889 wxASSERT(symTraits != NULL);
f1c40652
SC
890
891 if (symTraits != NULL) {
892 // Create a dictionary to hold our traits values.
893 traits = CFDictionaryCreateMutable(kCFAllocatorDefault, 0,
894 &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks);
2e587bb9 895 wxASSERT(traits != NULL);
f1c40652
SC
896
897 if (traits != NULL) {
898 // Add the symbolic traits value to the traits dictionary.
899 CFDictionaryAddValue(traits, kCTFontSymbolicTrait, symTraits);
900
901 // Add the traits attribute to our attributes.
902 CFDictionaryAddValue(attributes, kCTFontTraitsAttribute, traits);
903 CFRelease(traits);
904 }
905 CFRelease(symTraits);
906 }
907 }
908 // Create the font descriptor with our attributes
909 descriptor = CTFontDescriptorCreateWithAttributes(attributes);
2e587bb9 910 wxASSERT(descriptor != NULL);
f1c40652
SC
911
912 CFRelease(attributes);
913 }
914 // Return our font descriptor.
915 return descriptor ;
916}
917
918#endif
919
920void wxNativeFontInfo::Init()
921{
f1c40652
SC
922#if wxOSX_USE_ATSU_TEXT
923 m_atsuFontID = 0 ;
924 m_atsuAdditionalQDStyles = 0;
925 m_atsuFontValid = false;
926#if wxOSX_USE_CARBON
927 m_qdFontStyle = 0;
928 m_qdFontFamily = 0;
929#endif
f1c40652
SC
930#endif
931 m_pointSize = 0;
932 m_family = wxFONTFAMILY_DEFAULT;
933 m_style = wxFONTSTYLE_NORMAL;
934 m_weight = wxFONTWEIGHT_NORMAL;
935 m_underlined = false;
936 m_faceName.clear();
c443ff6f 937 m_encoding = wxFont::GetDefaultEncoding();
f1c40652
SC
938 m_descriptorValid = false;
939}
940
941#if wxOSX_USE_CORE_TEXT
942void wxNativeFontInfo::Init(CTFontDescriptorRef descr)
943{
944 Init();
03647350 945
03c28161 946 wxCFRef< CFNumberRef > sizevalue( (CFNumberRef) CTFontDescriptorCopyAttribute( descr, kCTFontSizeAttribute ) );
f1c40652
SC
947 float fsize;
948 if ( CFNumberGetValue( sizevalue , kCFNumberFloatType , &fsize ) )
949 m_pointSize = (int)( fsize + 0.5 );
950
03c28161 951 wxCFRef< CFDictionaryRef > traitsvalue( (CFDictionaryRef) CTFontDescriptorCopyAttribute( descr, kCTFontTraitsAttribute ) );
f1c40652
SC
952 CTFontSymbolicTraits traits;
953 if ( CFNumberGetValue((CFNumberRef) CFDictionaryGetValue(traitsvalue,kCTFontSymbolicTrait),kCFNumberIntType,&traits) )
954 {
955 if ( traits & kCTFontItalicTrait )
956 m_style = wxFONTSTYLE_ITALIC;
957 if ( traits & kCTFontBoldTrait )
958 m_weight = wxFONTWEIGHT_BOLD ;
959 }
960
03c28161 961 wxCFStringRef familyName( (CFStringRef) CTFontDescriptorCopyAttribute(descr, kCTFontFamilyNameAttribute));
03647350 962 m_faceName = familyName.AsString();
489468fe
SC
963}
964#endif
965
f1c40652
SC
966void wxNativeFontInfo::EnsureValid()
967{
968 if ( m_descriptorValid )
969 return;
03647350 970
f1c40652
SC
971#if wxOSX_USE_ATSU_TEXT
972 if ( !m_atsuFontValid )
973 {
9a672c75
SC
974#if !wxOSX_USE_CARBON
975 // not needed outside
976 wxInt16 m_qdFontFamily;
977 wxInt16 m_qdFontStyle;
978#endif
f1c40652
SC
979 wxCFStringRef cf( m_faceName, wxLocale::GetSystemEncoding() );
980 ATSFontFamilyRef atsfamily = ATSFontFamilyFindFromName( cf , kATSOptionFlagsDefault );
981 if ( atsfamily == (ATSFontFamilyRef) -1 )
982 {
983 wxLogDebug( wxT("ATSFontFamilyFindFromName failed for ") + m_faceName );
984 m_qdFontFamily = GetAppFont();
985 }
986 else
987 {
988 m_qdFontFamily = FMGetFontFamilyFromATSFontFamilyRef( atsfamily );
989 }
990
991 m_qdFontStyle = 0;
992 if (m_weight == wxFONTWEIGHT_BOLD)
993 m_qdFontStyle |= bold;
994 if (m_style == wxFONTSTYLE_ITALIC || m_style == wxFONTSTYLE_SLANT)
995 m_qdFontStyle |= italic;
996 if (m_underlined)
997 m_qdFontStyle |= underline;
998
489468fe 999
f1c40652
SC
1000 // we try to get as much styles as possible into ATSU
1001
1002 // ATSUFontID and FMFont are equivalent
1003 FMFontStyle intrinsicStyle = 0 ;
1004 OSStatus status = FMGetFontFromFontFamilyInstance( m_qdFontFamily , m_qdFontStyle , (FMFont*)&m_atsuFontID , &intrinsicStyle);
ca910e1a
VZ
1005 if ( status != noErr )
1006 {
1007 wxFAIL_MSG( wxT("couldn't get an ATSUFont from font family") );
1008 }
f1c40652
SC
1009 m_atsuAdditionalQDStyles = m_qdFontStyle & (~intrinsicStyle );
1010 m_atsuFontValid = true;
1011 }
f1c40652
SC
1012#endif
1013 m_descriptorValid = true;
1014}
1015
1016void wxNativeFontInfo::Init(const wxNativeFontInfo& info)
489468fe 1017{
f1c40652 1018 Init();
f1c40652
SC
1019#if wxOSX_USE_ATSU_TEXT
1020 m_atsuFontValid = info.m_atsuFontValid;
1021 m_atsuFontID = info.m_atsuFontID ;
1022 m_atsuAdditionalQDStyles = info.m_atsuAdditionalQDStyles;
1023#if wxOSX_USE_CARBON
1024 m_qdFontFamily = info.m_qdFontFamily;
1025 m_qdFontStyle = info.m_qdFontStyle;
1026#endif
f1c40652
SC
1027#endif
1028 m_pointSize = info.m_pointSize;
1029 m_family = info.m_family;
1030 m_style = info.m_style;
1031 m_weight = info.m_weight;
1032 m_underlined = info.m_underlined;
1033 m_faceName = info.m_faceName;
1034 m_encoding = info.m_encoding;
1035 m_descriptorValid = info.m_descriptorValid;
1036}
1037
1038void wxNativeFontInfo::Init(int size,
1039 wxFontFamily family,
1040 wxFontStyle style,
1041 wxFontWeight weight,
1042 bool underlined,
1043 const wxString& faceName,
1044 wxFontEncoding encoding)
1045{
1046 Init();
1047 m_pointSize = size;
1048 m_family = family;
1049 m_style = style;
1050 m_weight = weight;
1051 m_underlined = underlined;
1052 m_faceName = faceName;
c443ff6f
SC
1053 if ( encoding == wxFONTENCODING_DEFAULT )
1054 encoding = wxFont::GetDefaultEncoding();
f1c40652 1055 m_encoding = encoding;
489468fe 1056
489468fe
SC
1057}
1058
f1c40652
SC
1059void wxNativeFontInfo::Free()
1060{
f1c40652
SC
1061#if wxOSX_USE_ATSU_TEXT
1062 m_atsuFontID = 0 ;
1063 m_atsuAdditionalQDStyles = 0;
1064 m_atsuFontValid = false;
489468fe 1065#endif
f1c40652
SC
1066 m_descriptorValid = false;
1067}
489468fe 1068
f1c40652 1069bool wxNativeFontInfo::FromString(const wxString& s)
489468fe 1070{
f1c40652 1071 long l;
489468fe 1072
9a83f860 1073 wxStringTokenizer tokenizer(s, wxT(";"));
489468fe 1074
f1c40652
SC
1075 wxString token = tokenizer.GetNextToken();
1076 //
1077 // Ignore the version for now
1078 //
1079
1080 token = tokenizer.GetNextToken();
1081 if ( !token.ToLong(&l) )
1082 return false;
1083 m_pointSize = (int)l;
1084
1085 token = tokenizer.GetNextToken();
1086 if ( !token.ToLong(&l) )
1087 return false;
1088 m_family = (wxFontFamily)l;
1089
1090 token = tokenizer.GetNextToken();
1091 if ( !token.ToLong(&l) )
1092 return false;
1093 m_style = (wxFontStyle)l;
1094
1095 token = tokenizer.GetNextToken();
1096 if ( !token.ToLong(&l) )
1097 return false;
1098 m_weight = (wxFontWeight)l;
1099
1100 token = tokenizer.GetNextToken();
1101 if ( !token.ToLong(&l) )
1102 return false;
1103 m_underlined = l != 0;
1104
1105 m_faceName = tokenizer.GetNextToken();
1106
1107#ifndef __WXMAC__
1108 if( !faceName )
1109 return false;
1110#endif
1111
1112 token = tokenizer.GetNextToken();
1113 if ( !token.ToLong(&l) )
1114 return false;
1115 m_encoding = (wxFontEncoding)l;
1116
1117 return true;
1118}
1119
1120wxString wxNativeFontInfo::ToString() const
1121{
1122 wxString s;
1123
9a83f860 1124 s.Printf(wxT("%d;%d;%d;%d;%d;%d;%s;%d"),
f1c40652
SC
1125 0, // version
1126 m_pointSize,
1127 m_family,
1128 (int)m_style,
1129 (int)m_weight,
1130 m_underlined,
1131 m_faceName.GetData(),
1132 (int)m_encoding);
1133
1134 return s;
1135}
1136
1137int wxNativeFontInfo::GetPointSize() const
1138{
1139 return m_pointSize;
1140}
1141
1142wxFontStyle wxNativeFontInfo::GetStyle() const
1143{
1144 return m_style;
1145}
1146
1147wxFontWeight wxNativeFontInfo::GetWeight() const
1148{
1149 return m_weight;
1150}
1151
1152bool wxNativeFontInfo::GetUnderlined() const
1153{
1154 return m_underlined;
1155}
1156
1157wxString wxNativeFontInfo::GetFaceName() const
1158{
1159 return m_faceName;
1160}
1161
1162wxFontFamily wxNativeFontInfo::GetFamily() const
1163{
1164 return m_family;
489468fe 1165}
f1c40652
SC
1166
1167wxFontEncoding wxNativeFontInfo::GetEncoding() const
1168{
1169 return m_encoding;
1170}
1171
1172// changing the font descriptor
1173
1174void wxNativeFontInfo::SetPointSize(int pointsize)
1175{
1176 if ( m_pointSize != pointsize )
1177 {
1178 m_pointSize = pointsize;
1179 Free();
1180 }
1181}
1182
1183void wxNativeFontInfo::SetStyle(wxFontStyle style_)
1184{
1185 if ( m_style != style_ )
1186 {
1187 m_style = style_;
1188 Free();
1189 }
1190}
1191
1192void wxNativeFontInfo::SetWeight(wxFontWeight weight_)
1193{
1194 if ( m_weight != weight_ )
1195 {
1196 m_weight = weight_;
1197 Free();
1198 }
1199}
1200
1201void wxNativeFontInfo::SetUnderlined(bool underlined_)
1202{
1203 if ( m_underlined != underlined_ )
1204 {
1205 m_underlined = underlined_;
1206 Free();
1207 }
1208}
1209
1210bool wxNativeFontInfo::SetFaceName(const wxString& facename_)
1211{
1212 if ( m_faceName != facename_ )
1213 {
1214 m_faceName = facename_;
1215 Free();
1216 }
1217 return true;
1218}
1219
1220void wxNativeFontInfo::SetFamily(wxFontFamily family_)
1221{
1222 if ( m_family != family_ )
1223 {
1224 m_family = family_;
1225 Free();
1226 }
1227}
1228
1229void wxNativeFontInfo::SetEncoding(wxFontEncoding encoding_)
1230{
c443ff6f
SC
1231 if ( encoding_ == wxFONTENCODING_DEFAULT )
1232 encoding_ = wxFont::GetDefaultEncoding();
f1c40652
SC
1233 m_encoding = encoding_;
1234 // not reflected in native descriptors
c22ace4d 1235}