Index: src/gpu/batches/GrAAStrokeRectBatch.cpp |
diff --git a/src/gpu/batches/GrAAStrokeRectBatch.cpp b/src/gpu/batches/GrAAStrokeRectBatch.cpp |
index 4472b0125b74ea48fe9d968fa6b0d83eed876a3b..037f2f9d12026d5697edfccbd6a19f9e71ec5e12 100644 |
--- a/src/gpu/batches/GrAAStrokeRectBatch.cpp |
+++ b/src/gpu/batches/GrAAStrokeRectBatch.cpp |
@@ -54,13 +54,14 @@ public: |
SkRect fDevInside; |
GrColor fColor; |
bool fMiterStroke; |
+ bool fDegenerate; |
}; |
static GrDrawBatch* Create(GrColor color, const SkMatrix& viewMatrix, const SkRect& devOutside, |
const SkRect& devOutsideAssist, const SkRect& devInside, |
- bool miterStroke) { |
+ bool miterStroke, bool degenerate) { |
return new AAStrokeRectBatch(color, viewMatrix, devOutside, devOutsideAssist, devInside, |
- miterStroke); |
+ miterStroke, degenerate); |
} |
const char* name() const override { return "AAStrokeRect"; } |
@@ -81,7 +82,8 @@ private: |
void initBatchTracker(const GrPipelineOptimizations&) override; |
AAStrokeRectBatch(GrColor color, const SkMatrix& viewMatrix, const SkRect& devOutside, |
- const SkRect& devOutsideAssist, const SkRect& devInside, bool miterStroke) |
+ const SkRect& devOutsideAssist, const SkRect& devInside, bool miterStroke, |
+ bool degenerate) |
: INHERITED(ClassID()) { |
fBatch.fViewMatrix = viewMatrix; |
Geometry& geometry = fGeoData.push_back(); |
@@ -90,6 +92,7 @@ private: |
geometry.fDevOutsideAssist = devOutsideAssist; |
geometry.fDevInside = devInside; |
geometry.fMiterStroke = miterStroke; |
+ geometry.fDegenerate = degenerate; |
// If we have miterstroke then we inset devOutside and outset devOutsideAssist, so we need |
// the join for proper bounds |
@@ -129,6 +132,7 @@ private: |
const SkRect& devOutsideAssist, |
const SkRect& devInside, |
bool miterStroke, |
+ bool degenerate, |
bool tweakAlphaForCoverage) const; |
struct BatchTracker { |
@@ -211,6 +215,7 @@ void AAStrokeRectBatch::onPrepareDraws(Target* target) { |
args.fDevOutsideAssist, |
args.fDevInside, |
args.fMiterStroke, |
+ args.fDegenerate, |
canTweakAlphaForCoverage); |
} |
helper.recordDraw(target); |
@@ -351,6 +356,7 @@ void AAStrokeRectBatch::generateAAStrokeRectGeometry(void* vertices, |
const SkRect& devOutsideAssist, |
const SkRect& devInside, |
bool miterStroke, |
+ bool degenerate, |
bool tweakAlphaForCoverage) const { |
intptr_t verts = reinterpret_cast<intptr_t>(vertices) + offset; |
@@ -386,9 +392,16 @@ void AAStrokeRectBatch::generateAAStrokeRectGeometry(void* vertices, |
set_inset_fan(fan0Pos, vertexStride, devOutside, -SK_ScalarHalf, -SK_ScalarHalf); |
// inner two |
set_inset_fan(fan1Pos, vertexStride, devOutside, inset, inset); |
- set_inset_fan(fan2Pos, vertexStride, devInside, -inset, -inset); |
- // innermost |
- set_inset_fan(fan3Pos, vertexStride, devInside, SK_ScalarHalf, SK_ScalarHalf); |
+ if (!degenerate) { |
+ set_inset_fan(fan2Pos, vertexStride, devInside, -inset, -inset); |
+ // innermost |
+ set_inset_fan(fan3Pos, vertexStride, devInside, SK_ScalarHalf, SK_ScalarHalf); |
+ } else { |
robertphillips
2015/09/21 17:12:44
// When the interior rect has become degenerate ..
joshualitt
2015/09/21 19:51:25
Acknowledged.
|
+ fan2Pos->setRectFan(devInside.fLeft, devInside.fTop, |
+ devInside.fRight, devInside.fBottom, vertexStride); |
+ fan3Pos->setRectFan(devInside.fLeft, devInside.fTop, |
+ devInside.fRight, devInside.fBottom, vertexStride); |
+ } |
} else { |
SkPoint* fan0AssistPos = reinterpret_cast<SkPoint*>(verts + 4 * vertexStride); |
SkPoint* fan1AssistPos = reinterpret_cast<SkPoint*>(verts + |
@@ -401,10 +414,17 @@ void AAStrokeRectBatch::generateAAStrokeRectGeometry(void* vertices, |
// outer one of the inner two |
set_inset_fan(fan1Pos, vertexStride, devOutside, inset, inset); |
set_inset_fan(fan1AssistPos, vertexStride, devOutsideAssist, inset, inset); |
- // inner one of the inner two |
- set_inset_fan(fan2Pos, vertexStride, devInside, -inset, -inset); |
- // innermost |
- set_inset_fan(fan3Pos, vertexStride, devInside, SK_ScalarHalf, SK_ScalarHalf); |
+ if (!degenerate) { |
+ // inner one of the inner two |
+ set_inset_fan(fan2Pos, vertexStride, devInside, -inset, -inset); |
+ // innermost |
+ set_inset_fan(fan3Pos, vertexStride, devInside, SK_ScalarHalf, SK_ScalarHalf); |
+ } else { |
robertphillips
2015/09/21 17:12:44
// When the interior rect has become degenerate ..
joshualitt
2015/09/21 19:51:25
Acknowledged.
|
+ fan2Pos->setRectFan(devInside.fLeft, devInside.fTop, |
+ devInside.fRight, devInside.fBottom, vertexStride); |
+ fan3Pos->setRectFan(devInside.fLeft, devInside.fTop, |
+ devInside.fRight, devInside.fBottom, vertexStride); |
+ } |
} |
// Make verts point to vertex color and then set all the color and coverage vertex attrs |
@@ -421,7 +441,7 @@ void AAStrokeRectBatch::generateAAStrokeRectGeometry(void* vertices, |
// scale is the coverage for the the inner two rects. |
int scale; |
robertphillips
2015/09/21 17:12:44
This hardens the inner/outer fan too
joshualitt
2015/09/21 19:51:25
Acknowledged.
|
- if (inset < SK_ScalarHalf) { |
+ if (inset < SK_ScalarHalf && !degenerate) { |
scale = SkScalarFloorToInt(512.0f * inset / (inset + SK_ScalarHalf)); |
SkASSERT(scale >= 0 && scale <= 255); |
} else { |
@@ -442,14 +462,18 @@ void AAStrokeRectBatch::generateAAStrokeRectGeometry(void* vertices, |
} |
} |
- // The innermost rect has 0 coverage |
+ // The innermost rect has 0 coverage, unless we are degenerate |
verts += (outerVertexNum + innerVertexNum) * vertexStride; |
+ scale = 0; |
+ if (degenerate) { |
+ scale = 0xff; |
+ } |
for (int i = 0; i < innerVertexNum; ++i) { |
if (tweakAlphaForCoverage) { |
- *reinterpret_cast<GrColor*>(verts + i * vertexStride) = 0; |
+ *reinterpret_cast<GrColor*>(verts + i * vertexStride) = scale; |
} else { |
*reinterpret_cast<GrColor*>(verts + i * vertexStride) = color; |
- *reinterpret_cast<GrColor*>(verts + i * vertexStride + sizeof(GrColor)) = 0; |
+ *reinterpret_cast<GrColor*>(verts + i * vertexStride + sizeof(GrColor)) = scale; |
} |
} |
} |
@@ -461,9 +485,10 @@ GrDrawBatch* Create(GrColor color, |
const SkRect& devOutside, |
const SkRect& devOutsideAssist, |
const SkRect& devInside, |
- bool miterStroke) { |
+ bool miterStroke, |
+ bool degenerate) { |
return AAStrokeRectBatch::Create(color, viewMatrix, devOutside, devOutsideAssist, devInside, |
- miterStroke); |
+ miterStroke, degenerate); |
} |
}; |
@@ -476,6 +501,7 @@ GrDrawBatch* Create(GrColor color, |
DRAW_BATCH_TEST_DEFINE(AAStrokeRectBatch) { |
bool miterStroke = random->nextBool(); |
+ bool degenerate = random->nextBool(); |
// Create mock stroke rect |
SkRect outside = GrTest::TestRect(random); |
@@ -489,7 +515,7 @@ DRAW_BATCH_TEST_DEFINE(AAStrokeRectBatch) { |
GrColor color = GrRandomColor(random); |
return GrAAStrokeRectBatch::Create(color, GrTest::TestMatrix(random), outside, outsideAssist, |
- inside, miterStroke); |
+ inside, degenerate, miterStroke); |
} |
#endif |