1 /* 2 * Copyright 2019 Google LLC. 3 * 4 * Use of this source code is governed by a BSD-style license that can be 5 * found in the LICENSE file. 6 */ 7 8 #ifndef GrTessellatePathOp_DEFINED 9 #define GrTessellatePathOp_DEFINED 10 11 #include "src/gpu/ops/GrDrawOp.h" 12 13 class GrAppliedHardClip; 14 class GrFillPathShader; 15 class GrStencilPathShader; 16 17 // Renders paths using the classic Red Book "stencil, then cover" method. Curves get linearized by 18 // GPU tessellation shaders. This Op doesn't apply analytic AA, so it requires a render target that 19 // supports either MSAA or mixed samples if AA is desired. 20 class GrTessellatePathOp : public GrDrawOp { 21 public: 22 enum class Flags { 23 kNone = 0, 24 kStencilOnly = (1 << 0), 25 kWireframe = (1 << 1) 26 }; 27 28 private: 29 DEFINE_OP_CLASS_ID 30 31 GrTessellatePathOp(const SkMatrix& viewMatrix, const SkPath& path, GrPaint&& paint, 32 GrAAType aaType, Flags flags = Flags::kNone) GrDrawOp(ClassID ())33 : GrDrawOp(ClassID()) 34 , fFlags(flags) 35 , fViewMatrix(viewMatrix) 36 , fPath(path) 37 , fAAType(aaType) 38 , fColor(paint.getColor4f()) 39 , fProcessors(std::move(paint)) { 40 SkRect devBounds; 41 fViewMatrix.mapRect(&devBounds, path.getBounds()); 42 this->setBounds(devBounds, HasAABloat(GrAAType::kCoverage == fAAType), IsHairline::kNo); 43 } 44 name()45 const char* name() const override { return "GrTessellatePathOp"; } visitProxies(const VisitProxyFunc & fn)46 void visitProxies(const VisitProxyFunc& fn) const override { fProcessors.visitProxies(fn); } finalize(const GrCaps & caps,const GrAppliedClip * clip,bool hasMixedSampledCoverage,GrClampType clampType)47 GrProcessorSet::Analysis finalize(const GrCaps& caps, const GrAppliedClip* clip, 48 bool hasMixedSampledCoverage, 49 GrClampType clampType) override { 50 return fProcessors.finalize( 51 fColor, GrProcessorAnalysisCoverage::kNone, clip, &GrUserStencilSettings::kUnused, 52 hasMixedSampledCoverage, caps, clampType, &fColor); 53 } 54 55 FixedFunctionFlags fixedFunctionFlags() const override; 56 void onPrepare(GrOpFlushState* state) override; 57 void onExecute(GrOpFlushState*, const SkRect& chainBounds) override; 58 59 void drawStencilPass(GrOpFlushState*, const GrAppliedHardClip&, 60 const GrPipeline::FixedDynamicState*); 61 void drawCoverPass(GrOpFlushState*, GrAppliedClip&&, const GrPipeline::FixedDynamicState*); 62 63 const Flags fFlags; 64 const SkMatrix fViewMatrix; 65 const SkPath fPath; 66 const GrAAType fAAType; 67 SkPMColor4f fColor; 68 GrProcessorSet fProcessors; 69 70 // These path shaders get created during onPrepare for drawing the below path vertex data. 71 // 72 // If fFillPathShader is null, then we just stencil the full path using fStencilPathShader and 73 // fCubicInstanceBuffer, and then fill it using a simple bounding box. 74 // 75 // If fFillPathShader is not null, then we fill the path using it plus cubic hulls from 76 // fCubicInstanceBuffer instead of a bounding box. 77 // 78 // If fFillPathShader is not null and fStencilPathShader *is* null, then the vertex data 79 // contains non-overlapping path geometry that can be drawn directly to the final render target. 80 // We only need to stencil curves from fCubicInstanceBuffer, and then draw the rest of the path 81 // directly. 82 GrStencilPathShader* fStencilPathShader = nullptr; 83 GrFillPathShader* fFillPathShader = nullptr; 84 85 // The "path vertex data" is made up of cubic wedges or inner polygon triangles (either red book 86 // style or fully tessellated). The geometry is generated by 87 // GrPathParser::EmitCenterWedgePatches, GrPathParser::EmitInnerPolygonTriangles, 88 // or GrTessellator::PathToTriangles. 89 sk_sp<const GrBuffer> fPathVertexBuffer; 90 int fBasePathVertex; 91 int fPathVertexCount; 92 93 // The cubic instance buffer defines standalone cubics to tessellate into the stencil buffer, in 94 // addition to the above path geometry. 95 sk_sp<const GrBuffer> fCubicInstanceBuffer; 96 int fBaseCubicInstance; 97 int fCubicInstanceCount; 98 99 friend class GrOpMemoryPool; // For ctor. 100 }; 101 102 GR_MAKE_BITFIELD_CLASS_OPS(GrTessellatePathOp::Flags); 103 104 #endif 105