From 50d7d6fd72801aa37e09fb201777861a3dfce5f2 Mon Sep 17 00:00:00 2001 From: Robert Phillips Date: Wed, 4 Mar 2020 11:12:24 -0500 Subject: [PATCH] Surface GrFillRectOp programs on DDLs Bug: skia:9455 Change-Id: I48ea4cc5045a23fd962f28c7e7d6a47b6b464608 Reviewed-on: https://skia-review.googlesource.com/c/skia/+/275036 Reviewed-by: Greg Daniel Commit-Queue: Robert Phillips --- src/gpu/ops/GrFillRectOp.cpp | 66 +++++++++++++++---- .../GrSimpleMeshDrawOpHelperWithStencil.cpp | 20 ++++++ .../ops/GrSimpleMeshDrawOpHelperWithStencil.h | 9 +++ 3 files changed, 82 insertions(+), 13 deletions(-) diff --git a/src/gpu/ops/GrFillRectOp.cpp b/src/gpu/ops/GrFillRectOp.cpp index d1ef972dcdb6c..534f61c8a6aaf 100644 --- a/src/gpu/ops/GrFillRectOp.cpp +++ b/src/gpu/ops/GrFillRectOp.cpp @@ -12,6 +12,7 @@ #include "src/gpu/GrCaps.h" #include "src/gpu/GrGeometryProcessor.h" #include "src/gpu/GrPaint.h" +#include "src/gpu/GrProgramInfo.h" #include "src/gpu/SkGr.h" #include "src/gpu/geometry/GrQuad.h" #include "src/gpu/geometry/GrQuadBuffer.h" @@ -112,7 +113,11 @@ class FillRectOp final : public GrMeshDrawOp { const char* name() const override { return "FillRectOp"; } void visitProxies(const VisitProxyFunc& func) const override { - return fHelper.visitProxies(func); + if (fProgramInfo) { + fProgramInfo->visitProxies(func); + } else { + return fHelper.visitProxies(func); + } } #ifdef SK_DEBUG @@ -212,16 +217,46 @@ class FillRectOp final : public GrMeshDrawOp { fHelper.compatibleWithCoverageAsAlpha(), indexBufferOption); } + GrProgramInfo* createProgramInfo(const GrCaps* caps, + SkArenaAlloc* arena, + const GrSurfaceProxyView* outputView, + GrAppliedClip&& appliedClip, + const GrXferProcessor::DstProxyView& dstProxyView) { + const VertexSpec vertexSpec = this->vertexSpec(); + + GrGeometryProcessor* gp = GrQuadPerEdgeAA::MakeProcessor(arena, vertexSpec); + SkASSERT(gp->vertexStride() == vertexSpec.vertexSize()); + + return fHelper.createProgramInfoWithStencil(caps, arena, outputView, std::move(appliedClip), + dstProxyView, gp, vertexSpec.primitiveType()); + } + + GrProgramInfo* createProgramInfo(GrOpFlushState* flushState) { + return this->createProgramInfo(&flushState->caps(), + flushState->allocator(), + flushState->outputView(), + flushState->detachAppliedClip(), + flushState->dstProxyView()); + } + void onPrePrepareDraws(GrRecordingContext* context, - const GrSurfaceProxyView*, - GrAppliedClip*, - const GrXferProcessor::DstProxyView&) override { + const GrSurfaceProxyView* outputView, + GrAppliedClip* clip, + const GrXferProcessor::DstProxyView& dstProxyView) override { TRACE_EVENT0("skia.gpu", TRACE_FUNC); SkASSERT(!fPrePreparedVertices); SkArenaAlloc* arena = context->priv().recordTimeAllocator(); + // This is equivalent to a GrOpFlushState::detachAppliedClip + GrAppliedClip appliedClip = clip ? std::move(*clip) : GrAppliedClip(); + + fProgramInfo = this->createProgramInfo(context->priv().caps(), arena, outputView, + std::move(appliedClip), dstProxyView); + + context->priv().recordProgramInfo(fProgramInfo); + const VertexSpec vertexSpec = this->vertexSpec(); const int totalNumVertices = fQuads.count() * vertexSpec.verticesPerQuad(); @@ -256,9 +291,6 @@ class FillRectOp final : public GrMeshDrawOp { // local coords. SkASSERT(!fHelper.isTrivial() || !fHelper.usesLocalCoords()); - GrGeometryProcessor* gp = GrQuadPerEdgeAA::MakeProcessor(target->allocator(), vertexSpec); - SkASSERT(gp->vertexStride() == vertexSpec.vertexSize()); - sk_sp vertexBuffer; int vertexOffsetInBuffer = 0; @@ -290,17 +322,23 @@ class FillRectOp final : public GrMeshDrawOp { } // Configure the mesh for the vertex data - GrMesh* mesh = target->allocMeshes(1); - GrQuadPerEdgeAA::ConfigureMesh(target->caps(), mesh, vertexSpec, 0, fQuads.count(), + fMesh = target->allocMeshes(1); + GrQuadPerEdgeAA::ConfigureMesh(target->caps(), fMesh, vertexSpec, 0, fQuads.count(), totalNumVertices, std::move(vertexBuffer), std::move(indexBuffer), vertexOffsetInBuffer); - target->recordDraw(gp, mesh, 1, vertexSpec.primitiveType()); } void onExecute(GrOpFlushState* flushState, const SkRect& chainBounds) override { - auto pipeline = fHelper.createPipelineWithStencil(flushState); + if (!fMesh) { + return; + } + + if (!fProgramInfo) { + fProgramInfo = this->createProgramInfo(flushState); + } - flushState->executeDrawsAndUploadsForMeshDrawOp(this, chainBounds, pipeline); + flushState->opsRenderPass()->bindPipeline(*fProgramInfo, chainBounds); + flushState->opsRenderPass()->drawMeshes(*fProgramInfo, fMesh, 1); } CombineResult onCombineIfPossible(GrOp* t, GrRecordingContext::Arenas*, @@ -412,7 +450,9 @@ class FillRectOp final : public GrMeshDrawOp { GrQuadBuffer fQuads; char* fPrePreparedVertices = nullptr; - ColorType fColorType; + GrMesh* fMesh = nullptr; + GrProgramInfo* fProgramInfo = nullptr; + ColorType fColorType; typedef GrMeshDrawOp INHERITED; }; diff --git a/src/gpu/ops/GrSimpleMeshDrawOpHelperWithStencil.cpp b/src/gpu/ops/GrSimpleMeshDrawOpHelperWithStencil.cpp index a336fa6e63fe1..eaa8e66b7e6b8 100644 --- a/src/gpu/ops/GrSimpleMeshDrawOpHelperWithStencil.cpp +++ b/src/gpu/ops/GrSimpleMeshDrawOpHelperWithStencil.cpp @@ -54,6 +54,26 @@ bool GrSimpleMeshDrawOpHelperWithStencil::isCompatible( fStencilSettings == that.fStencilSettings; } +GrProgramInfo* GrSimpleMeshDrawOpHelperWithStencil::createProgramInfoWithStencil( + const GrCaps* caps, + SkArenaAlloc* arena, + const GrSurfaceProxyView* outputView, + GrAppliedClip&& appliedClip, + const GrXferProcessor::DstProxyView& dstProxyView, + GrGeometryProcessor* gp, + GrPrimitiveType primType) { + return CreateProgramInfo(caps, + arena, + outputView, + std::move(appliedClip), + dstProxyView, + gp, + this->detachProcessorSet(), + primType, + this->pipelineFlags(), + this->stencilSettings()); +} + #ifdef SK_DEBUG SkString GrSimpleMeshDrawOpHelperWithStencil::dumpInfo() const { SkString result = INHERITED::dumpInfo(); diff --git a/src/gpu/ops/GrSimpleMeshDrawOpHelperWithStencil.h b/src/gpu/ops/GrSimpleMeshDrawOpHelperWithStencil.h index 506b48ad7c020..496f38f54bdac 100644 --- a/src/gpu/ops/GrSimpleMeshDrawOpHelperWithStencil.h +++ b/src/gpu/ops/GrSimpleMeshDrawOpHelperWithStencil.h @@ -24,6 +24,15 @@ class GrSimpleMeshDrawOpHelperWithStencil : private GrSimpleMeshDrawOpHelper { const GrPipeline* createPipelineWithStencil(GrOpFlushState* flushState); + GrProgramInfo* createProgramInfoWithStencil(const GrCaps*, + SkArenaAlloc*, + const GrSurfaceProxyView* outputView, + GrAppliedClip&&, + const GrXferProcessor::DstProxyView&, + GrGeometryProcessor*, + GrPrimitiveType); + + // using declarations can't be templated, so this is a pass through function instead. template static std::unique_ptr FactoryHelper(GrRecordingContext* context, GrPaint&& paint,