OLD | NEW |
---|---|
1 /* | 1 /* |
2 * Copyright 2006 The Android Open Source Project | 2 * Copyright 2006 The Android Open Source Project |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #include "SkTypes.h" // Keep this before any #ifdef ... | 8 #include "SkTypes.h" // Keep this before any #ifdef ... |
9 #if defined(SK_BUILD_FOR_MAC) || defined(SK_BUILD_FOR_IOS) | 9 #if defined(SK_BUILD_FOR_MAC) || defined(SK_BUILD_FOR_IOS) |
10 | 10 |
(...skipping 540 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
551 if (!ctFontDesc) { | 551 if (!ctFontDesc) { |
552 return nullptr; | 552 return nullptr; |
553 } | 553 } |
554 | 554 |
555 AutoCFRelease<CTFontRef> ctFont(CTFontCreateWithFontDescriptor(ctFontDesc, 0 , nullptr)); | 555 AutoCFRelease<CTFontRef> ctFont(CTFontCreateWithFontDescriptor(ctFontDesc, 0 , nullptr)); |
556 if (!ctFont) { | 556 if (!ctFont) { |
557 return nullptr; | 557 return nullptr; |
558 } | 558 } |
559 | 559 |
560 SkTypeface* face = SkTypefaceCache::FindByProcAndRef(find_by_CTFontRef, (voi d*)ctFont.get()); | 560 SkTypeface* face = SkTypefaceCache::FindByProcAndRef(find_by_CTFontRef, (voi d*)ctFont.get()); |
561 if (!face) { | 561 if (face) { |
562 face = NewFromFontRef(ctFont.release(), nullptr, nullptr, false); | 562 return face; |
563 SkTypefaceCache::Add(face, face->fontStyle()); | |
564 } | 563 } |
564 face = NewFromFontRef(ctFont.release(), nullptr, nullptr, false); | |
565 SkTypefaceCache::Add(face, face->fontStyle()); | |
565 return face; | 566 return face; |
566 } | 567 } |
567 | 568 |
568 SK_DECLARE_STATIC_MUTEX(gGetDefaultFaceMutex); | 569 SK_DECLARE_STATIC_MUTEX(gGetDefaultFaceMutex); |
569 static SkTypeface* GetDefaultFace() { | 570 static SkTypeface* GetDefaultFace() { |
570 SkAutoMutexAcquire ma(gGetDefaultFaceMutex); | 571 SkAutoMutexAcquire ma(gGetDefaultFaceMutex); |
571 | 572 |
572 static SkTypeface* gDefaultFace; | 573 static SkTypeface* gDefaultFace; |
573 | 574 |
574 if (nullptr == gDefaultFace) { | 575 if (nullptr == gDefaultFace) { |
575 gDefaultFace = NewFromName(FONT_DEFAULT_NAME, SkFontStyle()); | 576 gDefaultFace = NewFromName(FONT_DEFAULT_NAME, SkFontStyle()); |
576 SkTypefaceCache::Add(gDefaultFace, SkFontStyle()); | |
577 } | 577 } |
578 return gDefaultFace; | 578 return gDefaultFace; |
579 } | 579 } |
580 | 580 |
581 /////////////////////////////////////////////////////////////////////////////// | 581 /////////////////////////////////////////////////////////////////////////////// |
582 | 582 |
583 extern CTFontRef SkTypeface_GetCTFontRef(const SkTypeface* face); | 583 extern CTFontRef SkTypeface_GetCTFontRef(const SkTypeface* face); |
584 CTFontRef SkTypeface_GetCTFontRef(const SkTypeface* face) { | 584 CTFontRef SkTypeface_GetCTFontRef(const SkTypeface* face) { |
585 const SkTypeface_Mac* macface = (const SkTypeface_Mac*)face; | 585 const SkTypeface_Mac* macface = (const SkTypeface_Mac*)face; |
586 return macface ? macface->fFontRef.get() : nullptr; | 586 return macface ? macface->fFontRef.get() : nullptr; |
587 } | 587 } |
588 | 588 |
589 /* This function is visible on the outside. It first searches the cache, and if | 589 /* This function is visible on the outside. It first searches the cache, and if |
590 * not found, returns a new entry (after adding it to the cache). | 590 * not found, returns a new entry (after adding it to the cache). |
591 */ | 591 */ |
592 SkTypeface* SkCreateTypefaceFromCTFont(CTFontRef fontRef, CFTypeRef resourceRef) { | 592 SkTypeface* SkCreateTypefaceFromCTFont(CTFontRef fontRef, CFTypeRef resourceRef) { |
593 SkTypeface* face = SkTypefaceCache::FindByProcAndRef(find_by_CTFontRef, (voi d*)fontRef); | 593 SkTypeface* face = SkTypefaceCache::FindByProcAndRef(find_by_CTFontRef, (voi d*)fontRef); |
594 if (!face) { | 594 if (face) { |
595 CFRetain(fontRef); | 595 return face; |
596 if (resourceRef) { | |
597 CFRetain(resourceRef); | |
598 } | |
599 face = NewFromFontRef(fontRef, resourceRef, nullptr, false); | |
600 SkTypefaceCache::Add(face, face->fontStyle()); | |
601 } | 596 } |
597 CFRetain(fontRef); | |
598 if (resourceRef) { | |
599 CFRetain(resourceRef); | |
600 } | |
601 face = NewFromFontRef(fontRef, resourceRef, nullptr, false); | |
602 SkTypefaceCache::Add(face, face->fontStyle()); | |
602 return face; | 603 return face; |
603 } | 604 } |
604 | 605 |
605 struct NameStyle { | 606 struct NameStyle { |
606 const char* fName; | 607 const char* fName; |
607 SkFontStyle fStyle; | 608 SkFontStyle fStyle; |
608 }; | 609 }; |
609 | 610 |
610 static bool find_by_NameStyle(SkTypeface* cachedFace, const SkFontStyle& cachedS tyle, void* ctx) { | 611 static bool find_by_NameStyle(SkTypeface* cachedFace, const SkFontStyle& cachedS tyle, void* ctx) { |
611 const SkTypeface_Mac* cachedMacFace = static_cast<SkTypeface_Mac*>(cachedFac e); | 612 const SkTypeface_Mac* cachedMacFace = static_cast<SkTypeface_Mac*>(cachedFac e); |
(...skipping 1561 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2173 } | 2174 } |
2174 | 2175 |
2175 // We normalize each axis (weight, width, italic) to be base-900 | 2176 // We normalize each axis (weight, width, italic) to be base-900 |
2176 static int compute_metric(const SkFontStyle& a, const SkFontStyle& b) { | 2177 static int compute_metric(const SkFontStyle& a, const SkFontStyle& b) { |
2177 return sqr(a.weight() - b.weight()) + | 2178 return sqr(a.weight() - b.weight()) + |
2178 sqr((a.width() - b.width()) * 100) + | 2179 sqr((a.width() - b.width()) * 100) + |
2179 sqr((a.isItalic() != b.isItalic()) * 900); | 2180 sqr((a.isItalic() != b.isItalic()) * 900); |
2180 } | 2181 } |
2181 | 2182 |
2182 static SkTypeface* createFromDesc(CFStringRef cfFamilyName, CTFontDescriptorRef desc) { | 2183 static SkTypeface* createFromDesc(CFStringRef cfFamilyName, CTFontDescriptorRef desc) { |
2183 NameStyle cacheRequest; | |
2184 SkString skFamilyName; | 2184 SkString skFamilyName; |
2185 CFStringToSkString(cfFamilyName, &skFamilyName); | 2185 CFStringToSkString(cfFamilyName, &skFamilyName); |
2186 cacheRequest.fName = skFamilyName.c_str(); | |
2187 cacheRequest.fStyle = fontstyle_from_descriptor(desc); | |
2188 | |
2189 SkTypeface* face = SkTypefaceCache::FindByProcAndRef(find_by_NameStyle, &cac heRequest); | |
2190 if (face) { | |
2191 return face; | |
2192 } | |
2193 | 2186 |
2194 AutoCFRelease<CTFontRef> ctFont(CTFontCreateWithFontDescriptor(desc, 0, null ptr)); | 2187 AutoCFRelease<CTFontRef> ctFont(CTFontCreateWithFontDescriptor(desc, 0, null ptr)); |
2195 if (!ctFont) { | 2188 if (!ctFont) { |
2196 return nullptr; | 2189 return nullptr; |
2197 } | 2190 } |
2198 | 2191 |
2199 bool isFixedPitch; | 2192 SkTypeface* face = SkTypefaceCache::FindByProcAndRef(find_by_CTFontRef, (voi d*)ctFont.get()); |
2200 (void)computeStyleBits(ctFont, &isFixedPitch); | 2193 if (face) { |
2194 return face; | |
2195 } | |
2201 | 2196 |
2202 face = new SkTypeface_Mac(ctFont.release(), nullptr, cacheRequest.fStyle, is FixedPitch, | 2197 face = NewFromFontRef(ctFont.release(), nullptr, skFamilyName.c_str(), false ); |
2203 skFamilyName.c_str(), false); | |
2204 SkTypefaceCache::Add(face, face->fontStyle()); | 2198 SkTypefaceCache::Add(face, face->fontStyle()); |
2205 return face; | 2199 return face; |
2206 } | 2200 } |
2207 | 2201 |
2208 class SkFontStyleSet_Mac : public SkFontStyleSet { | 2202 class SkFontStyleSet_Mac : public SkFontStyleSet { |
2209 public: | 2203 public: |
2210 SkFontStyleSet_Mac(CFStringRef familyName, CTFontDescriptorRef desc) | 2204 SkFontStyleSet_Mac(CFStringRef familyName, CTFontDescriptorRef desc) |
2211 : fArray(CTFontDescriptorCreateMatchingFontDescriptors(desc, nullptr)) | 2205 : fArray(CTFontDescriptorCreateMatchingFontDescriptors(desc, nullptr)) |
2212 , fFamilyName(familyName) | 2206 , fFamilyName(familyName) |
2213 , fCount(0) { | 2207 , fCount(0) { |
(...skipping 390 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2604 SkFontStyle style = SkFontStyle((SkTypeface::Style)styleBits); | 2598 SkFontStyle style = SkFontStyle((SkTypeface::Style)styleBits); |
2605 if (familyName) { | 2599 if (familyName) { |
2606 familyName = map_css_names(familyName); | 2600 familyName = map_css_names(familyName); |
2607 } | 2601 } |
2608 | 2602 |
2609 if (!familyName || !*familyName) { | 2603 if (!familyName || !*familyName) { |
2610 familyName = FONT_DEFAULT_NAME; | 2604 familyName = FONT_DEFAULT_NAME; |
2611 } | 2605 } |
2612 | 2606 |
2613 NameStyle cacheRequest = { familyName, style }; | 2607 NameStyle cacheRequest = { familyName, style }; |
2614 SkTypeface* face = SkTypefaceCache::FindByProcAndRef(find_by_NameStyle, &cacheRequest); | 2608 SkTypeface* face = SkTypefaceCache::FindByProcAndRef(find_by_NameStyle, &cacheRequest); |
bungeman-skia
2016/04/05 22:03:26
Leaving this find_by_NameStyle here is trouble, wh
| |
2609 if (face) { | |
2610 return face; | |
2611 } | |
2615 | 2612 |
2616 if (nullptr == face) { | 2613 face = NewFromName(familyName, style); |
2617 face = NewFromName(familyName, style); | 2614 if (face) { |
2618 if (face) { | 2615 return face; |
2619 SkTypefaceCache::Add(face, style); | |
2620 } else { | |
2621 face = GetDefaultFace(); | |
2622 face->ref(); | |
2623 } | |
2624 } | 2616 } |
2625 return face; | 2617 |
2618 return SkSafeRef(GetDefaultFace()); | |
2626 } | 2619 } |
2627 }; | 2620 }; |
2628 | 2621 |
2629 /////////////////////////////////////////////////////////////////////////////// | 2622 /////////////////////////////////////////////////////////////////////////////// |
2630 | 2623 |
2631 SkFontMgr* SkFontMgr::Factory() { return new SkFontMgr_Mac; } | 2624 SkFontMgr* SkFontMgr::Factory() { return new SkFontMgr_Mac; } |
2632 | 2625 |
2633 #endif//defined(SK_BUILD_FOR_MAC) || defined(SK_BUILD_FOR_IOS) | 2626 #endif//defined(SK_BUILD_FOR_MAC) || defined(SK_BUILD_FOR_IOS) |
OLD | NEW |