| /* |
| Copyright 2011 Google Inc. |
| |
| Licensed under the Apache License, Version 2.0 (the "License"); |
| you may not use this file except in compliance with the License. |
| You may obtain a copy of the License at |
| |
| http://www.apache.org/licenses/LICENSE-2.0 |
| |
| Unless required by applicable law or agreed to in writing, software |
| distributed under the License is distributed on an "AS IS" BASIS, |
| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| See the License for the specific language governing permissions and |
| limitations under the License. |
| */ |
| |
| |
| #ifndef GrInOrderDrawBuffer_DEFINED |
| #define GrInOrderDrawBuffer_DEFINED |
| |
| #include "GrDrawTarget.h" |
| #include "GrAllocPool.h" |
| #include "GrAllocator.h" |
| #include "GrClip.h" |
| |
| class GrVertexBufferAllocPool; |
| class GrIndexBufferAllocPool; |
| |
| /** |
| * GrInOrderDrawBuffer is an implementation of GrDrawTarget that queues up |
| * draws for eventual playback into a GrGpu. In theory one draw buffer could |
| * playback into another. When index or vertex buffers are used as geometry |
| * sources it is the callers the draw buffer only holds references to the |
| * buffers. It is the callers responsibility to ensure that the data is still |
| * valid when the draw buffer is played back into a GrGpu. Similarly, it is the |
| * caller's responsibility to ensure that all referenced textures, buffers, |
| * and rendertargets are associated in the GrGpu object that the buffer is |
| * played back into. The buffer requires VB and IB pools to store geometry. |
| */ |
| |
| class GrInOrderDrawBuffer : public GrDrawTarget { |
| public: |
| |
| /** |
| * Creates a GrInOrderDrawBuffer |
| * |
| * @param vertexPool pool where vertices for queued draws will be saved when |
| * the vertex source is either reserved or array. |
| * @param indexPool pool where indices for queued draws will be saved when |
| * the index source is either reserved or array. |
| */ |
| GrInOrderDrawBuffer(GrVertexBufferAllocPool* vertexPool, |
| GrIndexBufferAllocPool* indexPool); |
| |
| virtual ~GrInOrderDrawBuffer(); |
| |
| /** |
| * Copies the draw state and clip from target to this draw buffer. |
| * |
| * @param target the target whose clip and state should be copied. |
| */ |
| void initializeDrawStateAndClip(const GrDrawTarget& target); |
| |
| /** |
| * Provides the buffer with an index buffer that can be used for quad rendering. |
| * The buffer may be able to batch consecutive drawRects if this is provided. |
| * @param indexBuffer index buffer with quad indices. |
| */ |
| void setQuadIndexBuffer(const GrIndexBuffer* indexBuffer); |
| |
| /** |
| * Empties the draw buffer of any queued up draws. |
| */ |
| void reset(); |
| |
| /** |
| * plays the queued up draws to another target. Does not empty this buffer so |
| * that it can be played back multiple times. |
| * @param target the target to receive the playback |
| */ |
| void playback(GrDrawTarget* target); |
| |
| // overrides from GrDrawTarget |
| virtual void drawIndexed(GrPrimitiveType primitiveType, |
| int startVertex, |
| int startIndex, |
| int vertexCount, |
| int indexCount); |
| virtual void drawNonIndexed(GrPrimitiveType primitiveType, |
| int startVertex, |
| int vertexCount); |
| |
| virtual void drawRect(const GrRect& rect, |
| const GrMatrix* matrix = NULL, |
| int stageEnableMask = 0, |
| const GrRect* srcRects[] = NULL, |
| const GrMatrix* srcMatrices[] = NULL); |
| |
| virtual bool geometryHints(GrVertexLayout vertexLayout, |
| int* vertexCount, |
| int* indexCount) const; |
| |
| virtual void clear(const GrIRect* rect, GrColor color); |
| |
| private: |
| |
| struct Draw { |
| GrPrimitiveType fPrimitiveType; |
| int fStartVertex; |
| int fStartIndex; |
| int fVertexCount; |
| int fIndexCount; |
| bool fStateChanged; |
| bool fClipChanged; |
| GrVertexLayout fVertexLayout; |
| const GrVertexBuffer* fVertexBuffer; |
| const GrIndexBuffer* fIndexBuffer; |
| }; |
| |
| struct Clear { |
| int fBeforeDrawIdx; |
| GrIRect fRect; |
| GrColor fColor; |
| }; |
| |
| virtual bool onAcquireGeometry(GrVertexLayout vertexLayout, |
| void** vertices, |
| void** indices); |
| virtual void onReleaseGeometry(); |
| virtual void clipWillBeSet(const GrClip& newClip); |
| |
| virtual void onSetVertexSourceToArray(const void* vertexArray, |
| int vertexCount); |
| |
| virtual void onSetIndexSourceToArray(const void* indexArray, |
| int indexCount); |
| |
| bool needsNewState() const; |
| bool needsNewClip() const; |
| |
| void pushState(); |
| void pushClip(); |
| |
| GrTAllocator<Draw> fDraws; |
| GrTAllocator<SavedDrawState> fStates; |
| GrTAllocator<Clear> fClears; |
| |
| GrTAllocator<GrClip> fClips; |
| bool fClipSet; |
| |
| GrVertexLayout fLastRectVertexLayout; |
| const GrIndexBuffer* fQuadIndexBuffer; |
| int fMaxQuads; |
| int fCurrQuad; |
| |
| GrVertexBufferAllocPool& fVertexPool; |
| const GrVertexBuffer* fCurrPoolVertexBuffer; |
| int fCurrPoolStartVertex; |
| |
| GrIndexBufferAllocPool& fIndexPool; |
| const GrIndexBuffer* fCurrPoolIndexBuffer; |
| int fCurrPoolStartIndex; |
| |
| // caller may conservatively over reserve vertices / indices. |
| // we release unused space back to allocator if possible |
| size_t fReservedVertexBytes; |
| size_t fReservedIndexBytes; |
| size_t fUsedReservedVertexBytes; |
| size_t fUsedReservedIndexBytes; |
| |
| enum { |
| kDrawPreallocCnt = 8, |
| kStatePreallocCnt = 8, |
| kClipPreallocCnt = 8, |
| kClearPreallocCnt = 4, |
| }; |
| |
| GrAlignedSTStorage<kDrawPreallocCnt, Draw> fDrawStorage; |
| GrAlignedSTStorage<kStatePreallocCnt, SavedDrawState> fStateStorage; |
| GrAlignedSTStorage<kClipPreallocCnt, GrClip> fClipStorage; |
| GrAlignedSTStorage<kClearPreallocCnt, Clear> fClearStorage; |
| |
| typedef GrDrawTarget INHERITED; |
| }; |
| |
| #endif |