Flutter Engine
The Flutter Engine
Loading...
Searching...
No Matches
SkStrikeSpec.cpp
Go to the documentation of this file.
1/*
2 * Copyright 2019 The Android Open Source Project
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
9
10#include "include/core/SkFont.h"
16#include "src/base/SkTLazy.h"
17#include "src/core/SkFontPriv.h"
18#include "src/core/SkGlyph.h"
19#include "src/core/SkStrike.h"
22
23#include <utility>
24
26 : fAutoDescriptor{descriptor}
27 , fTypeface{std::move(typeface)} {}
28
32
34 const SkSurfaceProps& surfaceProps,
35 SkScalerContextFlags scalerContextFlags,
36 const SkMatrix& deviceMatrix) {
37
38 return SkStrikeSpec(font, paint, surfaceProps, scalerContextFlags, deviceMatrix);
39}
40
42 const SkPaint& paint,
43 const SkSurfaceProps& surfaceProps,
44 SkScalerContextFlags scalerContextFlags,
45 const SkMatrix& deviceMatrix) {
46 SkFont sourceFont{font};
47 sourceFont.setSubpixel(false);
48 return SkStrikeSpec(sourceFont, paint, surfaceProps, scalerContextFlags, deviceMatrix);
49}
50
51std::tuple<SkStrikeSpec, SkScalar> SkStrikeSpec::MakePath(
52 const SkFont& font, const SkPaint& paint,
53 const SkSurfaceProps& surfaceProps,
54 SkScalerContextFlags scalerContextFlags) {
55
56 // setup our std runPaint, in hopes of getting hits in the cache
57 SkPaint pathPaint{paint};
58 SkFont pathFont{font};
59
60 // The sub-pixel position will always happen when transforming to the screen.
61 pathFont.setSubpixel(false);
62
63 // The factor to get from the size stored in the strike to the size needed for
64 // the source.
65 SkScalar strikeToSourceScale = pathFont.setupForAsPaths(&pathPaint);
66
67 return {SkStrikeSpec(pathFont, pathPaint, surfaceProps, scalerContextFlags, SkMatrix::I()),
68 strikeToSourceScale};
69}
70
71std::tuple<SkStrikeSpec, SkScalar> SkStrikeSpec::MakeCanonicalized(
72 const SkFont& font, const SkPaint* paint) {
73 SkPaint canonicalizedPaint;
74 if (paint != nullptr) {
75 canonicalizedPaint = *paint;
76 }
77
78 const SkFont* canonicalizedFont = &font;
79 SkTLazy<SkFont> pathFont;
80 SkScalar strikeToSourceScale = 1;
81 if (ShouldDrawAsPath(canonicalizedPaint, font, SkMatrix::I())) {
82 canonicalizedFont = pathFont.set(font);
83 strikeToSourceScale = pathFont->setupForAsPaths(nullptr);
84 canonicalizedPaint.reset();
85 }
86
87 return {SkStrikeSpec(*canonicalizedFont, canonicalizedPaint, SkSurfaceProps(),
89 strikeToSourceScale};
90}
91
93 SkPaint setupPaint;
94 if (paint != nullptr) {
95 setupPaint = *paint;
96 }
97
98 return SkStrikeSpec(font, setupPaint, SkSurfaceProps(),
100}
101
103 const SkPaint& paint, const SkFont& font, const SkMatrix& viewMatrix) {
104
105 // hairline glyphs are fast enough, so we don't need to cache them
106 if (SkPaint::kStroke_Style == paint.getStyle() && 0 == paint.getStrokeWidth()) {
107 return true;
108 }
109
110 // we don't cache perspective
111 if (viewMatrix.hasPerspective()) {
112 return true;
113 }
114
115 SkMatrix textMatrix = SkFontPriv::MakeTextMatrix(font);
116 textMatrix.postConcat(viewMatrix);
117
118 // we have a self-imposed maximum, just to limit memory-usage
119 constexpr SkScalar memoryLimit = 256;
120 constexpr SkScalar maxSizeSquared = memoryLimit * memoryLimit;
121
122 auto distance = [&textMatrix](int XIndex, int YIndex) {
123 return textMatrix[XIndex] * textMatrix[XIndex] + textMatrix[YIndex] * textMatrix[YIndex];
124 };
125
126 return distance(SkMatrix::kMScaleX, SkMatrix::kMSkewY ) > maxSizeSquared
127 || distance(SkMatrix::kMSkewX, SkMatrix::kMScaleY) > maxSizeSquared;
128}
129
131 return fAutoDescriptor.getDesc()->dumpRec();
132}
133
135 SkFont font;
136 font.setHinting(SkFontHinting::kNone);
137 font.setEdging(SkFont::Edging::kAlias);
138 font.setTypeface(sk_ref_sp(&typeface));
139 int unitsPerEm = typeface.getUnitsPerEm();
140 if (unitsPerEm <= 0) {
141 unitsPerEm = 1024;
142 }
143 if (size) {
144 *size = unitsPerEm;
145 }
146 font.setSize((SkScalar)unitsPerEm);
147
148 return SkStrikeSpec(font,
149 SkPaint(),
152 SkMatrix::I());
153}
154
156 const SkSurfaceProps& surfaceProps,
157 SkScalerContextFlags scalerContextFlags,
158 const SkMatrix& deviceMatrix) {
160
162 font, paint, surfaceProps, scalerContextFlags, deviceMatrix,
163 &fAutoDescriptor, &effects);
164
165 fMaskFilter = sk_ref_sp(effects.fMaskFilter);
166 fPathEffect = sk_ref_sp(effects.fPathEffect);
167 fTypeface = font.refTypeface();
168}
169
172 return cache->findOrCreateScopedStrike(*this);
173}
174
176 SkScalerContextEffects effects{fPathEffect.get(), fMaskFilter.get()};
178}
179
181 SkScalerContextEffects effects{fPathEffect.get(), fMaskFilter.get()};
182 return cache->findOrCreateStrike(*this);
183}
184
186 : fStrike{spec.findOrCreateStrike()} { }
187
189
191 fGlyphs.reset(glyphIDs.size());
192 return fStrike->metrics(glyphIDs, fGlyphs.get());
193}
194
196 return this->glyphs(SkSpan<const SkGlyphID>{&glyphID, 1})[0];
197}
198
200 : fStrike{spec.findOrCreateStrike()} { }
201
204
206
208 fGlyphs.reset(glyphIDs.size());
209 return fStrike->preparePaths(glyphIDs, fGlyphs.get());
210}
211
213 return this->glyphs(SkSpan<const SkGlyphID>{&glyphID, 1})[0];
214}
215
217 const SkScalar* bounds, SkScalar scale, SkScalar xPos,
218 const SkGlyph* glyph, SkScalar* array, int* count) {
219 // TODO(herb): remove this abominable const_cast. Do the intercepts really need to be on the
220 // glyph?
221 fStrike->findIntercepts(bounds, scale, xPos, const_cast<SkGlyph*>(glyph), array, count);
222}
223
225 : fStrike{spec.findOrCreateStrike()} { }
226
229
231
233 fGlyphs.reset(glyphIDs.size());
234 return fStrike->prepareDrawables(glyphIDs, fGlyphs.get());
235}
236
238 return this->glyphs(SkSpan<const SkGlyphID>{&glyphID, 1})[0];
239}
240
242 : fStrike{spec.findOrCreateStrike()} { }
243
246
248
250 fGlyphs.reset(glyphIDs.size());
251 return fStrike->prepareImages(glyphIDs, fGlyphs.get());
252}
253
255 return this->glyphs(SkSpan<const SkPackedGlyphID>{&packedID, 1})[0];
256}
257
259 return fStrike->getDescriptor();
260}
uint16_t glyphs[5]
int count
@ kNone
glyph outlines unchanged
sk_sp< T > sk_ref_sp(T *obj)
Definition SkRefCnt.h:381
SkScalerContextFlags
uint16_t SkGlyphID
Definition SkTypes.h:179
SkDescriptor * getDesc() const
SkSpan< const SkGlyph * > glyphs(SkSpan< const SkGlyphID > glyphIDs)
SkBulkGlyphMetricsAndDrawables(const SkStrikeSpec &spec)
const SkGlyph * glyph(SkGlyphID glyphID)
const SkDescriptor & descriptor() const
SkSpan< const SkGlyph * > glyphs(SkSpan< const SkPackedGlyphID > packedIDs)
SkBulkGlyphMetricsAndImages(const SkStrikeSpec &spec)
const SkGlyph * glyph(SkPackedGlyphID packedID)
SkBulkGlyphMetricsAndPaths(const SkStrikeSpec &spec)
SkSpan< const SkGlyph * > glyphs(SkSpan< const SkGlyphID > glyphIDs)
void findIntercepts(const SkScalar bounds[2], SkScalar scale, SkScalar xPos, const SkGlyph *glyph, SkScalar *array, int *count)
const SkGlyph * glyph(SkGlyphID glyphID)
SkBulkGlyphMetrics(const SkStrikeSpec &spec)
SkSpan< const SkGlyph * > glyphs(SkSpan< const SkGlyphID > glyphIDs)
const SkGlyph * glyph(SkGlyphID glyphID)
SkString dumpRec() const
static SkMatrix MakeTextMatrix(SkScalar size, SkScalar scaleX, SkScalar skewX)
Definition SkFontPriv.h:41
@ kAlias
no transparent pixels on glyph edges
static constexpr int kMScaleX
horizontal scale factor
Definition SkMatrix.h:353
SkMatrix & postConcat(const SkMatrix &other)
Definition SkMatrix.cpp:683
static const SkMatrix & I()
bool hasPerspective() const
Definition SkMatrix.h:312
static constexpr int kMSkewY
vertical skew factor
Definition SkMatrix.h:356
static constexpr int kMScaleY
vertical scale factor
Definition SkMatrix.h:357
static constexpr int kMSkewX
horizontal skew factor
Definition SkMatrix.h:354
void reset()
Definition SkPaint.cpp:103
@ kStroke_Style
set to stroke geometry
Definition SkPaint.h:194
static SkDescriptor * CreateDescriptorAndEffectsUsingPaint(const SkFont &, const SkPaint &, const SkSurfaceProps &, SkScalerContextFlags scalerContextFlags, const SkMatrix &deviceMatrix, SkAutoDescriptor *ad, SkScalerContextEffects *effects)
constexpr size_t size() const
Definition SkSpan_impl.h:95
sk_sp< SkStrike > findOrCreateStrike(const SkStrikeSpec &strikeSpec) SK_EXCLUDES(fLock)
static SkStrikeCache * GlobalStrikeCache()
sk_sp< sktext::StrikeForGPU > findOrCreateScopedStrike(sktext::StrikeForGPUCacheInterface *cache) const
static SkStrikeSpec MakeTransformMask(const SkFont &font, const SkPaint &paint, const SkSurfaceProps &surfaceProps, SkScalerContextFlags scalerContextFlags, const SkMatrix &deviceMatrix)
static SkStrikeSpec MakeMask(const SkFont &font, const SkPaint &paint, const SkSurfaceProps &surfaceProps, SkScalerContextFlags scalerContextFlags, const SkMatrix &deviceMatrix)
SkString dump() const
static SkStrikeSpec MakeWithNoDevice(const SkFont &font, const SkPaint *paint=nullptr)
const SkTypeface & typeface() const
static bool ShouldDrawAsPath(const SkPaint &paint, const SkFont &font, const SkMatrix &matrix)
sk_sp< SkStrike > findOrCreateStrike() const
static std::tuple< SkStrikeSpec, SkScalar > MakeCanonicalized(const SkFont &font, const SkPaint *paint=nullptr)
static SkStrikeSpec MakePDFVector(const SkTypeface &typeface, int *size)
static std::tuple< SkStrikeSpec, SkScalar > MakePath(const SkFont &font, const SkPaint &paint, const SkSurfaceProps &surfaceProps, SkScalerContextFlags scalerContextFlags)
SkStrikeSpec(const SkDescriptor &descriptor, sk_sp< SkTypeface > typeface)
const SkDescriptor & getDescriptor() const override
Definition SkStrike.h:103
SkSpan< const SkGlyph * > metrics(SkSpan< const SkGlyphID > glyphIDs, const SkGlyph *results[]) SK_EXCLUDES(fStrikeLock)
Definition SkStrike.cpp:218
SkSpan< const SkGlyph * > preparePaths(SkSpan< const SkGlyphID > glyphIDs, const SkGlyph *results[]) SK_EXCLUDES(fStrikeLock)
Definition SkStrike.cpp:224
void findIntercepts(const SkScalar bounds[2], SkScalar scale, SkScalar xPos, SkGlyph *, SkScalar *array, int *count) SK_EXCLUDES(fStrikeLock)
Definition SkStrike.cpp:212
SkSpan< const SkGlyph * > prepareDrawables(SkSpan< const SkGlyphID > glyphIDs, const SkGlyph *results[]) SK_EXCLUDES(fStrikeLock)
Definition SkStrike.cpp:243
SkSpan< const SkGlyph * > prepareImages(SkSpan< const SkPackedGlyphID > glyphIDs, const SkGlyph *results[]) SK_EXCLUDES(fStrikeLock)
Definition SkStrike.cpp:230
T * set(const T &src)
Definition SkTLazy.h:56
int getUnitsPerEm() const
T * get() const
Definition SkRefCnt.h:303
const Paint & paint
float SkScalar
Definition extension.cpp:12
Definition ref_ptr.h:256
const Scalar scale