blob: 18a25e6f85f8f9108808b97010395a1f958b09e3 [file] [log] [blame]
epoger@google.comec3ed6a2011-07-28 14:26:00 +00001
reed@google.comac10a2d2010-12-22 21:39:39 +00002/*
epoger@google.comec3ed6a2011-07-28 14:26:00 +00003 * Copyright 2011 Google Inc.
4 *
5 * Use of this source code is governed by a BSD-style license that can be
6 * found in the LICENSE file.
reed@google.comac10a2d2010-12-22 21:39:39 +00007 */
8
9
10#include "GrInOrderDrawBuffer.h"
bsalomon@google.comded4f4b2012-06-28 18:48:06 +000011#include "GrBufferAllocPool.h"
12#include "GrGpu.h"
13#include "GrIndexBuffer.h"
14#include "GrPath.h"
bsalomon@google.com8f9cbd62011-12-09 15:55:34 +000015#include "GrRenderTarget.h"
reed@google.comac10a2d2010-12-22 21:39:39 +000016#include "GrTexture.h"
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000017#include "GrVertexBuffer.h"
reed@google.comac10a2d2010-12-22 21:39:39 +000018
bsalomon@google.com471d4712011-08-23 15:45:25 +000019GrInOrderDrawBuffer::GrInOrderDrawBuffer(const GrGpu* gpu,
20 GrVertexBufferAllocPool* vertexPool,
bsalomon@google.com25fb21f2011-06-21 18:17:25 +000021 GrIndexBufferAllocPool* indexPool)
bsalomon@google.com97805382012-03-13 14:32:07 +000022 : fAutoFlushTarget(NULL)
23 , fClipSet(true)
robertphillips@google.com69705572012-03-21 19:46:50 +000024 , fVertexPool(*vertexPool)
25 , fIndexPool(*indexPool)
bsalomon@google.com25fb21f2011-06-21 18:17:25 +000026 , fLastRectVertexLayout(0)
27 , fQuadIndexBuffer(NULL)
28 , fMaxQuads(0)
robertphillips@google.comc82a8b72012-06-21 20:15:48 +000029 , fFlushing(false) {
bsalomon@google.com18c9c192011-09-22 21:01:31 +000030
31 fCaps = gpu->getCaps();
32
bsalomon@google.com1c13c962011-02-14 16:51:21 +000033 GrAssert(NULL != vertexPool);
34 GrAssert(NULL != indexPool);
bsalomon@google.com25fb21f2011-06-21 18:17:25 +000035
36 GeometryPoolState& poolState = fGeoPoolStateStack.push_back();
37 poolState.fUsedPoolVertexBytes = 0;
38 poolState.fUsedPoolIndexBytes = 0;
39#if GR_DEBUG
40 poolState.fPoolVertexBuffer = (GrVertexBuffer*)~0;
41 poolState.fPoolStartVertex = ~0;
42 poolState.fPoolIndexBuffer = (GrIndexBuffer*)~0;
43 poolState.fPoolStartIndex = ~0;
44#endif
bsalomon@google.coma4f6b102012-06-26 21:04:22 +000045 this->reset();
reed@google.comac10a2d2010-12-22 21:39:39 +000046}
47
48GrInOrderDrawBuffer::~GrInOrderDrawBuffer() {
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000049 this->reset();
bsalomon@google.com4a018bb2011-10-28 19:50:21 +000050 // This must be called by before the GrDrawTarget destructor
51 this->releaseGeometry();
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000052 GrSafeUnref(fQuadIndexBuffer);
bsalomon@google.com97805382012-03-13 14:32:07 +000053 GrSafeUnref(fAutoFlushTarget);
reed@google.comac10a2d2010-12-22 21:39:39 +000054}
55
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000056void GrInOrderDrawBuffer::setQuadIndexBuffer(const GrIndexBuffer* indexBuffer) {
57 bool newIdxBuffer = fQuadIndexBuffer != indexBuffer;
58 if (newIdxBuffer) {
59 GrSafeUnref(fQuadIndexBuffer);
60 fQuadIndexBuffer = indexBuffer;
61 GrSafeRef(fQuadIndexBuffer);
62 fCurrQuad = 0;
63 fMaxQuads = (NULL == indexBuffer) ? 0 : indexBuffer->maxQuads();
64 } else {
bsalomon@google.comd302f142011-03-03 13:54:13 +000065 GrAssert((NULL == indexBuffer && 0 == fMaxQuads) ||
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000066 (indexBuffer->maxQuads() == fMaxQuads));
67 }
68}
69
bsalomon@google.com934c5702012-03-20 21:17:58 +000070////////////////////////////////////////////////////////////////////////////////
71
72void GrInOrderDrawBuffer::resetDrawTracking() {
73 fCurrQuad = 0;
74 fInstancedDrawTracker.reset();
75}
76
bsalomon@google.comd302f142011-03-03 13:54:13 +000077void GrInOrderDrawBuffer::drawRect(const GrRect& rect,
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000078 const GrMatrix* matrix,
bsalomon@google.com39ee0ff2011-12-06 15:32:52 +000079 StageMask stageMask,
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000080 const GrRect* srcRects[],
81 const GrMatrix* srcMatrices[]) {
bsalomon@google.comd302f142011-03-03 13:54:13 +000082
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000083 GrAssert(!(NULL == fQuadIndexBuffer && fCurrQuad));
84 GrAssert(!(fDraws.empty() && fCurrQuad));
85 GrAssert(!(0 != fMaxQuads && NULL == fQuadIndexBuffer));
86
bsalomon@google.com8f9cbd62011-12-09 15:55:34 +000087 GrDrawState* drawState = this->drawState();
88
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000089 // if we have a quad IB then either append to the previous run of
90 // rects or start a new run
91 if (fMaxQuads) {
bsalomon@google.comd302f142011-03-03 13:54:13 +000092
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000093 bool appendToPreviousDraw = false;
bsalomon@google.com39ee0ff2011-12-06 15:32:52 +000094 GrVertexLayout layout = GetRectVertexLayout(stageMask, srcRects);
bsalomon@google.com86afc2a2011-02-16 16:12:19 +000095 AutoReleaseGeometry geo(this, layout, 4, 0);
bsalomon@google.com6513cd02011-08-05 20:12:30 +000096 if (!geo.succeeded()) {
97 GrPrintf("Failed to get space for vertices!\n");
98 return;
99 }
bsalomon@google.com8f9cbd62011-12-09 15:55:34 +0000100 GrMatrix combinedMatrix = drawState->getViewMatrix();
bsalomon@google.com3f5a95e2012-03-08 16:41:42 +0000101 // We go to device space so that matrix changes allow us to concat
102 // rect draws. When the caller has provided explicit source rects
103 // then we don't want to modify the sampler matrices. Otherwise we do
104 // we have to account for the view matrix change in the sampler
105 // matrices.
106 StageMask devCoordMask = (NULL == srcRects) ? stageMask : 0;
107 GrDrawTarget::AutoDeviceCoordDraw adcd(this, devCoordMask);
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000108 if (NULL != matrix) {
109 combinedMatrix.preConcat(*matrix);
110 }
111
112 SetRectVertices(rect, &combinedMatrix, srcRects, srcMatrices, layout, geo.vertices());
113
114 // we don't want to miss an opportunity to batch rects together
115 // simply because the clip has changed if the clip doesn't affect
116 // the rect.
117 bool disabledClip = false;
bsalomon@google.com8f9cbd62011-12-09 15:55:34 +0000118 if (drawState->isClipState() && fClip.isRect()) {
bsalomon@google.comd302f142011-03-03 13:54:13 +0000119
bsalomon@google.com0b50b2e2011-03-08 21:07:21 +0000120 GrRect clipRect = fClip.getRect(0);
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000121 // If the clip rect touches the edge of the viewport, extended it
122 // out (close) to infinity to avoid bogus intersections.
bsalomon@google.comd302f142011-03-03 13:54:13 +0000123 // We might consider a more exact clip to viewport if this
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000124 // conservative test fails.
bsalomon@google.com8f9cbd62011-12-09 15:55:34 +0000125 const GrRenderTarget* target = drawState->getRenderTarget();
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000126 if (0 >= clipRect.fLeft) {
127 clipRect.fLeft = GR_ScalarMin;
128 }
129 if (target->width() <= clipRect.fRight) {
130 clipRect.fRight = GR_ScalarMax;
131 }
132 if (0 >= clipRect.top()) {
133 clipRect.fTop = GR_ScalarMin;
134 }
135 if (target->height() <= clipRect.fBottom) {
136 clipRect.fBottom = GR_ScalarMax;
137 }
138 int stride = VertexSize(layout);
139 bool insideClip = true;
140 for (int v = 0; v < 4; ++v) {
141 const GrPoint& p = *GetVertexPoint(geo.vertices(), v, stride);
142 if (!clipRect.contains(p)) {
143 insideClip = false;
144 break;
145 }
146 }
147 if (insideClip) {
bsalomon@google.com8f9cbd62011-12-09 15:55:34 +0000148 drawState->disableState(GrDrawState::kClip_StateBit);
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000149 disabledClip = true;
150 }
151 }
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000152 if (!this->needsNewClip() &&
153 !this->needsNewState() &&
154 fCurrQuad > 0 &&
155 fCurrQuad < fMaxQuads &&
156 layout == fLastRectVertexLayout) {
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000157
158 int vsize = VertexSize(layout);
bsalomon@google.comd302f142011-03-03 13:54:13 +0000159
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000160 Draw& lastDraw = fDraws.back();
161
162 GrAssert(lastDraw.fIndexBuffer == fQuadIndexBuffer);
bsalomon@google.com47059542012-06-06 20:51:20 +0000163 GrAssert(kTriangles_GrPrimitiveType == lastDraw.fPrimitiveType);
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000164 GrAssert(0 == lastDraw.fVertexCount % 4);
165 GrAssert(0 == lastDraw.fIndexCount % 6);
166 GrAssert(0 == lastDraw.fStartIndex);
167
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000168 GeometryPoolState& poolState = fGeoPoolStateStack.back();
bsalomon@google.com6aa25c32011-04-27 19:55:29 +0000169
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000170 appendToPreviousDraw =
171 kDraw_Cmd != fCmds.back() &&
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000172 lastDraw.fVertexBuffer == poolState.fPoolVertexBuffer &&
173 (fCurrQuad * 4 + lastDraw.fStartVertex) == poolState.fPoolStartVertex;
174
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000175 if (appendToPreviousDraw) {
176 lastDraw.fVertexCount += 4;
177 lastDraw.fIndexCount += 6;
178 fCurrQuad += 1;
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000179 // we reserved above, so we should be the first
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000180 // use of this vertex reservation.
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000181 GrAssert(0 == poolState.fUsedPoolVertexBytes);
182 poolState.fUsedPoolVertexBytes = 4 * vsize;
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000183 }
184 }
185 if (!appendToPreviousDraw) {
186 this->setIndexSourceToBuffer(fQuadIndexBuffer);
bsalomon@google.com47059542012-06-06 20:51:20 +0000187 this->drawIndexed(kTriangles_GrPrimitiveType, 0, 0, 4, 6);
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000188 fCurrQuad = 1;
189 fLastRectVertexLayout = layout;
190 }
191 if (disabledClip) {
bsalomon@google.com8f9cbd62011-12-09 15:55:34 +0000192 drawState->enableState(GrDrawState::kClip_StateBit);
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000193 }
bsalomon@google.com934c5702012-03-20 21:17:58 +0000194 fInstancedDrawTracker.reset();
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000195 } else {
bsalomon@google.com39ee0ff2011-12-06 15:32:52 +0000196 INHERITED::drawRect(rect, matrix, stageMask, srcRects, srcMatrices);
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000197 }
198}
199
bsalomon@google.com934c5702012-03-20 21:17:58 +0000200void GrInOrderDrawBuffer::drawIndexedInstances(GrPrimitiveType type,
201 int instanceCount,
202 int verticesPerInstance,
203 int indicesPerInstance) {
204 if (!verticesPerInstance || !indicesPerInstance) {
205 return;
206 }
207
208 const GeometrySrcState& geomSrc = this->getGeomSrc();
209
210 // we only attempt to concat the case when reserved verts are used with
211 // an index buffer.
212 if (kReserved_GeometrySrcType == geomSrc.fVertexSrc &&
213 kBuffer_GeometrySrcType == geomSrc.fIndexSrc) {
214
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000215 if (this->needsNewClip()) {
216 this->recordClip();
217 }
218 if (this->needsNewState()) {
219 this->recordState();
220 }
221
bsalomon@google.com934c5702012-03-20 21:17:58 +0000222 Draw* draw = NULL;
223 // if the last draw used the same indices/vertices per shape then we
224 // may be able to append to it.
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000225 if (kDraw_Cmd == fCmds.back() &&
226 verticesPerInstance == fInstancedDrawTracker.fVerticesPerInstance &&
bsalomon@google.com934c5702012-03-20 21:17:58 +0000227 indicesPerInstance == fInstancedDrawTracker.fIndicesPerInstance) {
228 GrAssert(fDraws.count());
229 draw = &fDraws.back();
230 }
231
bsalomon@google.com934c5702012-03-20 21:17:58 +0000232 GeometryPoolState& poolState = fGeoPoolStateStack.back();
233 const GrVertexBuffer* vertexBuffer = poolState.fPoolVertexBuffer;
234
235 // Check whether the draw is compatible with this draw in order to
236 // append
237 if (NULL == draw ||
bsalomon@google.com934c5702012-03-20 21:17:58 +0000238 draw->fIndexBuffer != geomSrc.fIndexBuffer ||
239 draw->fPrimitiveType != type ||
240 draw->fVertexBuffer != vertexBuffer) {
241
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000242 draw = this->recordDraw();
bsalomon@google.com934c5702012-03-20 21:17:58 +0000243 draw->fIndexBuffer = geomSrc.fIndexBuffer;
244 geomSrc.fIndexBuffer->ref();
245 draw->fVertexBuffer = vertexBuffer;
246 vertexBuffer->ref();
247 draw->fPrimitiveType = type;
248 draw->fStartIndex = 0;
249 draw->fIndexCount = 0;
250 draw->fStartVertex = poolState.fPoolStartVertex;
251 draw->fVertexCount = 0;
252 draw->fVertexLayout = geomSrc.fVertexLayout;
253 } else {
254 GrAssert(!(draw->fIndexCount % indicesPerInstance));
255 GrAssert(!(draw->fVertexCount % verticesPerInstance));
256 GrAssert(poolState.fPoolStartVertex == draw->fStartVertex +
257 draw->fVertexCount);
258 }
259
260 // how many instances can be in a single draw
261 int maxInstancesPerDraw = this->indexCountInCurrentSource() /
262 indicesPerInstance;
263 if (!maxInstancesPerDraw) {
264 return;
265 }
266 // how many instances should be concat'ed onto draw
267 int instancesToConcat = maxInstancesPerDraw - draw->fVertexCount /
268 verticesPerInstance;
269 if (maxInstancesPerDraw > instanceCount) {
270 maxInstancesPerDraw = instanceCount;
271 if (instancesToConcat > instanceCount) {
272 instancesToConcat = instanceCount;
273 }
274 }
275
276 // update the amount of reserved data actually referenced in draws
277 size_t vertexBytes = instanceCount * verticesPerInstance *
278 VertexSize(draw->fVertexLayout);
279 poolState.fUsedPoolVertexBytes =
280 GrMax(poolState.fUsedPoolVertexBytes, vertexBytes);
281
282 while (instanceCount) {
283 if (!instancesToConcat) {
284 int startVertex = draw->fStartVertex + draw->fVertexCount;
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000285 draw = this->recordDraw();
bsalomon@google.com934c5702012-03-20 21:17:58 +0000286 draw->fIndexBuffer = geomSrc.fIndexBuffer;
287 geomSrc.fIndexBuffer->ref();
288 draw->fVertexBuffer = vertexBuffer;
289 vertexBuffer->ref();
290 draw->fPrimitiveType = type;
291 draw->fStartIndex = 0;
292 draw->fStartVertex = startVertex;
293 draw->fVertexCount = 0;
294 draw->fVertexLayout = geomSrc.fVertexLayout;
295 instancesToConcat = maxInstancesPerDraw;
296 }
297 draw->fVertexCount += instancesToConcat * verticesPerInstance;
298 draw->fIndexCount += instancesToConcat * indicesPerInstance;
299 instanceCount -= instancesToConcat;
300 instancesToConcat = 0;
301 }
302
303 // update draw tracking for next draw
304 fCurrQuad = 0;
305 fInstancedDrawTracker.fVerticesPerInstance = verticesPerInstance;
306 fInstancedDrawTracker.fIndicesPerInstance = indicesPerInstance;
307 } else {
308 this->INHERITED::drawIndexedInstances(type,
309 instanceCount,
310 verticesPerInstance,
311 indicesPerInstance);
312 }
313
314}
315
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000316void GrInOrderDrawBuffer::onDrawIndexed(GrPrimitiveType primitiveType,
317 int startVertex,
318 int startIndex,
319 int vertexCount,
320 int indexCount) {
reed@google.comac10a2d2010-12-22 21:39:39 +0000321
322 if (!vertexCount || !indexCount) {
323 return;
324 }
325
bsalomon@google.com934c5702012-03-20 21:17:58 +0000326 this->resetDrawTracking();
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000327
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000328 GeometryPoolState& poolState = fGeoPoolStateStack.back();
329
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000330 if (this->needsNewClip()) {
331 this->recordClip();
332 }
333 if (this->needsNewState()) {
334 this->recordState();
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000335 }
336
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000337 Draw* draw = this->recordDraw();
reed@google.comac10a2d2010-12-22 21:39:39 +0000338
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000339 draw->fPrimitiveType = primitiveType;
340 draw->fStartVertex = startVertex;
341 draw->fStartIndex = startIndex;
342 draw->fVertexCount = vertexCount;
343 draw->fIndexCount = indexCount;
344
345 draw->fVertexLayout = this->getVertexLayout();
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000346 switch (this->getGeomSrc().fVertexSrc) {
reed@google.comac10a2d2010-12-22 21:39:39 +0000347 case kBuffer_GeometrySrcType:
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000348 draw->fVertexBuffer = this->getGeomSrc().fVertexBuffer;
reed@google.comac10a2d2010-12-22 21:39:39 +0000349 break;
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000350 case kReserved_GeometrySrcType: // fallthrough
351 case kArray_GeometrySrcType: {
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000352 size_t vertexBytes = (vertexCount + startVertex) *
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000353 VertexSize(draw->fVertexLayout);
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000354 poolState.fUsedPoolVertexBytes =
355 GrMax(poolState.fUsedPoolVertexBytes, vertexBytes);
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000356 draw->fVertexBuffer = poolState.fPoolVertexBuffer;
357 draw->fStartVertex += poolState.fPoolStartVertex;
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000358 break;
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000359 }
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000360 default:
361 GrCrash("unknown geom src type");
reed@google.comac10a2d2010-12-22 21:39:39 +0000362 }
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000363 draw->fVertexBuffer->ref();
reed@google.comac10a2d2010-12-22 21:39:39 +0000364
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000365 switch (this->getGeomSrc().fIndexSrc) {
reed@google.comac10a2d2010-12-22 21:39:39 +0000366 case kBuffer_GeometrySrcType:
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000367 draw->fIndexBuffer = this->getGeomSrc().fIndexBuffer;
reed@google.comac10a2d2010-12-22 21:39:39 +0000368 break;
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000369 case kReserved_GeometrySrcType: // fallthrough
370 case kArray_GeometrySrcType: {
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000371 size_t indexBytes = (indexCount + startIndex) * sizeof(uint16_t);
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000372 poolState.fUsedPoolIndexBytes =
373 GrMax(poolState.fUsedPoolIndexBytes, indexBytes);
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000374 draw->fIndexBuffer = poolState.fPoolIndexBuffer;
375 draw->fStartIndex += poolState.fPoolStartIndex;
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000376 break;
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000377 }
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000378 default:
379 GrCrash("unknown geom src type");
reed@google.comac10a2d2010-12-22 21:39:39 +0000380 }
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000381 draw->fIndexBuffer->ref();
reed@google.comac10a2d2010-12-22 21:39:39 +0000382}
383
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000384void GrInOrderDrawBuffer::onDrawNonIndexed(GrPrimitiveType primitiveType,
385 int startVertex,
386 int vertexCount) {
reed@google.comac10a2d2010-12-22 21:39:39 +0000387 if (!vertexCount) {
388 return;
389 }
390
bsalomon@google.com934c5702012-03-20 21:17:58 +0000391 this->resetDrawTracking();
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000392
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000393 GeometryPoolState& poolState = fGeoPoolStateStack.back();
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000394 if (this->needsNewClip()) {
395 this->recordClip();
396 }
397 if (this->needsNewState()) {
398 this->recordState();
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000399 }
400
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000401 Draw* draw = this->recordDraw();
402 draw->fPrimitiveType = primitiveType;
403 draw->fStartVertex = startVertex;
404 draw->fStartIndex = 0;
405 draw->fVertexCount = vertexCount;
406 draw->fIndexCount = 0;
reed@google.comac10a2d2010-12-22 21:39:39 +0000407
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000408 draw->fVertexLayout = this->getVertexLayout();
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000409 switch (this->getGeomSrc().fVertexSrc) {
reed@google.comac10a2d2010-12-22 21:39:39 +0000410 case kBuffer_GeometrySrcType:
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000411 draw->fVertexBuffer = this->getGeomSrc().fVertexBuffer;
reed@google.comac10a2d2010-12-22 21:39:39 +0000412 break;
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000413 case kReserved_GeometrySrcType: // fallthrough
414 case kArray_GeometrySrcType: {
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000415 size_t vertexBytes = (vertexCount + startVertex) *
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000416 VertexSize(draw->fVertexLayout);
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000417 poolState.fUsedPoolVertexBytes =
418 GrMax(poolState.fUsedPoolVertexBytes, vertexBytes);
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000419 draw->fVertexBuffer = poolState.fPoolVertexBuffer;
420 draw->fStartVertex += poolState.fPoolStartVertex;
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000421 break;
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000422 }
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000423 default:
424 GrCrash("unknown geom src type");
reed@google.comac10a2d2010-12-22 21:39:39 +0000425 }
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000426 draw->fVertexBuffer->ref();
427 draw->fIndexBuffer = NULL;
reed@google.comac10a2d2010-12-22 21:39:39 +0000428}
429
bsalomon@google.comded4f4b2012-06-28 18:48:06 +0000430void GrInOrderDrawBuffer::onStencilPath(const GrPath* path, GrPathFill fill) {
431 if (this->needsNewClip()) {
432 this->recordClip();
433 }
434 // Only compare the subset of GrDrawState relevant to path stenciling?
435 if (this->needsNewState()) {
436 this->recordState();
437 }
438 StencilPath* sp = this->recordStencilPath();
439 sp->fPath.reset(path);
440 path->ref();
441 sp->fFill = fill;
bsalomon@google.com64aef2b2012-06-11 15:36:13 +0000442}
443
robertphillips@google.comc82a8b72012-06-21 20:15:48 +0000444void GrInOrderDrawBuffer::clear(const GrIRect* rect,
445 GrColor color,
446 GrRenderTarget* renderTarget) {
bsalomon@google.com6aa25c32011-04-27 19:55:29 +0000447 GrIRect r;
448 if (NULL == rect) {
449 // We could do something smart and remove previous draws and clears to
450 // the current render target. If we get that smart we have to make sure
451 // those draws aren't read before this clear (render-to-texture).
452 r.setLTRB(0, 0,
bsalomon@google.com8f9cbd62011-12-09 15:55:34 +0000453 this->getDrawState().getRenderTarget()->width(),
454 this->getDrawState().getRenderTarget()->height());
bsalomon@google.com6aa25c32011-04-27 19:55:29 +0000455 rect = &r;
456 }
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000457 Clear* clr = this->recordClear();
458 clr->fColor = color;
459 clr->fRect = *rect;
460 clr->fRenderTarget = renderTarget;
461 GrSafeRef(clr->fRenderTarget);
bsalomon@google.com0b335c12011-04-25 19:17:44 +0000462}
463
reed@google.comac10a2d2010-12-22 21:39:39 +0000464void GrInOrderDrawBuffer::reset() {
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000465 GrAssert(1 == fGeoPoolStateStack.count());
466 this->resetVertexSource();
467 this->resetIndexSource();
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000468 int numDraws = fDraws.count();
469 for (int d = 0; d < numDraws; ++d) {
470 // we always have a VB, but not always an IB
471 GrAssert(NULL != fDraws[d].fVertexBuffer);
472 fDraws[d].fVertexBuffer->unref();
473 GrSafeUnref(fDraws[d].fIndexBuffer);
474 }
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000475 fCmds.reset();
reed@google.comac10a2d2010-12-22 21:39:39 +0000476 fDraws.reset();
bsalomon@google.comded4f4b2012-06-28 18:48:06 +0000477 fStencilPaths.reset();
reed@google.comac10a2d2010-12-22 21:39:39 +0000478 fStates.reset();
bsalomon@google.com0b335c12011-04-25 19:17:44 +0000479 fClears.reset();
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000480 fVertexPool.reset();
481 fIndexPool.reset();
reed@google.comac10a2d2010-12-22 21:39:39 +0000482 fClips.reset();
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000483 fClipSet = true;
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000484
bsalomon@google.com934c5702012-03-20 21:17:58 +0000485 this->resetDrawTracking();
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000486
487 // we start off with a default clip and state so that we don't have
488 // to do count checks on fClips, fStates, or fCmds before checking their
489 // last entry.
490 this->recordDefaultState();
491 this->recordDefaultClip();
reed@google.comac10a2d2010-12-22 21:39:39 +0000492}
493
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000494bool GrInOrderDrawBuffer::playback(GrDrawTarget* target) {
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000495 GrAssert(kReserved_GeometrySrcType != this->getGeomSrc().fVertexSrc);
496 GrAssert(kReserved_GeometrySrcType != this->getGeomSrc().fIndexSrc);
bsalomon@google.com3f5a95e2012-03-08 16:41:42 +0000497
reed@google.comac10a2d2010-12-22 21:39:39 +0000498 GrAssert(NULL != target);
499 GrAssert(target != this); // not considered and why?
500
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000501 int numCmds = fCmds.count();
502 GrAssert(numCmds >= 2);
503 if (2 == numCmds) {
504 GrAssert(kSetState_Cmd == fCmds[0]);
505 GrAssert(kSetClip_Cmd == fCmds[1]);
506 return false;
reed@google.comac10a2d2010-12-22 21:39:39 +0000507 }
508
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000509 fVertexPool.unlock();
510 fIndexPool.unlock();
reed@google.comac10a2d2010-12-22 21:39:39 +0000511
reed@google.comac10a2d2010-12-22 21:39:39 +0000512 GrDrawTarget::AutoClipRestore acr(target);
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000513 AutoGeometryPush agp(target);
bsalomon@google.coma5d056a2012-03-27 15:59:58 +0000514 GrDrawState* prevDrawState = target->drawState();
515 prevDrawState->ref();
reed@google.comac10a2d2010-12-22 21:39:39 +0000516
bsalomon@google.comded4f4b2012-06-28 18:48:06 +0000517 int currState = 0;
518 int currClip = 0;
519 int currClear = 0;
520 int currDraw = 0;
521 int currStencilPath = 0;
reed@google.comac10a2d2010-12-22 21:39:39 +0000522
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000523 for (int c = 0; c < numCmds; ++c) {
524 switch (fCmds[c]) {
525 case kDraw_Cmd: {
526 const Draw& draw = fDraws[currDraw];
527 target->setVertexSourceToBuffer(draw.fVertexLayout, draw.fVertexBuffer);
528 if (draw.fIndexCount) {
529 target->setIndexSourceToBuffer(draw.fIndexBuffer);
530 }
bsalomon@google.com0b335c12011-04-25 19:17:44 +0000531
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000532 if (draw.fIndexCount) {
533 target->drawIndexed(draw.fPrimitiveType,
534 draw.fStartVertex,
535 draw.fStartIndex,
536 draw.fVertexCount,
537 draw.fIndexCount);
538 } else {
539 target->drawNonIndexed(draw.fPrimitiveType,
540 draw.fStartVertex,
541 draw.fVertexCount);
542 }
543 ++currDraw;
544 break;
545 }
bsalomon@google.comded4f4b2012-06-28 18:48:06 +0000546 case kStencilPath_Cmd: {
547 const StencilPath& sp = fStencilPaths[currStencilPath];
548 target->stencilPath(sp.fPath.get(), sp.fFill);
549 ++currStencilPath;
550 break;
551 }
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000552 case kSetState_Cmd:
553 target->setDrawState(&fStates[currState]);
554 ++currState;
555 break;
556 case kSetClip_Cmd:
557 target->setClip(fClips[currClip]);
558 ++currClip;
559 break;
560 case kClear_Cmd:
561 target->clear(&fClears[currClear].fRect,
562 fClears[currClear].fColor,
563 fClears[currClear].fRenderTarget);
564 ++currClear;
565 break;
reed@google.comac10a2d2010-12-22 21:39:39 +0000566 }
567 }
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000568 // we should have consumed all the states, clips, etc.
569 GrAssert(fStates.count() == currState);
570 GrAssert(fClips.count() == currClip);
571 GrAssert(fClears.count() == currClear);
572 GrAssert(fDraws.count() == currDraw);
573
bsalomon@google.coma5d056a2012-03-27 15:59:58 +0000574 target->setDrawState(prevDrawState);
575 prevDrawState->unref();
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000576 return true;
reed@google.comac10a2d2010-12-22 21:39:39 +0000577}
578
bsalomon@google.com97805382012-03-13 14:32:07 +0000579void GrInOrderDrawBuffer::setAutoFlushTarget(GrDrawTarget* target) {
580 GrSafeAssign(fAutoFlushTarget, target);
581}
582
583void GrInOrderDrawBuffer::willReserveVertexAndIndexSpace(
584 GrVertexLayout vertexLayout,
585 int vertexCount,
586 int indexCount) {
587 if (NULL != fAutoFlushTarget) {
588 // We use geometryHints() to know whether to flush the draw buffer. We
589 // can't flush if we are inside an unbalanced pushGeometrySource.
590 // Moreover, flushing blows away vertex and index data that was
591 // previously reserved. So if the vertex or index data is pulled from
592 // reserved space and won't be released by this request then we can't
593 // flush.
594 bool insideGeoPush = fGeoPoolStateStack.count() > 1;
595
596 bool unreleasedVertexSpace =
597 !vertexCount &&
598 kReserved_GeometrySrcType == this->getGeomSrc().fVertexSrc;
599
600 bool unreleasedIndexSpace =
601 !indexCount &&
602 kReserved_GeometrySrcType == this->getGeomSrc().fIndexSrc;
603
604 // we don't want to finalize any reserved geom on the target since
605 // we don't know that the client has finished writing to it.
606 bool targetHasReservedGeom =
607 fAutoFlushTarget->hasReservedVerticesOrIndices();
608
609 int vcount = vertexCount;
610 int icount = indexCount;
611
612 if (!insideGeoPush &&
613 !unreleasedVertexSpace &&
614 !unreleasedIndexSpace &&
615 !targetHasReservedGeom &&
616 this->geometryHints(vertexLayout, &vcount, &icount)) {
617
618 this->flushTo(fAutoFlushTarget);
619 }
620 }
621}
622
reed@google.comac10a2d2010-12-22 21:39:39 +0000623bool GrInOrderDrawBuffer::geometryHints(GrVertexLayout vertexLayout,
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000624 int* vertexCount,
625 int* indexCount) const {
626 // we will recommend a flush if the data could fit in a single
627 // preallocated buffer but none are left and it can't fit
628 // in the current buffer (which may not be prealloced).
reed@google.comac10a2d2010-12-22 21:39:39 +0000629 bool flush = false;
630 if (NULL != indexCount) {
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000631 int32_t currIndices = fIndexPool.currentBufferIndices();
632 if (*indexCount > currIndices &&
633 (!fIndexPool.preallocatedBuffersRemaining() &&
634 *indexCount <= fIndexPool.preallocatedBufferIndices())) {
635
636 flush = true;
637 }
638 *indexCount = currIndices;
reed@google.comac10a2d2010-12-22 21:39:39 +0000639 }
640 if (NULL != vertexCount) {
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000641 int32_t currVertices = fVertexPool.currentBufferVertices(vertexLayout);
642 if (*vertexCount > currVertices &&
643 (!fVertexPool.preallocatedBuffersRemaining() &&
644 *vertexCount <= fVertexPool.preallocatedBufferVertices(vertexLayout))) {
reed@google.comac10a2d2010-12-22 21:39:39 +0000645
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000646 flush = true;
reed@google.comac10a2d2010-12-22 21:39:39 +0000647 }
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000648 *vertexCount = currVertices;
reed@google.comac10a2d2010-12-22 21:39:39 +0000649 }
650 return flush;
651}
652
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000653bool GrInOrderDrawBuffer::onReserveVertexSpace(GrVertexLayout vertexLayout,
654 int vertexCount,
655 void** vertices) {
656 GeometryPoolState& poolState = fGeoPoolStateStack.back();
657 GrAssert(vertexCount > 0);
658 GrAssert(NULL != vertices);
659 GrAssert(0 == poolState.fUsedPoolVertexBytes);
660
661 *vertices = fVertexPool.makeSpace(vertexLayout,
662 vertexCount,
663 &poolState.fPoolVertexBuffer,
664 &poolState.fPoolStartVertex);
665 return NULL != *vertices;
666}
667
668bool GrInOrderDrawBuffer::onReserveIndexSpace(int indexCount, void** indices) {
669 GeometryPoolState& poolState = fGeoPoolStateStack.back();
670 GrAssert(indexCount > 0);
671 GrAssert(NULL != indices);
672 GrAssert(0 == poolState.fUsedPoolIndexBytes);
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000673
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000674 *indices = fIndexPool.makeSpace(indexCount,
675 &poolState.fPoolIndexBuffer,
676 &poolState.fPoolStartIndex);
677 return NULL != *indices;
reed@google.comac10a2d2010-12-22 21:39:39 +0000678}
679
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000680void GrInOrderDrawBuffer::releaseReservedVertexSpace() {
681 GeometryPoolState& poolState = fGeoPoolStateStack.back();
682 const GeometrySrcState& geoSrc = this->getGeomSrc();
683
684 GrAssert(kReserved_GeometrySrcType == geoSrc.fVertexSrc);
bsalomon@google.com3f5a95e2012-03-08 16:41:42 +0000685
686 // When the caller reserved vertex buffer space we gave it back a pointer
687 // provided by the vertex buffer pool. At each draw we tracked the largest
688 // offset into the pool's pointer that was referenced. Now we return to the
689 // pool any portion at the tail of the allocation that no draw referenced.
690 size_t reservedVertexBytes = VertexSize(geoSrc.fVertexLayout) *
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000691 geoSrc.fVertexCount;
692 fVertexPool.putBack(reservedVertexBytes -
693 poolState.fUsedPoolVertexBytes);
694 poolState.fUsedPoolVertexBytes = 0;
bsalomon@google.com3f5a95e2012-03-08 16:41:42 +0000695 poolState.fPoolVertexBuffer = NULL;
696 poolState.fPoolStartVertex = 0;
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000697}
698
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000699void GrInOrderDrawBuffer::releaseReservedIndexSpace() {
700 GeometryPoolState& poolState = fGeoPoolStateStack.back();
701 const GeometrySrcState& geoSrc = this->getGeomSrc();
702
703 GrAssert(kReserved_GeometrySrcType == geoSrc.fIndexSrc);
bsalomon@google.com3f5a95e2012-03-08 16:41:42 +0000704
705 // Similar to releaseReservedVertexSpace we return any unused portion at
706 // the tail
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000707 size_t reservedIndexBytes = sizeof(uint16_t) * geoSrc.fIndexCount;
708 fIndexPool.putBack(reservedIndexBytes - poolState.fUsedPoolIndexBytes);
709 poolState.fUsedPoolIndexBytes = 0;
bsalomon@google.com3f5a95e2012-03-08 16:41:42 +0000710 poolState.fPoolIndexBuffer = NULL;
711 poolState.fPoolStartIndex = 0;
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000712}
713
bsalomon@google.combcdbbe62011-04-12 15:40:00 +0000714void GrInOrderDrawBuffer::onSetVertexSourceToArray(const void* vertexArray,
715 int vertexCount) {
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000716
717 GeometryPoolState& poolState = fGeoPoolStateStack.back();
718 GrAssert(0 == poolState.fUsedPoolVertexBytes);
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000719#if GR_DEBUG
720 bool success =
721#endif
bsalomon@google.come79c8152012-03-29 19:07:12 +0000722 fVertexPool.appendVertices(this->getVertexLayout(),
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000723 vertexCount,
724 vertexArray,
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000725 &poolState.fPoolVertexBuffer,
726 &poolState.fPoolStartVertex);
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000727 GR_DEBUGASSERT(success);
728}
729
bsalomon@google.combcdbbe62011-04-12 15:40:00 +0000730void GrInOrderDrawBuffer::onSetIndexSourceToArray(const void* indexArray,
731 int indexCount) {
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000732 GeometryPoolState& poolState = fGeoPoolStateStack.back();
733 GrAssert(0 == poolState.fUsedPoolIndexBytes);
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000734#if GR_DEBUG
735 bool success =
736#endif
737 fIndexPool.appendIndices(indexCount,
738 indexArray,
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000739 &poolState.fPoolIndexBuffer,
740 &poolState.fPoolStartIndex);
bsalomon@google.com1c13c962011-02-14 16:51:21 +0000741 GR_DEBUGASSERT(success);
reed@google.comac10a2d2010-12-22 21:39:39 +0000742}
743
bsalomon@google.com3f5a95e2012-03-08 16:41:42 +0000744void GrInOrderDrawBuffer::releaseVertexArray() {
745 // When the client provides an array as the vertex source we handled it
746 // by copying their array into reserved space.
747 this->GrInOrderDrawBuffer::releaseReservedVertexSpace();
748}
749
750void GrInOrderDrawBuffer::releaseIndexArray() {
751 // When the client provides an array as the index source we handled it
752 // by copying their array into reserved space.
753 this->GrInOrderDrawBuffer::releaseReservedIndexSpace();
754}
755
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000756void GrInOrderDrawBuffer::geometrySourceWillPush() {
757 GeometryPoolState& poolState = fGeoPoolStateStack.push_back();
758 poolState.fUsedPoolVertexBytes = 0;
759 poolState.fUsedPoolIndexBytes = 0;
bsalomon@google.com934c5702012-03-20 21:17:58 +0000760 this->resetDrawTracking();
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000761#if GR_DEBUG
762 poolState.fPoolVertexBuffer = (GrVertexBuffer*)~0;
763 poolState.fPoolStartVertex = ~0;
764 poolState.fPoolIndexBuffer = (GrIndexBuffer*)~0;
765 poolState.fPoolStartIndex = ~0;
766#endif
767}
768
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000769void GrInOrderDrawBuffer::geometrySourceWillPop(
770 const GeometrySrcState& restoredState) {
771 GrAssert(fGeoPoolStateStack.count() > 1);
772 fGeoPoolStateStack.pop_back();
773 GeometryPoolState& poolState = fGeoPoolStateStack.back();
774 // we have to assume that any slack we had in our vertex/index data
775 // is now unreleasable because data may have been appended later in the
776 // pool.
777 if (kReserved_GeometrySrcType == restoredState.fVertexSrc ||
778 kArray_GeometrySrcType == restoredState.fVertexSrc) {
779 poolState.fUsedPoolVertexBytes =
780 VertexSize(restoredState.fVertexLayout) *
781 restoredState.fVertexCount;
782 }
783 if (kReserved_GeometrySrcType == restoredState.fIndexSrc ||
784 kArray_GeometrySrcType == restoredState.fIndexSrc) {
bsalomon@google.com3f5a95e2012-03-08 16:41:42 +0000785 poolState.fUsedPoolIndexBytes = sizeof(uint16_t) *
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000786 restoredState.fIndexCount;
787 }
bsalomon@google.com934c5702012-03-20 21:17:58 +0000788 this->resetDrawTracking();
bsalomon@google.com25fb21f2011-06-21 18:17:25 +0000789}
790
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000791bool GrInOrderDrawBuffer::needsNewState() const {
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000792 // we should have recorded a default state in reset()
793 GrAssert(!fStates.empty());
794 return fStates.back() != this->getDrawState();
reed@google.comac10a2d2010-12-22 21:39:39 +0000795}
796
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000797bool GrInOrderDrawBuffer::needsNewClip() const {
bsalomon@google.com8f9cbd62011-12-09 15:55:34 +0000798 if (this->getDrawState().isClipState()) {
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000799 if (fClipSet && fClips.back() != fClip) {
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000800 return true;
801 }
reed@google.comac10a2d2010-12-22 21:39:39 +0000802 }
803 return false;
804}
bsalomon@google.comd302f142011-03-03 13:54:13 +0000805
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000806void GrInOrderDrawBuffer::recordClip() {
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000807 fClips.push_back() = fClip;
808 fClipSet = false;
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000809 fCmds.push_back(kSetClip_Cmd);
810}
811
812void GrInOrderDrawBuffer::recordDefaultClip() {
813 fClips.push_back() = GrClip();
814 fCmds.push_back(kSetClip_Cmd);
815}
816
817void GrInOrderDrawBuffer::recordState() {
818 fStates.push_back(this->getDrawState());
819 fCmds.push_back(kSetState_Cmd);
820}
821
822void GrInOrderDrawBuffer::recordDefaultState() {
823 fStates.push_back(GrDrawState());
824 fCmds.push_back(kSetState_Cmd);
825}
826
827GrInOrderDrawBuffer::Draw* GrInOrderDrawBuffer::recordDraw() {
828 fCmds.push_back(kDraw_Cmd);
829 return &fDraws.push_back();
830}
831
bsalomon@google.comded4f4b2012-06-28 18:48:06 +0000832GrInOrderDrawBuffer::StencilPath* GrInOrderDrawBuffer::recordStencilPath() {
833 fCmds.push_back(kStencilPath_Cmd);
834 return &fStencilPaths.push_back();
835}
836
bsalomon@google.coma4f6b102012-06-26 21:04:22 +0000837GrInOrderDrawBuffer::Clear* GrInOrderDrawBuffer::recordClear() {
838 fCmds.push_back(kClear_Cmd);
839 return &fClears.push_back();
reed@google.comac10a2d2010-12-22 21:39:39 +0000840}
bsalomon@google.comd302f142011-03-03 13:54:13 +0000841
bsalomon@google.comdea2f8d2011-08-01 15:51:05 +0000842void GrInOrderDrawBuffer::clipWillBeSet(const GrClip& newClip) {
843 INHERITED::clipWillBeSet(newClip);
bsalomon@google.com86afc2a2011-02-16 16:12:19 +0000844 fClipSet = true;
845}