• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2006-2012 The Android Open Source Project
3  * Copyright 2012 Mozilla Foundation
4  *
5  * Use of this source code is governed by a BSD-style license that can be
6  * found in the LICENSE file.
7  */
8 
9 #ifndef SKFONTHOST_FREETYPE_COMMON_H_
10 #define SKFONTHOST_FREETYPE_COMMON_H_
11 
12 #include "include/core/SkSpan.h"
13 #include "include/core/SkTypeface.h"
14 #include "include/core/SkTypes.h"
15 #include "include/private/base/SkMutex.h"
16 #include "src/core/SkGlyph.h"
17 #include "src/core/SkScalerContext.h"
18 #include "src/core/SkSharedMutex.h"
19 #include "src/utils/SkCharToGlyphCache.h"
20 
21 struct SkAdvancedTypefaceMetrics;
22 class SkFontDescriptor;
23 class SkFontData;
24 
25 // These are forward declared to avoid pimpl but also hide the FreeType implementation.
26 typedef struct FT_LibraryRec_* FT_Library;
27 typedef struct FT_FaceRec_* FT_Face;
28 typedef struct FT_StreamRec_* FT_Stream;
29 typedef signed long FT_Pos;
30 typedef struct FT_BBox_ FT_BBox;
31 
32 
33 #ifdef SK_DEBUG
34 const char* SkTraceFtrGetError(int);
35 #define SK_TRACEFTR(ERR, MSG, ...) \
36     SkDebugf("%s:%d:1: error: 0x%x '%s' " MSG "\n", __FILE__, __LINE__, ERR, \
37             SkTraceFtrGetError((int)(ERR)), __VA_ARGS__)
38 #else
39 #define SK_TRACEFTR(ERR, ...) do { sk_ignore_unused_variable(ERR); } while (false)
40 #endif
41 
42 
43 class SkScalerContext_FreeType_Base : public SkScalerContext {
44 protected:
45     // See http://freetype.sourceforge.net/freetype2/docs/reference/ft2-bitmap_handling.html#FT_Bitmap_Embolden
46     // This value was chosen by eyeballing the result in Firefox and trying to match it.
47     static const FT_Pos kBitmapEmboldenStrength = 1 << 6;
48 
SkScalerContext_FreeType_Base(sk_sp<SkTypeface> typeface,const SkScalerContextEffects & effects,const SkDescriptor * desc)49     SkScalerContext_FreeType_Base(sk_sp<SkTypeface> typeface, const SkScalerContextEffects& effects,
50                                   const SkDescriptor *desc)
51         : INHERITED(std::move(typeface), effects, desc)
52     {}
53 
54     bool drawCOLRv0Glyph(FT_Face, const SkGlyph&, uint32_t loadGlyphFlags,
55                          SkSpan<SkColor> palette, SkCanvas*);
56     bool drawCOLRv1Glyph(FT_Face, const SkGlyph&, uint32_t loadGlyphFlags,
57                          SkSpan<SkColor> palette, SkCanvas*);
58     bool drawSVGGlyph(FT_Face, const SkGlyph&, uint32_t loadGlyphFlags,
59                       SkSpan<SkColor> palette, SkCanvas*);
60     void generateGlyphImage(FT_Face, const SkGlyph&, const SkMatrix& bitmapTransform);
61     bool generateGlyphPath(FT_Face, SkPath*);
62     bool generateFacePath(FT_Face, SkGlyphID, uint32_t loadGlyphFlags, SkPath*);
63 
64     /** Computes a bounding box for a COLRv1 glyph.
65      *
66      *  This method may change the configured size and transforms on FT_Face. Make sure to
67      *  configure size, matrix and load glyphs as needed after using this function to restore the
68      *  state of FT_Face.
69      */
70     static bool computeColrV1GlyphBoundingBox(FT_Face, SkGlyphID, SkRect* bounds);
71 
72     struct ScalerContextBits {
73         static const constexpr uint32_t COLRv0 = 1;
74         static const constexpr uint32_t COLRv1 = 2;
75         static const constexpr uint32_t SVG    = 3;
76     };
77 private:
78     using INHERITED = SkScalerContext;
79 };
80 
81 class SkTypeface_FreeType : public SkTypeface {
82 public:
83     /** For SkFontMgrs to make use of our ability to extract
84      *  name and style from a stream, using FreeType's API.
85      */
86     class Scanner : ::SkNoncopyable {
87     public:
88         Scanner();
89         ~Scanner();
90         struct AxisDefinition {
91             SkFourByteTag fTag;
92             SkFixed fMinimum;
93             SkFixed fDefault;
94             SkFixed fMaximum;
95         };
96         using AxisDefinitions = SkSTArray<4, AxisDefinition, true>;
97         bool recognizedFont(SkStreamAsset* stream, int* numFonts) const;
98         bool scanFont(SkStreamAsset* stream, int ttcIndex,
99                       SkString* name, SkFontStyle* style, bool* isFixedPitch,
100                       AxisDefinitions* axes) const;
101         static void computeAxisValues(
102             AxisDefinitions axisDefinitions,
103             const SkFontArguments::VariationPosition position,
104             SkFixed* axisValues,
105             const SkString& name,
106             const SkFontArguments::VariationPosition::Coordinate* currentPosition = nullptr);
107         static bool GetAxes(FT_Face face, AxisDefinitions* axes);
108     private:
109         FT_Face openFace(SkStreamAsset* stream, int ttcIndex, FT_Stream ftStream) const;
110         FT_Library fLibrary;
111         mutable SkMutex fLibraryMutex;
112     };
113 
114     /** Fetch units/EM from "head" table if needed (ie for bitmap fonts) */
115     static int GetUnitsPerEm(FT_Face face);
116 
117     /** Return the font data, or nullptr on failure. */
118     std::unique_ptr<SkFontData> makeFontData() const;
119     class FaceRec;
120     FaceRec* getFaceRec() const;
121 
122     static constexpr SkTypeface::FactoryId FactoryId = SkSetFourByteTag('f','r','e','e');
123     static sk_sp<SkTypeface> MakeFromStream(std::unique_ptr<SkStreamAsset>, const SkFontArguments&);
124 
125 protected:
126     SkTypeface_FreeType(const SkFontStyle& style, bool isFixedPitch);
127     ~SkTypeface_FreeType() override;
128 
129     std::unique_ptr<SkFontData> cloneFontData(const SkFontArguments&) const;
130     std::unique_ptr<SkScalerContext> onCreateScalerContext(const SkScalerContextEffects&,
131                                                            const SkDescriptor*) const override;
132     void onFilterRec(SkScalerContextRec*) const override;
133     void getGlyphToUnicodeMap(SkUnichar*) const override;
134     std::unique_ptr<SkAdvancedTypefaceMetrics> onGetAdvancedMetrics() const override;
135     void getPostScriptGlyphNames(SkString* dstArray) const override;
136     bool onGetPostScriptName(SkString*) const override;
137     int onGetUPEM() const override;
138     bool onGetKerningPairAdjustments(const uint16_t glyphs[], int count,
139                                      int32_t adjustments[]) const override;
140     void onCharsToGlyphs(const SkUnichar uni[], int count, SkGlyphID glyphs[]) const override;
141     int onCountGlyphs() const override;
142 
143     LocalizedStrings* onCreateFamilyNameIterator() const override;
144 
145     bool onGlyphMaskNeedsCurrentColor() const override;
146     int onGetVariationDesignPosition(SkFontArguments::VariationPosition::Coordinate coordinates[],
147                                      int coordinateCount) const override;
148     int onGetVariationDesignParameters(SkFontParameters::Variation::Axis parameters[],
149                                        int parameterCount) const override;
150     int onGetTableTags(SkFontTableTag tags[]) const override;
151     size_t onGetTableData(SkFontTableTag, size_t offset,
152                           size_t length, void* data) const override;
153     sk_sp<SkData> onCopyTableData(SkFontTableTag) const override;
154 
155     virtual std::unique_ptr<SkFontData> onMakeFontData() const = 0;
156     /** Utility to fill out the SkFontDescriptor palette information from the SkFontData. */
157     static void FontDataPaletteToDescriptorPalette(const SkFontData&, SkFontDescriptor*);
158 
159 private:
160     mutable SkOnce fFTFaceOnce;
161     mutable std::unique_ptr<FaceRec> fFaceRec;
162 
163     mutable SkSharedMutex fC2GCacheMutex;
164     mutable SkCharToGlyphCache fC2GCache;
165 
166     mutable SkOnce fGlyphMasksMayNeedCurrentColorOnce;
167     mutable bool fGlyphMasksMayNeedCurrentColor;
168 
169     using INHERITED = SkTypeface;
170 };
171 
172 class SkTypeface_FreeTypeStream : public SkTypeface_FreeType {
173 public:
174     SkTypeface_FreeTypeStream(std::unique_ptr<SkFontData> fontData, const SkString familyName,
175                               const SkFontStyle& style, bool isFixedPitch);
176     ~SkTypeface_FreeTypeStream() override;
177 
178 protected:
179     void onGetFamilyName(SkString* familyName) const override;
180     void onGetFontDescriptor(SkFontDescriptor*, bool* serialize) const override;
181     std::unique_ptr<SkStreamAsset> onOpenStream(int* ttcIndex) const override;
182     std::unique_ptr<SkFontData> onMakeFontData() const override;
183     sk_sp<SkTypeface> onMakeClone(const SkFontArguments&) const override;
184 
185 private:
186     const SkString fFamilyName;
187     const std::unique_ptr<const SkFontData> fData;
188 };
189 
190 #endif // SKFONTHOST_FREETYPE_COMMON_H_
191