1cb93a386Sopenharmony_ci/* 2cb93a386Sopenharmony_ci * Copyright 2017 Google Inc. 3cb93a386Sopenharmony_ci * 4cb93a386Sopenharmony_ci * Use of this source code is governed by a BSD-style license that can be 5cb93a386Sopenharmony_ci * found in the LICENSE file. 6cb93a386Sopenharmony_ci */ 7cb93a386Sopenharmony_ci 8cb93a386Sopenharmony_ci#ifndef GrSimpleMeshDrawOpHelper_DEFINED 9cb93a386Sopenharmony_ci#define GrSimpleMeshDrawOpHelper_DEFINED 10cb93a386Sopenharmony_ci 11cb93a386Sopenharmony_ci#include "include/gpu/GrRecordingContext.h" 12cb93a386Sopenharmony_ci#include "src/gpu/GrMemoryPool.h" 13cb93a386Sopenharmony_ci#include "src/gpu/GrOpFlushState.h" 14cb93a386Sopenharmony_ci#include "src/gpu/GrPipeline.h" 15cb93a386Sopenharmony_ci#include "src/gpu/GrRecordingContextPriv.h" 16cb93a386Sopenharmony_ci#include "src/gpu/ops/GrMeshDrawOp.h" 17cb93a386Sopenharmony_ci#include "src/gpu/ops/GrOp.h" 18cb93a386Sopenharmony_ci#include <new> 19cb93a386Sopenharmony_ci 20cb93a386Sopenharmony_cistruct SkRect; 21cb93a386Sopenharmony_ci 22cb93a386Sopenharmony_ci/** 23cb93a386Sopenharmony_ci * This class can be used to help implement simple mesh draw ops. It reduces the amount of 24cb93a386Sopenharmony_ci * boilerplate code to type and also provides a mechanism for optionally allocating space for a 25cb93a386Sopenharmony_ci * GrProcessorSet based on a GrPaint. It is intended to be used by ops that construct a single 26cb93a386Sopenharmony_ci * GrPipeline for a uniform primitive color and a GrPaint. 27cb93a386Sopenharmony_ci */ 28cb93a386Sopenharmony_ciclass GrSimpleMeshDrawOpHelper { 29cb93a386Sopenharmony_cipublic: 30cb93a386Sopenharmony_ci /** 31cb93a386Sopenharmony_ci * This can be used by a Op class to perform allocation and initialization such that a 32cb93a386Sopenharmony_ci * GrProcessorSet (if required) is allocated as part of the the same allocation that as 33cb93a386Sopenharmony_ci * the Op instance. It requires that Op implements a constructor of the form: 34cb93a386Sopenharmony_ci * Op(ProcessorSet*, GrColor, OpArgs...). 35cb93a386Sopenharmony_ci */ 36cb93a386Sopenharmony_ci template <typename Op, typename... OpArgs> 37cb93a386Sopenharmony_ci static GrOp::Owner FactoryHelper(GrRecordingContext*, GrPaint&&, OpArgs&&...); 38cb93a386Sopenharmony_ci 39cb93a386Sopenharmony_ci // Here we allow callers to specify a subset of the GrPipeline::InputFlags upon creation. 40cb93a386Sopenharmony_ci enum class InputFlags : uint8_t { 41cb93a386Sopenharmony_ci kNone = 0, 42cb93a386Sopenharmony_ci kSnapVerticesToPixelCenters = (uint8_t)GrPipeline::InputFlags::kSnapVerticesToPixelCenters, 43cb93a386Sopenharmony_ci kConservativeRaster = (uint8_t)GrPipeline::InputFlags::kConservativeRaster, 44cb93a386Sopenharmony_ci }; 45cb93a386Sopenharmony_ci GR_DECL_BITFIELD_CLASS_OPS_FRIENDS(InputFlags); 46cb93a386Sopenharmony_ci 47cb93a386Sopenharmony_ci GrSimpleMeshDrawOpHelper(GrProcessorSet*, GrAAType, InputFlags = InputFlags::kNone); 48cb93a386Sopenharmony_ci ~GrSimpleMeshDrawOpHelper(); 49cb93a386Sopenharmony_ci 50cb93a386Sopenharmony_ci GrSimpleMeshDrawOpHelper() = delete; 51cb93a386Sopenharmony_ci GrSimpleMeshDrawOpHelper(const GrSimpleMeshDrawOpHelper&) = delete; 52cb93a386Sopenharmony_ci GrSimpleMeshDrawOpHelper& operator=(const GrSimpleMeshDrawOpHelper&) = delete; 53cb93a386Sopenharmony_ci 54cb93a386Sopenharmony_ci GrDrawOp::FixedFunctionFlags fixedFunctionFlags() const; 55cb93a386Sopenharmony_ci 56cb93a386Sopenharmony_ci // ignoreAAType should be set to true if the op already knows the AA settings are acceptible 57cb93a386Sopenharmony_ci bool isCompatible(const GrSimpleMeshDrawOpHelper& that, const GrCaps&, const SkRect& thisBounds, 58cb93a386Sopenharmony_ci const SkRect& thatBounds, bool ignoreAAType = false) const; 59cb93a386Sopenharmony_ci 60cb93a386Sopenharmony_ci /** 61cb93a386Sopenharmony_ci * Finalizes the processor set and determines whether the destination must be provided 62cb93a386Sopenharmony_ci * to the fragment shader as a texture for blending. 63cb93a386Sopenharmony_ci * 64cb93a386Sopenharmony_ci * @param geometryCoverage Describes the coverage output of the op's geometry processor 65cb93a386Sopenharmony_ci * @param geometryColor An in/out param. As input this informs processor analysis about the 66cb93a386Sopenharmony_ci * color the op expects to output from its geometry processor. As output 67cb93a386Sopenharmony_ci * this may be set to a known color in which case the op must output this 68cb93a386Sopenharmony_ci * color from its geometry processor instead. 69cb93a386Sopenharmony_ci */ 70cb93a386Sopenharmony_ci GrProcessorSet::Analysis finalizeProcessors(const GrCaps& caps, const GrAppliedClip* clip, 71cb93a386Sopenharmony_ci GrClampType clampType, 72cb93a386Sopenharmony_ci GrProcessorAnalysisCoverage geometryCoverage, 73cb93a386Sopenharmony_ci GrProcessorAnalysisColor* geometryColor) { 74cb93a386Sopenharmony_ci return this->finalizeProcessors(caps, clip, &GrUserStencilSettings::kUnused, clampType, 75cb93a386Sopenharmony_ci geometryCoverage, geometryColor); 76cb93a386Sopenharmony_ci } 77cb93a386Sopenharmony_ci 78cb93a386Sopenharmony_ci /** 79cb93a386Sopenharmony_ci * Version of above that can be used by ops that have a constant color geometry processor 80cb93a386Sopenharmony_ci * output. The op passes this color as 'geometryColor' and after return if 'geometryColor' has 81cb93a386Sopenharmony_ci * changed the op must override its geometry processor color output with the new color. 82cb93a386Sopenharmony_ci */ 83cb93a386Sopenharmony_ci GrProcessorSet::Analysis finalizeProcessors(const GrCaps&, const GrAppliedClip*, GrClampType, 84cb93a386Sopenharmony_ci GrProcessorAnalysisCoverage geometryCoverage, 85cb93a386Sopenharmony_ci SkPMColor4f* geometryColor, bool* wideColor); 86cb93a386Sopenharmony_ci 87cb93a386Sopenharmony_ci bool isTrivial() const { 88cb93a386Sopenharmony_ci return fProcessors == nullptr; 89cb93a386Sopenharmony_ci } 90cb93a386Sopenharmony_ci 91cb93a386Sopenharmony_ci bool usesLocalCoords() const { 92cb93a386Sopenharmony_ci SkASSERT(fDidAnalysis); 93cb93a386Sopenharmony_ci return fUsesLocalCoords; 94cb93a386Sopenharmony_ci } 95cb93a386Sopenharmony_ci 96cb93a386Sopenharmony_ci bool compatibleWithCoverageAsAlpha() const { return fCompatibleWithCoverageAsAlpha; } 97cb93a386Sopenharmony_ci 98cb93a386Sopenharmony_ci void visitProxies(const GrVisitProxyFunc& func) const { 99cb93a386Sopenharmony_ci if (fProcessors) { 100cb93a386Sopenharmony_ci fProcessors->visitProxies(func); 101cb93a386Sopenharmony_ci } 102cb93a386Sopenharmony_ci } 103cb93a386Sopenharmony_ci 104cb93a386Sopenharmony_ci#if GR_TEST_UTILS 105cb93a386Sopenharmony_ci SkString dumpInfo() const; 106cb93a386Sopenharmony_ci#endif 107cb93a386Sopenharmony_ci GrAAType aaType() const { return static_cast<GrAAType>(fAAType); } 108cb93a386Sopenharmony_ci 109cb93a386Sopenharmony_ci void setAAType(GrAAType aaType) { 110cb93a386Sopenharmony_ci fAAType = static_cast<unsigned>(aaType); 111cb93a386Sopenharmony_ci } 112cb93a386Sopenharmony_ci 113cb93a386Sopenharmony_ci static const GrPipeline* CreatePipeline( 114cb93a386Sopenharmony_ci const GrCaps*, 115cb93a386Sopenharmony_ci SkArenaAlloc*, 116cb93a386Sopenharmony_ci GrSwizzle writeViewSwizzle, 117cb93a386Sopenharmony_ci GrAppliedClip&&, 118cb93a386Sopenharmony_ci const GrDstProxyView&, 119cb93a386Sopenharmony_ci GrProcessorSet&&, 120cb93a386Sopenharmony_ci GrPipeline::InputFlags pipelineFlags); 121cb93a386Sopenharmony_ci static const GrPipeline* CreatePipeline( 122cb93a386Sopenharmony_ci GrOpFlushState*, 123cb93a386Sopenharmony_ci GrProcessorSet&&, 124cb93a386Sopenharmony_ci GrPipeline::InputFlags pipelineFlags); 125cb93a386Sopenharmony_ci 126cb93a386Sopenharmony_ci const GrPipeline* createPipeline(GrOpFlushState* flushState); 127cb93a386Sopenharmony_ci 128cb93a386Sopenharmony_ci const GrPipeline* createPipeline(const GrCaps*, 129cb93a386Sopenharmony_ci SkArenaAlloc*, 130cb93a386Sopenharmony_ci GrSwizzle writeViewSwizzle, 131cb93a386Sopenharmony_ci GrAppliedClip&&, 132cb93a386Sopenharmony_ci const GrDstProxyView&); 133cb93a386Sopenharmony_ci 134cb93a386Sopenharmony_ci static GrProgramInfo* CreateProgramInfo(const GrCaps*, 135cb93a386Sopenharmony_ci SkArenaAlloc*, 136cb93a386Sopenharmony_ci const GrPipeline*, 137cb93a386Sopenharmony_ci const GrSurfaceProxyView& writeView, 138cb93a386Sopenharmony_ci bool usesMSAASurface, 139cb93a386Sopenharmony_ci GrGeometryProcessor*, 140cb93a386Sopenharmony_ci GrPrimitiveType, 141cb93a386Sopenharmony_ci GrXferBarrierFlags renderPassXferBarriers, 142cb93a386Sopenharmony_ci GrLoadOp colorLoadOp, 143cb93a386Sopenharmony_ci const GrUserStencilSettings* 144cb93a386Sopenharmony_ci = &GrUserStencilSettings::kUnused); 145cb93a386Sopenharmony_ci 146cb93a386Sopenharmony_ci // Create a programInfo with the following properties: 147cb93a386Sopenharmony_ci // its primitive processor uses no textures 148cb93a386Sopenharmony_ci // it has no dynamic state besides the scissor clip 149cb93a386Sopenharmony_ci static GrProgramInfo* CreateProgramInfo(const GrCaps*, 150cb93a386Sopenharmony_ci SkArenaAlloc*, 151cb93a386Sopenharmony_ci const GrSurfaceProxyView& writeView, 152cb93a386Sopenharmony_ci bool usesMSAASurface, 153cb93a386Sopenharmony_ci GrAppliedClip&&, 154cb93a386Sopenharmony_ci const GrDstProxyView&, 155cb93a386Sopenharmony_ci GrGeometryProcessor*, 156cb93a386Sopenharmony_ci GrProcessorSet&&, 157cb93a386Sopenharmony_ci GrPrimitiveType, 158cb93a386Sopenharmony_ci GrXferBarrierFlags renderPassXferBarriers, 159cb93a386Sopenharmony_ci GrLoadOp colorLoadOp, 160cb93a386Sopenharmony_ci GrPipeline::InputFlags pipelineFlags 161cb93a386Sopenharmony_ci = GrPipeline::InputFlags::kNone, 162cb93a386Sopenharmony_ci const GrUserStencilSettings* 163cb93a386Sopenharmony_ci = &GrUserStencilSettings::kUnused); 164cb93a386Sopenharmony_ci 165cb93a386Sopenharmony_ci GrProgramInfo* createProgramInfo(const GrCaps*, 166cb93a386Sopenharmony_ci SkArenaAlloc*, 167cb93a386Sopenharmony_ci const GrSurfaceProxyView& writeView, 168cb93a386Sopenharmony_ci bool usesMSAASurface, 169cb93a386Sopenharmony_ci GrAppliedClip&&, 170cb93a386Sopenharmony_ci const GrDstProxyView&, 171cb93a386Sopenharmony_ci GrGeometryProcessor*, 172cb93a386Sopenharmony_ci GrPrimitiveType, 173cb93a386Sopenharmony_ci GrXferBarrierFlags renderPassXferBarriers, 174cb93a386Sopenharmony_ci GrLoadOp colorLoadOp); 175cb93a386Sopenharmony_ci 176cb93a386Sopenharmony_ci GrProcessorSet detachProcessorSet() { 177cb93a386Sopenharmony_ci return fProcessors ? std::move(*fProcessors) : GrProcessorSet::MakeEmptySet(); 178cb93a386Sopenharmony_ci } 179cb93a386Sopenharmony_ci 180cb93a386Sopenharmony_ci GrPipeline::InputFlags pipelineFlags() const { return fPipelineFlags; } 181cb93a386Sopenharmony_ci 182cb93a386Sopenharmony_ciprotected: 183cb93a386Sopenharmony_ci GrProcessorSet::Analysis finalizeProcessors(const GrCaps& caps, const GrAppliedClip*, 184cb93a386Sopenharmony_ci const GrUserStencilSettings*, GrClampType, 185cb93a386Sopenharmony_ci GrProcessorAnalysisCoverage geometryCoverage, 186cb93a386Sopenharmony_ci GrProcessorAnalysisColor* geometryColor); 187cb93a386Sopenharmony_ci 188cb93a386Sopenharmony_ci GrProcessorSet* fProcessors; 189cb93a386Sopenharmony_ci GrPipeline::InputFlags fPipelineFlags; 190cb93a386Sopenharmony_ci unsigned fAAType : 2; 191cb93a386Sopenharmony_ci unsigned fUsesLocalCoords : 1; 192cb93a386Sopenharmony_ci unsigned fCompatibleWithCoverageAsAlpha : 1; 193cb93a386Sopenharmony_ci SkDEBUGCODE(unsigned fMadePipeline : 1;) 194cb93a386Sopenharmony_ci SkDEBUGCODE(unsigned fDidAnalysis : 1;) 195cb93a386Sopenharmony_ci}; 196cb93a386Sopenharmony_ci 197cb93a386Sopenharmony_citemplate<typename Op, typename... Args> 198cb93a386Sopenharmony_ciGrOp::Owner GrOp::MakeWithProcessorSet( 199cb93a386Sopenharmony_ci GrRecordingContext* context, const SkPMColor4f& color, 200cb93a386Sopenharmony_ci GrPaint&& paint, Args&&... args) { 201cb93a386Sopenharmony_ci char* bytes = (char*)::operator new(sizeof(Op) + sizeof(GrProcessorSet)); 202cb93a386Sopenharmony_ci char* setMem = bytes + sizeof(Op); 203cb93a386Sopenharmony_ci GrProcessorSet* processorSet = new (setMem) GrProcessorSet{std::move(paint)}; 204cb93a386Sopenharmony_ci return Owner{new (bytes) Op(processorSet, color, std::forward<Args>(args)...)}; 205cb93a386Sopenharmony_ci} 206cb93a386Sopenharmony_ci 207cb93a386Sopenharmony_citemplate <typename Op, typename... OpArgs> 208cb93a386Sopenharmony_ciGrOp::Owner GrSimpleMeshDrawOpHelper::FactoryHelper(GrRecordingContext* context, 209cb93a386Sopenharmony_ci GrPaint&& paint, 210cb93a386Sopenharmony_ci OpArgs&& ... opArgs) { 211cb93a386Sopenharmony_ci auto color = paint.getColor4f(); 212cb93a386Sopenharmony_ci if (paint.isTrivial()) { 213cb93a386Sopenharmony_ci return GrOp::Make<Op>(context, nullptr, color, std::forward<OpArgs>(opArgs)...); 214cb93a386Sopenharmony_ci } else { 215cb93a386Sopenharmony_ci return GrOp::MakeWithProcessorSet<Op>( 216cb93a386Sopenharmony_ci context, color, std::move(paint), std::forward<OpArgs>(opArgs)...); 217cb93a386Sopenharmony_ci } 218cb93a386Sopenharmony_ci} 219cb93a386Sopenharmony_ci 220cb93a386Sopenharmony_ciGR_MAKE_BITFIELD_CLASS_OPS(GrSimpleMeshDrawOpHelper::InputFlags) 221cb93a386Sopenharmony_ci 222cb93a386Sopenharmony_ci#endif 223