• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2014 Google Inc.
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 
8 #ifndef GrStencilAndCoverTextContext_DEFINED
9 #define GrStencilAndCoverTextContext_DEFINED
10 
11 #include "GrRenderTargetContext.h"
12 #include "GrStyle.h"
13 #include "SkDrawFilter.h"
14 #include "SkOpts.h"
15 #include "SkTHash.h"
16 #include "SkTInternalLList.h"
17 #include "SkTLList.h"
18 #include "SkTextBlob.h"
19 #include "ops/GrDrawPathOp.h"
20 
21 class GrAtlasTextContext;
22 class GrTextStrike;
23 class GrPath;
24 class SkSurfaceProps;
25 
26 /*
27  * This class implements text rendering using stencil and cover path rendering
28  * (by the means of GrOpList::drawPath).
29  */
30 class GrStencilAndCoverTextContext {
31 public:
32     static GrStencilAndCoverTextContext* Create(GrAtlasTextContext* fallbackTextContext);
33 
34     void drawText(GrContext*, GrRenderTargetContext* rtc, const GrClip&, const SkPaint&,
35                   const SkMatrix& viewMatrix, const SkSurfaceProps&, const char text[],
36                   size_t byteLength, SkScalar x, SkScalar y, const SkIRect& clipBounds);
37     void drawPosText(GrContext*, GrRenderTargetContext*, const GrClip&, const SkPaint&,
38                      const SkMatrix& viewMatrix, const SkSurfaceProps&, const char text[],
39                      size_t byteLength, const SkScalar pos[], int scalarsPerPosition,
40                      const SkPoint& offset, const SkIRect& clipBounds);
41     void drawTextBlob(GrContext*, GrRenderTargetContext*, const GrClip&, const SkPaint&,
42                       const SkMatrix& viewMatrix, const SkSurfaceProps&, const SkTextBlob*,
43                       SkScalar x, SkScalar y,
44                       SkDrawFilter*, const SkIRect& clipBounds);
45 
46     virtual ~GrStencilAndCoverTextContext();
47 
48 private:
49     GrStencilAndCoverTextContext(GrAtlasTextContext* fallbackTextContext);
50 
canDraw(const SkPaint & skPaint,const SkMatrix &)51     bool canDraw(const SkPaint& skPaint, const SkMatrix&) {
52         return this->internalCanDraw(skPaint);
53     }
54 
55     bool internalCanDraw(const SkPaint&);
56 
57     void uncachedDrawTextBlob(GrContext*, GrRenderTargetContext* rtc,
58                               const GrClip& clip, const SkPaint& skPaint,
59                               const SkMatrix& viewMatrix,
60                               const SkSurfaceProps&,
61                               const SkTextBlob* blob,
62                               SkScalar x, SkScalar y,
63                               SkDrawFilter* drawFilter,
64                               const SkIRect& clipBounds);
65 
66     class FallbackBlobBuilder;
67 
68     class TextRun {
69     public:
70         TextRun(const SkPaint& fontAndStroke);
71         ~TextRun();
72 
73         void setText(const char text[], size_t byteLength, SkScalar x, SkScalar y);
74 
75         void setPosText(const char text[], size_t byteLength, const SkScalar pos[],
76                         int scalarsPerPosition, const SkPoint& offset);
77 
78         void draw(GrContext*, GrRenderTargetContext*, const GrClip&, const SkMatrix&,
79                   const SkSurfaceProps&, SkScalar x, SkScalar y, const SkIRect& clipBounds,
80                   GrAtlasTextContext* fallbackTextContext, const SkPaint& originalSkPaint) const;
81 
82         void releaseGlyphCache() const;
83 
84         size_t computeSizeInCache() const;
85 
aa()86         GrAA aa() const { return fFont.isAntiAlias() ? GrAA::kYes : GrAA::kNo; }
87 
88     private:
89         typedef GrDrawPathRangeOp::InstanceData InstanceData;
90 
91         SkGlyphCache* getGlyphCache() const;
92         sk_sp<GrPathRange> createGlyphs(GrResourceProvider*) const;
93         void appendGlyph(const SkGlyph&, const SkPoint&, FallbackBlobBuilder*);
94 
95         GrStyle                         fStyle;
96         SkPaint                         fFont;
97         SkScalar                        fTextRatio;
98         float                           fTextInverseRatio;
99         bool                            fUsingRawGlyphPaths;
100         GrUniqueKey                     fGlyphPathsKey;
101         int                             fTotalGlyphCount;
102         sk_sp<InstanceData>             fInstanceData;
103         int                             fFallbackGlyphCount;
104         sk_sp<SkTextBlob>               fFallbackTextBlob;
105         mutable SkGlyphCache*           fDetachedGlyphCache;
106         mutable GrGpuResource::UniqueID fLastDrawnGlyphsID;
107     };
108 
109     // Text blobs/caches.
110 
111     class TextBlob : public SkTLList<TextRun, 1> {
112     public:
113         typedef SkTArray<uint32_t, true> Key;
114 
GetKey(const TextBlob * blob)115         static const Key& GetKey(const TextBlob* blob) { return blob->key(); }
116 
Hash(const Key & key)117         static uint32_t Hash(const Key& key) {
118             SkASSERT(key.count() > 1); // 1-length keys should be using the blob-id hash map.
119             return SkOpts::hash(key.begin(), sizeof(uint32_t) * key.count());
120         }
121 
TextBlob(uint32_t blobId,const SkTextBlob * skBlob,const SkPaint & skPaint)122         TextBlob(uint32_t blobId, const SkTextBlob* skBlob, const SkPaint& skPaint)
123             : fKey(&blobId, 1) { this->init(skBlob, skPaint); }
124 
TextBlob(const Key & key,const SkTextBlob * skBlob,const SkPaint & skPaint)125         TextBlob(const Key& key, const SkTextBlob* skBlob, const SkPaint& skPaint)
126             : fKey(key) {
127             // 1-length keys are unterstood to be the blob id and must use the other constructor.
128             SkASSERT(fKey.count() > 1);
129             this->init(skBlob, skPaint);
130         }
131 
key()132         const Key& key() const { return fKey; }
133 
cpuMemorySize()134         size_t cpuMemorySize() const { return fCpuMemorySize; }
135 
136     private:
137         void init(const SkTextBlob*, const SkPaint&);
138 
139         const SkSTArray<1, uint32_t, true>   fKey;
140         size_t                               fCpuMemorySize;
141 
142         SK_DECLARE_INTERNAL_LLIST_INTERFACE(TextBlob);
143     };
144 
145     const TextBlob& findOrCreateTextBlob(const SkTextBlob*, const SkPaint&);
146     void purgeToFit(const TextBlob&);
147 
148     GrAtlasTextContext*                                       fFallbackTextContext;
149     SkTHashMap<uint32_t, TextBlob*>                           fBlobIdCache;
150     SkTHashTable<TextBlob*, const TextBlob::Key&, TextBlob>   fBlobKeyCache;
151     SkTInternalLList<TextBlob>                                fLRUList;
152     size_t                                                    fCacheSize;
153 };
154 
155 #endif
156