blob: c4319958a47a3a58880f73770cf85533cce6a809 [file] [log] [blame]
egdaniel3658f382014-09-15 07:01:59 -07001/*
egdaniel8dd688b2015-01-22 10:16:09 -08002 * Copyright 2015 Google Inc.
egdaniel3658f382014-09-15 07:01:59 -07003 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
egdaniel8dd688b2015-01-22 10:16:09 -08008#ifndef GrPipeline_DEFINED
9#define GrPipeline_DEFINED
egdaniel3658f382014-09-15 07:01:59 -070010
egdanielb109ac22014-10-07 06:45:44 -070011#include "GrColor.h"
bsalomonac856c92015-08-27 06:30:17 -070012#include "GrFragmentProcessor.h"
joshualittdbe1e6f2015-07-16 08:12:45 -070013#include "GrNonAtomicRef.h"
bsalomonac856c92015-08-27 06:30:17 -070014#include "GrPendingProgramElement.h"
Brian Salomon5298dc82017-02-22 11:52:03 -050015#include "GrProcessorSet.h"
joshualitt79f8fae2014-10-28 17:59:26 -070016#include "GrProgramDesc.h"
Brian Salomona4677b52017-05-04 12:39:56 -040017#include "GrRect.h"
Robert Phillips2890fbf2017-07-26 15:48:41 -040018#include "GrRenderTargetProxy.h"
csmartdaltonbf4a8f92016-09-06 10:01:06 -070019#include "GrScissorState.h"
csmartdaltonc633abb2016-11-01 08:55:55 -070020#include "GrUserStencilSettings.h"
csmartdaltonbf4a8f92016-09-06 10:01:06 -070021#include "GrWindowRectsState.h"
egdanielb109ac22014-10-07 06:45:44 -070022#include "SkMatrix.h"
23#include "SkRefCnt.h"
robertphillips5fa7f302016-07-21 09:21:04 -070024#include "effects/GrCoverageSetOpXP.h"
25#include "effects/GrDisableColorXP.h"
26#include "effects/GrPorterDuffXferProcessor.h"
27#include "effects/GrSimpleTextureEffect.h"
28
Brian Salomon652ecb52017-01-17 12:39:53 -050029class GrAppliedClip;
joshualitt79f8fae2014-10-28 17:59:26 -070030class GrDeviceCoordTexture;
Brian Salomon25a88092016-12-01 09:36:50 -050031class GrOp;
Brian Salomon25a88092016-12-01 09:36:50 -050032class GrRenderTargetContext;
egdaniel3658f382014-09-15 07:01:59 -070033
Brian Salomon92aee3d2016-12-21 09:20:25 -050034/**
Brian Salomone5b399e2017-07-19 13:50:54 -040035 * This immutable object contains information needed to set build a shader program and set API
36 * state for a draw. It is used along with a GrPrimitiveProcessor and a source of geometric
37 * data (GrMesh or GrPath) to draw.
egdaniel3658f382014-09-15 07:01:59 -070038 */
Brian Salomon16351462017-07-19 16:35:31 -040039class GrPipeline {
egdaniel3658f382014-09-15 07:01:59 -070040public:
bsalomoncb02b382015-08-12 11:14:50 -070041 ///////////////////////////////////////////////////////////////////////////
42 /// @name Creation
43
Brian Salomon189098e72017-01-19 09:55:19 -050044 enum Flags {
45 /**
46 * Perform HW anti-aliasing. This means either HW FSAA, if supported by the render target,
47 * or smooth-line rendering if a line primitive is drawn and line smoothing is supported by
48 * the 3D API.
49 */
50 kHWAntialias_Flag = 0x1,
Brian Salomon189098e72017-01-19 09:55:19 -050051 /**
52 * Modifies the vertex shader so that vertices will be positioned at pixel centers.
53 */
54 kSnapVerticesToPixelCenters_Flag = 0x2,
Brian Salomon611572c2017-04-28 08:57:12 -040055 /** Disables conversion to sRGB from linear when writing to a sRGB destination. */
56 kDisableOutputConversionToSRGB_Flag = 0x4,
57 /** Allows conversion from sRGB to linear when reading from processor's sRGB texture. */
58 kAllowSRGBInputs_Flag = 0x8,
Brian Salomon189098e72017-01-19 09:55:19 -050059 };
60
Brian Salomon611572c2017-04-28 08:57:12 -040061 static uint32_t SRGBFlagsFromPaint(const GrPaint& paint) {
62 uint32_t flags = 0;
63 if (paint.getAllowSRGBInputs()) {
64 flags |= kAllowSRGBInputs_Flag;
65 }
66 if (paint.getDisableOutputConversionToSRGB()) {
67 flags |= kDisableOutputConversionToSRGB_Flag;
68 }
69 return flags;
70 }
71
Chris Dalton46983b72017-06-06 12:27:16 -060072 enum ScissorState : bool {
73 kEnabled = true,
74 kDisabled = false
75 };
76
Brian Salomonb5cb6832017-02-24 11:01:15 -050077 struct InitArgs {
Brian Salomon189098e72017-01-19 09:55:19 -050078 uint32_t fFlags = 0;
Brian Salomon189098e72017-01-19 09:55:19 -050079 const GrUserStencilSettings* fUserStencil = &GrUserStencilSettings::kUnused;
Robert Phillips2890fbf2017-07-26 15:48:41 -040080 GrRenderTargetProxy* fProxy = nullptr;
Brian Salomon189098e72017-01-19 09:55:19 -050081 const GrCaps* fCaps = nullptr;
Robert Phillips9bee2e52017-05-29 12:37:20 -040082 GrResourceProvider* fResourceProvider = nullptr;
Robert Phillipsbb581ce2017-05-29 15:05:15 -040083 GrXferProcessor::DstProxy fDstProxy;
bsalomona387a112015-08-11 14:47:42 -070084 };
85
Brian Salomonb5cb6832017-02-24 11:01:15 -050086 /**
Chris Dalton46983b72017-06-06 12:27:16 -060087 * Graphics state that can change dynamically without creating a new pipeline.
88 **/
89 struct DynamicState {
90 // Overrides the scissor rectangle (if scissor is enabled in the pipeline).
91 // TODO: eventually this should be the only way to specify a scissor rectangle, as is the
92 // case with the simple constructor.
93 SkIRect fScissorRect;
94 };
95
96 /**
csmartdalton119fb2b2017-02-08 14:41:05 -050097 * Creates a simple pipeline with default settings and no processors. The provided blend mode
Chris Dalton46983b72017-06-06 12:27:16 -060098 * must be "Porter Duff" (<= kLastCoeffMode). If using ScissorState::kEnabled, the caller must
99 * specify a scissor rectangle through the DynamicState struct.
csmartdalton119fb2b2017-02-08 14:41:05 -0500100 **/
Robert Phillips2890fbf2017-07-26 15:48:41 -0400101 GrPipeline(GrRenderTargetProxy*, ScissorState, SkBlendMode);
csmartdalton119fb2b2017-02-08 14:41:05 -0500102
Brian Salomonbfd18cd2017-08-09 16:27:09 -0400103 GrPipeline(const InitArgs&, GrProcessorSet&&, GrAppliedClip&&);
Brian Salomon6d4b65e2017-05-03 17:06:09 -0400104
Brian Salomon16351462017-07-19 16:35:31 -0400105 GrPipeline(const GrPipeline&) = delete;
106 GrPipeline& operator=(const GrPipeline&) = delete;
107
egdaniel89af44a2014-09-26 06:15:04 -0700108 /// @}
109
110 ///////////////////////////////////////////////////////////////////////////
bsalomon6be6f7c2015-02-26 13:05:21 -0800111 /// @name GrFragmentProcessors
egdaniel89af44a2014-09-26 06:15:04 -0700112
Robert Phillipsd261e102017-06-23 12:37:20 -0400113 // Make the renderTargetContext's GrOpList be dependent on any GrOpLists in this pipeline
114 void addDependenciesTo(GrOpList* recipient, const GrCaps&) const;
bsalomon6be6f7c2015-02-26 13:05:21 -0800115
bsalomonac856c92015-08-27 06:30:17 -0700116 int numColorFragmentProcessors() const { return fNumColorProcessors; }
117 int numCoverageFragmentProcessors() const {
118 return fFragmentProcessors.count() - fNumColorProcessors;
119 }
120 int numFragmentProcessors() const { return fFragmentProcessors.count(); }
egdaniel89af44a2014-09-26 06:15:04 -0700121
bsalomon2047b782015-12-21 13:12:54 -0800122 const GrXferProcessor& getXferProcessor() const {
Brian Salomond61c9d92017-04-10 10:54:25 -0400123 if (fXferProcessor) {
bsalomon2047b782015-12-21 13:12:54 -0800124 return *fXferProcessor.get();
125 } else {
126 // A null xp member means the common src-over case. GrXferProcessor's ref'ing
127 // mechanism is not thread safe so we do not hold a ref on this global.
128 return GrPorterDuffXPFactory::SimpleSrcOverXP();
129 }
130 }
egdaniel378092f2014-12-03 10:40:13 -0800131
Brian Salomon18dfa982017-04-03 16:57:43 -0400132 /**
133 * If the GrXferProcessor uses a texture to access the dst color, then this returns that
134 * texture and the offset to the dst contents within that texture.
135 */
Robert Phillipsbb581ce2017-05-29 15:05:15 -0400136 GrTextureProxy* dstTextureProxy(SkIPoint* offset = nullptr) const {
Brian Salomon18dfa982017-04-03 16:57:43 -0400137 if (offset) {
138 *offset = fDstTextureOffset;
139 }
Robert Phillipsbb581ce2017-05-29 15:05:15 -0400140 return fDstTextureProxy.get();
141 }
142
143 GrTexture* peekDstTexture(SkIPoint* offset = nullptr) const {
144 if (GrTextureProxy* dstProxy = this->dstTextureProxy(offset)) {
145 return dstProxy->priv().peekTexture();
146 }
147
148 return nullptr;
Brian Salomon18dfa982017-04-03 16:57:43 -0400149 }
150
bsalomonac856c92015-08-27 06:30:17 -0700151 const GrFragmentProcessor& getColorFragmentProcessor(int idx) const {
152 SkASSERT(idx < this->numColorFragmentProcessors());
153 return *fFragmentProcessors[idx].get();
egdanield9aa2182014-10-09 13:47:05 -0700154 }
bsalomonac856c92015-08-27 06:30:17 -0700155
156 const GrFragmentProcessor& getCoverageFragmentProcessor(int idx) const {
157 SkASSERT(idx < this->numCoverageFragmentProcessors());
158 return *fFragmentProcessors[fNumColorProcessors + idx].get();
egdanield9aa2182014-10-09 13:47:05 -0700159 }
bsalomonac856c92015-08-27 06:30:17 -0700160
161 const GrFragmentProcessor& getFragmentProcessor(int idx) const {
162 return *fFragmentProcessors[idx].get();
bsalomonae59b772014-11-19 08:23:49 -0800163 }
egdaniel89af44a2014-09-26 06:15:04 -0700164
165 /// @}
166
egdaniel89af44a2014-09-26 06:15:04 -0700167 /**
168 * Retrieves the currently set render-target.
169 *
170 * @return The currently set render target.
171 */
Robert Phillips2890fbf2017-07-26 15:48:41 -0400172 GrRenderTargetProxy* proxy() const { return fProxy.get(); }
173 GrRenderTarget* renderTarget() const { return fProxy.get()->priv().peekRenderTarget(); }
egdaniel89af44a2014-09-26 06:15:04 -0700174
csmartdaltonc633abb2016-11-01 08:55:55 -0700175 const GrUserStencilSettings* getUserStencil() const { return fUserStencilSettings; }
egdaniel89af44a2014-09-26 06:15:04 -0700176
bsalomon3e791242014-12-17 13:43:13 -0800177 const GrScissorState& getScissorState() const { return fScissorState; }
joshualitt54e0c122014-11-19 09:38:51 -0800178
csmartdaltonbf4a8f92016-09-06 10:01:06 -0700179 const GrWindowRectsState& getWindowRectsState() const { return fWindowRectsState; }
csmartdalton28341fa2016-08-17 10:00:21 -0700180
Brian Salomon189098e72017-01-19 09:55:19 -0500181 bool isHWAntialiasState() const { return SkToBool(fFlags & kHWAntialias_Flag); }
182 bool snapVerticesToPixelCenters() const {
183 return SkToBool(fFlags & kSnapVerticesToPixelCenters_Flag);
184 }
brianosman64d094d2016-03-25 06:01:59 -0700185 bool getDisableOutputConversionToSRGB() const {
186 return SkToBool(fFlags & kDisableOutputConversionToSRGB_Flag);
187 }
brianosman898235c2016-04-06 07:38:23 -0700188 bool getAllowSRGBInputs() const {
189 return SkToBool(fFlags & kAllowSRGBInputs_Flag);
190 }
cdalton193d9cf2016-05-12 11:52:02 -0700191 bool hasStencilClip() const {
192 return SkToBool(fFlags & kHasStencilClip_Flag);
193 }
csmartdaltonc633abb2016-11-01 08:55:55 -0700194 bool isStencilEnabled() const {
195 return SkToBool(fFlags & kStencilEnabled_Flag);
196 }
Robert Phillipsa91e0b72017-05-01 13:12:20 -0400197 bool isBad() const { return SkToBool(fFlags & kIsBad_Flag); }
bsalomonae59b772014-11-19 08:23:49 -0800198
Robert Phillipsc9c06d42017-06-12 10:58:31 -0400199 GrXferBarrierType xferBarrierType(const GrCaps& caps) const;
bsalomoncb02b382015-08-12 11:14:50 -0700200
Brian Salomon82dfd3d2017-06-14 12:30:35 -0400201 static SkString DumpFlags(uint32_t flags) {
202 if (flags) {
203 SkString result;
204 if (flags & GrPipeline::kSnapVerticesToPixelCenters_Flag) {
205 result.append("Snap vertices to pixel center.\n");
206 }
207 if (flags & GrPipeline::kHWAntialias_Flag) {
208 result.append("HW Antialiasing enabled.\n");
209 }
210 if (flags & GrPipeline::kDisableOutputConversionToSRGB_Flag) {
211 result.append("Disable output conversion to sRGB.\n");
212 }
213 if (flags & GrPipeline::kAllowSRGBInputs_Flag) {
214 result.append("Allow sRGB Inputs.\n");
215 }
216 return result;
217 }
218 return SkString("No pipeline flags\n");
219 }
220
bsalomonae59b772014-11-19 08:23:49 -0800221private:
Robert Phillipsa91e0b72017-05-01 13:12:20 -0400222 void markAsBad() { fFlags |= kIsBad_Flag; }
223
Brian Salomonf87e2b92017-01-19 11:31:50 -0500224 /** This is a continuation of the public "Flags" enum. */
Brian Salomon189098e72017-01-19 09:55:19 -0500225 enum PrivateFlags {
Brian Salomone23bffd2017-06-02 11:01:10 -0400226 kHasStencilClip_Flag = 0x10,
227 kStencilEnabled_Flag = 0x20,
228 kIsBad_Flag = 0x40,
bsalomon04ddf892014-11-19 12:36:22 -0800229 };
230
Robert Phillips2890fbf2017-07-26 15:48:41 -0400231 using RenderTargetProxy = GrPendingIOResource<GrRenderTargetProxy, kWrite_GrIOType>;
Robert Phillipsbb581ce2017-05-29 15:05:15 -0400232 using DstTextureProxy = GrPendingIOResource<GrTextureProxy, kRead_GrIOType>;
Brian Salomonaff329b2017-08-11 09:40:37 -0400233 using FragmentProcessorArray = SkAutoSTArray<8, std::unique_ptr<const GrFragmentProcessor>>;
Brian Salomon18dfa982017-04-03 16:57:43 -0400234
Robert Phillipsbb581ce2017-05-29 15:05:15 -0400235 DstTextureProxy fDstTextureProxy;
Brian Salomon18dfa982017-04-03 16:57:43 -0400236 SkIPoint fDstTextureOffset;
Robert Phillips19e51dc2017-08-09 09:30:51 -0400237 // MDB TODO: do we still need the destination proxy here?
Robert Phillips2890fbf2017-07-26 15:48:41 -0400238 RenderTargetProxy fProxy;
Brian Salomon18dfa982017-04-03 16:57:43 -0400239 GrScissorState fScissorState;
240 GrWindowRectsState fWindowRectsState;
241 const GrUserStencilSettings* fUserStencilSettings;
Brian Salomon18dfa982017-04-03 16:57:43 -0400242 uint16_t fFlags;
Brian Salomond61c9d92017-04-10 10:54:25 -0400243 sk_sp<const GrXferProcessor> fXferProcessor;
Brian Salomon18dfa982017-04-03 16:57:43 -0400244 FragmentProcessorArray fFragmentProcessors;
egdanield9aa2182014-10-09 13:47:05 -0700245
bsalomonac856c92015-08-27 06:30:17 -0700246 // This value is also the index in fFragmentProcessors where coverage processors begin.
Brian Salomon18dfa982017-04-03 16:57:43 -0400247 int fNumColorProcessors;
egdaniel89af44a2014-09-26 06:15:04 -0700248
egdaniel89af44a2014-09-26 06:15:04 -0700249 typedef SkRefCnt INHERITED;
egdaniel3658f382014-09-15 07:01:59 -0700250};
251
252#endif