aboutsummaryrefslogtreecommitdiffhomepage
path: root/gpu/include
diff options
context:
space:
mode:
authorGravatar bsalomon@google.com <bsalomon@google.com@2bbb7eff-a529-9590-31e7-b0007b416f81>2011-03-03 13:54:13 +0000
committerGravatar bsalomon@google.com <bsalomon@google.com@2bbb7eff-a529-9590-31e7-b0007b416f81>2011-03-03 13:54:13 +0000
commitd302f1401b3c9aea094804bad4e76de98782cfe8 (patch)
treeb46ec6c4de175842aef051d7b812785dacbd1d73 /gpu/include
parent1d12b1fd66e5be27fb4769ee09ce4fcd6bcc5979 (diff)
Add support for clipstack to Gr. GrClip is now a list of rects and paths with set operations to combine them. The stencil buffer is used to perform the set operations to put the clip into the stencil buffer. Building Gr's clip from Skia's clipStack is currently disabled due to the fact that Skia's clipStack is relative to the root layer not the current layer. This will be fixed in a subsequent CL.
git-svn-id: http://skia.googlecode.com/svn/trunk@878 2bbb7eff-a529-9590-31e7-b0007b416f81
Diffstat (limited to 'gpu/include')
-rw-r--r--gpu/include/GrClip.h152
-rw-r--r--gpu/include/GrClipIterator.h50
-rw-r--r--gpu/include/GrContext.h13
-rw-r--r--gpu/include/GrDrawTarget.h159
-rw-r--r--gpu/include/GrGLTexture.h9
-rw-r--r--gpu/include/GrGpu.h122
-rw-r--r--gpu/include/GrPath.h4
-rw-r--r--gpu/include/GrPathIter.h30
-rw-r--r--gpu/include/GrRect.h107
-rw-r--r--gpu/include/GrStencil.h211
-rw-r--r--gpu/include/GrTArray.h2
-rw-r--r--gpu/include/GrTexture.h32
-rw-r--r--gpu/include/GrTypes.h20
13 files changed, 668 insertions, 243 deletions
diff --git a/gpu/include/GrClip.h b/gpu/include/GrClip.h
index 8e3030c753..414a6d6806 100644
--- a/gpu/include/GrClip.h
+++ b/gpu/include/GrClip.h
@@ -20,96 +20,116 @@
#include "GrClipIterator.h"
#include "GrRect.h"
-#include "GrTDArray.h"
+#include "GrPath.h"
+#include "GrTArray.h"
+
class GrClip {
public:
GrClip();
GrClip(const GrClip& src);
- GrClip(GrClipIterator* iter);
+ GrClip(GrClipIterator* iter, const GrRect* bounds = NULL);
+ GrClip(const GrIRect& rect);
+ GrClip(const GrRect& rect);
+
~GrClip();
GrClip& operator=(const GrClip& src);
- bool isEmpty() const { return fBounds.isEmpty(); }
- bool isComplex() const { return fList.count() > 0; }
- bool isRect() const {
- return !this->isEmpty() && !this->isComplex();
- }
-
- const GrIRect& getBounds() const { return fBounds; }
+ bool hasBounds() const { return fBoundsValid; }
- /**
- * Resets this clip to be empty (fBounds is empty, and fList is empty)
- */
- void setEmpty();
+ const GrRect& getBounds() const { return fBounds; }
- /**
- * Resets this clip to have fBounds == rect, and fList is empty.
- */
- void setRect(const GrIRect& rect);
+ int getElementCount() const { return fList.count(); }
- /**
- * Append a rect to an existing clip. The call must ensure that rect does
- * not overlap with any previous rect in this clip (either from setRect
- * or addRect). fBounds is automatically updated to reflect the union of
- * all rects that have been added.
- */
- void addRect(const GrIRect&);
+ GrClipType getElementType(int i) const { return fList[i].fType; }
- void setFromIterator(GrClipIterator* iter);
+ const GrPath& getPath(int i) const {
+ GrAssert(kPath_ClipType == fList[i].fType);
+ return fList[i].fPath;
+ }
- friend bool operator==(const GrClip& a, const GrClip& b) {
- return a.fBounds == b.fBounds && a.fList == b.fList;
+ GrPathFill getPathFill(int i) const {
+ GrAssert(kPath_ClipType == fList[i].fType);
+ return fList[i].fPathFill;
}
- friend bool operator!=(const GrClip& a, const GrClip& b) {
- return !(a == b);
+
+ const GrRect& getRect(int i) const {
+ GrAssert(kRect_ClipType == fList[i].fType);
+ return fList[i].fRect;
}
- /**
- * Return the number of rects in this clip: 0 for empty, 1 for a rect,
- * or N for a complex clip.
- */
- int countRects() const {
- return this->isEmpty() ? 0 : GrMax<int>(1, fList.count());
+ const GrSetOp getOp(int i) const { return fList[i].fOp; }
+
+ bool isRect() const {
+ if (1 == fList.count() && kRect_ClipType == fList[0].fType) {
+ GrAssert(fBoundsValid);
+ GrAssert(fBounds == fList[0].fRect);
+ return true;
+ } else {
+ return false;
+ }
}
+ bool isEmpty() const { return 0 == fList.count(); }
+
/**
- * Return an array of rects for this clip. Use countRects() to know the
- * number of entries.
+ * Resets this clip to be empty
*/
- const GrIRect* getRects() const {
- return fList.count() > 0 ? fList.begin() : &fBounds;
- }
-
-#if GR_DEBUG
- void validate() const;
-#else
- void validate() const {}
-#endif
+ void setEmpty();
+ void setFromIterator(GrClipIterator* iter, const GrRect* bounds = NULL);
+ void setFromRect(const GrRect& rect);
+ void setFromIRect(const GrIRect& rect);
-private:
- GrTDArray<GrIRect> fList;
- GrIRect fBounds;
-};
+ friend bool operator==(const GrClip& a, const GrClip& b) {
+ if (a.fList.count() != b.fList.count()) {
+ return false;
+ }
+ int count = a.fList.count();
+ for (int i = 0; i < count; ++i) {
+ if (a.fList[i] != b.fList[i]) {
+ return false;
+ }
+ }
+ return true;
+ }
+ friend bool operator!=(const GrClip& a, const GrClip& b) {
+ return !(a == b);
+ }
-class GrClipIter : public GrClipIterator {
-public:
- GrClipIter(const GrClip& clip) : fClip(&clip), fIndex(0) {}
- GrClipIter() : fClip(NULL), fIndex(0) {}
-
- void reset(const GrClip& clip);
-
- virtual bool isDone();
- virtual void rewind();
- virtual void getRect(GrIRect* r);
- virtual void next();
- virtual void computeBounds(GrIRect* r);
-
private:
- const GrClip* fClip;
- int fIndex;
+ struct Element {
+ GrClipType fType;
+ GrRect fRect;
+ GrPath fPath;
+ GrPathFill fPathFill;
+ GrSetOp fOp;
+ bool operator ==(const Element& e) const {
+ if (e.fType != fType || e.fOp != fOp) {
+ return false;
+ }
+ switch (fType) {
+ case kRect_ClipType:
+ return fRect == e.fRect;
+ break;
+ case kPath_ClipType:
+ return fPath == e.fPath;
+ default:
+ GrCrash("Unknown clip element type.");
+ return false; // suppress warning
+ }
+ }
+ bool operator !=(const Element& e) const { return !(*this == e); }
+ };
+
+ GrRect fBounds;
+ bool fBoundsValid;
+
+ enum {
+ kPreAllocElements = 4,
+ };
+ uint8_t fListMemory[sizeof(Element) * kPreAllocElements];
+ GrTArray<Element> fList;
};
-
#endif
diff --git a/gpu/include/GrClipIterator.h b/gpu/include/GrClipIterator.h
index d1fe4dde2f..abad619623 100644
--- a/gpu/include/GrClipIterator.h
+++ b/gpu/include/GrClipIterator.h
@@ -18,54 +18,60 @@
#ifndef GrClipIterator_DEFINED
#define GrClipIterator_DEFINED
+#include "GrPath.h"
#include "GrRect.h"
+/**
+ * A clip is a list of paths and/or rects with set operations to combine them.
+ */
class GrClipIterator {
public:
- GrClipIterator() : fNeedBounds(true) {}
virtual ~GrClipIterator() {}
/**
* Returns true if there are no more rects to process
*/
- virtual bool isDone() = 0;
+ virtual bool isDone() const = 0;
/**
- * Rewind the iterate to replay the set of rects again
+ * Rewind the iterator to replay the set of clip elements again
*/
virtual void rewind() = 0;
/**
- * Return the current rect. It is an error to call this when done() is true
+ * Get the type of the current clip element
*/
- virtual void getRect(GrIRect*) = 0;
+ virtual GrClipType getType() const = 0;
/**
- * Call to move to the next rect in the set
+ * Return the current path. It is an error to call this when isDone() is
+ * true or when getType() is kRect_Type.
*/
- virtual void next() = 0;
+ virtual GrPathIter* getPathIter() = 0;
/**
- * Set bounds to be the bounds of the clip.
+ * Return the fill rule for the path. It is an error to call this when
+ * isDone() is true or when getType is kRect_Type.
*/
- virtual void computeBounds(GrIRect* bounds) = 0;
+ virtual GrPathFill getPathFill() const = 0;
+
+ /**
+ * Return the current rect. It is an error to call this when isDone is true
+ * or when getType() is kPath_Type.
+ */
+ virtual void getRect(GrRect* rect) const = 0;
/**
- * Subclass should call this whenever their underlying bounds has changed.
+ * Gets the operation used to apply the current item to previously iterated
+ * items. Iterators should not produce a Replace op.
*/
- void invalidateBoundsCache() { fNeedBounds = true; }
-
- const GrIRect& getBounds() {
- if (fNeedBounds) {
- this->computeBounds(&fBounds);
- fNeedBounds = false;
- }
- return fBounds;
- }
+ virtual GrSetOp getOp() const = 0;
-private:
- GrIRect fBounds;
- bool fNeedBounds;
+ /**
+ * Call to move to the next rect in the set, previous path iter can be made
+ * invalid.
+ */
+ virtual void next() = 0;
};
/**
diff --git a/gpu/include/GrContext.h b/gpu/include/GrContext.h
index caba6efcec..b43375cb48 100644
--- a/gpu/include/GrContext.h
+++ b/gpu/include/GrContext.h
@@ -278,16 +278,23 @@ public:
const GrMatrix* srcMatrix = NULL);
/**
- * Tessellates and draws a path.
+ * Draws a path.
*
* @param paint describes how to color pixels.
- * @param path the path to draw
+ * @param pathIter the path to draw
* @param fill the path filling rule to use.
* @param translate optional additional translation applied to the
* path.
*/
void drawPath(const GrPaint& paint,
- GrPathIter* path,
+ GrPathIter* pathIter,
+ GrPathFill fill,
+ const GrPoint* translate = NULL);
+ /**
+ * Helper version of drawPath that takes a GrPath
+ */
+ void drawPath(const GrPaint& paint,
+ const GrPath& path,
GrPathFill fill,
const GrPoint* translate = NULL);
/**
diff --git a/gpu/include/GrDrawTarget.h b/gpu/include/GrDrawTarget.h
index 10c6d48462..576bd7ae41 100644
--- a/gpu/include/GrDrawTarget.h
+++ b/gpu/include/GrDrawTarget.h
@@ -23,9 +23,10 @@
#include "GrRefCnt.h"
#include "GrSamplerState.h"
#include "GrClip.h"
+#include "GrTexture.h"
+#include "GrStencil.h"
class GrTexture;
-class GrRenderTarget;
class GrClipIterator;
class GrVertexBuffer;
class GrIndexBuffer;
@@ -72,56 +73,63 @@ public:
kClip_StateBit = 0x4,//<! Controls whether drawing is clipped
// against the region specified by
// setClip.
+ kNoColorWrites_StateBit = 0x8,//<! If set it disables writing colors.
+ // Useful while performing stencil ops.
+
+ // subclass may use additional bits internally
+ kDummyStateBit,
+ kLastPublicStateBit = kDummyStateBit-1
+ };
+
+ enum DrawFace {
+ kBoth_DrawFace,
+ kCCW_DrawFace,
+ kCW_DrawFace,
};
/**
- * StencilPass
- *
- * Sets the stencil state for subsequent draw calls. Used to fill paths.
- *
- * Winding requires two passes when the GPU/API doesn't support separate
- * stencil.
- *
- * The color pass for path fill is used to zero out stencil bits used for
- * path filling. Every pixel covere by a winding/EO stencil pass must get
- * covered by the color pass in order to leave stencil buffer in the correct
- * state for the next path draw.
- *
- * NOTE: Stencil-based Winding fill has alias-to-zero problems. (e.g. A
- * winding count of 128,256,512,etc with a 8 bit stencil buffer
- * will be unfilled)
+ * The DrawTarget may reserve some of the high bits of the stencil. The draw
+ * target will automatically trim reference and mask values so that the
+ * client doesn't overwrite these bits.
+ * The number of bits available is relative to the currently set render
+ *target.
+ * @return the number of bits usable by the draw target client.
*/
- enum StencilPass {
- kNone_StencilPass, //<! Not drawing a path or clip.
- kEvenOddStencil_StencilPass, //<! records in/out in stencil buffer
- // using the Even/Odd fill rule.
- kEvenOddColor_StencilPass, //<! writes colors to color target in
- // pixels marked inside the fill by
- // kEOFillStencil_StencilPass. Clears
- // stencil in pixels covered by
- // geometry.
- kWindingStencil1_StencilPass, //<! records in/out in stencil buffer
- // using the Winding fill rule.
- kWindingStencil2_StencilPass, //<! records in/out in stencil buffer
- // using the Winding fill rule.
- // Run when single-stencil-pass winding
- // not supported (i.e. no separate
- // stencil support)
- kWindingColor_StencilPass, //<! writes colors to color target in
- // pixels marked inside the fill by
- // kWindFillStencil_StencilPass. Clears
- // stencil in pixels covered by
- // geometry.
- kDrawTargetCount_StencilPass //<! Subclass may extend this enum to use
- // the stencil for other purposes (e.g.
- // to do stencil-based clipping)
- // This value is provided as basis for
- // defining these extended enum values.
- };
+ int getUsableStencilBits() const {
+ int bits = fCurrDrawState.fRenderTarget->stencilBits();
+ if (bits) {
+ return bits - 1;
+ } else {
+ return 0;
+ }
+ }
+
+ /**
+ * Sets the stencil settings to use for the next draw.
+ * @param settings the stencil settings to use.
+ */
+ void setStencil(const GrStencilSettings& settings) {
+ fCurrDrawState.fStencilSettings = settings;
+ }
+
+ /**
+ * Shortcut to disable stencil testing and ops.
+ */
+ void disableStencil() {
+ fCurrDrawState.fStencilSettings.setDisabled();
+ }
protected:
struct DrState {
+ DrState() {
+ // make sure any pad is zero for memcmp
+ // all DrState members should default to something
+ // valid by the memset
+ memset(this, 0, sizeof(DrState));
+ GrAssert((intptr_t)(void*)NULL == 0LL);
+ GrAssert(fStencilSettings.isDisabled());
+ }
uint32_t fFlagBits;
GrBlendCoeff fSrcBlend;
GrBlendCoeff fDstBlend;
@@ -129,8 +137,9 @@ protected:
GrSamplerState fSamplerStates[kNumStages];
GrRenderTarget* fRenderTarget;
GrColor fColor;
- StencilPass fStencilPass;
- bool fReverseFill;
+ DrawFace fDrawFace;
+
+ GrStencilSettings fStencilSettings;
GrMatrix fViewMatrix;
bool operator ==(const DrState& s) const {
return 0 == memcmp(this, &s, sizeof(DrState));
@@ -196,7 +205,7 @@ public:
/**
* Sets the sampler state for a stage used in subsequent draws.
*
- * The sampler state determines how texture coordinates are
+ * The sampler state determines how texture coordinates are
* intepretted and used to sample the texture.
*
* @param stage the stage of the sampler to set
@@ -291,19 +300,17 @@ public:
void setAlpha(uint8_t alpha);
/**
- * Sets pass for path rendering
- *
- * @param pass of path rendering
+ * Controls whether clockwise, counterclockwise, or both faces are drawn.
+ * @param face the face(s) to draw.
*/
- void setStencilPass(StencilPass pass);
+ void setDrawFace(DrawFace face) { fCurrDrawState.fDrawFace = face; }
/**
- * Reveses the in/out decision of the fill rule for path rendering.
- * Only affects kEOFillColor_StencilPass and kWindingFillColor_StencilPass
- *
- * @param reverse true to reverse, false otherwise
+ * Gets whether the target is drawing clockwise, counterclockwise,
+ * or both faces.
+ * @return the current draw face(s).
*/
- void setReverseFill(bool reverse);
+ DrawFace getDrawFace() const { return fCurrDrawState.fDrawFace; }
/**
* Enable render state settings.
@@ -327,6 +334,10 @@ public:
return 0 != (fCurrDrawState.fFlagBits & kClip_StateBit);
}
+ bool isColorWriteDisabled() const {
+ return 0 != (fCurrDrawState.fFlagBits & kNoColorWrites_StateBit);
+ }
+
/**
* Sets the blending function coeffecients.
*
@@ -457,8 +468,8 @@ public:
// text [GrGpuTextVertex vs
// GrPoint].)
// for below assert
- kDummy,
- kHighVertexLayoutBit = kDummy - 1
+ kDummyVertexLayoutBit,
+ kHighVertexLayoutBit = kDummyVertexLayoutBit - 1
};
// make sure we haven't exceeded the number of bits in GrVertexLayout.
GR_STATIC_ASSERT(kHighVertexLayoutBit < (1 << 8*sizeof(GrVertexLayout)));
@@ -648,7 +659,7 @@ public:
* have changed. They should be reestablished before the next drawIndexed
* or drawNonIndexed. This cannot be called between reserving and releasing
* geometry. The GrDrawTarget subclass may be able to perform additional
- * optimizations if drawRect is used rather than drawIndexed or
+ * optimizations if drawRect is used rather than drawIndexed or
* drawNonIndexed.
* @param rect the rect to draw
* @param matrix optional matrix applied to rect (before viewMatrix)
@@ -665,18 +676,18 @@ public:
* srcMatrix[i]. srcMatrices can be NULL when no
* srcMatrices are desired.
*/
- virtual void drawRect(const GrRect& rect,
+ virtual void drawRect(const GrRect& rect,
const GrMatrix* matrix,
StageBitfield stageEnableBitfield,
const GrRect* srcRects[],
const GrMatrix* srcMatrices[]);
/**
- * Helper for drawRect when the caller doesn't need separate src rects or
+ * Helper for drawRect when the caller doesn't need separate src rects or
* matrices.
*/
- void drawSimpleRect(const GrRect& rect,
- const GrMatrix* matrix,
+ void drawSimpleRect(const GrRect& rect,
+ const GrMatrix* matrix,
StageBitfield stageEnableBitfield) {
drawRect(rect, matrix, stageEnableBitfield, NULL, NULL);
}
@@ -912,20 +923,20 @@ public:
* Defaults to zero (corresponding to vertex position)
* @return pointer to the vertex component as a GrPoint
*/
- static GrPoint* GetVertexPoint(void* vertices,
+ static GrPoint* GetVertexPoint(void* vertices,
int vertexIndex,
int vertexSize,
int offset = 0) {
intptr_t start = GrTCast<intptr_t>(vertices);
- return GrTCast<GrPoint*>(start + offset +
+ return GrTCast<GrPoint*>(start + offset +
vertexIndex * vertexSize);
}
static const GrPoint* GetVertexPoint(const void* vertices,
int vertexIndex,
- int vertexSize,
+ int vertexSize,
int offset = 0) {
intptr_t start = GrTCast<intptr_t>(vertices);
- return GrTCast<const GrPoint*>(start + offset +
+ return GrTCast<const GrPoint*>(start + offset +
vertexIndex * vertexSize);
}
@@ -937,20 +948,20 @@ public:
* @param offset the offset in bytes of the vertex color
* @return pointer to the vertex component as a GrColor
*/
- static GrColor* GetVertexColor(void* vertices,
+ static GrColor* GetVertexColor(void* vertices,
int vertexIndex,
int vertexSize,
int offset) {
intptr_t start = GrTCast<intptr_t>(vertices);
- return GrTCast<GrColor*>(start + offset +
+ return GrTCast<GrColor*>(start + offset +
vertexIndex * vertexSize);
}
static const GrColor* GetVertexColor(const void* vertices,
int vertexIndex,
- int vertexSize,
+ int vertexSize,
int offset) {
const intptr_t start = GrTCast<intptr_t>(vertices);
- return GrTCast<const GrColor*>(start + offset +
+ return GrTCast<const GrColor*>(start + offset +
vertexIndex * vertexSize);
}
@@ -985,10 +996,10 @@ protected:
const GrRect* srcRects[]);
static void SetRectVertices(const GrRect& rect,
- const GrMatrix* matrix,
- const GrRect* srcRects[],
+ const GrMatrix* matrix,
+ const GrRect* srcRects[],
const GrMatrix* srcMatrices[],
- GrVertexLayout layout,
+ GrVertexLayout layout,
void* vertices);
enum GeometrySrcType {
@@ -997,7 +1008,7 @@ protected:
kBuffer_GeometrySrcType // src was set using set*SourceToBuffer
};
- struct {
+ struct ReservedGeometry {
bool fLocked;
uint32_t fVertexCount;
uint32_t fIndexCount;
diff --git a/gpu/include/GrGLTexture.h b/gpu/include/GrGLTexture.h
index fc12ee0878..14370abb80 100644
--- a/gpu/include/GrGLTexture.h
+++ b/gpu/include/GrGLTexture.h
@@ -36,9 +36,6 @@ public:
GLuint renderFBOID() const { return fRTFBOID; }
GLuint textureFBOID() const { return fTexFBOID; }
- GLuint getStencilBits() const { return fStencilBits; }
-
- const GrGLIRect& viewport() const { return fViewport; }
void abandon();
protected:
@@ -58,17 +55,13 @@ protected:
GrGpuGL* gl);
void setViewport(const GrGLIRect& rect) { fViewport = rect; }
-
- virtual int width() const { return fViewport.fWidth; }
- virtual int height() const { return fViewport.fHeight; }
-
+ const GrGLIRect& getViewport() const { return fViewport; }
private:
GrGpuGL* fGL;
GLuint fRTFBOID;
GLuint fTexFBOID;
GLuint fStencilRenderbufferID;
GLuint fMSColorRenderbufferID;
- GLuint fStencilBits;
// Should this object delete IDs when it is destroyed or does someone
// else own them.
diff --git a/gpu/include/GrGpu.h b/gpu/include/GrGpu.h
index 661708b51a..5a88ef481f 100644
--- a/gpu/include/GrGpu.h
+++ b/gpu/include/GrGpu.h
@@ -25,6 +25,7 @@
class GrVertexBufferAllocPool;
class GrIndexBufferAllocPool;
+class GrPathRenderer;
class GrGpu : public GrDrawTarget {
@@ -229,15 +230,21 @@ public:
bool supports8BitPalette() const { return f8bitPaletteSupport; }
/**
- * If single stencil pass winding is supported then one stencil pass
- * (kWindingStencil1_PathPass) is required to do winding rule path filling
- * (or inverse winding rule). Otherwise, two passes are required
- * (kWindingStencil1_PathPass followed by kWindingStencil2_PathPass).
- *
+ * returns true if two sided stenciling is supported. If false then only
+ * the front face values of the GrStencilSettings
* @return true if only a single stencil pass is needed.
*/
- bool supportsSingleStencilPassWinding() const
- { return fSingleStencilPassForWinding; }
+ bool supportsTwoSidedStencil() const
+ { return fTwoSidedStencilSupport; }
+
+ /**
+ * returns true if stencil wrap is supported. If false then
+ * kIncWrap_StencilOp and kDecWrap_StencilOp are treated as
+ * kIncClamp_StencilOp and kDecClamp_StencilOp, respectively.
+ * @return true if stencil wrap ops are supported.
+ */
+ bool supportsStencilWrapOps() const
+ { return fStencilWrapOpsSupport; }
/**
* Checks whether locking vertex and index buffers is supported.
@@ -304,7 +311,7 @@ public:
const GrIndexBuffer* getQuadIndexBuffer() const;
/**
- * Returns a vertex buffer with four position-only vertices [(0,0), (1,0),
+ * Returns a vertex buffer with four position-only vertices [(0,0), (1,0),
* (1,1), (0,1)].
* @ return unit square vertex buffer
*/
@@ -326,16 +333,12 @@ public:
void printStats() const;
protected:
- /**
- * Extensions to GrDrawTarget::StencilPass to implement stencil clipping
- */
- enum GpuStencilPass {
- kSetClip_StencilPass = kDrawTargetCount_StencilPass,
- /* rendering a hard clip to the stencil
- buffer. Subsequent draws with other
- StencilPass values will be clipped
- if kClip_StateBit is set. */
- kGpuCount_StencilPass
+ enum PrivateStateBits {
+ kFirstBit = (kLastPublicStateBit << 1),
+
+ kModifyStencilClip_StateBit = kFirstBit, // allows draws to modify
+ // stencil bits used for
+ // clipping.
};
/**
@@ -344,7 +347,6 @@ protected:
struct ClipState {
bool fClipInStencil;
bool fClipIsDirty;
- GrRenderTarget* fStencilClipTarget;
} fClipState;
// GrDrawTarget override
@@ -353,6 +355,21 @@ protected:
// prepares clip flushes gpu state before a draw
bool setupClipAndFlushState(GrPrimitiveType type);
+ // Functions used to map clip-respecting stencil tests into normal
+ // stencil funcs supported by GPUs.
+ static GrStencilFunc ConvertStencilFunc(bool stencilInClip,
+ GrStencilFunc func);
+ static void ConvertStencilFuncAndMask(GrStencilFunc func,
+ bool clipInStencil,
+ unsigned int clipBit,
+ unsigned int userBits,
+ unsigned int* ref,
+ unsigned int* mask);
+
+ // stencil settings to clip drawing when stencil clipping is in effect
+ // and the client isn't using the stencil test.
+ static const GrStencilSettings gClipStencilSettings;
+
// defaults to false, subclass can set true to support palleted textures
bool f8bitPaletteSupport;
@@ -360,10 +377,8 @@ protected:
bool fNPOTTextureSupport;
bool fNPOTTextureTileSupport;
bool fNPOTRenderTargetSupport;
-
- // True if only one stencil pass is required to implement the winding path
- // fill rule. Subclass responsible for setting this value.
- bool fSingleStencilPassForWinding;
+ bool fTwoSidedStencilSupport;
+ bool fStencilWrapOpsSupport;
// set by subclass to true if index and vertex buffers can be locked, false
// otherwise.
@@ -427,13 +442,15 @@ protected:
virtual void flushScissor(const GrIRect* rect) = 0;
// GrGpu subclass removes the clip from the stencil buffer
- virtual void eraseStencilClip() = 0;
+ virtual void eraseStencilClip(const GrIRect& rect) = 0;
private:
-
+ // readies the pools to provide vertex/index data.
void prepareVertexPool();
void prepareIndexPool();
+ GrPathRenderer* getPathRenderer();
+
GrVertexBufferAllocPool* fVertexPool;
GrIndexBufferAllocPool* fIndexPool;
@@ -443,6 +460,61 @@ private:
mutable GrVertexBuffer* fUnitSquareVertexBuffer; // mutable so it can be
// created on-demand
+
+ GrPathRenderer* fPathRenderer;
+
+ // when in an internal draw these indicate whether the pools are in use
+ // by one of the outer draws. If false then it is safe to reset the
+ // pool.
+ bool fVertexPoolInUse;
+ bool fIndexPoolInUse;
+
+ // used to save and restore state when the GrGpu needs
+ // to make its geometry pools available internally
+ class AutoInternalDrawGeomRestore {
+ public:
+ AutoInternalDrawGeomRestore(GrGpu* gpu) : fAgsr(gpu) {
+ fGpu = gpu;
+
+ fVertexPoolWasInUse = gpu->fVertexPoolInUse;
+ fIndexPoolWasInUse = gpu->fIndexPoolInUse;
+
+ gpu->fVertexPoolInUse = fVertexPoolWasInUse ||
+ (kBuffer_GeometrySrcType !=
+ gpu->fGeometrySrc.fVertexSrc);
+ gpu->fIndexPoolInUse = fIndexPoolWasInUse ||
+ (kBuffer_GeometrySrcType !=
+ gpu->fGeometrySrc.fIndexSrc);;
+
+ fSavedPoolVertexBuffer = gpu->fCurrPoolVertexBuffer;
+ fSavedPoolStartVertex = gpu->fCurrPoolStartVertex;
+ fSavedPoolIndexBuffer = gpu->fCurrPoolIndexBuffer;
+ fSavedPoolStartIndex = gpu->fCurrPoolStartIndex;
+
+ fSavedReservedGeometry = gpu->fReservedGeometry;
+ gpu->fReservedGeometry.fLocked = false;
+ }
+ ~AutoInternalDrawGeomRestore() {
+ fGpu->fCurrPoolVertexBuffer = fSavedPoolVertexBuffer;
+ fGpu->fCurrPoolStartVertex = fSavedPoolStartVertex;
+ fGpu->fCurrPoolIndexBuffer = fSavedPoolIndexBuffer;
+ fGpu->fCurrPoolStartIndex = fSavedPoolStartIndex;
+ fGpu->fVertexPoolInUse = fVertexPoolWasInUse;
+ fGpu->fIndexPoolInUse = fIndexPoolWasInUse;
+ fGpu->fReservedGeometry = fSavedReservedGeometry;
+ }
+ private:
+ AutoGeometrySrcRestore fAgsr;
+ GrGpu* fGpu;
+ const GrVertexBuffer* fSavedPoolVertexBuffer;
+ int fSavedPoolStartVertex;
+ const GrIndexBuffer* fSavedPoolIndexBuffer;
+ int fSavedPoolStartIndex;
+ bool fVertexPoolWasInUse;
+ bool fIndexPoolWasInUse;
+ ReservedGeometry fSavedReservedGeometry;
+ };
+
typedef GrDrawTarget INHERITED;
};
diff --git a/gpu/include/GrPath.h b/gpu/include/GrPath.h
index cf7b97f2d8..23fc4a86b6 100644
--- a/gpu/include/GrPath.h
+++ b/gpu/include/GrPath.h
@@ -35,6 +35,8 @@ public:
void resetFromIter(GrPathIter*);
+ bool operator ==(const GrPath& path) const;
+ bool operator !=(const GrPath& path) const { return !(*this == path); }
// overrides from GrPathSink
virtual void moveTo(GrScalar x, GrScalar y);
@@ -50,7 +52,7 @@ public:
// overrides from GrPathIter
virtual Command next(GrPoint points[]);
- virtual ConvexHint hint() const;
+ virtual ConvexHint convexHint() const;
virtual Command next();
virtual void rewind();
private:
diff --git a/gpu/include/GrPathIter.h b/gpu/include/GrPathIter.h
index 028faaa14d..140cbcba56 100644
--- a/gpu/include/GrPathIter.h
+++ b/gpu/include/GrPathIter.h
@@ -30,7 +30,7 @@ struct GrPoint;
class GrPathIter {
public:
/**
- Returned by next(). Indicates the next piece of the path.
+ Returned by next(). Indicates the next piece of the path.
*/
enum Command {
kMove_Command, //!< next() returns 1 pt
@@ -44,35 +44,35 @@ public:
// Adds a cubic segment
kClose_Command, //!< next() returns 0 pts
kEnd_Command //!< next() returns 0 pts
- // Implictly closes the last
+ // Implictly closes the last
// point
};
-
+
enum ConvexHint {
- kNone_ConvexHint, //<! No hint about convexity
+ kNone_ConvexHint, //<! No hint about convexity
// of the path
kConvex_ConvexHint, //<! Path is one convex piece
- kNonOverlappingConvexPieces_ConvexHint, //<! Multiple convex pieces,
+ kNonOverlappingConvexPieces_ConvexHint, //<! Multiple convex pieces,
// pieces are known to be
// disjoint
- kSameWindingConvexPieces_ConvexHint, //<! Multiple convex pieces,
+ kSameWindingConvexPieces_ConvexHint, //<! Multiple convex pieces,
// may or may not intersect,
- // either all wind cw or all
+ // either all wind cw or all
// wind ccw.
- kConcave_ConvexHint //<! Path is known to be
+ kConcave_ConvexHint //<! Path is known to be
// concave
};
-
+
static int NumCommandPoints(Command cmd) {
static const int numPoints[] = {
1, 2, 3, 4, 0, 0
};
return numPoints[cmd];
}
-
+
virtual ~GrPathIter() {};
- /**
+ /**
Iterates through the path. Should not be called after
kEnd_Command has been returned once. This version retrieves the
points for the command.
@@ -85,14 +85,14 @@ public:
/**
* If the host API has knowledge of the convexity of the path
* it can be communicated by this hint. Ganesh can make these
- * determinations itself. So it is not necessary to compute
+ * determinations itself. So it is not necessary to compute
* convexity status if it isn't already determined.
*
* @return a hint about the convexity of the path.
- */
- virtual ConvexHint hint() const { return kNone_ConvexHint; }
+ */
+ virtual ConvexHint convexHint() const { return kNone_ConvexHint; }
- /**
+ /**
Iterates through the path. Should not be called after
kEnd_Command has been returned once. This version does not retrieve the
points for the command.
diff --git a/gpu/include/GrRect.h b/gpu/include/GrRect.h
index e98913a57c..96d302f53d 100644
--- a/gpu/include/GrRect.h
+++ b/gpu/include/GrRect.h
@@ -22,7 +22,7 @@
struct GrIRect {
int32_t fLeft, fTop, fRight, fBottom;
-
+
GrIRect() {}
GrIRect(int32_t left, int32_t top, int32_t right, int32_t bottom) {
fLeft = left;
@@ -47,23 +47,22 @@ struct GrIRect {
fRight = x + w;
fBottom = y + h;
}
-
+
void setLTRB(int32_t l, int32_t t, int32_t r, int32_t b) {
fLeft = l;
fTop = t;
fRight = r;
fBottom = b;
}
-
+
/**
* Make the largest representable rectangle
-
*/
void setLargest() {
fLeft = fTop = GR_Int32Min;
fRight = fBottom = GR_Int32Max;
}
-
+
bool quickReject(int l, int t, int r, int b) const {
return l >= fRight || fLeft >= r || t >= fBottom || fTop >= b;
}
@@ -75,10 +74,28 @@ struct GrIRect {
if (fBottom < r.fBottom) fBottom = r.fBottom;
}
+ /**
+ * Sets this rect to the intersection with a clip rect. If there is no
+ * intersection then this rect will be made empty.
+ */
+ void intersectWith(const GrIRect& clipRect) {
+ if (fRight < clipRect.fLeft ||
+ fLeft > clipRect.fRight ||
+ fBottom < clipRect.fTop ||
+ fTop > clipRect.fBottom) {
+ this->setEmpty();
+ } else {
+ fLeft = GrMax(fLeft, clipRect.fLeft);
+ fRight = GrMin(fRight, clipRect.fRight);
+ fTop = GrMax(fTop, clipRect.fTop);
+ fBottom = GrMin(fBottom, clipRect.fBottom);
+ }
+ }
+
friend bool operator==(const GrIRect& a, const GrIRect& b) {
return 0 == memcmp(&a, &b, sizeof(a));
}
-
+
friend bool operator!=(const GrIRect& a, const GrIRect& b) {
return 0 != memcmp(&a, &b, sizeof(a));
}
@@ -91,7 +108,7 @@ struct GrIRect {
return fLeft == x && fTop == y &&
this->width() == w && this->height() == h;
}
-
+
bool contains(const GrIRect& r) const {
return fLeft <= r.fLeft &&
fRight >= r.fRight &&
@@ -102,12 +119,12 @@ struct GrIRect {
struct GrIRect16 {
int16_t fLeft, fTop, fRight, fBottom;
-
+
int width() const { return fRight - fLeft; }
int height() const { return fBottom - fTop; }
int area() const { return this->width() * this->height(); }
bool isEmpty() const { return fLeft >= fRight || fTop >= fBottom; }
-
+
void set(const GrIRect& r) {
fLeft = GrToS16(r.fLeft);
fTop = GrToS16(r.fTop);
@@ -116,12 +133,12 @@ struct GrIRect16 {
}
};
-/**
+/**
* 2D Rect struct
*/
struct GrRect {
GrScalar fLeft, fTop, fRight, fBottom;
-
+
/**
* Uninitialized rectangle.
*/
@@ -158,7 +175,7 @@ struct GrRect {
GrScalar top() const { return fTop; }
GrScalar right() const { return fRight; }
GrScalar bottom() const { return fBottom; }
-
+
GrScalar diagonalLengthSqd() const {
GrScalar w = width();
GrScalar h = height();
@@ -169,18 +186,18 @@ struct GrRect {
// TODO: fixed point sqrt
return GrFloatToScalar(sqrtf(GrScalarToFloat(diagonalLengthSqd())));
}
-
+
/**
* Returns true if the width or height is <= 0
*/
bool isEmpty() const {
return fLeft >= fRight || fTop >= fBottom;
}
-
+
void setEmpty() {
fLeft = fTop = fRight = fBottom = 0;
}
-
+
/**
* returns true if the rectangle is inverted either in x or y
*/
@@ -192,7 +209,7 @@ struct GrRect {
return point.fX >= fLeft && point.fX < fRight &&
point.fY >= fTop && point.fY < fBottom;
}
-
+
/**
* Initialize a rectangle to a point.
* @param pt the point used to initialize the rectangle.
@@ -226,16 +243,16 @@ struct GrRect {
/**
* Make the largest representable rectangle
- * Set the rect to fLeft = fTop = GR_ScalarMin and
+ * Set the rect to fLeft = fTop = GR_ScalarMin and
* fRight = fBottom = GR_ScalarMax.
*/
void setLargest() {
fLeft = fTop = GR_ScalarMin;
fRight = fBottom = GR_ScalarMax;
}
-
+
/**
- Set the rect to fLeft = fTop = GR_ScalarMax and
+ Set the rect to fLeft = fTop = GR_ScalarMax and
fRight = fBottom = GR_ScalarMin.
Useful for initializing a bounding rectangle.
*/
@@ -243,24 +260,24 @@ struct GrRect {
fLeft = fTop = GR_ScalarMax;
fRight = fBottom = GR_ScalarMin;
}
-
- void setLTRB(GrScalar left,
- GrScalar top,
- GrScalar right,
+
+ void setLTRB(GrScalar left,
+ GrScalar top,
+ GrScalar right,
GrScalar bottom) {
fLeft = left;
fTop = top;
fRight = right;
fBottom = bottom;
}
-
+
void setXYWH(GrScalar x, GrScalar y, GrScalar width, GrScalar height) {
fLeft = x;
fTop = y;
fRight = x + width;
fBottom = y + height;
}
-
+
/**
Expand the edges of the rectangle to include a point.
Useful for constructing a bounding rectangle.
@@ -269,12 +286,43 @@ struct GrRect {
void growToInclude(const GrPoint& pt) {
fLeft = GrMin(pt.fX, fLeft);
fRight = GrMax(pt.fX, fRight);
-
+
fTop = GrMin(pt.fY, fTop);
fBottom = GrMax(pt.fY, fBottom);
}
/**
+ * Grows a rect to include another rect.
+ * @param rect the rect to include
+ */
+ void growToInclude(const GrRect& rect) {
+ GrAssert(!rect.isEmpty());
+ fLeft = GrMin(rect.fLeft, fLeft);
+ fRight = GrMax(rect.fRight, fRight);
+
+ fTop = GrMin(rect.fTop, fTop);
+ fBottom = GrMax(rect.fBottom, fBottom);
+ }
+
+ /**
+ * Sets this rect to the intersection with a clip rect. If there is no
+ * intersection then this rect will be made empty.
+ */
+ void intersectWith(const GrRect& clipRect) {
+ if (fRight < clipRect.fLeft ||
+ fLeft > clipRect.fRight ||
+ fBottom < clipRect.fTop ||
+ fTop > clipRect.fBottom) {
+ this->setEmpty();
+ } else {
+ fLeft = GrMax(fLeft, clipRect.fLeft);
+ fRight = GrMin(fRight, clipRect.fRight);
+ fTop = GrMax(fTop, clipRect.fTop);
+ fBottom = GrMin(fBottom, clipRect.fBottom);
+ }
+ }
+
+ /**
* Assigns 4 sequential points in order to construct a counter-clockwise
* triangle fan, given the corners of this rect. Returns the address of
* the next point, treating pts as an array.
@@ -283,6 +331,13 @@ struct GrRect {
pts->setRectFan(fLeft, fTop, fRight, fBottom);
return pts + 4;
}
+
+ bool operator ==(const GrRect& r) const {
+ return fLeft == r.fLeft &&
+ fTop == r.fTop &&
+ fRight == r.fRight &&
+ fBottom == r.fBottom;
+ }
};
#endif
diff --git a/gpu/include/GrStencil.h b/gpu/include/GrStencil.h
new file mode 100644
index 0000000000..be3e0f66fb
--- /dev/null
+++ b/gpu/include/GrStencil.h
@@ -0,0 +1,211 @@
+/*
+ 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 GrStencil_DEFINED
+#define GrStencil_DEFINED
+
+#include "GrTypes.h"
+/**
+ * Gr uses the stencil buffer to implement complex clipping inside the
+ * GrDrawTarget class. The GrDrawTarget makes a subset of the stencil buffer
+ * bits available for other uses by external code (clients). Client code can
+ * modify these bits. GrDrawTarget will ignore ref, mask, and writemask bits
+ * provided by clients that overlap the bits used to implement clipping. The
+ * client can use the getUsableStencilBits() function to find out how many
+ * client accessible stencil bits are available.
+ *
+ * When code outside the GrDrawTarget class uses the stencil buffer the contract
+ * is as follows:
+ *
+ * > Normal stencil funcs allow the GrGpu client to modify the client bits of
+ * the stencil buffer outside of the clip.
+ * > Special functions allow a test against the clip. These are more limited
+ * than the general stencil functions.
+ * > Client can assume all client bits are zero initially.
+ * > Client must ensure that after all its passes are finished it has only
+ * written to the color buffer in the region inside the clip. Furthermore, it
+ * must zero all client bits that were modifed (both inside and outside the
+ * clip).
+ */
+
+/**
+ * Determines which pixels pass / fail the stencil test.
+ * Stencil test passes if (ref & mask) FUNC (stencil & mask) is true
+ */
+enum GrStencilFunc {
+ kAlways_StencilFunc = 0,
+ kNever_StencilFunc,
+ kGreater_StencilFunc,
+ kGEqual_StencilFunc,
+ kLess_StencilFunc,
+ kLEqual_StencilFunc,
+ kEqual_StencilFunc,
+ kNotEqual_StencilFunc,
+
+ // Gr stores the current clip in the
+ // stencil buffer in the high bits that
+ // are not directly accessible modifiable
+ // via the GrDrawTarget interface. The below
+ // stencil funcs test against the current
+ // clip in addition to the GrDrawTarget
+ // client's stencil bits.
+
+ // pass if inside the clip
+ kAlwaysIfInClip_StencilFunc,
+ kEqualIfInClip_StencilFunc,
+ kLessIfInClip_StencilFunc,
+ kLEqualIfInClip_StencilFunc,
+ kNonZeroIfInClip_StencilFunc, // this one forces the ref to be 0
+
+ // counts
+ kStencilFuncCount,
+ kClipStencilFuncCount = kNonZeroIfInClip_StencilFunc -
+ kAlwaysIfInClip_StencilFunc + 1,
+ kBasicStencilFuncCount = kStencilFuncCount - kClipStencilFuncCount
+};
+
+/**
+ * Operations to perform based on whether stencil test passed failed.
+ */
+enum GrStencilOp {
+ kKeep_StencilOp = 0, // preserve existing stencil value
+ kReplace_StencilOp, // replace with reference value from stencl test
+ kIncWrap_StencilOp, // increment and wrap at max
+ kIncClamp_StencilOp, // increment and clamp at max
+ kDecWrap_StencilOp, // decrement and wrap at 0
+ kDecClamp_StencilOp, // decrement and clamp at 0
+ kZero_StencilOp, // zero stencil bits
+ kInvert_StencilOp, // invert stencil bits
+
+ kStencilOpCount
+};
+
+/**
+ * Struct representing stencil state.
+ */
+struct GrStencilSettings {
+ GrStencilOp fFrontPassOp; // op to perform when front faces pass
+ GrStencilOp fBackPassOp; // op to perform when back faces pass
+ GrStencilOp fFrontFailOp; // op to perform when front faces fail
+ GrStencilOp fBackFailOp; // op to perform when back faces fail
+ GrStencilFunc fFrontFunc; // test function for front faces
+ GrStencilFunc fBackFunc; // test function for back faces
+ unsigned int fFrontFuncMask; // mask for front face test
+ unsigned int fBackFuncMask; // mask for back face test
+ unsigned int fFrontFuncRef; // reference value for front face test
+ unsigned int fBackFuncRef; // reference value for back face test
+ unsigned int fFrontWriteMask; // stencil write mask for front faces
+ unsigned int fBackWriteMask; // stencil write mask for back faces
+
+ bool operator == (const GrStencilSettings& s) const {
+ // make sure this is tightly packed.
+ GR_STATIC_ASSERT(0 == sizeof(GrStencilOp)%4);
+ GR_STATIC_ASSERT(0 == sizeof(GrStencilFunc)%4);
+ GR_STATIC_ASSERT(sizeof(GrStencilSettings) ==
+ 4*sizeof(GrStencilOp) +
+ 2*sizeof(GrStencilFunc) +
+ 6*sizeof(unsigned int));
+ return 0 == memcmp(this, &s, sizeof(GrStencilSettings));
+ }
+
+ bool operator != (const GrStencilSettings& s) const {
+ return !(*this == s);
+ }
+
+ GrStencilSettings& operator =(const GrStencilSettings& s) {
+ memcpy(this, &s, sizeof(GrStencilSettings));
+ return *this;
+ }
+
+ void setSame(GrStencilOp passOp,
+ GrStencilOp failOp,
+ GrStencilFunc func,
+ unsigned int funcMask,
+ unsigned int funcRef,
+ unsigned int writeMask) {
+ fFrontPassOp = passOp;
+ fBackPassOp = passOp;
+ fFrontFailOp = failOp;
+ fBackFailOp = failOp;
+ fFrontFunc = func;
+ fBackFunc = func;
+ fFrontFuncMask = funcMask;
+ fBackFuncMask = funcMask;
+ fFrontFuncRef = funcRef;
+ fBackFuncRef = funcRef;
+ fFrontWriteMask = writeMask;
+ fBackWriteMask = writeMask;
+ }
+
+ // canonical value for disabled stenciling
+ static const GrStencilSettings gDisabled;
+ void setDisabled() {
+ *this = gDisabled;
+ }
+ bool isDisabled() const {
+ return kKeep_StencilOp == fFrontPassOp &&
+ kKeep_StencilOp == fBackPassOp &&
+ kKeep_StencilOp == fFrontFailOp &&
+ kKeep_StencilOp == fFrontFailOp &&
+ kAlways_StencilFunc == fFrontFunc &&
+ kAlways_StencilFunc == fBackFunc;
+ }
+ void invalidate() {
+ // just write an illegal value to the first member
+ fFrontPassOp = (GrStencilOp)-1;
+ }
+
+private:
+ friend class GrGpu;
+
+ enum {
+ kMaxStencilClipPasses = 2 // maximum number of passes to add a clip
+ // element to the stencil buffer.
+ };
+
+ /**
+ * Given a thing to draw into the stencil clip, a fill type, and a set op
+ * this function determines:
+ * 1. Whether the thing can be draw directly to the stencil clip or
+ * needs to be drawn to the client portion of the stencil first.
+ * 2. How many passes are needed.
+ * 3. What those passes are.
+ * 4. The fill rule that should actually be used to render (will
+ * always be non-inverted).
+ *
+ * @param op the set op to combine this element with the
+ * existing clip
+ * @param stencilClipMask mask with just the stencil bit used for clipping
+ * enabled.
+ * @param fill in: the fill rule of the element to draw.
+ * out: the fill rule that should be used to draw
+ * @param numPasses out: the number of passes needed to add the
+ * element to the clip.
+ * @param settings out: the stencil settings to use for each pass
+ *
+ * @return true if the clip element's geometry can be drawn directly to the
+ * stencil clip bit. Will only be true if canBeDirect is true.
+ * numPasses will be 1 if return value is true.
+ */
+ static bool GetClipPasses(GrSetOp op,
+ bool canBeDirect,
+ unsigned int stencilClipMask,
+ GrPathFill* fill,
+ int* numPasses,
+ GrStencilSettings settings[kMaxStencilClipPasses]);
+};
+
+#endif
diff --git a/gpu/include/GrTArray.h b/gpu/include/GrTArray.h
index c31c820884..6ef1a13558 100644
--- a/gpu/include/GrTArray.h
+++ b/gpu/include/GrTArray.h
@@ -176,6 +176,8 @@ public:
}
}
+ void reset() { this->pop_back_n(fCount); }
+
int count() const { return fCount; }
bool empty() const { return !fCount; }
diff --git a/gpu/include/GrTexture.h b/gpu/include/GrTexture.h
index 098ac595a2..2d3928cb25 100644
--- a/gpu/include/GrTexture.h
+++ b/gpu/include/GrTexture.h
@@ -19,6 +19,7 @@
#define GrTexture_DEFINED
#include "GrRefCnt.h"
+#include "GrClip.h"
class GrTexture;
@@ -34,11 +35,16 @@ public:
/**
* @return the width of the rendertarget
*/
- virtual int width() const = 0;
+ int width() const { return fWidth; }
/**
* @return the height of the rendertarget
*/
- virtual int height() const = 0;
+ int height() const { return fHeight; }
+
+ /**
+ * @return the number of stencil bits in the rendertarget
+ */
+ int stencilBits() const { return fStencilBits; }
/**
* @return the texture associated with the rendertarget, may be NULL.
@@ -46,8 +52,28 @@ public:
GrTexture* asTexture() {return fTexture;}
protected:
- GrRenderTarget(GrTexture* texture) : fTexture(texture) {}
+ GrRenderTarget(GrTexture* texture,
+ int width,
+ int height,
+ int stencilBits)
+ : fTexture(texture),
+ fWidth(width),
+ fHeight(height),
+ fStencilBits(stencilBits) {}
+
+
GrTexture* fTexture;
+ int fWidth;
+ int fHeight;
+ int fStencilBits;
+
+private:
+ // GrGpu keeps a cached clip in the render target to avoid redundantly
+ // rendering the clip into the same stencil buffer.
+ friend class GrGpu;
+ GrClip fLastStencilClip;
+
+ typedef GrRefCnt INHERITED;
};
class GrTexture : public GrRefCnt {
diff --git a/gpu/include/GrTypes.h b/gpu/include/GrTypes.h
index 02a652a4c1..29e847fd09 100644
--- a/gpu/include/GrTypes.h
+++ b/gpu/include/GrTypes.h
@@ -201,6 +201,26 @@ enum GrBlendCoeff {
kIDA_BlendCoeff, //<! one minus dst alpha
};
+/**
+ * Set Operations used to construct clips.
+ */
+enum GrSetOp {
+ kReplace_SetOp,
+ kIntersect_SetOp,
+ kUnion_SetOp,
+ kXor_SetOp,
+ kDifference_SetOp,
+ kReverseDifference_SetOp,
+};
+
+/**
+ * Clips are composed from these objects.
+ */
+enum GrClipType {
+ kRect_ClipType,
+ kPath_ClipType
+};
+
///////////////////////////////////////////////////////////////////////////////
// this is included only to make it easy to use this debugging facility