OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2015 Google Inc. | 2 * Copyright 2015 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #include "GrNonAAFillRectBatch.h" | 8 #include "GrNonAAFillRectBatch.h" |
9 | 9 |
10 #include "GrBatchFlushState.h" | 10 #include "GrBatchFlushState.h" |
11 #include "GrColor.h" | 11 #include "GrColor.h" |
12 #include "GrDefaultGeoProcFactory.h" | 12 #include "GrDefaultGeoProcFactory.h" |
13 #include "GrPrimitiveProcessor.h" | 13 #include "GrPrimitiveProcessor.h" |
14 #include "GrResourceProvider.h" | 14 #include "GrResourceProvider.h" |
15 #include "GrTInstanceBatch.h" | |
16 #include "GrQuad.h" | 15 #include "GrQuad.h" |
17 #include "GrVertexBatch.h" | 16 #include "GrVertexBatch.h" |
18 | 17 |
19 // Common functions | 18 static const int kVertsPerInstance = 4; |
20 class NonAAFillRectBatchBase { | 19 static const int kIndicesPerInstance = 6; |
21 public: | |
22 static const int kVertsPerInstance = 4; | |
23 static const int kIndicesPerInstance = 6; | |
24 | |
25 static void InitInvariantOutputCoverage(GrInitInvariantOutput* out) { | |
26 out->setKnownSingleComponent(0xff); | |
27 } | |
28 | |
29 static const GrBuffer* GetIndexBuffer(GrResourceProvider* rp) { | |
30 return rp->refQuadIndexBuffer(); | |
31 } | |
32 | |
33 template <typename Geometry> | |
34 static void SetBounds(const Geometry& geo, SkRect* outBounds) { | |
35 geo.fViewMatrix.mapRect(outBounds, geo.fRect); | |
36 } | |
37 | |
38 template <typename Geometry> | |
39 static void UpdateBoundsAfterAppend(const Geometry& geo, SkRect* outBounds)
{ | |
40 SkRect bounds = geo.fRect; | |
41 geo.fViewMatrix.mapRect(&bounds); | |
42 outBounds->join(bounds); | |
43 } | |
44 }; | |
45 | 20 |
46 /** We always use per-vertex colors so that rects can be batched across color ch
anges. Sometimes | 21 /** We always use per-vertex colors so that rects can be batched across color ch
anges. Sometimes |
47 we have explicit local coords and sometimes not. We *could* always provide
explicit local | 22 we have explicit local coords and sometimes not. We *could* always provide
explicit local |
48 coords and just duplicate the positions when the caller hasn't provided a lo
cal coord rect, | 23 coords and just duplicate the positions when the caller hasn't provided a lo
cal coord rect, |
49 but we haven't seen a use case which frequently switches between local rect
and no local | 24 but we haven't seen a use case which frequently switches between local rect
and no local |
50 rect draws. | 25 rect draws. |
51 | 26 |
52 The vertex attrib order is always pos, color, [local coords]. | 27 The vertex attrib order is always pos, color, [local coords]. |
53 */ | 28 */ |
54 static sk_sp<GrGeometryProcessor> make_gp(const SkMatrix& viewMatrix, | 29 static sk_sp<GrGeometryProcessor> make_gp(const SkMatrix& viewMatrix, |
(...skipping 28 matching lines...) Expand all Loading... |
83 GrColor color, | 58 GrColor color, |
84 const SkMatrix& viewMatrix, | 59 const SkMatrix& viewMatrix, |
85 const SkRect& rect, | 60 const SkRect& rect, |
86 const GrQuad* localQuad) { | 61 const GrQuad* localQuad) { |
87 SkPoint* positions = reinterpret_cast<SkPoint*>(vertices); | 62 SkPoint* positions = reinterpret_cast<SkPoint*>(vertices); |
88 | 63 |
89 positions->setRectFan(rect.fLeft, rect.fTop, | 64 positions->setRectFan(rect.fLeft, rect.fTop, |
90 rect.fRight, rect.fBottom, vertexStride); | 65 rect.fRight, rect.fBottom, vertexStride); |
91 | 66 |
92 if (!viewMatrix.hasPerspective()) { | 67 if (!viewMatrix.hasPerspective()) { |
93 viewMatrix.mapPointsWithStride(positions, vertexStride, | 68 viewMatrix.mapPointsWithStride(positions, vertexStride, kVertsPerInstanc
e); |
94 NonAAFillRectBatchBase::kVertsPerInstance
); | |
95 } | 69 } |
96 | 70 |
97 // Setup local coords | 71 // Setup local coords |
98 // TODO we should only do this if local coords are being read | 72 // TODO we should only do this if local coords are being read |
99 if (localQuad) { | 73 if (localQuad) { |
100 static const int kLocalOffset = sizeof(SkPoint) + sizeof(GrColor); | 74 static const int kLocalOffset = sizeof(SkPoint) + sizeof(GrColor); |
101 for (int i = 0; i < NonAAFillRectBatchBase::kVertsPerInstance; i++) { | 75 for (int i = 0; i < kVertsPerInstance; i++) { |
102 SkPoint* coords = reinterpret_cast<SkPoint*>(vertices + kLocalOffset
+ | 76 SkPoint* coords = reinterpret_cast<SkPoint*>(vertices + kLocalOffset
+ |
103 i * vertexStride); | 77 i * vertexStride); |
104 *coords = localQuad->point(i); | 78 *coords = localQuad->point(i); |
105 } | 79 } |
106 } | 80 } |
107 | 81 |
108 static const int kColorOffset = sizeof(SkPoint); | 82 static const int kColorOffset = sizeof(SkPoint); |
109 GrColor* vertColor = reinterpret_cast<GrColor*>(vertices + kColorOffset); | 83 GrColor* vertColor = reinterpret_cast<GrColor*>(vertices + kColorOffset); |
110 for (int j = 0; j < 4; ++j) { | 84 for (int j = 0; j < 4; ++j) { |
111 *vertColor = color; | 85 *vertColor = color; |
112 vertColor = (GrColor*) ((intptr_t) vertColor + vertexStride); | 86 vertColor = (GrColor*) ((intptr_t) vertColor + vertexStride); |
113 } | 87 } |
114 } | 88 } |
115 | 89 |
116 class NonAAFillRectBatchImp : public NonAAFillRectBatchBase { | 90 class NonAAFillRectBatch : public GrVertexBatch { |
117 public: | 91 public: |
| 92 DEFINE_BATCH_CLASS_ID |
| 93 |
118 struct Geometry { | 94 struct Geometry { |
119 SkMatrix fViewMatrix; | 95 SkMatrix fViewMatrix; |
120 SkRect fRect; | 96 SkRect fRect; |
121 GrQuad fLocalQuad; | 97 GrQuad fLocalQuad; |
122 GrColor fColor; | 98 GrColor fColor; |
123 }; | 99 }; |
124 | 100 |
| 101 static NonAAFillRectBatch* Create() { return new NonAAFillRectBatch; } |
| 102 |
| 103 const char* name() const override { return Name(); } |
| 104 |
| 105 SkString dumpInfo() const override { |
| 106 SkString str; |
| 107 str.appendf("# batched: %d\n", fGeoData.count()); |
| 108 for (int i = 0; i < fGeoData.count(); ++i) { |
| 109 str.append(DumpInfo(fGeoData[i], i)); |
| 110 } |
| 111 str.append(INHERITED::dumpInfo()); |
| 112 return str; |
| 113 } |
| 114 |
| 115 void computePipelineOptimizations(GrInitInvariantOutput* color, |
| 116 GrInitInvariantOutput* coverage, |
| 117 GrBatchToXPOverrides* overrides) const ove
rride { |
| 118 // When this is called on a batch, there is only one geometry bundle |
| 119 color->setKnownFourComponents(fGeoData[0].fColor); |
| 120 InitInvariantOutputCoverage(coverage); |
| 121 } |
| 122 |
| 123 void initBatchTracker(const GrXPOverridesForBatch& overrides) override { |
| 124 overrides.getOverrideColorIfSet(&fGeoData[0].fColor); |
| 125 fOverrides = overrides; |
| 126 } |
| 127 |
| 128 SkSTArray<1, Geometry, true>* geoData() { return &fGeoData; } |
| 129 |
| 130 // After seeding, the client should call init() so the Batch can initialize
itself |
| 131 void init() { |
| 132 const Geometry& geo = fGeoData[0]; |
| 133 SetBounds(geo, &fBounds); |
| 134 } |
| 135 |
| 136 void updateBoundsAfterAppend() { |
| 137 const Geometry& geo = fGeoData.back(); |
| 138 UpdateBoundsAfterAppend(geo, &fBounds); |
| 139 } |
| 140 |
| 141 private: |
125 static const char* Name() { return "NonAAFillRectBatch"; } | 142 static const char* Name() { return "NonAAFillRectBatch"; } |
126 | 143 |
127 static SkString DumpInfo(const Geometry& geo, int index) { | 144 static SkString DumpInfo(const Geometry& geo, int index) { |
128 SkString str; | 145 SkString str; |
129 str.appendf("%d: Color: 0x%08x, Rect [L: %.2f, T: %.2f, R: %.2f, B: %.2f
]\n", | 146 str.appendf("%d: Color: 0x%08x, Rect [L: %.2f, T: %.2f, R: %.2f, B: %.2f
]\n", |
130 index, | 147 index, |
131 geo.fColor, | 148 geo.fColor, |
132 geo.fRect.fLeft, geo.fRect.fTop, geo.fRect.fRight, geo.fRect
.fBottom); | 149 geo.fRect.fLeft, geo.fRect.fTop, geo.fRect.fRight, geo.fRect
.fBottom); |
133 return str; | 150 return str; |
134 } | 151 } |
(...skipping 10 matching lines...) Expand all Loading... |
145 | 162 |
146 SkASSERT(gp->getVertexStride() == | 163 SkASSERT(gp->getVertexStride() == |
147 sizeof(GrDefaultGeoProcFactory::PositionColorLocalCoordAttr)); | 164 sizeof(GrDefaultGeoProcFactory::PositionColorLocalCoordAttr)); |
148 return gp; | 165 return gp; |
149 } | 166 } |
150 | 167 |
151 static void Tesselate(intptr_t vertices, size_t vertexStride, const Geometry
& geo, | 168 static void Tesselate(intptr_t vertices, size_t vertexStride, const Geometry
& geo, |
152 const GrXPOverridesForBatch& overrides) { | 169 const GrXPOverridesForBatch& overrides) { |
153 tesselate(vertices, vertexStride, geo.fColor, geo.fViewMatrix, geo.fRect
, &geo.fLocalQuad); | 170 tesselate(vertices, vertexStride, geo.fColor, geo.fViewMatrix, geo.fRect
, &geo.fLocalQuad); |
154 } | 171 } |
| 172 |
| 173 static void InitInvariantOutputCoverage(GrInitInvariantOutput* out) { |
| 174 out->setKnownSingleComponent(0xff); |
| 175 } |
| 176 |
| 177 static const GrBuffer* GetIndexBuffer(GrResourceProvider* rp) { |
| 178 return rp->refQuadIndexBuffer(); |
| 179 } |
| 180 |
| 181 static void SetBounds(const Geometry& geo, SkRect* outBounds) { |
| 182 geo.fViewMatrix.mapRect(outBounds, geo.fRect); |
| 183 } |
| 184 |
| 185 static void UpdateBoundsAfterAppend(const Geometry& geo, SkRect* outBounds)
{ |
| 186 SkRect bounds = geo.fRect; |
| 187 geo.fViewMatrix.mapRect(&bounds); |
| 188 outBounds->join(bounds); |
| 189 } |
| 190 |
| 191 NonAAFillRectBatch() : INHERITED(ClassID()) {} |
| 192 |
| 193 void onPrepareDraws(Target* target) const override { |
| 194 sk_sp<GrGeometryProcessor> gp(MakeGP(this->seedGeometry(), fOverrides)); |
| 195 if (!gp) { |
| 196 SkDebugf("Couldn't create GrGeometryProcessor\n"); |
| 197 return; |
| 198 } |
| 199 |
| 200 size_t vertexStride = gp->getVertexStride(); |
| 201 int instanceCount = fGeoData.count(); |
| 202 |
| 203 SkAutoTUnref<const GrBuffer> indexBuffer(GetIndexBuffer(target->resource
Provider())); |
| 204 InstancedHelper helper; |
| 205 void* vertices = helper.init(target, kTriangles_GrPrimitiveType, vertexS
tride, |
| 206 indexBuffer, kVertsPerInstance, |
| 207 kIndicesPerInstance, instanceCount); |
| 208 if (!vertices || !indexBuffer) { |
| 209 SkDebugf("Could not allocate vertices\n"); |
| 210 return; |
| 211 } |
| 212 |
| 213 for (int i = 0; i < instanceCount; i++) { |
| 214 intptr_t verts = reinterpret_cast<intptr_t>(vertices) + |
| 215 i * kVertsPerInstance * vertexStride; |
| 216 Tesselate(verts, vertexStride, fGeoData[i], fOverrides); |
| 217 } |
| 218 helper.recordDraw(target, gp.get()); |
| 219 } |
| 220 |
| 221 const Geometry& seedGeometry() const { return fGeoData[0]; } |
| 222 |
| 223 bool onCombineIfPossible(GrBatch* t, const GrCaps& caps) override { |
| 224 NonAAFillRectBatch* that = t->cast<NonAAFillRectBatch>(); |
| 225 if (!GrPipeline::CanCombine(*this->pipeline(), this->bounds(), *that->pi
peline(), |
| 226 that->bounds(), caps)) { |
| 227 return false; |
| 228 } |
| 229 |
| 230 if (!CanCombine(this->seedGeometry(), that->seedGeometry(), fOverrides))
{ |
| 231 return false; |
| 232 } |
| 233 |
| 234 // In the event of two batches, one who can tweak, one who cannot, we ju
st fall back to |
| 235 // not tweaking |
| 236 if (fOverrides.canTweakAlphaForCoverage() && !that->fOverrides.canTweakA
lphaForCoverage()) { |
| 237 fOverrides = that->fOverrides; |
| 238 } |
| 239 |
| 240 fGeoData.push_back_n(that->geoData()->count(), that->geoData()->begin())
; |
| 241 this->joinBounds(that->bounds()); |
| 242 return true; |
| 243 } |
| 244 |
| 245 GrXPOverridesForBatch fOverrides; |
| 246 SkSTArray<1, Geometry, true> fGeoData; |
| 247 |
| 248 typedef GrVertexBatch INHERITED; |
155 }; | 249 }; |
156 | 250 |
157 // We handle perspective in the local matrix or viewmatrix with special batches | 251 // We handle perspective in the local matrix or viewmatrix with special batches |
158 class NonAAFillRectBatchPerspectiveImp : public NonAAFillRectBatchBase { | 252 class NonAAFillRectPerspectiveBatch : public GrVertexBatch { |
159 public: | 253 public: |
| 254 DEFINE_BATCH_CLASS_ID |
| 255 |
160 struct Geometry { | 256 struct Geometry { |
161 SkMatrix fViewMatrix; | 257 SkMatrix fViewMatrix; |
162 SkMatrix fLocalMatrix; | 258 SkMatrix fLocalMatrix; |
163 SkRect fRect; | 259 SkRect fRect; |
164 SkRect fLocalRect; | 260 SkRect fLocalRect; |
165 GrColor fColor; | 261 GrColor fColor; |
166 bool fHasLocalMatrix; | 262 bool fHasLocalMatrix; |
167 bool fHasLocalRect; | 263 bool fHasLocalRect; |
168 }; | 264 }; |
169 | 265 |
170 static const char* Name() { return "NonAAFillRectBatchPerspective"; } | 266 static NonAAFillRectPerspectiveBatch* Create() { return new NonAAFillRectPer
spectiveBatch; } |
| 267 |
| 268 const char* name() const override { return Name(); } |
| 269 |
| 270 SkString dumpInfo() const override { |
| 271 SkString str; |
| 272 str.appendf("# batched: %d\n", fGeoData.count()); |
| 273 for (int i = 0; i < fGeoData.count(); ++i) { |
| 274 str.append(DumpInfo(fGeoData[i], i)); |
| 275 } |
| 276 str.append(INHERITED::dumpInfo()); |
| 277 return str; |
| 278 } |
| 279 |
| 280 void computePipelineOptimizations(GrInitInvariantOutput* color, |
| 281 GrInitInvariantOutput* coverage, |
| 282 GrBatchToXPOverrides* overrides) const ove
rride { |
| 283 // When this is called on a batch, there is only one geometry bundle |
| 284 color->setKnownFourComponents(fGeoData[0].fColor); |
| 285 InitInvariantOutputCoverage(coverage); |
| 286 } |
| 287 |
| 288 void initBatchTracker(const GrXPOverridesForBatch& overrides) override { |
| 289 overrides.getOverrideColorIfSet(&fGeoData[0].fColor); |
| 290 fOverrides = overrides; |
| 291 } |
| 292 |
| 293 SkSTArray<1, Geometry, true>* geoData() { return &fGeoData; } |
| 294 |
| 295 // After seeding, the client should call init() so the Batch can initialize
itself |
| 296 void init() { |
| 297 const Geometry& geo = fGeoData[0]; |
| 298 SetBounds(geo, &fBounds); |
| 299 } |
| 300 |
| 301 void updateBoundsAfterAppend() { |
| 302 const Geometry& geo = fGeoData.back(); |
| 303 UpdateBoundsAfterAppend(geo, &fBounds); |
| 304 } |
| 305 |
| 306 private: |
| 307 static const char* Name() { return "NonAAFillRectPerspectiveBatch"; } |
171 | 308 |
172 static SkString DumpInfo(const Geometry& geo, int index) { | 309 static SkString DumpInfo(const Geometry& geo, int index) { |
173 SkString str; | 310 SkString str; |
174 str.appendf("%d: Color: 0x%08x, Rect [L: %.2f, T: %.2f, R: %.2f, B: %.2f
]\n", | 311 str.appendf("%d: Color: 0x%08x, Rect [L: %.2f, T: %.2f, R: %.2f, B: %.2f
]\n", |
175 index, | 312 index, |
176 geo.fColor, | 313 geo.fColor, |
177 geo.fRect.fLeft, geo.fRect.fTop, geo.fRect.fRight, geo.fRect
.fBottom); | 314 geo.fRect.fLeft, geo.fRect.fTop, geo.fRect.fRight, geo.fRect
.fBottom); |
178 return str; | 315 return str; |
179 } | 316 } |
180 | 317 |
(...skipping 20 matching lines...) Expand all Loading... |
201 | 338 |
202 static void Tesselate(intptr_t vertices, size_t vertexStride, const Geometry
& geo, | 339 static void Tesselate(intptr_t vertices, size_t vertexStride, const Geometry
& geo, |
203 const GrXPOverridesForBatch& overrides) { | 340 const GrXPOverridesForBatch& overrides) { |
204 if (geo.fHasLocalRect) { | 341 if (geo.fHasLocalRect) { |
205 GrQuad quad(geo.fLocalRect); | 342 GrQuad quad(geo.fLocalRect); |
206 tesselate(vertices, vertexStride, geo.fColor, geo.fViewMatrix, geo.f
Rect, &quad); | 343 tesselate(vertices, vertexStride, geo.fColor, geo.fViewMatrix, geo.f
Rect, &quad); |
207 } else { | 344 } else { |
208 tesselate(vertices, vertexStride, geo.fColor, geo.fViewMatrix, geo.f
Rect, nullptr); | 345 tesselate(vertices, vertexStride, geo.fColor, geo.fViewMatrix, geo.f
Rect, nullptr); |
209 } | 346 } |
210 } | 347 } |
| 348 |
| 349 static void InitInvariantOutputCoverage(GrInitInvariantOutput* out) { |
| 350 out->setKnownSingleComponent(0xff); |
| 351 } |
| 352 |
| 353 static const GrBuffer* GetIndexBuffer(GrResourceProvider* rp) { |
| 354 return rp->refQuadIndexBuffer(); |
| 355 } |
| 356 |
| 357 static void SetBounds(const Geometry& geo, SkRect* outBounds) { |
| 358 geo.fViewMatrix.mapRect(outBounds, geo.fRect); |
| 359 } |
| 360 |
| 361 static void UpdateBoundsAfterAppend(const Geometry& geo, SkRect* outBounds)
{ |
| 362 SkRect bounds = geo.fRect; |
| 363 geo.fViewMatrix.mapRect(&bounds); |
| 364 outBounds->join(bounds); |
| 365 } |
| 366 |
| 367 NonAAFillRectPerspectiveBatch() : INHERITED(ClassID()) {} |
| 368 |
| 369 void onPrepareDraws(Target* target) const override { |
| 370 sk_sp<GrGeometryProcessor> gp(MakeGP(this->seedGeometry(), fOverrides)); |
| 371 if (!gp) { |
| 372 SkDebugf("Couldn't create GrGeometryProcessor\n"); |
| 373 return; |
| 374 } |
| 375 |
| 376 size_t vertexStride = gp->getVertexStride(); |
| 377 int instanceCount = fGeoData.count(); |
| 378 |
| 379 SkAutoTUnref<const GrBuffer> indexBuffer(GetIndexBuffer(target->resource
Provider())); |
| 380 InstancedHelper helper; |
| 381 void* vertices = helper.init(target, kTriangles_GrPrimitiveType, vertexS
tride, |
| 382 indexBuffer, kVertsPerInstance, |
| 383 kIndicesPerInstance, instanceCount); |
| 384 if (!vertices || !indexBuffer) { |
| 385 SkDebugf("Could not allocate vertices\n"); |
| 386 return; |
| 387 } |
| 388 |
| 389 for (int i = 0; i < instanceCount; i++) { |
| 390 intptr_t verts = reinterpret_cast<intptr_t>(vertices) + |
| 391 i * kVertsPerInstance * vertexStride; |
| 392 Tesselate(verts, vertexStride, fGeoData[i], fOverrides); |
| 393 } |
| 394 helper.recordDraw(target, gp.get()); |
| 395 } |
| 396 |
| 397 const Geometry& seedGeometry() const { return fGeoData[0]; } |
| 398 |
| 399 bool onCombineIfPossible(GrBatch* t, const GrCaps& caps) override { |
| 400 NonAAFillRectPerspectiveBatch* that = t->cast<NonAAFillRectPerspectiveBa
tch>(); |
| 401 if (!GrPipeline::CanCombine(*this->pipeline(), this->bounds(), *that->pi
peline(), |
| 402 that->bounds(), caps)) { |
| 403 return false; |
| 404 } |
| 405 |
| 406 if (!CanCombine(this->seedGeometry(), that->seedGeometry(), fOverrides))
{ |
| 407 return false; |
| 408 } |
| 409 |
| 410 // In the event of two batches, one who can tweak, one who cannot, we ju
st fall back to |
| 411 // not tweaking |
| 412 if (fOverrides.canTweakAlphaForCoverage() && !that->fOverrides.canTweakA
lphaForCoverage()) { |
| 413 fOverrides = that->fOverrides; |
| 414 } |
| 415 |
| 416 fGeoData.push_back_n(that->geoData()->count(), that->geoData()->begin())
; |
| 417 this->joinBounds(that->bounds()); |
| 418 return true; |
| 419 } |
| 420 |
| 421 GrXPOverridesForBatch fOverrides; |
| 422 SkSTArray<1, Geometry, true> fGeoData; |
| 423 |
| 424 typedef GrVertexBatch INHERITED; |
211 }; | 425 }; |
212 | 426 |
213 typedef GrTInstanceBatch<NonAAFillRectBatchImp> NonAAFillRectBatchSimple; | 427 inline static void append_to_batch(NonAAFillRectBatch* batch, GrColor color, |
214 typedef GrTInstanceBatch<NonAAFillRectBatchPerspectiveImp> NonAAFillRectBatchPer
spective; | |
215 | |
216 inline static void append_to_batch(NonAAFillRectBatchSimple* batch, GrColor colo
r, | |
217 const SkMatrix& viewMatrix, const SkRect& rec
t, | 428 const SkMatrix& viewMatrix, const SkRect& rec
t, |
218 const SkRect* localRect, const SkMatrix* loca
lMatrix) { | 429 const SkRect* localRect, const SkMatrix* loca
lMatrix) { |
219 SkASSERT(!viewMatrix.hasPerspective() && (!localMatrix || !localMatrix->hasP
erspective())); | 430 SkASSERT(!viewMatrix.hasPerspective() && (!localMatrix || !localMatrix->hasP
erspective())); |
220 NonAAFillRectBatchSimple::Geometry& geo = batch->geoData()->push_back(); | 431 NonAAFillRectBatch::Geometry& geo = batch->geoData()->push_back(); |
221 | 432 |
222 geo.fColor = color; | 433 geo.fColor = color; |
223 geo.fViewMatrix = viewMatrix; | 434 geo.fViewMatrix = viewMatrix; |
224 geo.fRect = rect; | 435 geo.fRect = rect; |
225 | 436 |
226 if (localRect && localMatrix) { | 437 if (localRect && localMatrix) { |
227 geo.fLocalQuad.setFromMappedRect(*localRect, *localMatrix); | 438 geo.fLocalQuad.setFromMappedRect(*localRect, *localMatrix); |
228 } else if (localRect) { | 439 } else if (localRect) { |
229 geo.fLocalQuad.set(*localRect); | 440 geo.fLocalQuad.set(*localRect); |
230 } else if (localMatrix) { | 441 } else if (localMatrix) { |
231 geo.fLocalQuad.setFromMappedRect(rect, *localMatrix); | 442 geo.fLocalQuad.setFromMappedRect(rect, *localMatrix); |
232 } else { | 443 } else { |
233 geo.fLocalQuad.set(rect); | 444 geo.fLocalQuad.set(rect); |
234 } | 445 } |
235 } | 446 } |
236 | 447 |
237 inline static void append_to_batch(NonAAFillRectBatchPerspective* batch, GrColor
color, | 448 inline static void append_to_batch(NonAAFillRectPerspectiveBatch* batch, GrColor
color, |
238 const SkMatrix& viewMatrix, const SkRect& rec
t, | 449 const SkMatrix& viewMatrix, const SkRect& rec
t, |
239 const SkRect* localRect, const SkMatrix* loca
lMatrix) { | 450 const SkRect* localRect, const SkMatrix* loca
lMatrix) { |
240 SkASSERT(viewMatrix.hasPerspective() || (localMatrix && localMatrix->hasPers
pective())); | 451 SkASSERT(viewMatrix.hasPerspective() || (localMatrix && localMatrix->hasPers
pective())); |
241 NonAAFillRectBatchPerspective::Geometry& geo = batch->geoData()->push_back()
; | 452 NonAAFillRectPerspectiveBatch::Geometry& geo = batch->geoData()->push_back()
; |
242 | 453 |
243 geo.fColor = color; | 454 geo.fColor = color; |
244 geo.fViewMatrix = viewMatrix; | 455 geo.fViewMatrix = viewMatrix; |
245 geo.fRect = rect; | 456 geo.fRect = rect; |
246 geo.fHasLocalRect = SkToBool(localRect); | 457 geo.fHasLocalRect = SkToBool(localRect); |
247 geo.fHasLocalMatrix = SkToBool(localMatrix); | 458 geo.fHasLocalMatrix = SkToBool(localMatrix); |
248 if (localMatrix) { | 459 if (localMatrix) { |
249 geo.fLocalMatrix = *localMatrix; | 460 geo.fLocalMatrix = *localMatrix; |
250 } | 461 } |
251 if (localRect) { | 462 if (localRect) { |
252 geo.fLocalRect = *localRect; | 463 geo.fLocalRect = *localRect; |
253 } | 464 } |
254 | 465 |
255 } | 466 } |
256 | 467 |
257 namespace GrNonAAFillRectBatch { | 468 namespace GrNonAAFillRectBatch { |
258 | 469 |
259 GrDrawBatch* Create(GrColor color, | 470 GrDrawBatch* Create(GrColor color, |
260 const SkMatrix& viewMatrix, | 471 const SkMatrix& viewMatrix, |
261 const SkRect& rect, | 472 const SkRect& rect, |
262 const SkRect* localRect, | 473 const SkRect* localRect, |
263 const SkMatrix* localMatrix) { | 474 const SkMatrix* localMatrix) { |
264 NonAAFillRectBatchSimple* batch = NonAAFillRectBatchSimple::Create(); | 475 NonAAFillRectBatch* batch = NonAAFillRectBatch::Create(); |
265 append_to_batch(batch, color, viewMatrix, rect, localRect, localMatrix); | 476 append_to_batch(batch, color, viewMatrix, rect, localRect, localMatrix); |
266 batch->init(); | 477 batch->init(); |
267 return batch; | 478 return batch; |
268 } | 479 } |
269 | 480 |
270 GrDrawBatch* CreateWithPerspective(GrColor color, | 481 GrDrawBatch* CreateWithPerspective(GrColor color, |
271 const SkMatrix& viewMatrix, | 482 const SkMatrix& viewMatrix, |
272 const SkRect& rect, | 483 const SkRect& rect, |
273 const SkRect* localRect, | 484 const SkRect* localRect, |
274 const SkMatrix* localMatrix) { | 485 const SkMatrix* localMatrix) { |
275 NonAAFillRectBatchPerspective* batch = NonAAFillRectBatchPerspective::Create
(); | 486 NonAAFillRectPerspectiveBatch* batch = NonAAFillRectPerspectiveBatch::Create
(); |
276 append_to_batch(batch, color, viewMatrix, rect, localRect, localMatrix); | 487 append_to_batch(batch, color, viewMatrix, rect, localRect, localMatrix); |
277 batch->init(); | 488 batch->init(); |
278 return batch; | 489 return batch; |
279 } | 490 } |
280 | 491 |
281 bool Append(GrBatch* origBatch, | 492 bool Append(GrBatch* origBatch, |
282 GrColor color, | 493 GrColor color, |
283 const SkMatrix& viewMatrix, | 494 const SkMatrix& viewMatrix, |
284 const SkRect& rect, | 495 const SkRect& rect, |
285 const SkRect* localRect, | 496 const SkRect* localRect, |
286 const SkMatrix* localMatrix) { | 497 const SkMatrix* localMatrix) { |
287 bool usePerspective = viewMatrix.hasPerspective() || | 498 bool usePerspective = viewMatrix.hasPerspective() || |
288 (localMatrix && localMatrix->hasPerspective()); | 499 (localMatrix && localMatrix->hasPerspective()); |
289 | 500 |
290 if (usePerspective && origBatch->classID() != NonAAFillRectBatchPerspective:
:ClassID()) { | 501 if (usePerspective && origBatch->classID() != NonAAFillRectPerspectiveBatch:
:ClassID()) { |
291 return false; | 502 return false; |
292 } | 503 } |
293 | 504 |
294 if (!usePerspective) { | 505 if (!usePerspective) { |
295 NonAAFillRectBatchSimple* batch = origBatch->cast<NonAAFillRectBatchSimp
le>(); | 506 NonAAFillRectBatch* batch = origBatch->cast<NonAAFillRectBatch>(); |
296 append_to_batch(batch, color, viewMatrix, rect, localRect, localMatrix); | 507 append_to_batch(batch, color, viewMatrix, rect, localRect, localMatrix); |
297 batch->updateBoundsAfterAppend(); | 508 batch->updateBoundsAfterAppend(); |
298 } else { | 509 } else { |
299 NonAAFillRectBatchPerspective* batch = origBatch->cast<NonAAFillRectBatc
hPerspective>(); | 510 NonAAFillRectPerspectiveBatch* batch = origBatch->cast<NonAAFillRectPers
pectiveBatch>(); |
300 const NonAAFillRectBatchPerspective::Geometry& geo = batch->geoData()->b
ack(); | 511 const NonAAFillRectPerspectiveBatch::Geometry& geo = batch->geoData()->b
ack(); |
301 | 512 |
302 if (!geo.fViewMatrix.cheapEqualTo(viewMatrix) || | 513 if (!geo.fViewMatrix.cheapEqualTo(viewMatrix) || |
303 geo.fHasLocalRect != SkToBool(localRect) || | 514 geo.fHasLocalRect != SkToBool(localRect) || |
304 geo.fHasLocalMatrix != SkToBool(localMatrix) || | 515 geo.fHasLocalMatrix != SkToBool(localMatrix) || |
305 (geo.fHasLocalMatrix && !geo.fLocalMatrix.cheapEqualTo(*localMatrix)
)) { | 516 (geo.fHasLocalMatrix && !geo.fLocalMatrix.cheapEqualTo(*localMatrix)
)) { |
306 return false; | 517 return false; |
307 } | 518 } |
308 | 519 |
309 append_to_batch(batch, color, viewMatrix, rect, localRect, localMatrix); | 520 append_to_batch(batch, color, viewMatrix, rect, localRect, localMatrix); |
310 batch->updateBoundsAfterAppend(); | 521 batch->updateBoundsAfterAppend(); |
(...skipping 18 matching lines...) Expand all Loading... |
329 SkMatrix localMatrix = GrTest::TestMatrix(random); | 540 SkMatrix localMatrix = GrTest::TestMatrix(random); |
330 | 541 |
331 bool hasLocalRect = random->nextBool(); | 542 bool hasLocalRect = random->nextBool(); |
332 bool hasLocalMatrix = random->nextBool(); | 543 bool hasLocalMatrix = random->nextBool(); |
333 return GrNonAAFillRectBatch::Create(color, viewMatrix, rect, | 544 return GrNonAAFillRectBatch::Create(color, viewMatrix, rect, |
334 hasLocalRect ? &localRect : nullptr, | 545 hasLocalRect ? &localRect : nullptr, |
335 hasLocalMatrix ? &localMatrix : nullptr)
; | 546 hasLocalMatrix ? &localMatrix : nullptr)
; |
336 } | 547 } |
337 | 548 |
338 #endif | 549 #endif |
OLD | NEW |