move some of the impl in fonthost into typeface virtuals
authormike@reedtribe.org <mike@reedtribe.org@2bbb7eff-a529-9590-31e7-b0007b416f81>
Sun, 3 Mar 2013 01:15:48 +0000 (01:15 +0000)
committermike@reedtribe.org <mike@reedtribe.org@2bbb7eff-a529-9590-31e7-b0007b416f81>
Sun, 3 Mar 2013 01:15:48 +0000 (01:15 +0000)
git-svn-id: http://skia.googlecode.com/svn/trunk@7944 2bbb7eff-a529-9590-31e7-b0007b416f81

include/core/SkTypeface.h
src/core/SkTypeface.cpp
src/ports/SkFontHost_mac_coretext.cpp

index 7fb6b81..79b821f 100644 (file)
 #include "SkAdvancedTypefaceMetrics.h"
 #include "SkWeakRefCnt.h"
 
+class SkDescriptor;
+class SkFontDescriptor;
+class SkScalerContext;
+struct SkScalerContextRec;
 class SkStream;
 class SkAdvancedTypefaceMetrics;
 class SkWStream;
@@ -184,7 +188,7 @@ public:
     int getUnitsPerEm() const;
 
 protected:
-    /** uniqueID must be unique (please!) and non-zero
+    /** uniqueID must be unique and non-zero
     */
     SkTypeface(Style style, SkFontID uniqueID, bool isFixedWidth = false);
     virtual ~SkTypeface();
@@ -192,11 +196,22 @@ protected:
     friend class SkScalerContext;
     static SkTypeface* GetDefaultTypeface();
 
+    virtual int onGetUPEM() const;
+    virtual int onGetTableTags(SkFontTableTag tags[]) const;
+    virtual size_t onGetTableData(SkFontTableTag, size_t offset,
+                                  size_t length, void* data) const;
+    virtual SkScalerContext* onCreateScalerContext(const SkDescriptor*) const;
+    virtual void onFilterRec(SkScalerContextRec*) const;
+    virtual void onGetFontDescriptor(SkFontDescriptor*) const;
+
 private:
     SkFontID    fUniqueID;
     Style       fStyle;
     bool        fIsFixedWidth;
 
+    // just so deprecated fonthost can call protected methods
+    friend class SkFontHost;
+
     typedef SkWeakRefCnt INHERITED;
 };
 
index c30e5a9..e700450 100644 (file)
@@ -134,3 +134,21 @@ int SkTypeface::getUnitsPerEm() const {
 #endif
     return upem;
 }
+
+///////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////
+
+#include "SkFontDescriptor.h"
+
+int SkTypeface::onGetUPEM() const { return 0; }
+int SkTypeface::onGetTableTags(SkFontTableTag tags[]) const { return 0; }
+size_t SkTypeface::onGetTableData(SkFontTableTag, size_t offset,
+                                  size_t length, void* data) const { return 0; }
+SkScalerContext* SkTypeface::onCreateScalerContext(const SkDescriptor*) const {
+    return NULL;
+}
+void SkTypeface::onFilterRec(SkScalerContextRec*) const {}
+void SkTypeface::onGetFontDescriptor(SkFontDescriptor* desc) const {
+    desc->setStyle(this->style());
+}
+
index ceb9a04..74ff3e1 100644 (file)
@@ -407,12 +407,21 @@ public:
 
     SkString fName;
     AutoCFRelease<CTFontRef> fFontRef;
-};
 
