Move vertex layout from GeometrySrcState to GrDrawState.
authorjvanverth@google.com <jvanverth@google.com@2bbb7eff-a529-9590-31e7-b0007b416f81>
Tue, 5 Feb 2013 20:33:30 +0000 (20:33 +0000)
committerjvanverth@google.com <jvanverth@google.com@2bbb7eff-a529-9590-31e7-b0007b416f81>
Tue, 5 Feb 2013 20:33:30 +0000 (20:33 +0000)
Also adds AutoStateRestore member to AutoGeometryPush to push DrawState as well
as GeometrySrcState. And removed vertex layout as an argument to a number of
functions -- they will get vertex layout info from the current DrawState.

Review URL: https://codereview.appspot.com/7286047

git-svn-id: http://skia.googlecode.com/svn/trunk@7600 2bbb7eff-a529-9590-31e7-b0007b416f81

15 files changed:
src/gpu/GrAAConvexPathRenderer.cpp
src/gpu/GrAAHairLinePathRenderer.cpp
src/gpu/GrAARectRenderer.cpp
src/gpu/GrClipMaskManager.cpp
src/gpu/GrContext.cpp
src/gpu/GrDefaultPathRenderer.cpp
src/gpu/GrDrawState.h
src/gpu/GrDrawTarget.cpp
src/gpu/GrDrawTarget.h
src/gpu/GrGpu.cpp
src/gpu/GrGpu.h
src/gpu/GrInOrderDrawBuffer.cpp
src/gpu/GrInOrderDrawBuffer.h
src/gpu/GrTextContext.cpp
src/gpu/gl/GrGpuGL_program.cpp

index 930d8a2..98eaab8 100644 (file)
@@ -481,7 +481,8 @@ bool GrAAConvexPathRenderer::onDrawPath(const SkPath& origPath,
         return false;
     }
 
-    GrDrawTarget::AutoReleaseGeometry arg(target, layout, vCount, iCount);
+    drawState->setVertexLayout(layout);
+    GrDrawTarget::AutoReleaseGeometry arg(target, vCount, iCount);
     if (!arg.succeeded()) {
         return false;
     }
