Index: src/gpu/GrStencilAndCoverPathRenderer.cpp |
diff --git a/src/gpu/GrStencilAndCoverPathRenderer.cpp b/src/gpu/GrStencilAndCoverPathRenderer.cpp |
index 5f55c1a21412eaa43c523f96afbe52049013dbb3..6ed4b9e61c3e3dc40a8a7d7b4afaaf1a992816f3 100644 |
--- a/src/gpu/GrStencilAndCoverPathRenderer.cpp |
+++ b/src/gpu/GrStencilAndCoverPathRenderer.cpp |
@@ -14,6 +14,22 @@ |
#include "GrPath.h" |
#include "SkStrokeRec.h" |
+/* |
+ * For now paths only natively support winding and even odd fill types |
+ */ |
+static GrPathRendering::FillType convert_skpath_filltype(SkPath::FillType fill) { |
+ switch (fill) { |
+ default: |
+ SkFAIL("Incomplete Switch\n"); |
+ case SkPath::kWinding_FillType: |
+ case SkPath::kInverseWinding_FillType: |
+ return GrPathRendering::kWinding_FillType; |
+ case SkPath::kEvenOdd_FillType: |
+ case SkPath::kInverseEvenOdd_FillType: |
+ return GrPathRendering::kEvenOdd_FillType; |
+ } |
+} |
+ |
GrPathRenderer* GrStencilAndCoverPathRenderer::Create(GrContext* context) { |
SkASSERT(context); |
SkASSERT(context->getGpu()); |
@@ -44,10 +60,10 @@ bool GrStencilAndCoverPathRenderer::canDrawPath(const SkPath& path, |
target->getDrawState().getStencil().isDisabled(); |
} |
-GrPathRenderer::StencilSupport GrStencilAndCoverPathRenderer::onGetStencilSupport( |
- const SkPath&, |
- const SkStrokeRec& , |
- const GrDrawTarget*) const { |
+GrPathRenderer::StencilSupport |
+GrStencilAndCoverPathRenderer::onGetStencilSupport(const SkPath&, |
+ const SkStrokeRec& , |
+ const GrDrawTarget*) const { |
return GrPathRenderer::kStencilOnly_StencilSupport; |
} |
@@ -67,7 +83,7 @@ void GrStencilAndCoverPathRenderer::onStencilPath(const SkPath& path, |
GrDrawTarget* target) { |
SkASSERT(!path.isInverseFillType()); |
SkAutoTUnref<GrPath> p(get_gr_path(fGpu, path, stroke)); |
- target->stencilPath(p, path.getFillType()); |
+ target->stencilPath(p, convert_skpath_filltype(path.getFillType())); |
} |
bool GrStencilAndCoverPathRenderer::onDrawPath(const SkPath& path, |
@@ -94,7 +110,27 @@ bool GrStencilAndCoverPathRenderer::onDrawPath(const SkPath& path, |
0x0000, |
0xffff); |
- *drawState->stencil() = kInvertedStencilPass; |
+ drawState->setStencil(kInvertedStencilPass); |
Kimmo Kinnunen
2014/11/03 20:39:12
So this hunk was intentionally moved from here dow
bsalomon
2014/11/03 20:46:07
This CL arose out a of a desire to make GrGpu no l
joshualitt
2014/11/03 20:51:46
Ahh, so I should explain. It seems very possible
|
+ |
+ // fake inverse with a stencil and cover |
+ target->stencilPath(p, convert_skpath_filltype(path.getFillType())); |
+ |
+ GrDrawState::AutoViewMatrixRestore avmr; |
+ SkRect bounds = SkRect::MakeLTRB(0, 0, |
+ SkIntToScalar(drawState->getRenderTarget()->width()), |
+ SkIntToScalar(drawState->getRenderTarget()->height())); |
+ SkMatrix vmi; |
+ // mapRect through persp matrix may not be correct |
+ if (!drawState->getViewMatrix().hasPerspective() && drawState->getViewInverse(&vmi)) { |
+ vmi.mapRect(&bounds); |
+ // theoretically could set bloat = 0, instead leave it because of matrix inversion |
+ // precision. |
+ SkScalar bloat = drawState->getViewMatrix().getMaxScale() * SK_ScalarHalf; |
+ bounds.outset(bloat, bloat); |
+ } else { |
+ avmr.setIdentity(drawState); |
+ } |
+ target->drawSimpleRect(bounds); |
} else { |
GR_STATIC_CONST_SAME_STENCIL(kStencilPass, |
kZero_StencilOp, |
@@ -104,11 +140,10 @@ bool GrStencilAndCoverPathRenderer::onDrawPath(const SkPath& path, |
0x0000, |
0xffff); |
- *drawState->stencil() = kStencilPass; |
+ drawState->setStencil(kStencilPass); |
+ target->drawPath(p, convert_skpath_filltype(path.getFillType())); |
} |
- target->drawPath(p, path.getFillType()); |
- |
target->drawState()->stencil()->setDisabled(); |
return true; |
} |