]> git.saurik.com Git - wxWidgets.git/blame_incremental - src/common/fontcmn.cpp
install wxUniv headers in make install and include wxUniv sources in make dist
[wxWidgets.git] / src / common / fontcmn.cpp
... / ...
CommitLineData
1/////////////////////////////////////////////////////////////////////////////
2// Name: common/fontcmn.cpp
3// Purpose: implementation of wxFontBase methods
4// Author: Vadim Zeitlin
5// Modified by:
6// Created: 20.09.99
7// RCS-ID: $Id$
8// Copyright: (c) wxWindows team
9// Licence: wxWindows license
10/////////////////////////////////////////////////////////////////////////////
11
12// ============================================================================
13// declarations
14// ============================================================================
15
16// ----------------------------------------------------------------------------
17// headers
18// ----------------------------------------------------------------------------
19
20#ifdef __GNUG__
21#pragma implementation "fontbase.h"
22#endif
23
24// For compilers that support precompilation, includes "wx.h".
25#include "wx/wxprec.h"
26
27#ifdef __BORLANDC__
28#pragma hdrstop
29#endif
30
31#ifndef WX_PRECOMP
32#include "wx/font.h"
33#include "wx/intl.h"
34#endif // WX_PRECOMP
35
36#include "wx/gdicmn.h"
37#include "wx/fontutil.h" // for wxNativeFontInfo
38#include "wx/fontmap.h"
39
40#include "wx/tokenzr.h"
41
42// ============================================================================
43// implementation
44// ============================================================================
45
46// ----------------------------------------------------------------------------
47// wxFontBase
48// ----------------------------------------------------------------------------
49
50wxFontEncoding wxFontBase::ms_encodingDefault = wxFONTENCODING_SYSTEM;
51
52/* static */
53void wxFontBase::SetDefaultEncoding(wxFontEncoding encoding)
54{
55 // GetDefaultEncoding() should return something != wxFONTENCODING_DEFAULT
56 // and, besides, using this value here doesn't make any sense
57 wxCHECK_RET( encoding != wxFONTENCODING_DEFAULT,
58 _T("can't set default encoding to wxFONTENCODING_DEFAULT") );
59
60 ms_encodingDefault = encoding;
61}
62
63wxFontBase::~wxFontBase()
64{
65 // this destructor is required for Darwin
66}
67
68/* static */
69wxFont *wxFontBase::New(int size,
70 int family,
71 int style,
72 int weight,
73 bool underlined,
74 const wxString& face,
75 wxFontEncoding encoding)
76{
77 return new wxFont(size, family, style, weight, underlined, face, encoding);
78}
79
80/* static */
81wxFont *wxFontBase::New(const wxNativeFontInfo& info)
82{
83 return new wxFont(info);
84}
85
86/* static */
87wxFont *wxFontBase::New(const wxString& strNativeFontDesc)
88{
89 wxNativeFontInfo fontInfo;
90 if ( !fontInfo.FromString(strNativeFontDesc) )
91 return new wxFont(*wxNORMAL_FONT);
92
93 return New(fontInfo);
94}
95
96bool wxFontBase::IsFixedWidth() const
97{
98 return GetFamily() == wxFONTFAMILY_TELETYPE;
99}
100
101wxNativeFontInfo *wxFontBase::GetNativeFontInfo() const
102{
103#ifdef wxNO_NATIVE_FONTINFO
104 wxNativeFontInfo *fontInfo = new wxNativeFontInfo();
105
106 fontInfo->SetPointSize(GetPointSize());
107 fontInfo->SetFamily((wxFontFamily)GetFamily());
108 fontInfo->SetStyle((wxFontStyle)GetStyle());
109 fontInfo->SetWeight((wxFontWeight)GetWeight());
110 fontInfo->SetUnderlined(GetUnderlined());
111 fontInfo->SetFaceName(GetFaceName());
112 fontInfo->SetEncoding(GetEncoding());
113
114 return fontInfo;
115#else
116 return (wxNativeFontInfo *)NULL;
117#endif
118}
119
120void wxFontBase::SetNativeFontInfo(const wxNativeFontInfo& info)
121{
122#ifdef wxNO_NATIVE_FONTINFO
123 SetPointSize(info.pointSize);
124 SetFamily(info.family);
125 SetStyle(info.style);
126 SetWeight(info.weight);
127 SetUnderlined(info.underlined);
128 SetFaceName(info.faceName);
129 SetEncoding(info.encoding);
130#else
131 (void)info;
132#endif
133}
134
135wxString wxFontBase::GetNativeFontInfoDesc() const
136{
137 wxString fontDesc;
138 wxNativeFontInfo *fontInfo = GetNativeFontInfo();
139 if ( fontInfo )
140 {
141 fontDesc = fontInfo->ToString();
142 delete fontInfo;
143 }
144
145 return fontDesc;
146}
147
148wxString wxFontBase::GetNativeFontInfoUserDesc() const
149{
150 wxString fontDesc;
151 wxNativeFontInfo *fontInfo = GetNativeFontInfo();
152 if ( fontInfo )
153 {
154 fontDesc = fontInfo->ToUserString();
155 delete fontInfo;
156 }
157
158 return fontDesc;
159}
160
161void wxFontBase::SetNativeFontInfo(const wxString& info)
162{
163 wxNativeFontInfo fontInfo;
164 if ( !info.empty() && fontInfo.FromString(info) )
165 {
166 SetNativeFontInfo(fontInfo);
167 }
168}
169
170void wxFontBase::SetNativeFontInfoUserDesc(const wxString& info)
171{
172 wxNativeFontInfo fontInfo;
173 if ( !info.empty() && fontInfo.FromUserString(info) )
174 {
175 SetNativeFontInfo(fontInfo);
176 }
177}
178
179wxFont& wxFont::operator=(const wxFont& font)
180{
181 if ( this != &font )
182 Ref(font);
183
184 return (wxFont &)*this;
185}
186
187bool wxFontBase::operator==(const wxFont& font) const
188{
189 // either it is the same font, i.e. they share the same common data or they
190 // have different ref datas but still describe the same font
191 return GetFontData() == font.GetFontData() ||
192 (
193 Ok() == font.Ok() &&
194 GetPointSize() == font.GetPointSize() &&
195 GetFamily() == font.GetFamily() &&
196 GetStyle() == font.GetStyle() &&
197 GetWeight() == font.GetWeight() &&
198 GetUnderlined() == font.GetUnderlined() &&
199 GetFaceName() == font.GetFaceName() &&
200 GetEncoding() == font.GetEncoding()
201 );
202}
203
204bool wxFontBase::operator!=(const wxFont& font) const
205{
206 return !(*this == font);
207}
208
209wxString wxFontBase::GetFamilyString() const
210{
211 wxCHECK_MSG( Ok(), wxT("wxDEFAULT"), wxT("invalid font") );
212
213 switch ( GetFamily() )
214 {
215 case wxDECORATIVE: return wxT("wxDECORATIVE");
216 case wxROMAN: return wxT("wxROMAN");
217 case wxSCRIPT: return wxT("wxSCRIPT");
218 case wxSWISS: return wxT("wxSWISS");
219 case wxMODERN: return wxT("wxMODERN");
220 case wxTELETYPE: return wxT("wxTELETYPE");
221 default: return wxT("wxDEFAULT");
222 }
223}
224
225wxString wxFontBase::GetStyleString() const
226{
227 wxCHECK_MSG( Ok(), wxT("wxDEFAULT"), wxT("invalid font") );
228
229 switch ( GetStyle() )
230 {
231 case wxNORMAL: return wxT("wxNORMAL");
232 case wxSLANT: return wxT("wxSLANT");
233 case wxITALIC: return wxT("wxITALIC");
234 default: return wxT("wxDEFAULT");
235 }
236}
237
238wxString wxFontBase::GetWeightString() const
239{
240 wxCHECK_MSG( Ok(), wxT("wxDEFAULT"), wxT("invalid font") );
241
242 switch ( GetWeight() )
243 {
244 case wxNORMAL: return wxT("wxNORMAL");
245 case wxBOLD: return wxT("wxBOLD");
246 case wxLIGHT: return wxT("wxLIGHT");
247 default: return wxT("wxDEFAULT");
248 }
249}
250
251// ----------------------------------------------------------------------------
252// wxNativeFontInfo
253// ----------------------------------------------------------------------------
254
255#ifdef wxNO_NATIVE_FONTINFO
256
257// These are the generic forms of FromString()/ToString.
258//
259// convert to/from the string representation: format is
260// version;pointsize;family;style;weight;underlined;facename;encoding
261
262bool wxNativeFontInfo::FromString(const wxString& s)
263{
264 long l;
265
266 wxStringTokenizer tokenizer(s, _T(";"));
267
268 wxString token = tokenizer.GetNextToken();
269 //
270 // Ignore the version for now
271 //
272
273 token = tokenizer.GetNextToken();
274 if ( !token.ToLong(&l) )
275 return FALSE;
276 pointSize = (int)l;
277
278 token = tokenizer.GetNextToken();
279 if ( !token.ToLong(&l) )
280 return FALSE;
281 family = (wxFontFamily)l;
282
283 token = tokenizer.GetNextToken();
284 if ( !token.ToLong(&l) )
285 return FALSE;
286 style = (wxFontStyle)l;
287
288 token = tokenizer.GetNextToken();
289 if ( !token.ToLong(&l) )
290 return FALSE;
291 weight = (wxFontWeight)l;
292
293 token = tokenizer.GetNextToken();
294 if ( !token.ToLong(&l) )
295 return FALSE;
296 underlined = l != 0;
297
298 faceName = tokenizer.GetNextToken();
299 if( !faceName )
300 return FALSE;
301
302 token = tokenizer.GetNextToken();
303 if ( !token.ToLong(&l) )
304 return FALSE;
305 encoding = (wxFontEncoding)l;
306
307 return TRUE;
308}
309
310wxString wxNativeFontInfo::ToString() const
311{
312 wxString s;
313
314 s.Printf(_T("%d;%d;%d;%d;%d;%d;%s;%d"),
315 0, // version
316 pointSize,
317 family,
318 (int)style,
319 (int)weight,
320 underlined,
321 faceName.GetData(),
322 (int)encoding);
323
324 return s;
325}
326
327void wxNativeFontInfo::Init()
328{
329 pointSize = wxNORMAL_FONT->GetPointSize();
330 family = wxFONTFAMILY_DEFAULT;
331 style = wxFONTSTYLE_NORMAL;
332 weight = wxFONTWEIGHT_NORMAL;
333 underlined = FALSE;
334 faceName.clear();
335 encoding = wxFONTENCODING_DEFAULT;
336}
337
338int wxNativeFontInfo::GetPointSize() const
339{
340 return pointSize;
341}
342
343wxFontStyle wxNativeFontInfo::GetStyle() const
344{
345 return style;
346}
347
348wxFontWeight wxNativeFontInfo::GetWeight() const
349{
350 return weight;
351}
352
353bool wxNativeFontInfo::GetUnderlined() const
354{
355 return underlined;
356}
357
358wxString wxNativeFontInfo::GetFaceName() const
359{
360 return faceName;
361}
362
363wxFontFamily wxNativeFontInfo::GetFamily() const
364{
365 return family;
366}
367
368wxFontEncoding wxNativeFontInfo::GetEncoding() const
369{
370 return encoding;
371}
372
373void wxNativeFontInfo::SetPointSize(int pointsize)
374{
375 pointSize = pointsize;
376}
377
378void wxNativeFontInfo::SetStyle(wxFontStyle style_)
379{
380 style = style_;
381}
382
383void wxNativeFontInfo::SetWeight(wxFontWeight weight_)
384{
385 weight = weight_;
386}
387
388void wxNativeFontInfo::SetUnderlined(bool underlined_)
389{
390 underlined = underlined_;
391}
392
393void wxNativeFontInfo::SetFaceName(wxString facename_)
394{
395 faceName = facename_;
396}
397
398void wxNativeFontInfo::SetFamily(wxFontFamily family_)
399{
400 family = family_;
401}
402
403void wxNativeFontInfo::SetEncoding(wxFontEncoding encoding_)
404{
405 encoding = encoding_;
406}
407
408#endif // generic wxNativeFontInfo implementation
409
410// conversion to/from user-readable string: this is used in the generic
411// versions and under MSW as well because there is no standard font description
412// format there anyhow (but there is a well-defined standard for X11 fonts used
413// by wxGTK and wxMotif)
414
415#if defined(wxNO_NATIVE_FONTINFO) || defined(__WXMSW__) || defined (__WXPM__)
416
417wxString wxNativeFontInfo::ToUserString() const
418{
419 wxString desc;
420
421 // first put the adjectives, if any - this is English-centric, of course,
422 // but what else can we do?
423 if ( GetUnderlined() )
424 {
425 desc << _("underlined ");
426 }
427
428 switch ( GetWeight() )
429 {
430 default:
431 wxFAIL_MSG( _T("unknown font weight") );
432 // fall through
433
434 case wxFONTWEIGHT_NORMAL:
435 break;
436
437 case wxFONTWEIGHT_LIGHT:
438 desc << _("light ");
439 break;
440
441 case wxFONTWEIGHT_BOLD:
442 desc << _("bold ");
443 break;
444 }
445
446 switch ( GetStyle() )
447 {
448 default:
449 wxFAIL_MSG( _T("unknown font style") );
450 // fall through
451
452 case wxFONTSTYLE_NORMAL:
453 break;
454
455 // we don't distinguish between the two for now anyhow...
456 case wxFONTSTYLE_ITALIC:
457 case wxFONTSTYLE_SLANT:
458 desc << _("italic");
459 break;
460 }
461
462 wxString face = GetFaceName();
463 if ( !face.empty() )
464 {
465 desc << _T(' ') << face;
466 }
467
468 int size = GetPointSize();
469 if ( size != wxNORMAL_FONT->GetPointSize() )
470 {
471 desc << _T(' ') << size;
472 }
473
474#if wxUSE_FONTMAP
475 wxFontEncoding enc = GetEncoding();
476 if ( enc != wxFONTENCODING_DEFAULT && enc != wxFONTENCODING_SYSTEM )
477 {
478 desc << _T(' ') << wxTheFontMapper->GetEncodingName(enc);
479 }
480#endif // wxUSE_FONTMAP
481
482 return desc;
483}
484
485bool wxNativeFontInfo::FromUserString(const wxString& s)
486{
487 // reset to the default state
488 Init();
489
490 // parse a more or less free form string
491 //
492 // TODO: we should handle at least the quoted facenames
493 wxStringTokenizer tokenizer(s, _T(";, "), wxTOKEN_STRTOK);
494
495 wxString face;
496 unsigned long size;
497
498#if wxUSE_FONTMAP
499 wxFontEncoding encoding;
500#endif // wxUSE_FONTMAP
501
502 while ( tokenizer.HasMoreTokens() )
503 {
504 wxString token = tokenizer.GetNextToken();
505
506 // normalize it
507 token.Trim(TRUE).Trim(FALSE).MakeLower();
508
509 // look for the known tokens
510 if ( token == _T("underlined") || token == _("underlined") )
511 {
512 SetUnderlined(TRUE);
513 }
514 else if ( token == _T("light") || token == _("light") )
515 {
516 SetWeight(wxFONTWEIGHT_LIGHT);
517 }
518 else if ( token == _T("bold") || token == _("bold") )
519 {
520 SetWeight(wxFONTWEIGHT_BOLD);
521 }
522 else if ( token == _T("italic") || token == _("italic") )
523 {
524 SetStyle(wxFONTSTYLE_ITALIC);
525 }
526 else if ( token.ToULong(&size) )
527 {
528 SetPointSize(size);
529 }
530#if wxUSE_FONTMAP
531 else if ( (encoding = wxTheFontMapper->CharsetToEncoding(token, FALSE))
532 != wxFONTENCODING_DEFAULT )
533 {
534 SetEncoding(encoding);
535 }
536#endif // wxUSE_FONTMAP
537 else // assume it is the face name
538 {
539 if ( !face.empty() )
540 {
541 face += _T(' ');
542 }
543
544 face += token;
545
546 // skip the code which resets face below
547 continue;
548 }
549
550 // if we had had the facename, we shouldn't continue appending tokens
551 // to it (i.e. "foo bold bar" shouldn't result in the facename "foo
552 // bar")
553 if ( !face.empty() )
554 {
555 SetFaceName(face);
556 face.clear();
557 }
558 }
559
560 // we might not have flushed it inside the loop
561 if ( !face.empty() )
562 {
563 SetFaceName(face);
564 }
565
566 return TRUE;
567}
568
569#endif // generic or wxMSW or wxOS2
570