blob: bfc1e74505ea5c6df9e06f669ff1cb92d524ae40 [file] [log] [blame]
joshualitt8072caa2015-02-12 14:20:52 -08001/*
2 * Copyright 2013 Google Inc.
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 GrPrimitiveProcessor_DEFINED
9#define GrPrimitiveProcessor_DEFINED
10
11#include "GrColor.h"
12#include "GrProcessor.h"
13#include "GrShaderVar.h"
14
15/*
16 * The GrPrimitiveProcessor represents some kind of geometric primitive. This includes the shape
17 * of the primitive and the inherent color of the primitive. The GrPrimitiveProcessor is
18 * responsible for providing a color and coverage input into the Ganesh rendering pipeline. Through
19 * optimization, Ganesh may decide a different color, no color, and / or no coverage are required
20 * from the GrPrimitiveProcessor, so the GrPrimitiveProcessor must be able to support this
Brian Salomon09d994e2016-12-21 11:14:46 -050021 * functionality.
joshualitt8072caa2015-02-12 14:20:52 -080022 *
23 * There are two feedback loops between the GrFragmentProcessors, the GrXferProcessor, and the
Brian Salomoncb30bb22017-02-12 09:28:54 -050024 * GrPrimitiveProcessor. These loops run on the CPU and to determine known properties of the final
25 * color and coverage inputs to the GrXferProcessor in order to perform optimizations that preserve
26 * correctness. The GrDrawOp seeds these loops with initial color and coverage, in its
Brian Salomona811b122017-03-30 08:21:32 -040027 * getProcessorAnalysisInputs implementation. These seed values are processed by the
Brian Salomon5298dc82017-02-22 11:52:03 -050028 * subsequent
Brian Salomon92aee3d2016-12-21 09:20:25 -050029 * stages of the rendering pipeline and the output is then fed back into the GrDrawOp in
30 * the applyPipelineOptimizations call, where the op can use the information to inform decisions
31 * about GrPrimitiveProcessor creation.
joshualitt8072caa2015-02-12 14:20:52 -080032 */
33
egdaniele659a582015-11-13 09:55:43 -080034class GrGLSLPrimitiveProcessor;
joshualitt8072caa2015-02-12 14:20:52 -080035
joshualitt8072caa2015-02-12 14:20:52 -080036/*
joshualitt8072caa2015-02-12 14:20:52 -080037 * GrPrimitiveProcessor defines an interface which all subclasses must implement. All
38 * GrPrimitiveProcessors must proivide seed color and coverage for the Ganesh color / coverage
39 * pipelines, and they must provide some notion of equality
40 */
Brian Salomond61c9d92017-04-10 10:54:25 -040041class GrPrimitiveProcessor : public GrResourceIOProcessor, public GrProgramElement {
joshualitt8072caa2015-02-12 14:20:52 -080042public:
Brian Salomon19c12332018-06-18 12:52:47 -040043 /** Describes a vertex or instance attribute. */
Brian Salomon70132d02018-05-29 15:33:06 -040044 class Attribute {
45 public:
Brian Salomon70132d02018-05-29 15:33:06 -040046 constexpr Attribute() = default;
Brian Salomon19c12332018-06-18 12:52:47 -040047 constexpr Attribute(const char* name, GrVertexAttribType type) : fName(name), fType(type) {}
48 constexpr Attribute(const Attribute&) = default;
Brian Salomon70132d02018-05-29 15:33:06 -040049
Brian Salomon19c12332018-06-18 12:52:47 -040050 Attribute& operator=(const Attribute&) = default;
Brian Salomon70132d02018-05-29 15:33:06 -040051
Brian Salomon19c12332018-06-18 12:52:47 -040052 constexpr bool isInitialized() const { return SkToBool(fName); }
53
54 constexpr const char* name() const { return fName; }
55 constexpr GrVertexAttribType type() const { return fType; }
56
57 constexpr size_t size() const { return GrVertexAttribTypeSize(fType); }
58 constexpr size_t sizeAlign4() const { return SkAlign4(this->size()); }
Brian Salomon70132d02018-05-29 15:33:06 -040059
60 GrShaderVar asShaderVar() const {
61 return {fName, GrVertexAttribTypeToSLType(fType), GrShaderVar::kIn_TypeModifier};
62 }
63
64 private:
65 const char* fName = nullptr;
66 GrVertexAttribType fType = kFloat_GrVertexAttribType;
joshualitt8072caa2015-02-12 14:20:52 -080067 };
68
Brian Salomon19c12332018-06-18 12:52:47 -040069 GrPrimitiveProcessor(ClassID);
Ethan Nicholasabff9562017-10-09 10:54:08 -040070
Brian Salomon19c12332018-06-18 12:52:47 -040071 int numVertexAttributes() const { return fVertexAttributeCnt; }
72 const Attribute& vertexAttribute(int i) const;
73 int numInstanceAttributes() const { return fInstanceAttributeCnt; }
74 const Attribute& instanceAttribute(int i) const;
joshualitt8072caa2015-02-12 14:20:52 -080075
Brian Salomon19c12332018-06-18 12:52:47 -040076 bool hasVertexAttributes() const { return SkToBool(fVertexAttributeCnt); }
77 bool hasInstanceAttributes() const { return SkToBool(fInstanceAttributeCnt); }
Chris Dalton1d616352017-05-31 12:51:23 -060078
Brian Salomon19c12332018-06-18 12:52:47 -040079#ifdef SK_DEBUG
Chris Dalton1d616352017-05-31 12:51:23 -060080 /**
Brian Salomon19c12332018-06-18 12:52:47 -040081 * A common practice is to populate the the vertex/instance's memory using an implicit array of
82 * structs. In this case, it is best to assert that:
83 * debugOnly_stride == sizeof(struct) and
84 * offsetof(struct, field[i]) == debugOnly_AttributeOffset(i)
85 * In general having Op subclasses assert that attribute offsets and strides agree with their
86 * tessellation code's expectations is good practice.
87 * However, these functions walk the attributes to compute offsets and call virtual functions
88 * to access the attributes. Thus, they are only available in debug builds.
Chris Dalton1d616352017-05-31 12:51:23 -060089 */
Brian Salomon19c12332018-06-18 12:52:47 -040090 size_t debugOnly_vertexStride() const;
91 size_t debugOnly_instanceStride() const;
92 size_t debugOnly_vertexAttributeOffset(int) const;
93 size_t debugOnly_instanceAttributeOffset(int) const;
94#endif
Chris Dalton1d616352017-05-31 12:51:23 -060095
96 // Only the GrGeometryProcessor subclass actually has a geo shader or vertex attributes, but
97 // we put these calls on the base class to prevent having to cast
98 virtual bool willUseGeoShader() const = 0;
joshualitt8072caa2015-02-12 14:20:52 -080099
100 /**
wangyixa7f4c432015-08-20 07:25:02 -0700101 * Computes a transformKey from an array of coord transforms. Will only look at the first
102 * <numCoords> transforms in the array.
103 *
104 * TODO: A better name for this function would be "compute" instead of "get".
joshualitt8072caa2015-02-12 14:20:52 -0800105 */
wangyixa7f4c432015-08-20 07:25:02 -0700106 uint32_t getTransformKey(const SkTArray<const GrCoordTransform*, true>& coords,
107 int numCoords) const;
joshualitt8072caa2015-02-12 14:20:52 -0800108
109 /**
110 * Sets a unique key on the GrProcessorKeyBuilder that is directly associated with this geometry
111 * processor's GL backend implementation.
wangyixa7f4c432015-08-20 07:25:02 -0700112 *
113 * TODO: A better name for this function would be "compute" instead of "get".
joshualitt8072caa2015-02-12 14:20:52 -0800114 */
Brian Salomon94efbf52016-11-29 13:43:05 -0500115 virtual void getGLSLProcessorKey(const GrShaderCaps&, GrProcessorKeyBuilder*) const = 0;
joshualitt8072caa2015-02-12 14:20:52 -0800116
117
118 /** Returns a new instance of the appropriate *GL* implementation class
119 for the given GrProcessor; caller is responsible for deleting
120 the object. */
Brian Salomon94efbf52016-11-29 13:43:05 -0500121 virtual GrGLSLPrimitiveProcessor* createGLSLInstance(const GrShaderCaps&) const = 0;
joshualitt8072caa2015-02-12 14:20:52 -0800122
ethannicholas22793252016-01-30 09:59:10 -0800123 virtual bool isPathRendering() const { return false; }
joshualitt8072caa2015-02-12 14:20:52 -0800124
ethannicholas22793252016-01-30 09:59:10 -0800125 /**
126 * If non-null, overrides the dest color returned by GrGLSLFragmentShaderBuilder::dstColor().
127 */
128 virtual const char* getDestColorOverride() const { return nullptr; }
halcanary9d524f22016-03-29 09:03:52 -0700129
Brian Salomon19c12332018-06-18 12:52:47 -0400130 virtual float getSampleShading() const { return 0.0; }
ethannicholas28ef4452016-03-25 09:26:03 -0700131
joshualitt8072caa2015-02-12 14:20:52 -0800132protected:
Brian Salomon19c12332018-06-18 12:52:47 -0400133 void setVertexAttributeCnt(int cnt) { fVertexAttributeCnt = cnt; }
134 void setInstanceAttributeCnt(int cnt) { fInstanceAttributeCnt = cnt; }
joshualitt8072caa2015-02-12 14:20:52 -0800135
136private:
Brian Salomond61c9d92017-04-10 10:54:25 -0400137 void addPendingIOs() const override { GrResourceIOProcessor::addPendingIOs(); }
138 void removeRefs() const override { GrResourceIOProcessor::removeRefs(); }
139 void pendingIOComplete() const override { GrResourceIOProcessor::pendingIOComplete(); }
Mike Kleinfc6c37b2016-09-27 09:34:10 -0400140 void notifyRefCntIsZero() const final {}
joshualitt8072caa2015-02-12 14:20:52 -0800141
Brian Salomon19c12332018-06-18 12:52:47 -0400142 virtual const Attribute& onVertexAttribute(int) const = 0;
143 virtual const Attribute& onInstanceAttribute(int) const = 0;
Chris Dalton1d616352017-05-31 12:51:23 -0600144
Brian Salomon19c12332018-06-18 12:52:47 -0400145 int fVertexAttributeCnt = 0;
146 int fInstanceAttributeCnt = 0;
joshualitt8072caa2015-02-12 14:20:52 -0800147 typedef GrProcessor INHERITED;
148};
149
150#endif