index c229f66..00982ee 100644 (file)
@@ -514,9 +514,10 @@ bool GrAAHairLinePathRenderer::createGeom(
     *lineCnt = lines.count() / 2;
     int vertCnt = kVertsPerLineSeg * *lineCnt + kVertsPerQuad * *quadCnt;
 
-    GrAssert(sizeof(Vertex) == GrDrawState::VertexSize(layout));
+    target->drawState()->setVertexLayout(layout);
+    GrAssert(sizeof(Vertex) == target->getDrawState().getVertexSize());
 
-    if (!arg->set(target, layout, vertCnt, 0)) {
+    if (!arg->set(target, vertCnt, 0)) {
         return false;
     }
 
index b23ed9a..d23c4b4 100644 (file)
@@ -126,10 +126,9 @@ void GrAARectRenderer::fillAARect(GrGpu* gpu,
                                   const GrRect& devRect,
                                   bool useVertexCoverage) {
     GrVertexLayout layout = aa_rect_layout(useVertexCoverage);
+    target->drawState()->setVertexLayout(layout);
 
-    size_t vsize = GrDrawState::VertexSize(layout);
-
-    GrDrawTarget::AutoReleaseGeometry geo(target, layout, 8, 0);
+    GrDrawTarget::AutoReleaseGeometry geo(target, 8, 0);
     if (!geo.succeeded()) {
         GrPrintf("Failed to get space for vertices!\n");
         return;
@@ -142,6 +141,7 @@ void GrAARectRenderer::fillAARect(GrGpu* gpu,
     }
 
     intptr_t verts = reinterpret_cast<intptr_t>(geo.vertices());
+    size_t vsize = target->getDrawState().getVertexSize();
 
     GrPoint* fan0Pos = reinterpret_cast<GrPoint*>(verts);
     GrPoint* fan1Pos = reinterpret_cast<GrPoint*>(verts + 4 * vsize);
@@ -196,9 +196,9 @@ void GrAARectRenderer::strokeAARect(GrGpu* gpu,
         return;
     }
     GrVertexLayout layout = aa_rect_layout(useVertexCoverage);
-    size_t vsize = GrDrawState::VertexSize(layout);
+    target->drawState()->setVertexLayout(layout);
 
-    GrDrawTarget::AutoReleaseGeometry geo(target, layout, 16, 0);
+    GrDrawTarget::AutoReleaseGeometry geo(target, 16, 0);
     if (!geo.succeeded()) {
         GrPrintf("Failed to get space for vertices!\n");
         return;
@@ -210,6 +210,7 @@ void GrAARectRenderer::strokeAARect(GrGpu* gpu,
     }
 
     intptr_t verts = reinterpret_cast<intptr_t>(geo.vertices());
+    size_t vsize = target->getDrawState().getVertexSize();
 
     // We create vertices for four nested rectangles. There are two ramps from 0 to full
     // coverage, one on the exterior of the stroke and the other on the interior.
index d2bfe7b..1bbb885 100644 (file)
@@ -425,11 +425,9 @@ GrTexture* GrClipMaskManager::createAlphaClipMask(int32_t clipStackGenID,
         return NULL;
     }
 
-    GrDrawTarget::AutoStateRestore asr(fGpu, GrDrawTarget::kReset_ASRInit);
+    GrDrawTarget::AutoGeometryAndStatePush agasp(fGpu, GrDrawTarget::kReset_ASRInit);
     GrDrawState* drawState = fGpu->drawState();
 
-    GrDrawTarget::AutoGeometryPush agp(fGpu);
-
     // The top-left of the mask corresponds to the top-left corner of the bounds.
     SkVector clipToMaskOffset = {
         SkIntToScalar(-clipSpaceIBounds.fLeft),
@@ -579,10 +577,9 @@ bool GrClipMaskManager::createStencilClipMask(InitialState initialState,
 
         stencilBuffer->setLastClip(genID, clipSpaceIBounds, clipSpaceToStencilOffset);
 
-        GrDrawTarget::AutoStateRestore asr(fGpu, GrDrawTarget::kReset_ASRInit);
+        GrDrawTarget::AutoGeometryAndStatePush agasp(fGpu, GrDrawTarget::kReset_ASRInit);
         drawState = fGpu->drawState();
         drawState->setRenderTarget(rt);
-        GrDrawTarget::AutoGeometryPush agp(fGpu);
 
         // We set the current clip to the bounds so that our recursive draws are scissored to them.
         SkIRect stencilSpaceIBounds(clipSpaceIBounds);
index 52e2003..fdea1a8 100644 (file)
@@ -310,7 +310,8 @@ GrTexture* GrContext::createResizedTexture(const GrTextureDesc& desc,
         drawState->createTextureEffect(0, clampedTexture, SkMatrix::I(), params);
 
         static const GrVertexLayout layout = GrDrawState::StageTexCoordVertexLayoutBit(0,0);
-        GrDrawTarget::AutoReleaseGeometry arg(fGpu, layout, 4, 0);
+        drawState->setVertexLayout(layout);
+        GrDrawTarget::AutoReleaseGeometry arg(fGpu, 4, 0);
 
         if (arg.succeeded()) {
             GrPoint* verts = (GrPoint*) arg.vertices();
@@ -738,7 +739,8 @@ void GrContext::drawRect(const GrPaint& paint,
         // unitSquareVertexBuffer()
 
         static const int worstCaseVertCount = 10;
-        GrDrawTarget::AutoReleaseGeometry geo(target, 0, worstCaseVertCount, 0);
+        target->drawState()->setVertexLayout(GrDrawState::kDefault_VertexLayout);
+        GrDrawTarget::AutoReleaseGeometry geo(target, worstCaseVertCount, 0);
 
         if (!geo.succeeded()) {
             GrPrintf("Failed to get space for vertices!\n");
@@ -880,10 +882,11 @@ void GrContext::drawVertices(const GrPaint& paint,
     if (NULL != colors) {
         layout |= GrDrawState::kColor_VertexLayoutBit;
     }
-    int vertexSize = GrDrawState::VertexSize(layout);
+    target->drawState()->setVertexLayout(layout);
 
+    int vertexSize = target->getDrawState().getVertexSize();
     if (sizeof(GrPoint) != vertexSize) {
-        if (!geo.set(target, layout, vertexCount, 0)) {
+        if (!geo.set(target, vertexCount, 0)) {
             GrPrintf("Failed to get space for vertices!\n");
             return;
         }
@@ -908,7 +911,7 @@ void GrContext::drawVertices(const GrPaint& paint,
             curVertex = (void*)((intptr_t)curVertex + vertexSize);
         }
     } else {
-        target->setVertexSourceToArray(layout, positions, vertexCount);
+        target->setVertexSourceToArray(positions, vertexCount);
     }
 
     // we don't currently apply offscreen AA to this path. Need improved
@@ -1006,9 +1009,10 @@ void GrContext::internalDrawOval(const GrPaint& paint,
     }
 
     GrVertexLayout layout = GrDrawState::kEdge_VertexLayoutBit;
-    GrAssert(sizeof(CircleVertex) == GrDrawState::VertexSize(layout));
+    drawState->setVertexLayout(layout);
+    GrAssert(sizeof(CircleVertex) == drawState->getVertexSize());
 
-    GrDrawTarget::AutoReleaseGeometry geo(target, layout, 4, 0);
+    GrDrawTarget::AutoReleaseGeometry geo(target, 4, 0);
     if (!geo.succeeded()) {
         GrPrintf("Failed to get space for vertices!\n");
         return;
index dbed783..d5ebaaa 100644 (file)
@@ -233,8 +233,8 @@ bool GrDefaultPathRenderer::createGeom(const SkPath& path,
         }
     }
 
-
-    if (!arg->set(target, layout, maxPts, maxIdxs)) {
+    target->drawState()->setVertexLayout(layout);
+    if (!arg->set(target, maxPts, maxIdxs)) {
         return false;
     }
 
@@ -476,7 +476,7 @@ bool GrDefaultPathRenderer::internalDrawPath(const SkPath& path,
             } else {
                 bounds = path.getBounds();
             }
-            GrDrawTarget::AutoGeometryPush agp(target);
+            GrDrawTarget::AutoGeometryAndStatePush agasp(target, GrDrawTarget::kPreserve_ASRInit);
             target->drawSimpleRect(bounds, NULL);
         } else {
             if (passCount > 1) {
index 0a0b0da..de23df7 100644 (file)
@@ -84,6 +84,7 @@ public:
         fRenderTarget.reset(NULL);
 
         fCommon.fColor = 0xffffffff;
+        fCommon.fVertexLayout = kDefault_VertexLayout;
         fCommon.fViewMatrix.reset();
         fCommon.fSrcBlend = kOne_GrBlendCoeff;
         fCommon.fDstBlend = kZero_GrBlendCoeff;
@@ -107,7 +108,7 @@ public:
     void setFromPaint(const GrPaint& paint);
 
     ///////////////////////////////////////////////////////////////////////////
-    /// @name Vertex Format
+    /// @name Vertex Layout
     ////
 
     /**
@@ -179,6 +180,21 @@ public:
     // make sure we haven't exceeded the number of bits in GrVertexLayout.
     GR_STATIC_ASSERT(kHighVertexLayoutBit < ((uint64_t)1 << 8*sizeof(GrVertexLayout)));
 
+    enum VertexLayout {
+        kDefault_VertexLayout = 0
+    };
+
+    /**
+     *  Sets vertex layout for next draw.
+     *
+     *  @param layout    the vertex layout to set.
+     */
+    void setVertexLayout(GrVertexLayout layout) { fCommon.fVertexLayout = layout; }
+
+    GrVertexLayout getVertexLayout() const { return fCommon.fVertexLayout; }
+    size_t getVertexSize() const { return VertexSize(fCommon.fVertexLayout); }
+
+
     ////////////////////////////////////////////////////////////////////////////
     // Helpers for picking apart vertex layouts
 
@@ -1161,6 +1177,7 @@ private:
     struct CommonState {
         // These fields are roughly sorted by decreasing likelihood of being different in op==
         GrColor                         fColor;
+        GrVertexLayout                  fVertexLayout;
         SkMatrix                        fViewMatrix;
         GrBlendCoeff                    fSrcBlend;
         GrBlendCoeff                    fDstBlend;
@@ -1175,6 +1192,7 @@ private:
         DrawFace                        fDrawFace;
         bool operator== (const CommonState& other) const {
             return fColor == other.fColor &&
+                   fVertexLayout == other.fVertexLayout &&
                    fViewMatrix.cheapEqualTo(other.fViewMatrix) &&
                    fSrcBlend == other.fSrcBlend &&
                    fDstBlend == other.fDstBlend &&
index 2cbcf19..3282f13 100644 (file)
@@ -136,7 +136,7 @@ void GrDrawTarget::setDrawState(GrDrawState*  drawState) {
     }
 }
 
-bool GrDrawTarget::reserveVertexSpace(GrVertexLayout vertexLayout,
+bool GrDrawTarget::reserveVertexSpace(size_t vertexSize,
                                       int vertexCount,
                                       void** vertices) {
     GeometrySrcState& geoSrc = fGeoSrcStateStack.back();
@@ -146,14 +146,14 @@ bool GrDrawTarget::reserveVertexSpace(GrVertexLayout vertexLayout,
         this->releasePreviousVertexSource();
         geoSrc.fVertexSrc = kNone_GeometrySrcType;
 
-        acquired = this->onReserveVertexSpace(GrDrawState::VertexSize(vertexLayout),
+        acquired = this->onReserveVertexSpace(vertexSize,
                                               vertexCount,
                                               vertices);
     }
     if (acquired) {
         geoSrc.fVertexSrc = kReserved_GeometrySrcType;
         geoSrc.fVertexCount = vertexCount;
-        geoSrc.fVertexLayout = vertexLayout;
+        geoSrc.fVertexSize = vertexSize;
     } else if (NULL != vertices) {
         *vertices = NULL;
     }
@@ -181,14 +181,14 @@ bool GrDrawTarget::reserveIndexSpace(int indexCount,
 
 }
 
-bool GrDrawTarget::reserveVertexAndIndexSpace(GrVertexLayout vertexLayout,
-                                              int vertexCount,
+bool GrDrawTarget::reserveVertexAndIndexSpace(int vertexCount,
                                               int indexCount,
                                               void** vertices,
                                               void** indices) {
-    this->willReserveVertexAndIndexSpace(GrDrawState::VertexSize(vertexLayout), vertexCount, indexCount);
+    size_t vertexSize = this->drawState()->getVertexSize();
+    this->willReserveVertexAndIndexSpace(vertexCount, indexCount);
     if (vertexCount) {
-        if (!this->reserveVertexSpace(vertexLayout, vertexCount, vertices)) {
+        if (!this->reserveVertexSpace(vertexSize, vertexCount, vertices)) {
             if (indexCount) {
                 this->resetIndexSource();
             }
@@ -206,8 +206,7 @@ bool GrDrawTarget::reserveVertexAndIndexSpace(GrVertexLayout vertexLayout,
     return true;
 }
 
-bool GrDrawTarget::geometryHints(size_t vertexSize,
-                                 int32_t* vertexCount,
+bool GrDrawTarget::geometryHints(int32_t* vertexCount,
                                  int32_t* indexCount) const {
     if (NULL != vertexCount) {
         *vertexCount = -1;
@@ -264,13 +263,12 @@ void GrDrawTarget::releasePreviousIndexSource() {
     }
 }
 
-void GrDrawTarget::setVertexSourceToArray(GrVertexLayout vertexLayout,
-                                          const void* vertexArray,
+void GrDrawTarget::setVertexSourceToArray(const void* vertexArray,
                                           int vertexCount) {
     this->releasePreviousVertexSource();
     GeometrySrcState& geoSrc = fGeoSrcStateStack.back();
     geoSrc.fVertexSrc = kArray_GeometrySrcType;
-    geoSrc.fVertexLayout = vertexLayout;
+    geoSrc.fVertexSize = this->drawState()->getVertexSize();
     geoSrc.fVertexCount = vertexCount;
     this->onSetVertexSourceToArray(vertexArray, vertexCount);
 }
@@ -284,14 +282,13 @@ void GrDrawTarget::setIndexSourceToArray(const void* indexArray,
     this->onSetIndexSourceToArray(indexArray, indexCount);
 }
 
-void GrDrawTarget::setVertexSourceToBuffer(GrVertexLayout vertexLayout,
-                                           const GrVertexBuffer* buffer) {
+void GrDrawTarget::setVertexSourceToBuffer(const GrVertexBuffer* buffer) {
     this->releasePreviousVertexSource();
     GeometrySrcState& geoSrc = fGeoSrcStateStack.back();
     geoSrc.fVertexSrc    = kBuffer_GeometrySrcType;
     geoSrc.fVertexBuffer = buffer;
     buffer->ref();
-    geoSrc.fVertexLayout = vertexLayout;
+    geoSrc.fVertexSize = this->drawState()->getVertexSize();
 }
 
 void GrDrawTarget::setIndexSourceToBuffer(const GrIndexBuffer* buffer) {
@@ -355,7 +352,7 @@ bool GrDrawTarget::checkDraw(GrPrimitiveType type, int startVertex,
             maxValidVertex = geoSrc.fVertexCount;
             break;
         case kBuffer_GeometrySrcType:
-            maxValidVertex = geoSrc.fVertexBuffer->sizeInBytes() / GrDrawState::VertexSize(geoSrc.fVertexLayout);
+            maxValidVertex = geoSrc.fVertexBuffer->sizeInBytes() / geoSrc.fVertexSize;
             break;
     }
     if (maxVertex > maxValidVertex) {
@@ -490,15 +487,15 @@ GrDrawTarget::getBlendOpts(bool forceCoverage,
                            GrBlendCoeff* srcCoeff,
                            GrBlendCoeff* dstCoeff) const {
 
+    const GrDrawState& drawState = this->getDrawState();
+
     GrVertexLayout layout;
     if (kNone_GeometrySrcType == this->getGeomSrc().fVertexSrc) {
         layout = default_blend_opts_vertex_layout();
     } else {
-        layout = this->getVertexLayout();
+        layout = drawState.getVertexLayout();
     }
 
-    const GrDrawState& drawState = this->getDrawState();
-
     GrBlendCoeff bogusSrcCoeff, bogusDstCoeff;
     if (NULL == srcCoeff) {
         srcCoeff = &bogusSrcCoeff;
@@ -691,7 +688,8 @@ void GrDrawTarget::drawRect(const GrRect& rect,
         avmr.set(this->drawState(), *matrix, explicitCoordMask);
     }
 
-    AutoReleaseGeometry geo(this, layout, 4, 0);
+    this->drawState()->setVertexLayout(layout);
+    AutoReleaseGeometry geo(this, 4, 0);
     if (!geo.succeeded()) {
         GrPrintf("Failed to get space for vertices!\n");
         return;
@@ -763,11 +761,10 @@ void GrDrawTarget::AutoStateRestore::set(GrDrawTarget* target, ASRInit init) {
 
 GrDrawTarget::AutoReleaseGeometry::AutoReleaseGeometry(
                                          GrDrawTarget*  target,
-                                         GrVertexLayout vertexLayout,
                                          int vertexCount,
                                          int indexCount) {
     fTarget = NULL;
-    this->set(target, vertexLayout, vertexCount, indexCount);
+    this->set(target, vertexCount, indexCount);
 }
 
 GrDrawTarget::AutoReleaseGeometry::AutoReleaseGeometry() {
@@ -779,7 +776,6 @@ GrDrawTarget::AutoReleaseGeometry::~AutoReleaseGeometry() {
 }
 
 bool GrDrawTarget::AutoReleaseGeometry::set(GrDrawTarget*  target,
-                                            GrVertexLayout vertexLayout,
                                             int vertexCount,
                                             int indexCount) {
     this->reset();
@@ -787,8 +783,7 @@ bool GrDrawTarget::AutoReleaseGeometry::set(GrDrawTarget*  target,
     bool success = true;
     if (NULL != fTarget) {
         fTarget = target;
-        success = target->reserveVertexAndIndexSpace(vertexLayout,
-                                                     vertexCount,
+        success = target->reserveVertexAndIndexSpace(vertexCount,
                                                      indexCount,
                                                      &fVertices,
                                                      &fIndices);
index c1444b4..2a3681f 100644 (file)
@@ -211,6 +211,8 @@ public:
      *    GrDrawTarget subclass. For deferred subclasses the caller has to
      *    guarantee that the data is still available in the buffers at playback.
      *    (TODO: Make this more automatic as we have done for read/write pixels)
+     *
+     * The size of each vertex is determined by querying the current GrDrawState.
      */
 
     /**
@@ -232,17 +234,15 @@ public:
      * popGeomtrySource is called. At that point logically a snapshot of the
      * data is made and the pointers are invalid.
      *
-     * @param vertexLayout the format of vertices (ignored if vertexCount == 0).
      * @param vertexCount  the number of vertices to reserve space for. Can be
-     *                     0.
+     *                     0. Vertex size is queried from the current GrDrawState.
      * @param indexCount   the number of indices to reserve space for. Can be 0.
      * @param vertices     will point to reserved vertex space if vertexCount is
      *                     non-zero. Illegal to pass NULL if vertexCount > 0.
      * @param indices      will point to reserved index space if indexCount is
      *                     non-zero. Illegal to pass NULL if indexCount > 0.
      */
-     bool reserveVertexAndIndexSpace(GrVertexLayout vertexLayout,
-                                     int vertexCount,
+     bool reserveVertexAndIndexSpace(int vertexCount,
                                      int indexCount,
                                      void** vertices,
                                      void** indices);
@@ -255,9 +255,9 @@ public:
      * Also may hint whether the draw target should be flushed first. This is
      * useful for deferred targets.
      *
-     * @param vertexSize   size of vertices caller would like to reserve
      * @param vertexCount  in: hint about how many vertices the caller would
-     *                     like to allocate.
+     *                     like to allocate. Vertex size is queried from the
+     *                     current GrDrawState.
      *                     out: a hint about the number of vertices that can be
      *                     allocated cheaply. Negative means no hint.
      *                     Ignored if NULL.
@@ -269,27 +269,24 @@ public:
      *
      * @return  true if target should be flushed based on the input values.
      */
-    virtual bool geometryHints(size_t vertexSize,
-                               int* vertexCount,
+    virtual bool geometryHints(int* vertexCount,
                                int* indexCount) const;
 
     /**
      * Sets source of vertex data for the next draw. Array must contain
      * the vertex data when this is called.
      *
-     * @param array         cpu array containing vertex data.
-     * @param size          size of the vertex data.
-     * @param vertexCount   the number of vertices in the array.
+     * @param vertexArray   cpu array containing vertex data.
+     * @param vertexCount   the number of vertices in the array. Vertex size is 
+     *                      queried from the current GrDrawState.
      */
-    void setVertexSourceToArray(GrVertexLayout vertexLayout,
-                                const void* vertexArray,
-                                int vertexCount);
+    void setVertexSourceToArray(const void* vertexArray, int vertexCount);
 
     /**
      * Sets source of index data for the next indexed draw. Array must contain
      * the indices when this is called.
      *
-     * @param array         cpu array containing index data.
+     * @param indexArray    cpu array containing index data.
      * @param indexCount    the number of indices in the array.
      */
     void setIndexSourceToArray(const void* indexArray, int indexCount);
@@ -299,11 +296,10 @@ public:
      * in the buffer until drawIndexed, drawNonIndexed, or drawIndexedInstances.
      *
      * @param buffer        vertex buffer containing vertex data. Must be
-     *                      unlocked before draw call.
-     * @param vertexLayout  layout of the vertex data in the buffer.
+     *                      unlocked before draw call. Vertex size is queried 
+     *                      from current GrDrawState.
      */
-    void setVertexSourceToBuffer(GrVertexLayout vertexLayout,
-                                 const GrVertexBuffer* buffer);
+    void setVertexSourceToBuffer(const GrVertexBuffer* buffer);
 
     /**
      * Sets source of index data for the next indexed draw. Data does not have
@@ -557,13 +553,11 @@ public:
     class AutoReleaseGeometry : ::GrNoncopyable {
     public:
         AutoReleaseGeometry(GrDrawTarget*  target,
-                            GrVertexLayout vertexLayout,
                             int            vertexCount,
                             int            indexCount);
         AutoReleaseGeometry();
         ~AutoReleaseGeometry();
         bool set(GrDrawTarget*  target,
-                 GrVertexLayout vertexLayout,
                  int            vertexCount,
                  int            indexCount);
         bool succeeded() const { return NULL != fTarget; }
@@ -604,18 +598,20 @@ public:
 
     ////////////////////////////////////////////////////////////////////////////
 
-    class AutoGeometryPush : ::GrNoncopyable {
+    class AutoGeometryAndStatePush : ::GrNoncopyable {
     public:
-        AutoGeometryPush(GrDrawTarget* target) {
+        AutoGeometryAndStatePush(GrDrawTarget* target, ASRInit init) 
+            : fState(target, init) {
             GrAssert(NULL != target);
             fTarget = target;
             target->pushGeometrySource();
         }
-        ~AutoGeometryPush() {
+        ~AutoGeometryAndStatePush() {
             fTarget->popGeometrySource();
         }
     private:
-        GrDrawTarget* fTarget;
+        GrDrawTarget*    fTarget;
+        AutoStateRestore fState;
     };
 
 protected:
@@ -692,7 +688,7 @@ protected:
             int                     fIndexCount;
         };
 
-        GrVertexLayout          fVertexLayout;
+        size_t                  fVertexSize;
     };
 
     int indexCountInCurrentSource() const {
@@ -725,11 +721,11 @@ protected:
 
     // accessors for derived classes
     const GeometrySrcState& getGeomSrc() const { return fGeoSrcStateStack.back(); }
-    // it is preferable to call this rather than getGeomSrc()->fVertexLayout because of the assert.
-    GrVertexLayout getVertexLayout() const {
+    // it is preferable to call this rather than getGeomSrc()->fVertexSize because of the assert.
+    size_t getVertexSize() const {
         // the vertex layout is only valid if a vertex source has been specified.
         GrAssert(this->getGeomSrc().fVertexSrc != kNone_GeometrySrcType);
-        return this->getGeomSrc().fVertexLayout;
+        return this->getGeomSrc().fVertexSize;
     }
 
     Caps fCaps;
@@ -794,7 +790,7 @@ protected:
 private:
     // A subclass can optionally overload this function to be notified before
     // vertex and index space is reserved.
-    virtual void willReserveVertexAndIndexSpace(size_t vertexSize, int vertexCount, int indexCount) {}
+    virtual void willReserveVertexAndIndexSpace(int vertexCount, int indexCount) {}
 
     // implemented by subclass to allocate space for reserved geom
     virtual bool onReserveVertexSpace(size_t vertexSize, int vertexCount, void** vertices) = 0;
@@ -816,7 +812,7 @@ private:
     virtual void onStencilPath(const GrPath*, const SkStrokeRec& stroke, SkPath::FillType fill) = 0;
 
     // helpers for reserving vertex and index space.
-    bool reserveVertexSpace(GrVertexLayout vertexLayout,
+    bool reserveVertexSpace(size_t vertexSize,
                             int vertexCount,
                             void** vertices);
     bool reserveIndexSpace(int indexCount, void** indices);
index 47d4069..d695e16 100644 (file)
@@ -471,7 +471,7 @@ bool GrGpu::onReserveIndexSpace(int indexCount, void** indices) {
 void GrGpu::releaseReservedVertexSpace() {
     const GeometrySrcState& geoSrc = this->getGeomSrc();
     GrAssert(kReserved_GeometrySrcType == geoSrc.fVertexSrc);
-    size_t bytes = geoSrc.fVertexCount * GrDrawState::VertexSize(geoSrc.fVertexLayout);
+    size_t bytes = geoSrc.fVertexCount * geoSrc.fVertexSize;
     fVertexPool->putBack(bytes);
     --fVertexPoolUseCnt;
 }
@@ -490,7 +490,7 @@ void GrGpu::onSetVertexSourceToArray(const void* vertexArray, int vertexCount) {
 #if GR_DEBUG
     bool success =
 #endif
-    fVertexPool->appendVertices(GrDrawState::VertexSize(this->getVertexLayout()),
+    fVertexPool->appendVertices(this->getVertexSize(),
                                 vertexCount,
                                 vertexArray,
                                 &geomPoolState.fPoolVertexBuffer,
@@ -517,7 +517,7 @@ void GrGpu::releaseVertexArray() {
     // if vertex source was array, we stowed data in the pool
     const GeometrySrcState& geoSrc = this->getGeomSrc();
     GrAssert(kArray_GeometrySrcType == geoSrc.fVertexSrc);
-    size_t bytes = geoSrc.fVertexCount * GrDrawState::VertexSize(geoSrc.fVertexLayout);
+    size_t bytes = geoSrc.fVertexCount * geoSrc.fVertexSize;
     fVertexPool->putBack(bytes);
     --fVertexPoolUseCnt;
 }
index 85cbd3f..38c109d 100644 (file)
@@ -422,7 +422,7 @@ protected:
 
 private:
     // GrDrawTarget overrides
-    virtual bool onReserveVertexSpace(size_t vSize, int vertexCount, void** vertices) SK_OVERRIDE;
+    virtual bool onReserveVertexSpace(size_t vertexSize, int vertexCount, void** vertices) SK_OVERRIDE;
     virtual bool onReserveIndexSpace(int indexCount, void** indices) SK_OVERRIDE;
     virtual void releaseReservedVertexSpace() SK_OVERRIDE;
     virtual void releaseReservedIndexSpace() SK_OVERRIDE;
index bd54967..ce41ae1 100644 (file)
@@ -86,7 +86,7 @@ void GrInOrderDrawBuffer::drawRect(const GrRect& rect,
     // dual-source blending isn't available. This comes into play when there is coverage. If colors
     // were a stage it could take a hint that every vertex's color will be opaque.
     if (this->getCaps().dualSourceBlendingSupport() ||
-        this->getDrawState().hasSolidCoverage(this->getGeomSrc().fVertexLayout)) {
+        this->getDrawState().hasSolidCoverage(this->getDrawState().getVertexLayout())) {
         layout |= GrDrawState::kColor_VertexLayoutBit;;
         // We set the draw state's color to white here. This is done so that any batching performed
         // in our subclass's onDraw() won't get a false from GrDrawState::op== due to a color
@@ -107,7 +107,8 @@ void GrInOrderDrawBuffer::drawRect(const GrRect& rect,
         }
     }
 
-    AutoReleaseGeometry geo(this, layout, 4, 0);
+    this->drawState()->setVertexLayout(layout);
+    AutoReleaseGeometry geo(this, 4, 0);
     if (!geo.succeeded()) {
         GrPrintf("Failed to get space for vertices!\n");
         return;
@@ -215,6 +216,7 @@ int GrInOrderDrawBuffer::concatInstancedDraw(const DrawInfo& info) {
     GrAssert(info.isInstanced());
 
     const GeometrySrcState& geomSrc = this->getGeomSrc();
+    const GrDrawState& drawState = this->getDrawState();
 
     // we only attempt to concat the case when reserved verts are used with a client-specified index
     // buffer. To make this work with client-specified VBs we'd need to know if the VB was updated
@@ -237,8 +239,7 @@ int GrInOrderDrawBuffer::concatInstancedDraw(const DrawInfo& info) {
         draw->verticesPerInstance() != info.verticesPerInstance() ||
         draw->indicesPerInstance() != info.indicesPerInstance() ||
         draw->fVertexBuffer != vertexBuffer ||
-        draw->fIndexBuffer != geomSrc.fIndexBuffer ||
-        draw->fVertexLayout != geomSrc.fVertexLayout) {
+        draw->fIndexBuffer != geomSrc.fIndexBuffer) {
         return 0;
     }
     // info does not yet account for the offset from the start of the pool's VB while the previous
@@ -256,8 +257,8 @@ int GrInOrderDrawBuffer::concatInstancedDraw(const DrawInfo& info) {
     instancesToConcat = GrMin(instancesToConcat, info.instanceCount());
 
     // update the amount of reserved vertex data actually referenced in draws
-    size_t vertexBytes = instancesToConcat * info.verticesPerInstance() *
-                         GrDrawState::VertexSize(draw->fVertexLayout);
+    size_t vertexBytes = instancesToConcat * info.verticesPerInstance() * 
+                         drawState.getVertexSize();
     poolState.fUsedPoolVertexBytes = GrMax(poolState.fUsedPoolVertexBytes, vertexBytes);
 
     draw->adjustInstanceCount(instancesToConcat);
@@ -285,9 +286,10 @@ private:
 void GrInOrderDrawBuffer::onDraw(const DrawInfo& info) {
 
     GeometryPoolState& poolState = fGeoPoolStateStack.back();
+    const GrDrawState& drawState = this->getDrawState();
     AutoClipReenable acr;
 
-    if (this->getDrawState().isClipState() &&
+    if (drawState.isClipState() &&
         NULL != info.getDevBounds() &&
         this->quickInsideClip(*info.getDevBounds())) {
         acr.set(this->drawState());
@@ -312,7 +314,6 @@ void GrInOrderDrawBuffer::onDraw(const DrawInfo& info) {
     } else {
         draw = this->recordDraw(info);
     }
-    draw->fVertexLayout = this->getVertexLayout();
 
     switch (this->getGeomSrc().fVertexSrc) {
         case kBuffer_GeometrySrcType:
@@ -320,8 +321,8 @@ void GrInOrderDrawBuffer::onDraw(const DrawInfo& info) {
             break;
         case kReserved_GeometrySrcType: // fallthrough
         case kArray_GeometrySrcType: {
-            size_t vertexBytes = (info.vertexCount() + info.startVertex()) *
-                                 GrDrawState::VertexSize(draw->fVertexLayout);
+            size_t vertexBytes = (info.vertexCount() + info.startVertex()) * 
+                                 drawState.getVertexSize();
             poolState.fUsedPoolVertexBytes = GrMax(poolState.fUsedPoolVertexBytes, vertexBytes);
             draw->fVertexBuffer = poolState.fPoolVertexBuffer;
             draw->adjustStartVertex(poolState.fPoolStartVertex);
@@ -431,7 +432,7 @@ bool GrInOrderDrawBuffer::flushTo(GrDrawTarget* target) {
     fIndexPool.unlock();
 
     GrDrawTarget::AutoClipRestore acr(target);
-    AutoGeometryPush agp(target);
+    AutoGeometryAndStatePush agasp(target, kPreserve_ASRInit);
 
     GrDrawState playbackState;
     GrDrawState* prevDrawState = target->drawState();
@@ -451,7 +452,7 @@ bool GrInOrderDrawBuffer::flushTo(GrDrawTarget* target) {
         switch (fCmds[c]) {
             case kDraw_Cmd: {
                 const DrawRecord& draw = fDraws[currDraw];
-                target->setVertexSourceToBuffer(draw.fVertexLayout, draw.fVertexBuffer);
+                target->setVertexSourceToBuffer(draw.fVertexBuffer);
                 if (draw.isIndexed()) {
                     target->setIndexSourceToBuffer(draw.fIndexBuffer);
                 }
@@ -502,7 +503,6 @@ void GrInOrderDrawBuffer::setAutoFlushTarget(GrDrawTarget* target) {
 }
 
 void GrInOrderDrawBuffer::willReserveVertexAndIndexSpace(
-                                size_t vertexSize,
                                 int vertexCount,
                                 int indexCount) {
     if (NULL != fAutoFlushTarget) {
@@ -534,15 +534,14 @@ void GrInOrderDrawBuffer::willReserveVertexAndIndexSpace(
             !unreleasedVertexSpace &&
             !unreleasedIndexSpace &&
             !targetHasReservedGeom &&
-            this->geometryHints(vertexSize, &vcount, &icount)) {
+            this->geometryHints(&vcount, &icount)) {
 
             this->flushTo(fAutoFlushTarget);
         }
     }
 }
 
-bool GrInOrderDrawBuffer::geometryHints(size_t vertexSize,
-                                        int* vertexCount,
+bool GrInOrderDrawBuffer::geometryHints(int* vertexCount,
                                         int* indexCount) const {
     // we will recommend a flush if the data could fit in a single
     // preallocated buffer but none are left and it can't fit
@@ -559,6 +558,7 @@ bool GrInOrderDrawBuffer::geometryHints(size_t vertexSize,
         *indexCount = currIndices;
     }
     if (NULL != vertexCount) {
+        size_t vertexSize = this->getDrawState().getVertexSize();
         int32_t currVertices = fVertexPool.currentBufferVertices(vertexSize);
         if (*vertexCount > currVertices &&
             (!fVertexPool.preallocatedBuffersRemaining() &&
@@ -611,8 +611,7 @@ void GrInOrderDrawBuffer::releaseReservedVertexSpace() {
     // provided by the vertex buffer pool. At each draw we tracked the largest
     // offset into the pool's pointer that was referenced. Now we return to the
     // pool any portion at the tail of the allocation that no draw referenced.
-    size_t reservedVertexBytes = GrDrawState::VertexSize(geoSrc.fVertexLayout) *
-                                 geoSrc.fVertexCount;
+    size_t reservedVertexBytes = geoSrc.fVertexSize * geoSrc.fVertexCount;
     fVertexPool.putBack(reservedVertexBytes -
                         poolState.fUsedPoolVertexBytes);
     poolState.fUsedPoolVertexBytes = 0;
@@ -646,7 +645,7 @@ void GrInOrderDrawBuffer::onSetVertexSourceToArray(const void* vertexArray,
 #if GR_DEBUG
     bool success =
 #endif
-    fVertexPool.appendVertices(GrDrawState::VertexSize(this->getVertexLayout()),
+    fVertexPool.appendVertices(this->getVertexSize(),
                                vertexCount,
                                vertexArray,
                                &poolState.fPoolVertexBuffer,
@@ -702,9 +701,7 @@ void GrInOrderDrawBuffer::geometrySourceWillPop(
     // pool.
     if (kReserved_GeometrySrcType == restoredState.fVertexSrc ||
         kArray_GeometrySrcType == restoredState.fVertexSrc) {
-        poolState.fUsedPoolVertexBytes =
-            GrDrawState::VertexSize(restoredState.fVertexLayout) *
-            restoredState.fVertexCount;
+        poolState.fUsedPoolVertexBytes = restoredState.fVertexSize * restoredState.fVertexCount;
     }
     if (kReserved_GeometrySrcType == restoredState.fIndexSrc ||
         kArray_GeometrySrcType == restoredState.fIndexSrc) {
index daa5d06..d9bdd19 100644 (file)
@@ -82,8 +82,7 @@ public:
     void setAutoFlushTarget(GrDrawTarget* target);
 
     // overrides from GrDrawTarget
-    virtual bool geometryHints(size_t vertexSize,
-                               int* vertexCount,
+    virtual bool geometryHints(int* vertexCount,
                                int* indexCount) const SK_OVERRIDE;
     virtual void clear(const GrIRect* rect,
                        GrColor color,
@@ -108,7 +107,6 @@ private:
     class DrawRecord : public DrawInfo {
     public:
         DrawRecord(const DrawInfo& info) : DrawInfo(info) {}
-        GrVertexLayout          fVertexLayout;
         const GrVertexBuffer*   fVertexBuffer;
         const GrIndexBuffer*    fIndexBuffer;
     };
@@ -148,8 +146,7 @@ private:
     virtual void releaseIndexArray() SK_OVERRIDE;
     virtual void geometrySourceWillPush() SK_OVERRIDE;
     virtual void geometrySourceWillPop(const GeometrySrcState& restoredState) SK_OVERRIDE;
-    virtual void willReserveVertexAndIndexSpace(size_t vertexSize,
-                                                int vertexCount,
+    virtual void willReserveVertexAndIndexSpace(int vertexCount,
                                                 int indexCount) SK_OVERRIDE;
     bool quickInsideClip(const SkRect& devBounds);
 
index 97e92fa..2a26dae 100644 (file)
@@ -203,19 +203,19 @@ HAS_ATLAS:
         // If we need to reserve vertices allow the draw target to suggest
         // a number of verts to reserve and whether to perform a flush.
         fMaxVertices = kMinRequestedVerts;
-        bool flush = (NULL != fDrawTarget) &&
-                     fDrawTarget->geometryHints(GrDrawState::VertexSize(fVertexLayout),
-                                                &fMaxVertices,
-                                                NULL);
+        bool flush = false;
+        fDrawTarget = fContext->getTextTarget(fPaint);
+        if (NULL != fDrawTarget) {
+            fDrawTarget->drawState()->setVertexLayout(fVertexLayout);
+            flush = fDrawTarget->geometryHints(&fMaxVertices, NULL);
+        }    
         if (flush) {
             this->flushGlyphs();
             fContext->flush();
         }
-        fDrawTarget = fContext->getTextTarget(fPaint);
         fMaxVertices = kDefaultRequestedVerts;
         // ignore return, no point in flushing again.
-        fDrawTarget->geometryHints(GrDrawState::VertexSize(fVertexLayout),
-                                   &fMaxVertices,
+        fDrawTarget->geometryHints(&fMaxVertices,
                                    NULL);
 
         int maxQuadVertices = 4 * fContext->getQuadIndexBuffer()->maxQuads();
@@ -226,7 +226,6 @@ HAS_ATLAS:
             fMaxVertices = maxQuadVertices;
         }
         bool success = fDrawTarget->reserveVertexAndIndexSpace(
-                                                   fVertexLayout,
                                                    fMaxVertices,
                                                    0,
                                                    GrTCast<void**>(&fVertices),
index 28f76de..873317a 100644 (file)
@@ -181,7 +181,7 @@ void GrGpuGL::flushColor(GrColor color) {
     const ProgramDesc& desc = fCurrentProgram->getDesc();
     const GrDrawState& drawState = this->getDrawState();
 
-    if (this->getVertexLayout() & GrDrawState::kColor_VertexLayoutBit) {
+    if (drawState.getVertexLayout() & GrDrawState::kColor_VertexLayoutBit) {
         // color will be specified per-vertex as an attribute
         // invalidate the const vertex attrib color
         fHWConstAttribColor = GrColor_ILLEGAL;
@@ -230,7 +230,7 @@ void GrGpuGL::flushCoverage(GrColor coverage) {
     // const GrDrawState& drawState = this->getDrawState();
 
 
-    if (this->getVertexLayout() & GrDrawState::kCoverage_VertexLayoutBit) {
+    if (this->getDrawState().getVertexLayout() & GrDrawState::kCoverage_VertexLayoutBit) {
         // coverage will be specified per-vertex as an attribute
         // invalidate the const vertex attrib coverage
         fHWConstAttribCoverage = GrColor_ILLEGAL;
@@ -363,7 +363,7 @@ void GrGpuGL::setupGeometry(const DrawInfo& info, int* startIndexOffset) {
     int newTexCoordOffsets[GrDrawState::kMaxTexCoords];
     int newEdgeOffset;
 
-    GrVertexLayout currLayout = this->getVertexLayout();
+    GrVertexLayout currLayout = this->getDrawState().getVertexLayout();
 
     GrGLsizei newStride = GrDrawState::VertexSizeAndOffsetsByIdx(currLayout,
                                                                  newTexCoordOffsets,
@@ -502,7 +502,7 @@ void GrGpuGL::buildProgram(bool isPoints,
     // to a canonical value to avoid duplicate programs with different keys.
 
     // Must initialize all fields or cache will have false negatives!
-    desc->fVertexLayout = this->getVertexLayout();
+    desc->fVertexLayout = this->getDrawState().getVertexLayout();
 
     desc->fEmitsPointSize = isPoints;