blob: 90e401008d4ad5567f53b9030ccd0a47b035e348 [file] [log] [blame]
joshualitt1d89e8d2015-04-01 12:40:54 -07001/*
2 * Copyright 2015 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 GrAtlasTextContext_DEFINED
9#define GrAtlasTextContext_DEFINED
10
11#include "GrTextContext.h"
12
joshualitt374b2f72015-07-21 08:05:03 -070013#include "GrAtlasTextBlob.h"
joshualitt1d89e8d2015-04-01 12:40:54 -070014#include "GrGeometryProcessor.h"
halcanary33779752015-10-27 14:01:05 -070015#include "SkTextBlobRunIterator.h"
joshualitt1d89e8d2015-04-01 12:40:54 -070016
joshualitt79dfb2b2015-05-11 08:58:08 -070017#ifdef GR_TEST_UTILS
18#include "GrBatchTest.h"
19#endif
20
bsalomonabd30f52015-08-13 13:34:48 -070021class GrDrawBatch;
robertphillipsea461502015-05-26 11:38:03 -070022class GrDrawContext;
robertphillips2334fb62015-06-17 05:43:33 -070023class GrDrawTarget;
joshualitt1d89e8d2015-04-01 12:40:54 -070024class GrPipelineBuilder;
joshualittb7133be2015-04-08 09:08:31 -070025class GrTextBlobCache;
joshualitt6c2c2b02015-07-24 10:37:00 -070026class SkGlyph;
joshualitt1d89e8d2015-04-01 12:40:54 -070027
28/*
29 * This class implements GrTextContext using standard bitmap fonts, and can also process textblobs.
joshualitt1d89e8d2015-04-01 12:40:54 -070030 */
joshualittdbd35932015-04-02 09:19:04 -070031class GrAtlasTextContext : public GrTextContext {
joshualitt1d89e8d2015-04-01 12:40:54 -070032public:
robertphillipsf6703fa2015-09-01 05:36:47 -070033 static GrAtlasTextContext* Create(GrContext*, const SkSurfaceProps&);
joshualitt1d89e8d2015-04-01 12:40:54 -070034
joshualitt1d89e8d2015-04-01 12:40:54 -070035private:
robertphillipsf6703fa2015-09-01 05:36:47 -070036 GrAtlasTextContext(GrContext*, const SkSurfaceProps&);
joshualitt9bd2daf2015-04-17 09:30:06 -070037 ~GrAtlasTextContext() override {}
joshualitt1d89e8d2015-04-01 12:40:54 -070038
39 bool canDraw(const GrRenderTarget*, const GrClip&, const GrPaint&,
40 const SkPaint&, const SkMatrix& viewMatrix) override;
41
robertphillipsf6703fa2015-09-01 05:36:47 -070042 void onDrawText(GrDrawContext*, GrRenderTarget*, const GrClip&, const GrPaint&, const SkPaint&,
joshualitt1d89e8d2015-04-01 12:40:54 -070043 const SkMatrix& viewMatrix, const char text[], size_t byteLength,
44 SkScalar x, SkScalar y, const SkIRect& regionClipBounds) override;
robertphillipsf6703fa2015-09-01 05:36:47 -070045 void onDrawPosText(GrDrawContext*, GrRenderTarget*, const GrClip&, const GrPaint&,
robertphillipsccb1b572015-05-27 11:02:55 -070046 const SkPaint&, const SkMatrix& viewMatrix,
joshualitt1d89e8d2015-04-01 12:40:54 -070047 const char text[], size_t byteLength,
48 const SkScalar pos[], int scalarsPerPosition,
49 const SkPoint& offset, const SkIRect& regionClipBounds) override;
robertphillipsf6703fa2015-09-01 05:36:47 -070050 void drawTextBlob(GrDrawContext*, GrRenderTarget*, const GrClip&, const SkPaint&,
joshualitt1d89e8d2015-04-01 12:40:54 -070051 const SkMatrix& viewMatrix, const SkTextBlob*, SkScalar x, SkScalar y,
52 SkDrawFilter*, const SkIRect& clipBounds) override;
53
joshualitt374b2f72015-07-21 08:05:03 -070054 typedef GrAtlasTextBlob::Run Run;
joshualitt1d89e8d2015-04-01 12:40:54 -070055 typedef Run::SubRunInfo PerSubRunInfo;
56
joshualitt9bd2daf2015-04-17 09:30:06 -070057 inline bool canDrawAsDistanceFields(const SkPaint&, const SkMatrix& viewMatrix);
joshualitt374b2f72015-07-21 08:05:03 -070058 GrAtlasTextBlob* setupDFBlob(int glyphCount, const SkPaint& origPaint,
jvanverth157e6482015-09-09 08:05:12 -070059 const SkMatrix& viewMatrix, SkPaint* dfPaint,
60 SkScalar* textRatio);
joshualitt6c2c2b02015-07-24 10:37:00 -070061 void bmpAppendGlyph(GrAtlasTextBlob*, int runIndex, const SkGlyph&, int left, int top,
joshualitt9bd2daf2015-04-17 09:30:06 -070062 GrColor color, GrFontScaler*, const SkIRect& clipRect);
joshualitt6c2c2b02015-07-24 10:37:00 -070063 bool dfAppendGlyph(GrAtlasTextBlob*, int runIndex, const SkGlyph&, SkScalar sx, SkScalar sy,
joshualitt9bd2daf2015-04-17 09:30:06 -070064 GrColor color, GrFontScaler*, const SkIRect& clipRect, SkScalar textRatio,
65 const SkMatrix& viewMatrix);
joshualitt6c2c2b02015-07-24 10:37:00 -070066 inline void appendGlyphPath(GrAtlasTextBlob*, GrGlyph*, GrFontScaler*, const SkGlyph&,
joshualitt0fe04a22015-08-25 12:05:50 -070067 SkScalar x, SkScalar y, SkScalar scale = 1.0f,
68 bool applyVM = false);
joshualitt374b2f72015-07-21 08:05:03 -070069 inline void appendGlyphCommon(GrAtlasTextBlob*, Run*, Run::SubRunInfo*,
joshualitt9bd2daf2015-04-17 09:30:06 -070070 const SkRect& positions, GrColor color,
71 size_t vertexStride, bool useVertexColor,
joshualittae32c102015-04-21 09:37:57 -070072 GrGlyph*);
joshualitt9a27e632015-04-06 10:53:36 -070073
robertphillips7bceedc2015-12-01 12:51:26 -080074 inline void flushRunAsPaths(GrDrawContext*,
halcanary33779752015-10-27 14:01:05 -070075 const SkTextBlobRunIterator&, const GrClip& clip,
robertphillipsccb1b572015-05-27 11:02:55 -070076 const SkPaint&, SkDrawFilter*,
joshualitt9a27e632015-04-06 10:53:36 -070077 const SkMatrix& viewMatrix, const SkIRect& clipBounds, SkScalar x,
78 SkScalar y);
bsalomonabd30f52015-08-13 13:34:48 -070079 inline GrDrawBatch* createBatch(GrAtlasTextBlob*, const PerSubRunInfo&,
80 int glyphCount, int run, int subRun,
81 GrColor, SkScalar transX, SkScalar transY,
82 const SkPaint&);
robertphillipsf6703fa2015-09-01 05:36:47 -070083 inline void flushRun(GrDrawContext*, GrPipelineBuilder*, GrAtlasTextBlob*, int run, GrColor,
joshualitt9bd2daf2015-04-17 09:30:06 -070084 SkScalar transX, SkScalar transY, const SkPaint&);
robertphillips7bceedc2015-12-01 12:51:26 -080085 inline void flushBigGlyphs(GrAtlasTextBlob* cacheBlob, GrDrawContext*,
robertphillipsccb1b572015-05-27 11:02:55 -070086 const GrClip& clip, const SkPaint& skPaint,
joshualitt1107e902015-05-11 14:52:11 -070087 SkScalar transX, SkScalar transY, const SkIRect& clipBounds);
joshualitt9a27e632015-04-06 10:53:36 -070088
89 // We have to flush SkTextBlobs differently from drawText / drawPosText
robertphillipsf6703fa2015-09-01 05:36:47 -070090 void flush(const SkTextBlob*, GrAtlasTextBlob*, GrDrawContext*, GrRenderTarget*,
robertphillipsccb1b572015-05-27 11:02:55 -070091 const SkPaint&, const GrPaint&, SkDrawFilter*, const GrClip&,
92 const SkMatrix& viewMatrix, const SkIRect& clipBounds, SkScalar x, SkScalar y,
93 SkScalar transX, SkScalar transY);
robertphillipsf6703fa2015-09-01 05:36:47 -070094 void flush(GrAtlasTextBlob*, GrDrawContext*, GrRenderTarget*, const SkPaint&,
joshualitt1107e902015-05-11 14:52:11 -070095 const GrPaint&, const GrClip&, const SkIRect& clipBounds);
joshualitt1d89e8d2015-04-01 12:40:54 -070096
joshualitt9bd2daf2015-04-17 09:30:06 -070097 // A helper for drawing BitmapText in a run of distance fields
joshualitt374b2f72015-07-21 08:05:03 -070098 inline void fallbackDrawPosText(GrAtlasTextBlob*, int runIndex,
jvanverth0628a522015-08-18 07:44:22 -070099 GrRenderTarget*, const GrClip&, GrColor color,
joshualitt9bd2daf2015-04-17 09:30:06 -0700100 const SkPaint&, const SkMatrix& viewMatrix,
101 const SkTDArray<char>& fallbackTxt,
102 const SkTDArray<SkScalar>& fallbackPos,
103 int scalarsPerPosition,
104 const SkPoint& offset,
105 const SkIRect& clipRect);
106
joshualitt374b2f72015-07-21 08:05:03 -0700107 void internalDrawBMPText(GrAtlasTextBlob*, int runIndex, SkGlyphCache*, const SkPaint&,
joshualitt9e36c1a2015-04-14 12:17:27 -0700108 GrColor color, const SkMatrix& viewMatrix,
joshualitt1d89e8d2015-04-01 12:40:54 -0700109 const char text[], size_t byteLength,
joshualitt9bd2daf2015-04-17 09:30:06 -0700110 SkScalar x, SkScalar y, const SkIRect& clipRect);
joshualitt374b2f72015-07-21 08:05:03 -0700111 void internalDrawBMPPosText(GrAtlasTextBlob*, int runIndex, SkGlyphCache*, const SkPaint&,
joshualitt9bd2daf2015-04-17 09:30:06 -0700112 GrColor color, const SkMatrix& viewMatrix,
113 const char text[], size_t byteLength,
114 const SkScalar pos[], int scalarsPerPosition,
115 const SkPoint& offset, const SkIRect& clipRect);
116
jvanverth157e6482015-09-09 08:05:12 -0700117 void internalDrawDFText(GrAtlasTextBlob*, int runIndex, const SkPaint&,
joshualitt9bd2daf2015-04-17 09:30:06 -0700118 GrColor color, const SkMatrix& viewMatrix,
119 const char text[], size_t byteLength,
120 SkScalar x, SkScalar y, const SkIRect& clipRect,
121 SkScalar textRatio,
122 SkTDArray<char>* fallbackTxt,
123 SkTDArray<SkScalar>* fallbackPos,
124 SkPoint* offset, const SkPaint& origPaint);
jvanverth157e6482015-09-09 08:05:12 -0700125 void internalDrawDFPosText(GrAtlasTextBlob*, int runIndex, const SkPaint&,
joshualitt9bd2daf2015-04-17 09:30:06 -0700126 GrColor color, const SkMatrix& viewMatrix,
127 const char text[], size_t byteLength,
128 const SkScalar pos[], int scalarsPerPosition,
129 const SkPoint& offset, const SkIRect& clipRect,
130 SkScalar textRatio,
131 SkTDArray<char>* fallbackTxt,
132 SkTDArray<SkScalar>* fallbackPos);
joshualitt1d89e8d2015-04-01 12:40:54 -0700133
134 // sets up the descriptor on the blob and returns a detached cache. Client must attach
joshualitt9e36c1a2015-04-14 12:17:27 -0700135 inline static GrColor ComputeCanonicalColor(const SkPaint&, bool lcd);
joshualitt9bd2daf2015-04-17 09:30:06 -0700136 inline SkGlyphCache* setupCache(Run*, const SkPaint&, const SkMatrix* viewMatrix, bool noGamma);
joshualitt2a0e9f32015-04-13 06:12:21 -0700137 static inline bool MustRegenerateBlob(SkScalar* outTransX, SkScalar* outTransY,
jvanverth0628a522015-08-18 07:44:22 -0700138 const GrAtlasTextBlob&, const SkPaint&, GrColor,
joshualitt53b5f442015-04-13 06:33:59 -0700139 const SkMaskFilter::BlurRec&,
joshualitt1d89e8d2015-04-01 12:40:54 -0700140 const SkMatrix& viewMatrix, SkScalar x, SkScalar y);
joshualitt374b2f72015-07-21 08:05:03 -0700141 void regenerateTextBlob(GrAtlasTextBlob* bmp, const SkPaint& skPaint, GrColor,
joshualitt9e36c1a2015-04-14 12:17:27 -0700142 const SkMatrix& viewMatrix,
joshualitt1d89e8d2015-04-01 12:40:54 -0700143 const SkTextBlob* blob, SkScalar x, SkScalar y,
joshualittfcfb9fc2015-04-21 07:35:10 -0700144 SkDrawFilter* drawFilter, const SkIRect& clipRect, GrRenderTarget*,
jvanverth0628a522015-08-18 07:44:22 -0700145 const GrClip&);
joshualitt9e36c1a2015-04-14 12:17:27 -0700146 inline static bool HasLCD(const SkTextBlob*);
joshualitt374b2f72015-07-21 08:05:03 -0700147 inline void initDistanceFieldPaint(GrAtlasTextBlob*, SkPaint*, SkScalar* textRatio,
joshualitt64c99cc2015-04-21 09:43:03 -0700148 const SkMatrix&);
joshualitt9bd2daf2015-04-17 09:30:06 -0700149
joshualitt79dfb2b2015-05-11 08:58:08 -0700150 // Test methods
151 // TODO this is really ugly. It'd be much nicer if positioning could be moved to batch
joshualitt374b2f72015-07-21 08:05:03 -0700152 inline GrAtlasTextBlob* createDrawTextBlob(GrRenderTarget*, const GrClip&, const GrPaint&,
joshualitt79dfb2b2015-05-11 08:58:08 -0700153 const SkPaint&, const SkMatrix& viewMatrix,
154 const char text[], size_t byteLength,
155 SkScalar x, SkScalar y,
156 const SkIRect& regionClipBounds);
joshualitt374b2f72015-07-21 08:05:03 -0700157 inline GrAtlasTextBlob* createDrawPosTextBlob(GrRenderTarget*, const GrClip&, const GrPaint&,
joshualitt79dfb2b2015-05-11 08:58:08 -0700158 const SkPaint&, const SkMatrix& viewMatrix,
159 const char text[], size_t byteLength,
160 const SkScalar pos[], int scalarsPerPosition,
161 const SkPoint& offset,
162 const SkIRect& regionClipBounds);
163
joshualitt9bd2daf2015-04-17 09:30:06 -0700164 // Distance field text needs this table to compute a value for use in the fragment shader.
165 // Because the GrAtlasTextContext can go out of scope before the final flush, this needs to be
166 // refcnted and malloced
167 struct DistanceAdjustTable : public SkNVRefCnt<DistanceAdjustTable> {
robertphillips9fc82752015-06-19 04:46:45 -0700168 DistanceAdjustTable() { this->buildDistanceAdjustTable(); }
halcanary385fe4d2015-08-26 13:07:48 -0700169 ~DistanceAdjustTable() { delete[] fTable; }
joshualitt9bd2daf2015-04-17 09:30:06 -0700170
joshualitt9bd2daf2015-04-17 09:30:06 -0700171 const SkScalar& operator[] (int i) const {
172 return fTable[i];
173 }
174
robertphillips9fc82752015-06-19 04:46:45 -0700175 private:
176 void buildDistanceAdjustTable();
177
joshualitt9bd2daf2015-04-17 09:30:06 -0700178 SkScalar* fTable;
179 };
joshualitt1d89e8d2015-04-01 12:40:54 -0700180
joshualitt1d89e8d2015-04-01 12:40:54 -0700181 GrBatchTextStrike* fCurrStrike;
joshualittb7133be2015-04-08 09:08:31 -0700182 GrTextBlobCache* fCache;
robertphillipsf6703fa2015-09-01 05:36:47 -0700183 SkAutoTUnref<const DistanceAdjustTable> fDistanceAdjustTable;
joshualitt1d89e8d2015-04-01 12:40:54 -0700184
joshualittb7133be2015-04-08 09:08:31 -0700185 friend class GrTextBlobCache;
joshualitta751c972015-11-20 13:37:32 -0800186 friend class GrAtlasTextBatch;
joshualitt1d89e8d2015-04-01 12:40:54 -0700187
joshualitt79dfb2b2015-05-11 08:58:08 -0700188#ifdef GR_TEST_UTILS
bsalomonabd30f52015-08-13 13:34:48 -0700189 DRAW_BATCH_TEST_FRIEND(TextBlobBatch);
joshualitt79dfb2b2015-05-11 08:58:08 -0700190#endif
191
joshualitt1d89e8d2015-04-01 12:40:54 -0700192 typedef GrTextContext INHERITED;
193};
194
195#endif