| OLD | NEW |
| 1 | 1 |
| 2 /* | 2 /* |
| 3 * Copyright 2006 The Android Open Source Project | 3 * Copyright 2006 The Android Open Source Project |
| 4 * | 4 * |
| 5 * Use of this source code is governed by a BSD-style license that can be | 5 * Use of this source code is governed by a BSD-style license that can be |
| 6 * found in the LICENSE file. | 6 * found in the LICENSE file. |
| 7 */ | 7 */ |
| 8 | 8 |
| 9 #include "SkAdvancedTypefaceMetrics.h" | 9 #include "SkAdvancedTypefaceMetrics.h" |
| 10 #include "SkBase64.h" | 10 #include "SkBase64.h" |
| (...skipping 108 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 119 tchar_to_skstring(fontName.get(), familyName); | 119 tchar_to_skstring(fontName.get(), familyName); |
| 120 } | 120 } |
| 121 | 121 |
| 122 static void make_canonical(LOGFONT* lf) { | 122 static void make_canonical(LOGFONT* lf) { |
| 123 lf->lfHeight = -64; | 123 lf->lfHeight = -64; |
| 124 lf->lfQuality = CLEARTYPE_QUALITY;//PROOF_QUALITY; | 124 lf->lfQuality = CLEARTYPE_QUALITY;//PROOF_QUALITY; |
| 125 lf->lfCharSet = DEFAULT_CHARSET; | 125 lf->lfCharSet = DEFAULT_CHARSET; |
| 126 // lf->lfClipPrecision = 64; | 126 // lf->lfClipPrecision = 64; |
| 127 } | 127 } |
| 128 | 128 |
| 129 static SkFontStyle get_style(const LOGFONT& lf) { | 129 static SkTypeface::Style get_style(const LOGFONT& lf) { |
| 130 return SkFontStyle(lf.lfWeight, | 130 unsigned style = 0; |
| 131 lf.lfWidth, | 131 if (lf.lfWeight >= FW_BOLD) { |
| 132 lf.lfItalic ? SkFontStyle::kItalic_Slant : SkFontStyle::k
Upright_Slant); | 132 style |= SkTypeface::kBold; |
| 133 } |
| 134 if (lf.lfItalic) { |
| 135 style |= SkTypeface::kItalic; |
| 136 } |
| 137 return static_cast<SkTypeface::Style>(style); |
| 138 } |
| 139 |
| 140 static void setStyle(LOGFONT* lf, SkTypeface::Style style) { |
| 141 lf->lfWeight = (style & SkTypeface::kBold) != 0 ? FW_BOLD : FW_NORMAL ; |
| 142 lf->lfItalic = ((style & SkTypeface::kItalic) != 0); |
| 133 } | 143 } |
| 134 | 144 |
| 135 static inline FIXED SkFixedToFIXED(SkFixed x) { | 145 static inline FIXED SkFixedToFIXED(SkFixed x) { |
| 136 return *(FIXED*)(&x); | 146 return *(FIXED*)(&x); |
| 137 } | 147 } |
| 138 static inline SkFixed SkFIXEDToFixed(FIXED x) { | 148 static inline SkFixed SkFIXEDToFixed(FIXED x) { |
| 139 return *(SkFixed*)(&x); | 149 return *(SkFixed*)(&x); |
| 140 } | 150 } |
| 141 | 151 |
| 142 static inline FIXED SkScalarToFIXED(SkScalar x) { | 152 static inline FIXED SkScalarToFIXED(SkScalar x) { |
| (...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 200 if (0 == otmRet) { | 210 if (0 == otmRet) { |
| 201 call_ensure_accessible(lf); | 211 call_ensure_accessible(lf); |
| 202 otmRet = GetOutlineTextMetrics(hdc, sizeof(otm), &otm); | 212 otmRet = GetOutlineTextMetrics(hdc, sizeof(otm), &otm); |
| 203 } | 213 } |
| 204 | 214 |
| 205 return (0 == otmRet) ? 0 : otm.otmEMSquare; | 215 return (0 == otmRet) ? 0 : otm.otmEMSquare; |
| 206 } | 216 } |
| 207 | 217 |
| 208 class LogFontTypeface : public SkTypeface { | 218 class LogFontTypeface : public SkTypeface { |
| 209 public: | 219 public: |
| 210 LogFontTypeface(const SkFontStyle& style, const LOGFONT& lf, bool serializeA
sStream) | 220 LogFontTypeface(SkTypeface::Style style, SkFontID fontID, const LOGFONT& lf,
bool serializeAsStream = false) : |
| 211 : SkTypeface(style, SkTypefaceCache::NewFontID(), false) | 221 SkTypeface(style, fontID, false), fLogFont(lf), fSerializeAsStream(seria
lizeAsStream) { |
| 212 , fLogFont(lf) | |
| 213 , fSerializeAsStream(serializeAsStream) | |
| 214 { | |
| 215 | 222 |
| 216 // If the font has cubic outlines, it will not be rendered with ClearTyp
e. | 223 // If the font has cubic outlines, it will not be rendered with ClearTyp
e. |
| 217 HFONT font = CreateFontIndirect(&lf); | 224 HFONT font = CreateFontIndirect(&lf); |
| 218 | 225 |
| 219 HDC deviceContext = ::CreateCompatibleDC(NULL); | 226 HDC deviceContext = ::CreateCompatibleDC(NULL); |
| 220 HFONT savefont = (HFONT)SelectObject(deviceContext, font); | 227 HFONT savefont = (HFONT)SelectObject(deviceContext, font); |
| 221 | 228 |
| 222 TEXTMETRIC textMetric; | 229 TEXTMETRIC textMetric; |
| 223 if (0 == GetTextMetrics(deviceContext, &textMetric)) { | 230 if (0 == GetTextMetrics(deviceContext, &textMetric)) { |
| 224 call_ensure_accessible(lf); | 231 call_ensure_accessible(lf); |
| (...skipping 16 matching lines...) Expand all Loading... |
| 241 // Therefore all TMPF_DEVICE will be PostScript (cubic) fonts. | 248 // Therefore all TMPF_DEVICE will be PostScript (cubic) fonts. |
| 242 fCanBeLCD = !((textMetric.tmPitchAndFamily & TMPF_VECTOR) && | 249 fCanBeLCD = !((textMetric.tmPitchAndFamily & TMPF_VECTOR) && |
| 243 (textMetric.tmPitchAndFamily & TMPF_DEVICE)); | 250 (textMetric.tmPitchAndFamily & TMPF_DEVICE)); |
| 244 } | 251 } |
| 245 | 252 |
| 246 LOGFONT fLogFont; | 253 LOGFONT fLogFont; |
| 247 bool fSerializeAsStream; | 254 bool fSerializeAsStream; |
| 248 bool fCanBeLCD; | 255 bool fCanBeLCD; |
| 249 | 256 |
| 250 static LogFontTypeface* Create(const LOGFONT& lf) { | 257 static LogFontTypeface* Create(const LOGFONT& lf) { |
| 251 return new LogFontTypeface(get_style(lf), lf, false); | 258 SkTypeface::Style style = get_style(lf); |
| 259 SkFontID fontID = SkTypefaceCache::NewFontID(); |
| 260 return new LogFontTypeface(style, fontID, lf); |
| 252 } | 261 } |
| 253 | 262 |
| 254 static void EnsureAccessible(const SkTypeface* face) { | 263 static void EnsureAccessible(const SkTypeface* face) { |
| 255 call_ensure_accessible(static_cast<const LogFontTypeface*>(face)->fLogFo
nt); | 264 call_ensure_accessible(static_cast<const LogFontTypeface*>(face)->fLogFo
nt); |
| 256 } | 265 } |
| 257 | 266 |
| 258 protected: | 267 protected: |
| 259 virtual SkStream* onOpenStream(int* ttcIndex) const SK_OVERRIDE; | 268 virtual SkStream* onOpenStream(int* ttcIndex) const SK_OVERRIDE; |
| 260 virtual SkScalerContext* onCreateScalerContext(const SkDescriptor*) const SK
_OVERRIDE; | 269 virtual SkScalerContext* onCreateScalerContext(const SkDescriptor*) const SK
_OVERRIDE; |
| 261 virtual void onFilterRec(SkScalerContextRec*) const SK_OVERRIDE; | 270 virtual void onFilterRec(SkScalerContextRec*) const SK_OVERRIDE; |
| (...skipping 11 matching lines...) Expand all Loading... |
| 273 virtual size_t onGetTableData(SkFontTableTag, size_t offset, | 282 virtual size_t onGetTableData(SkFontTableTag, size_t offset, |
| 274 size_t length, void* data) const SK_OVERRIDE; | 283 size_t length, void* data) const SK_OVERRIDE; |
| 275 }; | 284 }; |
| 276 | 285 |
| 277 class FontMemResourceTypeface : public LogFontTypeface { | 286 class FontMemResourceTypeface : public LogFontTypeface { |
| 278 public: | 287 public: |
| 279 /** | 288 /** |
| 280 * The created FontMemResourceTypeface takes ownership of fontMemResource. | 289 * The created FontMemResourceTypeface takes ownership of fontMemResource. |
| 281 */ | 290 */ |
| 282 static FontMemResourceTypeface* Create(const LOGFONT& lf, HANDLE fontMemReso
urce) { | 291 static FontMemResourceTypeface* Create(const LOGFONT& lf, HANDLE fontMemReso
urce) { |
| 283 return new FontMemResourceTypeface(get_style(lf), lf, fontMemResource); | 292 SkTypeface::Style style = get_style(lf); |
| 293 SkFontID fontID = SkTypefaceCache::NewFontID(); |
| 294 return new FontMemResourceTypeface(style, fontID, lf, fontMemResource); |
| 284 } | 295 } |
| 285 | 296 |
| 286 protected: | 297 protected: |
| 287 virtual void weak_dispose() const SK_OVERRIDE { | 298 virtual void weak_dispose() const SK_OVERRIDE { |
| 288 RemoveFontMemResourceEx(fFontMemResource); | 299 RemoveFontMemResourceEx(fFontMemResource); |
| 289 //SkTypefaceCache::Remove(this); | 300 //SkTypefaceCache::Remove(this); |
| 290 INHERITED::weak_dispose(); | 301 INHERITED::weak_dispose(); |
| 291 } | 302 } |
| 292 | 303 |
| 293 private: | 304 private: |
| 294 /** | 305 /** |
| 295 * Takes ownership of fontMemResource. | 306 * Takes ownership of fontMemResource. |
| 296 */ | 307 */ |
| 297 FontMemResourceTypeface(const SkFontStyle& style, const LOGFONT& lf, HANDLE
fontMemResource) | 308 FontMemResourceTypeface(SkTypeface::Style style, SkFontID fontID, const LOGF
ONT& lf, HANDLE fontMemResource) : |
| 298 : LogFontTypeface(style, lf, true), fFontMemResource(fontMemResource) | 309 LogFontTypeface(style, fontID, lf, true), fFontMemResource(fontMemResour
ce) { |
| 299 { } | 310 } |
| 300 | 311 |
| 301 HANDLE fFontMemResource; | 312 HANDLE fFontMemResource; |
| 302 | 313 |
| 303 typedef LogFontTypeface INHERITED; | 314 typedef LogFontTypeface INHERITED; |
| 304 }; | 315 }; |
| 305 | 316 |
| 306 static const LOGFONT& get_default_font() { | 317 static const LOGFONT& get_default_font() { |
| 307 static LOGFONT gDefaultFont; | 318 static LOGFONT gDefaultFont; |
| 308 return gDefaultFont; | 319 return gDefaultFont; |
| 309 } | 320 } |
| 310 | 321 |
| 311 static bool FindByLogFont(SkTypeface* face, const SkFontStyle& requestedStyle, v
oid* ctx) { | 322 static bool FindByLogFont(SkTypeface* face, SkTypeface::Style requestedStyle, vo
id* ctx) { |
| 312 LogFontTypeface* lface = static_cast<LogFontTypeface*>(face); | 323 LogFontTypeface* lface = static_cast<LogFontTypeface*>(face); |
| 313 const LOGFONT* lf = reinterpret_cast<const LOGFONT*>(ctx); | 324 const LOGFONT* lf = reinterpret_cast<const LOGFONT*>(ctx); |
| 314 | 325 |
| 315 return lface && | 326 return lface && |
| 316 get_style(lface->fLogFont) == requestedStyle && | 327 get_style(lface->fLogFont) == requestedStyle && |
| 317 !memcmp(&lface->fLogFont, lf, sizeof(LOGFONT)); | 328 !memcmp(&lface->fLogFont, lf, sizeof(LOGFONT)); |
| 318 } | 329 } |
| 319 | 330 |
| 320 /** | 331 /** |
| 321 * This guy is public. It first searches the cache, and if a match is not found
, | 332 * This guy is public. It first searches the cache, and if a match is not found
, |
| (...skipping 2117 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2439 */ | 2450 */ |
| 2440 static int CALLBACK enum_family_proc(const LOGFONT* lf, const TEXTMETRIC*, | 2451 static int CALLBACK enum_family_proc(const LOGFONT* lf, const TEXTMETRIC*, |
| 2441 DWORD fontType, LPARAM builderParam) { | 2452 DWORD fontType, LPARAM builderParam) { |
| 2442 if (valid_logfont_for_enum(*lf)) { | 2453 if (valid_logfont_for_enum(*lf)) { |
| 2443 SkTDArray<ENUMLOGFONTEX>* array = (SkTDArray<ENUMLOGFONTEX>*)builderPara
m; | 2454 SkTDArray<ENUMLOGFONTEX>* array = (SkTDArray<ENUMLOGFONTEX>*)builderPara
m; |
| 2444 *array->append() = *(ENUMLOGFONTEX*)lf; | 2455 *array->append() = *(ENUMLOGFONTEX*)lf; |
| 2445 } | 2456 } |
| 2446 return 1; // non-zero means continue | 2457 return 1; // non-zero means continue |
| 2447 } | 2458 } |
| 2448 | 2459 |
| 2460 static SkFontStyle compute_fontstyle(const LOGFONT& lf) { |
| 2461 return SkFontStyle(lf.lfWeight, SkFontStyle::kNormal_Width, |
| 2462 lf.lfItalic ? SkFontStyle::kItalic_Slant |
| 2463 : SkFontStyle::kUpright_Slant); |
| 2464 } |
| 2465 |
| 2449 class SkFontStyleSetGDI : public SkFontStyleSet { | 2466 class SkFontStyleSetGDI : public SkFontStyleSet { |
| 2450 public: | 2467 public: |
| 2451 SkFontStyleSetGDI(const TCHAR familyName[]) { | 2468 SkFontStyleSetGDI(const TCHAR familyName[]) { |
| 2452 LOGFONT lf; | 2469 LOGFONT lf; |
| 2453 sk_bzero(&lf, sizeof(lf)); | 2470 sk_bzero(&lf, sizeof(lf)); |
| 2454 lf.lfCharSet = DEFAULT_CHARSET; | 2471 lf.lfCharSet = DEFAULT_CHARSET; |
| 2455 _tcscpy_s(lf.lfFaceName, familyName); | 2472 _tcscpy_s(lf.lfFaceName, familyName); |
| 2456 | 2473 |
| 2457 HDC hdc = ::CreateCompatibleDC(NULL); | 2474 HDC hdc = ::CreateCompatibleDC(NULL); |
| 2458 ::EnumFontFamiliesEx(hdc, &lf, enum_family_proc, (LPARAM)&fArray, 0); | 2475 ::EnumFontFamiliesEx(hdc, &lf, enum_family_proc, (LPARAM)&fArray, 0); |
| 2459 ::DeleteDC(hdc); | 2476 ::DeleteDC(hdc); |
| 2460 } | 2477 } |
| 2461 | 2478 |
| 2462 virtual int count() SK_OVERRIDE { | 2479 virtual int count() SK_OVERRIDE { |
| 2463 return fArray.count(); | 2480 return fArray.count(); |
| 2464 } | 2481 } |
| 2465 | 2482 |
| 2466 virtual void getStyle(int index, SkFontStyle* fs, SkString* styleName) SK_OV
ERRIDE { | 2483 virtual void getStyle(int index, SkFontStyle* fs, SkString* styleName) SK_OV
ERRIDE { |
| 2467 if (fs) { | 2484 if (fs) { |
| 2468 *fs = get_style(fArray[index].elfLogFont); | 2485 *fs = compute_fontstyle(fArray[index].elfLogFont); |
| 2469 } | 2486 } |
| 2470 if (styleName) { | 2487 if (styleName) { |
| 2471 const ENUMLOGFONTEX& ref = fArray[index]; | 2488 const ENUMLOGFONTEX& ref = fArray[index]; |
| 2472 // For some reason, ENUMLOGFONTEX and LOGFONT disagree on their type
in the | 2489 // For some reason, ENUMLOGFONTEX and LOGFONT disagree on their type
in the |
| 2473 // non-unicode version. | 2490 // non-unicode version. |
| 2474 // ENUMLOGFONTEX uses BYTE | 2491 // ENUMLOGFONTEX uses BYTE |
| 2475 // LOGFONT uses CHAR | 2492 // LOGFONT uses CHAR |
| 2476 // Here we assert they that the style name is logically the same (si
ze) as | 2493 // Here we assert they that the style name is logically the same (si
ze) as |
| 2477 // a TCHAR, so we can use the same converter function. | 2494 // a TCHAR, so we can use the same converter function. |
| 2478 SkASSERT(sizeof(TCHAR) == sizeof(ref.elfStyle[0])); | 2495 SkASSERT(sizeof(TCHAR) == sizeof(ref.elfStyle[0])); |
| (...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2561 } | 2578 } |
| 2562 | 2579 |
| 2563 virtual SkTypeface* onLegacyCreateTypeface(const char familyName[], | 2580 virtual SkTypeface* onLegacyCreateTypeface(const char familyName[], |
| 2564 unsigned styleBits) const SK_OVER
RIDE { | 2581 unsigned styleBits) const SK_OVER
RIDE { |
| 2565 LOGFONT lf; | 2582 LOGFONT lf; |
| 2566 if (NULL == familyName) { | 2583 if (NULL == familyName) { |
| 2567 lf = get_default_font(); | 2584 lf = get_default_font(); |
| 2568 } else { | 2585 } else { |
| 2569 logfont_for_name(familyName, &lf); | 2586 logfont_for_name(familyName, &lf); |
| 2570 } | 2587 } |
| 2571 | 2588 setStyle(&lf, (SkTypeface::Style)styleBits); |
| 2572 SkTypeface::Style style = (SkTypeface::Style)styleBits; | |
| 2573 lf.lfWeight = (style & SkTypeface::kBold) != 0 ? FW_BOLD : FW_NORMAL; | |
| 2574 lf.lfItalic = ((style & SkTypeface::kItalic) != 0); | |
| 2575 return SkCreateTypefaceFromLOGFONT(lf); | 2589 return SkCreateTypefaceFromLOGFONT(lf); |
| 2576 } | 2590 } |
| 2577 | 2591 |
| 2578 private: | 2592 private: |
| 2579 SkTDArray<ENUMLOGFONTEX> fLogFontArray; | 2593 SkTDArray<ENUMLOGFONTEX> fLogFontArray; |
| 2580 }; | 2594 }; |
| 2581 | 2595 |
| 2582 /////////////////////////////////////////////////////////////////////////////// | 2596 /////////////////////////////////////////////////////////////////////////////// |
| 2583 | 2597 |
| 2584 SkFontMgr* SkFontMgr_New_GDI() { | 2598 SkFontMgr* SkFontMgr_New_GDI() { |
| 2585 return SkNEW(SkFontMgrGDI); | 2599 return SkNEW(SkFontMgrGDI); |
| 2586 } | 2600 } |
| OLD | NEW |