From 703b476fa4adc0af369728f7a150aaf12af7434f Mon Sep 17 00:00:00 2001 From: Chris Dalton Date: Fri, 6 Apr 2018 16:11:48 -0600 Subject: ccpr: Remove WindMethod from GrCCCoverageProcessor Handles weighted triangles from the tessellator instead with a "kWeightedTriangles" PrimitiveType. Bug: skia: Change-Id: I8a6f7b4205e1b3d6f340a30f3e90079ec44b8b6d Reviewed-on: https://skia-review.googlesource.com/119202 Reviewed-by: Brian Salomon Commit-Queue: Chris Dalton --- samplecode/SampleCCPRGeometry.cpp | 9 ++++--- src/gpu/ccpr/GrCCCoverageProcessor.cpp | 6 ++--- src/gpu/ccpr/GrCCCoverageProcessor.h | 21 +++++---------- src/gpu/ccpr/GrCCCoverageProcessor_GSImpl.cpp | 13 +++++----- src/gpu/ccpr/GrCCCoverageProcessor_VSImpl.cpp | 12 ++++----- src/gpu/ccpr/GrCCGeometry.h | 8 +++--- src/gpu/ccpr/GrCCPathParser.cpp | 37 ++++++++++++--------------- src/gpu/ccpr/GrCCPathParser.h | 4 +-- 8 files changed, 51 insertions(+), 59 deletions(-) diff --git a/samplecode/SampleCCPRGeometry.cpp b/samplecode/SampleCCPRGeometry.cpp index ea3eafb591..7ddf91f0ae 100644 --- a/samplecode/SampleCCPRGeometry.cpp +++ b/samplecode/SampleCCPRGeometry.cpp @@ -204,7 +204,8 @@ void CCPRGeometryView::onDrawContent(SkCanvas* canvas) { SkRect::MakeIWH(this->width(), this->height())); // Add label. - caption.appendf("RenderPass_%s", GrCCCoverageProcessor::PrimitiveTypeName(fPrimitiveType)); + caption.appendf("PrimitiveType_%s", + GrCCCoverageProcessor::PrimitiveTypeName(fPrimitiveType)); if (PrimitiveType::kCubics == fPrimitiveType) { caption.appendf(" (%s)", SkCubicTypeName(fCubicType)); } @@ -295,8 +296,7 @@ void CCPRGeometryView::DrawCoverageCountOp::onExecute(GrOpFlushState* state) { ? static_cast(state->gpu()) : nullptr; - GrCCCoverageProcessor proc(rp, fView->fPrimitiveType, - GrCCCoverageProcessor::WindMethod::kCrossProduct); + GrCCCoverageProcessor proc(rp, fView->fPrimitiveType); SkDEBUGCODE(proc.enableDebugBloat(kDebugBloat)); SkSTArray<1, GrMesh> mesh; @@ -390,6 +390,9 @@ bool CCPRGeometryView::onQuery(SkEvent* evt) { if (SampleCode::CharQ(*evt, &unichar)) { if (unichar >= '1' && unichar <= '3') { fPrimitiveType = PrimitiveType(unichar - '1'); + if (fPrimitiveType >= PrimitiveType::kWeightedTriangles) { + fPrimitiveType = (PrimitiveType) ((int)fPrimitiveType + 1); + } this->updateAndInval(); return true; } diff --git a/src/gpu/ccpr/GrCCCoverageProcessor.cpp b/src/gpu/ccpr/GrCCCoverageProcessor.cpp index aac16afe90..b94b188e69 100644 --- a/src/gpu/ccpr/GrCCCoverageProcessor.cpp +++ b/src/gpu/ccpr/GrCCCoverageProcessor.cpp @@ -146,11 +146,8 @@ void GrCCCoverageProcessor::Shader::CalcCornerAttenuation(GrGLSLVertexGeoBuilder void GrCCCoverageProcessor::getGLSLProcessorKey(const GrShaderCaps&, GrProcessorKeyBuilder* b) const { - int key = (int)fPrimitiveType << 3; + int key = (int)fPrimitiveType << 2; if (GSSubpass::kCorners == fGSSubpass) { - key |= 4; - } - if (WindMethod::kInstanceData == fWindMethod) { key |= 2; } if (Impl::kVertexShader == fImpl) { @@ -168,6 +165,7 @@ GrGLSLPrimitiveProcessor* GrCCCoverageProcessor::createGLSLInstance(const GrShad std::unique_ptr shader; switch (fPrimitiveType) { case PrimitiveType::kTriangles: + case PrimitiveType::kWeightedTriangles: shader = skstd::make_unique(); break; case PrimitiveType::kQuadratics: diff --git a/src/gpu/ccpr/GrCCCoverageProcessor.h b/src/gpu/ccpr/GrCCCoverageProcessor.h index 9b83fc9275..40339baa07 100644 --- a/src/gpu/ccpr/GrCCCoverageProcessor.h +++ b/src/gpu/ccpr/GrCCCoverageProcessor.h @@ -37,6 +37,7 @@ class GrCCCoverageProcessor : public GrGeometryProcessor { public: enum class PrimitiveType { kTriangles, + kWeightedTriangles, // Triangles (from the tessellator) whose winding magnitude > 1. kQuadratics, kCubics, }; @@ -60,19 +61,12 @@ public: float fY[4]; void set(const SkPoint[4], float dx, float dy); - void set(const SkPoint&, const SkPoint&, const SkPoint&, const Sk2f& trans, float w); + void setW(const SkPoint&, const SkPoint&, const SkPoint&, const Sk2f& trans, float w); }; - enum class WindMethod : bool { - kCrossProduct, // Calculate wind = +/-1 by sign of the cross product. - kInstanceData // Instance data provides custom, signed wind values of any magnitude. - // (For tightly-wound tessellated triangles.) - }; - - GrCCCoverageProcessor(GrResourceProvider* rp, PrimitiveType type, WindMethod windMethod) + GrCCCoverageProcessor(GrResourceProvider* rp, PrimitiveType type) : INHERITED(kGrCCCoverageProcessor_ClassID) , fPrimitiveType(type) - , fWindMethod(windMethod) , fImpl(rp->caps()->shaderCaps()->geometryShaderSupport() ? Impl::kGeometryShader : Impl::kVertexShader) { if (Impl::kGeometryShader == fImpl) { @@ -222,7 +216,6 @@ private: GrCCCoverageProcessor(const GrCCCoverageProcessor& proc, GSSubpass subpass) : INHERITED(kGrCCCoverageProcessor_ClassID) , fPrimitiveType(proc.fPrimitiveType) - , fWindMethod(proc.fWindMethod) , fImpl(Impl::kGeometryShader) SkDEBUGCODE(, fDebugBloat(proc.fDebugBloat)) , fGSSubpass(subpass) { @@ -242,7 +235,6 @@ private: GrGLSLPrimitiveProcessor* createVSImpl(std::unique_ptr) const; const PrimitiveType fPrimitiveType; - const WindMethod fWindMethod; const Impl fImpl; SkDEBUGCODE(float fDebugBloat = 0); @@ -261,6 +253,7 @@ private: inline const char* GrCCCoverageProcessor::PrimitiveTypeName(PrimitiveType type) { switch (type) { case PrimitiveType::kTriangles: return "kTriangles"; + case PrimitiveType::kWeightedTriangles: return "kWeightedTriangles"; case PrimitiveType::kQuadratics: return "kQuadratics"; case PrimitiveType::kCubics: return "kCubics"; } @@ -287,9 +280,9 @@ inline void GrCCCoverageProcessor::QuadPointInstance::set(const SkPoint p[4], fl (Y + dy).store(&fY); } -inline void GrCCCoverageProcessor::QuadPointInstance::set(const SkPoint& p0, const SkPoint& p1, - const SkPoint& p2, const Sk2f& trans, - float w) { +inline void GrCCCoverageProcessor::QuadPointInstance::setW(const SkPoint& p0, const SkPoint& p1, + const SkPoint& p2, const Sk2f& trans, + float w) { Sk2f P0 = Sk2f::Load(&p0) + trans; Sk2f P1 = Sk2f::Load(&p1) + trans; Sk2f P2 = Sk2f::Load(&p2) + trans; diff --git a/src/gpu/ccpr/GrCCCoverageProcessor_GSImpl.cpp b/src/gpu/ccpr/GrCCCoverageProcessor_GSImpl.cpp index 4207f85c15..f933030177 100644 --- a/src/gpu/ccpr/GrCCCoverageProcessor_GSImpl.cpp +++ b/src/gpu/ccpr/GrCCCoverageProcessor_GSImpl.cpp @@ -58,7 +58,7 @@ protected: GrShaderVar wind("wind", kHalf_GrSLType); g->declareGlobal(wind); - if (WindMethod::kCrossProduct == proc.fWindMethod) { + if (PrimitiveType::kWeightedTriangles != proc.fPrimitiveType) { g->codeAppend ("float area_x2 = determinant(float2x2(pts[0] - pts[1], " "pts[0] - pts[2]));"); if (4 == numInputPoints) { @@ -67,7 +67,6 @@ protected: } g->codeAppendf("%s = sign(area_x2);", wind.c_str()); } else { - SkASSERT(WindMethod::kInstanceData == proc.fWindMethod); SkASSERT(3 == numInputPoints); SkASSERT(kFloat4_GrVertexAttribType == proc.getAttrib(0).fType); g->codeAppendf("%s = sk_in[0].sk_Position.w;", wind.c_str()); @@ -306,7 +305,8 @@ public: const GrShaderVar& wind, const char* emitVertexFn) const override { fShader->emitSetupCode(g, "pts", wind.c_str()); - bool isTriangle = PrimitiveType::kTriangles == proc.fPrimitiveType; + bool isTriangle = PrimitiveType::kTriangles == proc.fPrimitiveType || + PrimitiveType::kWeightedTriangles == proc.fPrimitiveType; g->codeAppendf("int corneridx = sk_InvocationID;"); if (!isTriangle) { g->codeAppendf("corneridx *= %i;", proc.numInputPoints() - 1); @@ -389,8 +389,8 @@ public: void GrCCCoverageProcessor::initGS() { SkASSERT(Impl::kGeometryShader == fImpl); - if (PrimitiveType::kCubics == fPrimitiveType || WindMethod::kInstanceData == fWindMethod) { - SkASSERT(WindMethod::kCrossProduct == fWindMethod || 3 == this->numInputPoints()); + if (PrimitiveType::kCubics == fPrimitiveType || + PrimitiveType::kWeightedTriangles == fPrimitiveType) { this->addVertexAttrib("x_or_y_values", kFloat4_GrVertexAttribType); SkASSERT(sizeof(QuadPointInstance) == this->getVertexStride() * 2); SkASSERT(offsetof(QuadPointInstance, fY) == this->getVertexStride()); @@ -416,7 +416,8 @@ void GrCCCoverageProcessor::appendGSMesh(GrBuffer* instanceBuffer, int instanceC GrGLSLPrimitiveProcessor* GrCCCoverageProcessor::createGSImpl(std::unique_ptr shadr) const { if (GSSubpass::kHulls == fGSSubpass) { - return (PrimitiveType::kTriangles == fPrimitiveType) + return (PrimitiveType::kTriangles == fPrimitiveType || + PrimitiveType::kWeightedTriangles == fPrimitiveType) ? (GSImpl*) new GSTriangleHullImpl(std::move(shadr)) : (GSImpl*) new GSCurveHullImpl(std::move(shadr)); } diff --git a/src/gpu/ccpr/GrCCCoverageProcessor_VSImpl.cpp b/src/gpu/ccpr/GrCCCoverageProcessor_VSImpl.cpp index a63b37e19e..561a293a51 100644 --- a/src/gpu/ccpr/GrCCCoverageProcessor_VSImpl.cpp +++ b/src/gpu/ccpr/GrCCCoverageProcessor_VSImpl.cpp @@ -262,7 +262,7 @@ void GrCCCoverageProcessor::VSImpl::onEmitCode(EmitArgs& args, GrGPArgs* gpArgs) numInputPoints, numInputPoints, proc.getAttrib(kAttribIdx_X).fName, swizzle, proc.getAttrib(kAttribIdx_Y).fName, swizzle); - if (WindMethod::kCrossProduct == proc.fWindMethod) { + if (PrimitiveType::kWeightedTriangles != proc.fPrimitiveType) { v->codeAppend ("float area_x2 = determinant(float2x2(pts[0] - pts[1], " "pts[0] - pts[2]));"); if (4 == numInputPoints) { @@ -271,7 +271,6 @@ void GrCCCoverageProcessor::VSImpl::onEmitCode(EmitArgs& args, GrGPArgs* gpArgs) } v->codeAppend ("half wind = sign(area_x2);"); } else { - SkASSERT(WindMethod::kInstanceData == proc.fWindMethod); SkASSERT(3 == numInputPoints); SkASSERT(kFloat4_GrVertexAttribType == proc.getAttrib(kAttribIdx_X).fType); v->codeAppendf("half wind = %s.w;", proc.getAttrib(kAttribIdx_X).fName); @@ -452,7 +451,8 @@ void GrCCCoverageProcessor::initVS(GrResourceProvider* rp) { const GrCaps& caps = *rp->caps(); switch (fPrimitiveType) { - case PrimitiveType::kTriangles: { + case PrimitiveType::kTriangles: + case PrimitiveType::kWeightedTriangles: { GR_DEFINE_STATIC_UNIQUE_KEY(gTriangleVertexBufferKey); fVSVertexBuffer = rp->findOrMakeStaticBuffer(kVertex_GrBufferType, sizeof(kTriangleVertices), @@ -499,9 +499,8 @@ void GrCCCoverageProcessor::initVS(GrResourceProvider* rp) { } } - if (PrimitiveType::kCubics == fPrimitiveType || WindMethod::kInstanceData == fWindMethod) { - SkASSERT(WindMethod::kCrossProduct == fWindMethod || 3 == this->numInputPoints()); - + if (PrimitiveType::kCubics == fPrimitiveType || + PrimitiveType::kWeightedTriangles == fPrimitiveType) { SkASSERT(kAttribIdx_X == this->numAttribs()); this->addInstanceAttrib("X", kFloat4_GrVertexAttribType); @@ -547,6 +546,7 @@ void GrCCCoverageProcessor::appendVSMesh(GrBuffer* instanceBuffer, int instanceC GrGLSLPrimitiveProcessor* GrCCCoverageProcessor::createVSImpl(std::unique_ptr shadr) const { switch (fPrimitiveType) { case PrimitiveType::kTriangles: + case PrimitiveType::kWeightedTriangles: return new VSImpl(std::move(shadr), 3); case PrimitiveType::kQuadratics: case PrimitiveType::kCubics: diff --git a/src/gpu/ccpr/GrCCGeometry.h b/src/gpu/ccpr/GrCCGeometry.h index 47b57c1c72..f593744b70 100644 --- a/src/gpu/ccpr/GrCCGeometry.h +++ b/src/gpu/ccpr/GrCCGeometry.h @@ -38,7 +38,7 @@ public: // These tallies track numbers of CCPR primitives that are required to draw a contour. struct PrimitiveTallies { int fTriangles; // Number of triangles in the contour's fan. - int fWoundTriangles; // Triangles (from the tessellator) whose winding magnitude > 1. + int fWeightedTriangles; // Triangles (from the tessellator) whose winding magnitude > 1. int fQuadratics; int fCubics; @@ -129,7 +129,7 @@ private: inline void GrCCGeometry::PrimitiveTallies::operator+=(const PrimitiveTallies& b) { fTriangles += b.fTriangles; - fWoundTriangles += b.fWoundTriangles; + fWeightedTriangles += b.fWeightedTriangles; fQuadratics += b.fQuadratics; fCubics += b.fCubics; } @@ -137,13 +137,13 @@ inline void GrCCGeometry::PrimitiveTallies::operator+=(const PrimitiveTallies& b GrCCGeometry::PrimitiveTallies inline GrCCGeometry::PrimitiveTallies::operator-(const PrimitiveTallies& b) const { return {fTriangles - b.fTriangles, - fWoundTriangles - b.fWoundTriangles, + fWeightedTriangles - b.fWeightedTriangles, fQuadratics - b.fQuadratics, fCubics - b.fCubics}; } inline bool GrCCGeometry::PrimitiveTallies::operator==(const PrimitiveTallies& b) { - return fTriangles == b.fTriangles && fWoundTriangles == b.fWoundTriangles && + return fTriangles == b.fTriangles && fWeightedTriangles == b.fWeightedTriangles && fQuadratics == b.fQuadratics && fCubics == b.fCubics; } diff --git a/src/gpu/ccpr/GrCCPathParser.cpp b/src/gpu/ccpr/GrCCPathParser.cpp index abeb164bbf..506efc752f 100644 --- a/src/gpu/ccpr/GrCCPathParser.cpp +++ b/src/gpu/ccpr/GrCCPathParser.cpp @@ -170,7 +170,7 @@ void GrCCPathParser::saveParsedPath(ScissorMode scissorMode, const SkIRect& clip int64_t fanningWork = (int64_t)clippedDevIBounds.height() * clippedDevIBounds.width(); if (tessellationWork * (50*50) + (100*100) < fanningWork) { // Don't tessellate under 100x100. fCurrPathPrimitiveCounts.fTriangles = - fCurrPathPrimitiveCounts.fWoundTriangles = 0; + fCurrPathPrimitiveCounts.fWeightedTriangles = 0; const SkTArray& verbs = fGeometry.verbs(); const SkTArray& pts = fGeometry.points(); @@ -236,7 +236,7 @@ void GrCCPathParser::saveParsedPath(ScissorMode scissorMode, const SkIRect& clip if (1 == abs(tessWinding)) { ++fCurrPathPrimitiveCounts.fTriangles; } else { - ++fCurrPathPrimitiveCounts.fWoundTriangles; + ++fCurrPathPrimitiveCounts.fWeightedTriangles; } } @@ -331,7 +331,7 @@ static void emit_tessellated_fan(const GrTessellator::WindingVertex* vertices, i triPointInstanceData[indices->fTriangles++].set(vertices[i].fPos, vertices[i + 1].fPos, vertices[i + 2].fPos, atlasOffset); } else { - quadPointInstanceData[indices->fWoundTriangles++].set( + quadPointInstanceData[indices->fWeightedTriangles++].setW( vertices[i].fPos, vertices[i+1].fPos, vertices[i + 2].fPos, atlasOffset, // Tessellator has opposite winding sense. -static_cast(vertices[i].fWinding)); @@ -372,11 +372,11 @@ bool GrCCPathParser::finalize(GrOnFlushResourceProvider* onFlushRP) { // them on the first index that will not overwrite previous TriPointInstance data. int quadBaseIdx = GR_CT_DIV_ROUND_UP(triEndIdx * sizeof(TriPointInstance), sizeof(QuadPointInstance)); - fBaseInstances[0].fWoundTriangles = quadBaseIdx; - fBaseInstances[1].fWoundTriangles = fBaseInstances[0].fWoundTriangles + - fTotalPrimitiveCounts[0].fWoundTriangles; - fBaseInstances[0].fCubics = fBaseInstances[1].fWoundTriangles + - fTotalPrimitiveCounts[1].fWoundTriangles; + fBaseInstances[0].fWeightedTriangles = quadBaseIdx; + fBaseInstances[1].fWeightedTriangles = fBaseInstances[0].fWeightedTriangles + + fTotalPrimitiveCounts[0].fWeightedTriangles; + fBaseInstances[0].fCubics = fBaseInstances[1].fWeightedTriangles + + fTotalPrimitiveCounts[1].fWeightedTriangles; fBaseInstances[1].fCubics = fBaseInstances[0].fCubics + fTotalPrimitiveCounts[0].fCubics; int quadEndIdx = fBaseInstances[1].fCubics + fTotalPrimitiveCounts[1].fCubics; @@ -487,8 +487,8 @@ bool GrCCPathParser::finalize(GrOnFlushResourceProvider* onFlushRP) { SkASSERT(instanceIndices[1].fTriangles == fBaseInstances[0].fQuadratics); SkASSERT(instanceIndices[0].fQuadratics == fBaseInstances[1].fQuadratics); SkASSERT(instanceIndices[1].fQuadratics == triEndIdx); - SkASSERT(instanceIndices[0].fWoundTriangles == fBaseInstances[1].fWoundTriangles); - SkASSERT(instanceIndices[1].fWoundTriangles == fBaseInstances[0].fCubics); + SkASSERT(instanceIndices[0].fWeightedTriangles == fBaseInstances[1].fWeightedTriangles); + SkASSERT(instanceIndices[1].fWeightedTriangles == fBaseInstances[0].fCubics); SkASSERT(instanceIndices[0].fCubics == fBaseInstances[1].fCubics); SkASSERT(instanceIndices[1].fCubics == quadEndIdx); @@ -501,7 +501,6 @@ bool GrCCPathParser::finalize(GrOnFlushResourceProvider* onFlushRP) { void GrCCPathParser::drawCoverageCount(GrOpFlushState* flushState, CoverageCountBatchID batchID, const SkIRect& drawBounds) const { using PrimitiveType = GrCCCoverageProcessor::PrimitiveType; - using WindMethod = GrCCCoverageProcessor::WindMethod; SkASSERT(fInstanceBuffer); @@ -512,30 +511,28 @@ void GrCCPathParser::drawCoverageCount(GrOpFlushState* flushState, CoverageCount if (batchTotalCounts.fTriangles) { this->drawPrimitives(flushState, pipeline, batchID, PrimitiveType::kTriangles, - WindMethod::kCrossProduct, &PrimitiveTallies::fTriangles, drawBounds); + &PrimitiveTallies::fTriangles, drawBounds); } - if (batchTotalCounts.fWoundTriangles) { - this->drawPrimitives(flushState, pipeline, batchID, PrimitiveType::kTriangles, - WindMethod::kInstanceData, &PrimitiveTallies::fWoundTriangles, - drawBounds); + if (batchTotalCounts.fWeightedTriangles) { + this->drawPrimitives(flushState, pipeline, batchID, PrimitiveType::kWeightedTriangles, + &PrimitiveTallies::fWeightedTriangles, drawBounds); } if (batchTotalCounts.fQuadratics) { this->drawPrimitives(flushState, pipeline, batchID, PrimitiveType::kQuadratics, - WindMethod::kCrossProduct, &PrimitiveTallies::fQuadratics, drawBounds); + &PrimitiveTallies::fQuadratics, drawBounds); } if (batchTotalCounts.fCubics) { this->drawPrimitives(flushState, pipeline, batchID, PrimitiveType::kCubics, - WindMethod::kCrossProduct, &PrimitiveTallies::fCubics, drawBounds); + &PrimitiveTallies::fCubics, drawBounds); } } void GrCCPathParser::drawPrimitives(GrOpFlushState* flushState, const GrPipeline& pipeline, CoverageCountBatchID batchID, GrCCCoverageProcessor::PrimitiveType primitiveType, - GrCCCoverageProcessor::WindMethod windMethod, int PrimitiveTallies::*instanceType, const SkIRect& drawBounds) const { SkASSERT(pipeline.getScissorState().enabled()); @@ -544,7 +541,7 @@ void GrCCPathParser::drawPrimitives(GrOpFlushState* flushState, const GrPipeline fMeshesScratchBuffer.pop_back_n(fMeshesScratchBuffer.count()); fDynamicStatesScratchBuffer.pop_back_n(fDynamicStatesScratchBuffer.count()); - GrCCCoverageProcessor proc(flushState->resourceProvider(), primitiveType, windMethod); + GrCCCoverageProcessor proc(flushState->resourceProvider(), primitiveType); SkASSERT(batchID > 0); SkASSERT(batchID < fCoverageCountBatches.count()); diff --git a/src/gpu/ccpr/GrCCPathParser.h b/src/gpu/ccpr/GrCCPathParser.h index b28ab3b489..973c873f2b 100644 --- a/src/gpu/ccpr/GrCCPathParser.h +++ b/src/gpu/ccpr/GrCCPathParser.h @@ -128,8 +128,8 @@ private: void endContourIfNeeded(bool insideContour); void drawPrimitives(GrOpFlushState*, const GrPipeline&, CoverageCountBatchID, - GrCCCoverageProcessor::PrimitiveType, GrCCCoverageProcessor::WindMethod, - int PrimitiveTallies::*instanceType, const SkIRect& drawBounds) const; + GrCCCoverageProcessor::PrimitiveType, int PrimitiveTallies::*instanceType, + const SkIRect& drawBounds) const; // Staging area for the path being parsed. SkDEBUGCODE(int fParsingPath = false); -- cgit v1.2.3