blob: e605b3e2924bd69201c16755c4d7ad8ab02742f5 [file] [log] [blame]
bsalomonadd79ef2015-08-19 13:26:49 -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 GrDrawPathBatch_DEFINED
9#define GrDrawPathBatch_DEFINED
10
bsalomon1fcc01c2015-09-09 09:48:06 -070011#include "GrBatchFlushState.h"
bsalomonadd79ef2015-08-19 13:26:49 -070012#include "GrDrawBatch.h"
13#include "GrGpu.h"
14#include "GrPath.h"
15#include "GrPathRendering.h"
16#include "GrPathProcessor.h"
17
bsalomon1fcc01c2015-09-09 09:48:06 -070018#include "SkTLList.h"
19
20class GrDrawPathBatchBase : public GrDrawBatch {
bsalomonadd79ef2015-08-19 13:26:49 -070021public:
bsalomon1fcc01c2015-09-09 09:48:06 -070022 void getInvariantOutputColor(GrInitInvariantOutput* out) const override {
23 this->pathProcessor()->getInvariantOutputColor(out);
24 }
25
26 void getInvariantOutputCoverage(GrInitInvariantOutput* out) const override {
27 this->pathProcessor()->getInvariantOutputCoverage(out);
28 }
29
30 void setStencilSettings(const GrStencilSettings& stencil) { fStencilSettings = stencil; }
31
32protected:
33 GrDrawPathBatchBase(const GrPathProcessor* pathProc) : fPrimitiveProcessor(pathProc) {}
34
35 GrBatchTracker* tracker() { return reinterpret_cast<GrBatchTracker*>(&fWhatchamacallit); }
36 const GrPathProcessor* pathProcessor() const { return fPrimitiveProcessor.get(); }
37 const GrStencilSettings& stencilSettings() const { return fStencilSettings; }
38 const GrPipelineOptimizations& opts() const { return fOpts; }
39
40private:
41 void initBatchTracker(const GrPipelineOptimizations& opts) override {
42 this->pathProcessor()->initBatchTracker(this->tracker(), opts);
43 fOpts = opts;
44 }
45
46 GrPendingProgramElement<const GrPathProcessor> fPrimitiveProcessor;
47 PathBatchTracker fWhatchamacallit; // TODO: delete this
48 GrStencilSettings fStencilSettings;
49 GrPipelineOptimizations fOpts;
50
51 typedef GrDrawBatch INHERITED;
52};
53
54class GrDrawPathBatch final : public GrDrawPathBatchBase {
55public:
56 // This can't return a more abstract type because we install the stencil settings late :(
57 static GrDrawPathBatchBase* Create(const GrPathProcessor* primProc, const GrPath* path) {
halcanary385fe4d2015-08-26 13:07:48 -070058 return new GrDrawPathBatch(primProc, path);
bsalomonadd79ef2015-08-19 13:26:49 -070059 }
60
61 const char* name() const override { return "DrawPath"; }
62
bsalomon1fcc01c2015-09-09 09:48:06 -070063 SkString dumpInfo() const override;
bsalomonadd79ef2015-08-19 13:26:49 -070064
65private:
bsalomon1fcc01c2015-09-09 09:48:06 -070066 GrDrawPathBatch(const GrPathProcessor* pathProc, const GrPath* path)
67 : INHERITED(pathProc)
68 , fPath(path) {
bsalomonadd79ef2015-08-19 13:26:49 -070069 fBounds = path->getBounds();
bsalomon1fcc01c2015-09-09 09:48:06 -070070 this->pathProcessor()->viewMatrix().mapRect(&fBounds);
bsalomonadd79ef2015-08-19 13:26:49 -070071 this->initClassID<GrDrawPathBatch>();
72 }
73
bsalomonadd79ef2015-08-19 13:26:49 -070074 bool onCombineIfPossible(GrBatch* t, const GrCaps& caps) override { return false; }
75
76 void onPrepare(GrBatchFlushState*) override {}
77
bsalomon1fcc01c2015-09-09 09:48:06 -070078 void onDraw(GrBatchFlushState* state) override;
79
80 GrPendingIOResource<const GrPath, kRead_GrIOType> fPath;
81
82 typedef GrDrawPathBatchBase INHERITED;
83};
84
85/**
86 * This could be nested inside the batch class, but for now it must be declarable in a public
87 * header (GrDrawContext)
88 */
89class GrPathRangeDraw : public GrNonAtomicRef {
90public:
91 typedef GrPathRendering::PathTransformType TransformType;
92
93 static GrPathRangeDraw* Create(GrPathRange* range, TransformType transformType,
94 int reserveCnt) {
95 return SkNEW_ARGS(GrPathRangeDraw, (range, transformType, reserveCnt));
bsalomonadd79ef2015-08-19 13:26:49 -070096 }
97
bsalomon1fcc01c2015-09-09 09:48:06 -070098 void append(uint16_t index, float transform[]) {
99 fTransforms.push_back_n(GrPathRendering::PathTransformSize(fTransformType), transform);
100 fIndices.push_back(index);
101 }
102
103 int count() const { return fIndices.count(); }
104
105 TransformType transformType() const { return fTransformType; }
106
107 const float* transforms() const { return fTransforms.begin(); }
108
109 const uint16_t* indices() const { return fIndices.begin(); }
110
111 const GrPathRange* range() const { return fPathRange.get(); }
112
113 static bool CanMerge(const GrPathRangeDraw& a, const GrPathRangeDraw& b) {
114 return a.transformType() == b.transformType() && a.range() == b.range();
115 }
116
117private:
118 GrPathRangeDraw(GrPathRange* range, TransformType transformType, int reserveCnt)
119 : fPathRange(SkRef(range))
120 , fTransformType(transformType)
121 , fIndices(reserveCnt)
122 , fTransforms(reserveCnt * GrPathRendering::PathTransformSize(transformType)) {
123 SkDEBUGCODE(fUsedInBatch = false;)
124 }
125
126 // Reserve space for 64 paths where indices are 16 bit and transforms are translations.
127 static const int kIndexReserveCnt = 64;
128 static const int kTransformBufferReserveCnt = 2 * 64;
129
130 GrPendingIOResource<const GrPathRange, kRead_GrIOType> fPathRange;
131 GrPathRendering::PathTransformType fTransformType;
132 SkSTArray<kIndexReserveCnt, uint16_t, true> fIndices;
133 SkSTArray<kTransformBufferReserveCnt, float, true> fTransforms;
134
135 // To ensure we don't reuse these across batches.
136#ifdef SK_DEBUG
137 bool fUsedInBatch;
138 friend class GrDrawPathRangeBatch;
139#endif
140
141 typedef GrNonAtomicRef INHERITED;
142};
143
144// Template this if we decide to support index types other than 16bit
145class GrDrawPathRangeBatch final : public GrDrawPathBatchBase {
146public:
147 // This can't return a more abstracet type because we install the stencil settings late :(
148 static GrDrawPathBatchBase* Create(const GrPathProcessor* pathProc,
149 GrPathRangeDraw* pathRangeDraw) {
150 return SkNEW_ARGS(GrDrawPathRangeBatch, (pathProc, pathRangeDraw));
151 }
152
153 ~GrDrawPathRangeBatch() override;
154
155 const char* name() const override { return "DrawPathRange"; }
156
157 SkString dumpInfo() const override;
158
159private:
160 inline bool isWinding() const;
161
162 GrDrawPathRangeBatch(const GrPathProcessor* pathProc, GrPathRangeDraw* pathRangeDraw);
163
164 bool onCombineIfPossible(GrBatch* t, const GrCaps& caps) override;
165
166 void onPrepare(GrBatchFlushState*) override {}
167
168 void onDraw(GrBatchFlushState* state) override;
169
170 typedef SkTLList<GrPathRangeDraw*> DrawList;
171 DrawList fDraws;
172 int fTotalPathCount;
173
174 typedef GrDrawPathBatchBase INHERITED;
bsalomonadd79ef2015-08-19 13:26:49 -0700175};
176
177#endif