-static CTFontRef typeface_to_fontref(const SkTypeface* face) {
-    const SkTypeface_Mac* macface = reinterpret_cast<const SkTypeface_Mac*>(face);
-    return macface->fFontRef;
-}
+protected:
+    friend class SkFontHost;    // to access our protected members for deprecated methods
+
+    virtual int onGetUPEM() const SK_OVERRIDE;
+    virtual int onGetTableTags(SkFontTableTag tags[]) const SK_OVERRIDE;
+    virtual size_t onGetTableData(SkFontTableTag, size_t offset,
+                                  size_t length, void* data) const SK_OVERRIDE;
+    virtual SkScalerContext* onCreateScalerContext(const SkDescriptor*) const SK_OVERRIDE;
+    virtual void onFilterRec(SkScalerContextRec*) const SK_OVERRIDE;
+    virtual void onGetFontDescriptor(SkFontDescriptor*) const SK_OVERRIDE;
+
+private:
+    typedef SkTypeface INHERITED;
+};
 
 static SkTypeface* NewFromFontRef(CTFontRef fontRef, const char name[]) {
     SkASSERT(fontRef);
@@ -1683,21 +1692,9 @@ size_t SkFontHost::GetFileName(SkFontID fontID, char path[], size_t length, int3
 
 #include "SkStream.h"
 
-// we take ownership of the ref
-static const char* get_str(CFStringRef ref, SkString* str) {
-    CFStringToSkString(ref, str);
-    CFSafeRelease(ref);
-    return str->c_str();
-}
-
 void SkFontHost::Serialize(const SkTypeface* face, SkWStream* stream) {
-    CTFontRef ctFont = typeface_to_fontref(face);
-    SkFontDescriptor desc(face->style());
-    SkString tmpStr;
-
-    desc.setFamilyName(get_str(CTFontCopyFamilyName(ctFont), &tmpStr));
-    desc.setFullName(get_str(CTFontCopyFullName(ctFont), &tmpStr));
-    desc.setPostscriptName(get_str(CTFontCopyPostScriptName(ctFont), &tmpStr));
+    SkFontDescriptor desc;
+    face->onGetFontDescriptor(&desc);
 
     desc.serialize(stream);
 
@@ -1719,10 +1716,12 @@ SkTypeface* SkFontHost::Deserialize(SkStream* stream) {
 
 ///////////////////////////////////////////////////////////////////////////////
 
+// DEPRECATED
 SkScalerContext* SkFontHost::CreateScalerContext(const SkDescriptor* desc) {
     return new SkScalerContext_Mac(desc);
 }
 
+// DEPRECATED
 SkFontID SkFontHost::NextLogicalFont(SkFontID currFontID, SkFontID origFontID) {
     SkFontID nextFontID = 0;
     SkTypeface* face = GetDefaultFace();
@@ -1732,14 +1731,105 @@ SkFontID SkFontHost::NextLogicalFont(SkFontID currFontID, SkFontID origFontID) {
     return nextFontID;
 }
 
-void SkFontHost::FilterRec(SkScalerContext::Rec* rec, SkTypeface*) {
+// DEPRECATED
+void SkFontHost::FilterRec(SkScalerContext::Rec* rec, SkTypeface* face) {
+    face->onFilterRec(rec);
+}
+
+// DEPRECATED
+int SkFontHost::CountTables(SkFontID fontID) {
+    SkTypeface* face = SkTypefaceCache::FindByID(fontID);
+    return face ? face->onGetTableTags(NULL) : 0;
+}
+
+// DEPRECATED
+int SkFontHost::GetTableTags(SkFontID fontID, SkFontTableTag tags[]) {
+    SkTypeface* face = SkTypefaceCache::FindByID(fontID);
+    return face ? face->onGetTableTags(tags) : 0;
+}
+
+// DEPRECATED
+size_t SkFontHost::GetTableSize(SkFontID fontID, SkFontTableTag tag) {
+    SkTypeface* face = SkTypefaceCache::FindByID(fontID);
+    return face ? face->onGetTableData(tag, 0, 0, NULL) : 0;
+}
+
+// DEPRECATED
+size_t SkFontHost::GetTableData(SkFontID fontID, SkFontTableTag tag,
+                                size_t offset, size_t length, void* dst) {
+    SkTypeface* face = SkTypefaceCache::FindByID(fontID);
+    return face ? face->onGetTableData(tag, offset, length, dst) : 0;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////
+
+int SkTypeface_Mac::onGetUPEM() const {
+    AutoCFRelease<CGFontRef> cgFont(CTFontCopyGraphicsFont(fFontRef, NULL));
+    return CGFontGetUnitsPerEm(cgFont);
+}
+
+// If, as is the case with web fonts, the CTFont data isn't available,
+// the CGFont data may work. While the CGFont may always provide the
+// right result, leave the CTFont code path to minimize disruption.
+static CFDataRef copyTableFromFont(CTFontRef ctFont, SkFontTableTag tag) {
+    CFDataRef data = CTFontCopyTable(ctFont, (CTFontTableTag) tag,
+                                     kCTFontTableOptionNoOptions);
+    if (NULL == data) {
+        AutoCFRelease<CGFontRef> cgFont(CTFontCopyGraphicsFont(ctFont, NULL));
+        data = CGFontCopyTableForTag(cgFont, tag);
+    }
+    return data;
+}
+
+int SkTypeface_Mac::onGetTableTags(SkFontTableTag tags[]) const {
+    AutoCFRelease<CFArrayRef> cfArray(CTFontCopyAvailableTables(fFontRef,
+                                                kCTFontTableOptionNoOptions));
+    if (NULL == cfArray) {
+        return 0;
+    }
+    int count = CFArrayGetCount(cfArray);
+    if (tags) {
+        for (int i = 0; i < count; ++i) {
+            uintptr_t fontTag = reinterpret_cast<uintptr_t>(CFArrayGetValueAtIndex(cfArray, i));
+            tags[i] = static_cast<SkFontTableTag>(fontTag);
+        }
+    }
+    return count;
+}
+
+size_t SkTypeface_Mac::onGetTableData(SkFontTableTag tag, size_t offset,
+                                      size_t length, void* dstData) const {
+    AutoCFRelease<CFDataRef> srcData(copyTableFromFont(fFontRef, tag));
+    if (NULL == srcData) {
+        return 0;
+    }
+
+    size_t srcSize = CFDataGetLength(srcData);
+    if (offset >= srcSize) {
+        return 0;
+    }
+    if (length > srcSize - offset) {
+        length = srcSize - offset;
+    }
+    if (dstData) {
+        memcpy(dstData, CFDataGetBytePtr(srcData) + offset, length);
+    }
+    return length;
+}
+
+SkScalerContext* SkTypeface_Mac::onCreateScalerContext(const SkDescriptor* desc) const {
+    return new SkScalerContext_Mac(desc);
+}
+
+void SkTypeface_Mac::onFilterRec(SkScalerContextRec* rec) const {
     unsigned flagsWeDontSupport = SkScalerContext::kDevKernText_Flag |
                                   SkScalerContext::kAutohinting_Flag;
-
+    
     rec->fFlags &= ~flagsWeDontSupport;
-
+    
     bool lcdSupport = supports_LCD();
-
+    
     // Only two levels of hinting are supported.
     // kNo_Hinting means avoid CoreGraphics outline dilation.
     // kNormal_Hinting means CoreGraphics outline dilation is allowed.
@@ -1751,18 +1841,18 @@ void SkFontHost::FilterRec(SkScalerContext::Rec* rec, SkTypeface*) {
         hinting = SkPaint::kNormal_Hinting;
     }
     rec->setHinting(hinting);
-
+    
     // FIXME: lcd smoothed un-hinted rasterization unsupported.
     // Tracked by http://code.google.com/p/skia/issues/detail?id=915 .
     // There is no current means to honor a request for unhinted lcd,
     // so arbitrarilly ignore the hinting request and honor lcd.
-
+    
     // Hinting and smoothing should be orthogonal, but currently they are not.
     // CoreGraphics has no API to influence hinting. However, its lcd smoothed
     // output is drawn from auto-dilated outlines (the amount of which is
     // determined by AppleFontSmoothing). Its regular anti-aliased output is
     // drawn from un-dilated outlines.
-
+    
     // The behavior of Skia is as follows:
     // [AA][no-hint]: generate AA using CoreGraphic's AA output.
     // [AA][yes-hint]: use CoreGraphic's LCD output and reduce it to a single
@@ -1770,7 +1860,7 @@ void SkFontHost::FilterRec(SkScalerContext::Rec* rec, SkTypeface*) {
     // [LCD][no-hint]: curently unable to honor, and must pick which to respect.
     // Currenly side with LCD, effectively ignoring the hinting setting.
     // [LCD][yes-hint]: generate LCD using CoreGraphic's LCD output.
-
+    
     if (isLCDFormat(rec->fMaskFormat)) {
         if (lcdSupport) {
             //CoreGraphics creates 555 masks for smoothed text anyway.
@@ -1780,7 +1870,7 @@ void SkFontHost::FilterRec(SkScalerContext::Rec* rec, SkTypeface*) {
             rec->fMaskFormat = SkMask::kA8_Format;
         }
     }
-
+    
     // Unhinted A8 masks (those not derived from LCD masks) must respect SK_GAMMA_APPLY_TO_A8.
     // All other masks can use regular gamma.
     if (SkMask::kA8_Format == rec->fMaskFormat && SkPaint::kNo_Hinting == hinting) {
@@ -1793,76 +1883,19 @@ void SkFontHost::FilterRec(SkScalerContext::Rec* rec, SkTypeface*) {
     }
 }
 
-///////////////////////////////////////////////////////////////////////////
-
-int SkFontHost::CountTables(SkFontID fontID) {
-    CTFontRef ctFont = GetFontRefFromFontID(fontID);
-    AutoCFRelease<CFArrayRef> cfArray(CTFontCopyAvailableTables(ctFont,
-                                                                kCTFontTableOptionNoOptions));
-    if (NULL == cfArray) {
-        return 0;
-    }
-    return CFArrayGetCount(cfArray);
-}
-
-int SkFontHost::GetTableTags(SkFontID fontID, SkFontTableTag tags[]) {
-    CTFontRef ctFont = GetFontRefFromFontID(fontID);
-    AutoCFRelease<CFArrayRef> cfArray(CTFontCopyAvailableTables(ctFont,
-                                                                kCTFontTableOptionNoOptions));
-    if (NULL == cfArray) {
-        return 0;
-    }
-
-    int count = CFArrayGetCount(cfArray);
-    if (tags) {
-        for (int i = 0; i < count; ++i) {
-            uintptr_t fontTag = reinterpret_cast<uintptr_t>(CFArrayGetValueAtIndex(cfArray, i));
-            tags[i] = static_cast<SkFontTableTag>(fontTag);
-        }
-    }
-    return count;
-}
-
-// If, as is the case with web fonts, the CTFont data isn't available,
-// the CGFont data may work. While the CGFont may always provide the
-// right result, leave the CTFont code path to minimize disruption.
-static CFDataRef copyTableFromFont(CTFontRef ctFont, SkFontTableTag tag) {
-    CFDataRef data = CTFontCopyTable(ctFont, (CTFontTableTag) tag, kCTFontTableOptionNoOptions);
-    if (NULL == data) {
-        AutoCFRelease<CGFontRef> cgFont(CTFontCopyGraphicsFont(ctFont, NULL));
-        data = CGFontCopyTableForTag(cgFont, tag);
-    }
-    return data;
+// we take ownership of the ref
+static const char* get_str(CFStringRef ref, SkString* str) {
+    CFStringToSkString(ref, str);
+    CFSafeRelease(ref);
+    return str->c_str();
 }
 
-size_t SkFontHost::GetTableSize(SkFontID fontID, SkFontTableTag tag) {
-    CTFontRef ctFont = GetFontRefFromFontID(fontID);
-    AutoCFRelease<CFDataRef> srcData(copyTableFromFont(ctFont, tag));
-    if (NULL == srcData) {
-        return 0;
-    }
-    return CFDataGetLength(srcData);
+void SkTypeface_Mac::onGetFontDescriptor(SkFontDescriptor* desc) const {
+    this->INHERITED::onGetFontDescriptor(desc);
+    SkString tmpStr;
+    
+    desc->setFamilyName(get_str(CTFontCopyFamilyName(fFontRef), &tmpStr));
+    desc->setFullName(get_str(CTFontCopyFullName(fFontRef), &tmpStr));
+    desc->setPostscriptName(get_str(CTFontCopyPostScriptName(fFontRef), &tmpStr));
 }
 
-size_t SkFontHost::GetTableData(SkFontID fontID, SkFontTableTag tag,
-                                size_t offset, size_t length, void* dst) {
-    CTFontRef ctFont = GetFontRefFromFontID(fontID);
-    AutoCFRelease<CFDataRef> srcData(copyTableFromFont(ctFont, tag));
-    if (NULL == srcData) {
-        return 0;
-    }
-
-    size_t srcSize = CFDataGetLength(srcData);
-    if (offset >= srcSize) {
-        return 0;
-    }
-
-    if ((offset + length) > srcSize) {
-        length = srcSize - offset;
-    }
-
-    if (dst) {
-        memcpy(dst, CFDataGetBytePtr(srcData) + offset, length);
-    }
-    return length;
-}