blob: 347bcda3444692f1ee9f6c2e4d85a56e085861ca [file] [log] [blame]
tomhudson@google.comf9ad8862012-05-11 20:38:48 +00001/*
2 * Copyright 2012 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 GrGLShaderBuilder_DEFINED
9#define GrGLShaderBuilder_DEFINED
10
11#include "GrAllocator.h"
12#include "gl/GrGLShaderVar.h"
13#include "gl/GrGLSL.h"
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +000014#include "gl/GrGLUniformManager.h"
tomhudson@google.comf9ad8862012-05-11 20:38:48 +000015
bsalomon@google.comad5e9372012-07-11 18:11:27 +000016class GrGLContextInfo;
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +000017
tomhudson@google.comf9ad8862012-05-11 20:38:48 +000018/**
bsalomon@google.comeb715c82012-07-11 15:03:31 +000019 Contains all the incremental state of a shader as it is being built,as well as helpers to
20 manipulate that state.
tomhudson@google.comf9ad8862012-05-11 20:38:48 +000021*/
tomhudson@google.comf9ad8862012-05-11 20:38:48 +000022class GrGLShaderBuilder {
23
24public:
bsalomon@google.com032b2212012-07-16 13:36:18 +000025
bsalomon@google.comeb715c82012-07-11 15:03:31 +000026 enum ShaderType {
27 kVertex_ShaderType = 0x1,
28 kGeometry_ShaderType = 0x2,
29 kFragment_ShaderType = 0x4,
30 };
31
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +000032 GrGLShaderBuilder(const GrGLContextInfo&, GrGLUniformManager&);
tomhudson@google.comf9ad8862012-05-11 20:38:48 +000033
tomhudson@google.com52598142012-05-24 17:44:30 +000034 void computeSwizzle(uint32_t configFlags);
35 void computeModulate(const char* fsInColor);
36
tomhudson@google.com5440f062012-06-01 15:55:50 +000037 // TODO: needs a better name
38 enum SamplerMode {
39 kDefault_SamplerMode,
40 kProj_SamplerMode,
41 kExplicitDivide_SamplerMode // must do an explicit divide
42 };
43
bsalomon@google.comeb715c82012-07-11 15:03:31 +000044 /** Determines whether we should use texture2D() or texture2Dproj(), and if an explicit divide
45 is required for the sample coordinates, creates the new variable and emits the code to
46 initialize it. */
tomhudson@google.com5440f062012-06-01 15:55:50 +000047 void setupTextureAccess(SamplerMode samplerMode, int stageNum);
tomhudson@google.com52598142012-05-24 17:44:30 +000048
bsalomon@google.comeb715c82012-07-11 15:03:31 +000049 /** texture2D(samplerName, coordName), with projection if necessary; if coordName is not
50 specified, uses fSampleCoords. */
tomhudson@google.com52598142012-05-24 17:44:30 +000051 void emitTextureLookup(const char* samplerName,
52 const char* coordName = NULL);
53
bsalomon@google.comeb715c82012-07-11 15:03:31 +000054 /** sets outColor to results of texture lookup, with swizzle, and/or modulate as necessary */
tomhudson@google.com52598142012-05-24 17:44:30 +000055 void emitDefaultFetch(const char* outColor,
56 const char* samplerName);
57
bsalomon@google.comeb715c82012-07-11 15:03:31 +000058 /** Add a uniform variable to the current program, that has visibilty in one or more shaders.
59 If stageNum is specified, it is appended to the name to guarantee uniqueness; if count is
60 specified, the uniform is an array. visibility is a bitfield of ShaderType values indicating
61 from which shaders the uniform should be accessible. At least one bit must be set. Geometry
62 shader uniforms are not supported at this time.
tomhudson@google.com242ed6f2012-05-30 17:38:57 +000063 */
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +000064 GrGLUniformManager::UniformHandle addUniform(uint32_t visibility,
65 GrSLType type,
66 const char* name,
67 int stageNum = -1,
68 int count = GrGLShaderVar::kNonArray);
bsalomon@google.com032b2212012-07-16 13:36:18 +000069
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +000070 const GrGLShaderVar& getUniformVariable(GrGLUniformManager::UniformHandle) const;
bsalomon@google.com032b2212012-07-16 13:36:18 +000071
72 /**
73 * Shorcut for getUniformVariable(u).c_str()
74 */
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +000075 const char* getUniformCStr(GrGLUniformManager::UniformHandle u) const {
bsalomon@google.com032b2212012-07-16 13:36:18 +000076 return this->getUniformVariable(u).c_str();
77 }
tomhudson@google.com242ed6f2012-05-30 17:38:57 +000078
bsalomon@google.comeb715c82012-07-11 15:03:31 +000079 /** Add a varying variable to the current program to pass values between vertex and fragment
80 shaders. If the last two parameters are non-NULL, they are filled in with the name
81 generated. */
tomhudson@google.com23cb2292012-05-30 18:26:03 +000082 void addVarying(GrSLType type,
83 const char* name,
84 const char** vsOutName = NULL,
85 const char** fsInName = NULL);
86
bsalomon@google.comeb715c82012-07-11 15:03:31 +000087 /** Add a varying variable to the current program to pass values between vertex and fragment
88 shaders; stageNum is appended to the name to guarantee uniqueness. If the last two
89 parameters are non-NULL, they are filled in with the name generated. */
tomhudson@google.com23cb2292012-05-30 18:26:03 +000090 void addVarying(GrSLType type,
91 const char* name,
92 int stageNum,
93 const char** vsOutName = NULL,
94 const char** fsInName = NULL);
bsalomon@google.comeb715c82012-07-11 15:03:31 +000095
bsalomon@google.comad5e9372012-07-11 18:11:27 +000096 /** Called after building is complete to get the final shader string. */
97 void getShader(ShaderType, SkString*) const;
98
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +000099 /**
100 * TODO: Make this do all the compiling, linking, etc. Hide this from the custom stages
101 */
102 void finished(GrGLuint programID);
103
bsalomon@google.com032b2212012-07-16 13:36:18 +0000104private:
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +0000105
bsalomon@google.com032b2212012-07-16 13:36:18 +0000106 typedef GrTAllocator<GrGLShaderVar> VarArray;
107
bsalomon@google.com032b2212012-07-16 13:36:18 +0000108 void appendDecls(const VarArray&, SkString*) const;
109 void appendUniformDecls(ShaderType, SkString*) const;
110
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +0000111 typedef GrGLUniformManager::BuilderUniform BuilderUniform;
112 GrGLUniformManager::BuilderUniformArray fUniforms;
bsalomon@google.com032b2212012-07-16 13:36:18 +0000113
bsalomon@google.comeb715c82012-07-11 15:03:31 +0000114 // TODO: Everything below here private.
bsalomon@google.com032b2212012-07-16 13:36:18 +0000115public:
bsalomon@google.comeb715c82012-07-11 15:03:31 +0000116
bsalomon@google.comf0a104e2012-07-10 17:51:07 +0000117 SkString fHeader; // VS+FS, GLSL version, etc
bsalomon@google.comf0a104e2012-07-10 17:51:07 +0000118 VarArray fVSAttrs;
119 VarArray fVSOutputs;
120 VarArray fGSInputs;
121 VarArray fGSOutputs;
122 VarArray fFSInputs;
123 SkString fGSHeader; // layout qualifiers specific to GS
bsalomon@google.comf0a104e2012-07-10 17:51:07 +0000124 VarArray fFSOutputs;
125 SkString fFSFunctions;
126 SkString fVSCode;
127 SkString fGSCode;
128 SkString fFSCode;
129 bool fUsesGS;
tomhudson@google.com040c41a2012-05-18 14:57:40 +0000130
bsalomon@google.comeb715c82012-07-11 15:03:31 +0000131 /// Per-stage settings - only valid while we're inside GrGLProgram::genStageCode().
tomhudson@google.com040c41a2012-05-18 14:57:40 +0000132 //@{
tomhudson@google.comf9ad8862012-05-11 20:38:48 +0000133
tomhudson@google.com52598142012-05-24 17:44:30 +0000134 int fVaryingDims;
tomhudson@google.com9c639a42012-05-14 19:58:06 +0000135 static const int fCoordDims = 2;
136
tomhudson@google.com040c41a2012-05-18 14:57:40 +0000137 /// True if fSampleCoords is an expression; false if it's a bare
138 /// variable name
tomhudson@google.com52598142012-05-24 17:44:30 +0000139 bool fComplexCoord;
bsalomon@google.comf0a104e2012-07-10 17:51:07 +0000140 SkString fSampleCoords;
tomhudson@google.com52598142012-05-24 17:44:30 +0000141
bsalomon@google.comf0a104e2012-07-10 17:51:07 +0000142 SkString fSwizzle;
143 SkString fModulate;
tomhudson@google.com040c41a2012-05-18 14:57:40 +0000144
bsalomon@google.comf0a104e2012-07-10 17:51:07 +0000145 SkString fTexFunc;
tomhudson@google.com5440f062012-06-01 15:55:50 +0000146
tomhudson@google.com040c41a2012-05-18 14:57:40 +0000147 //@}
tomhudson@google.com9c639a42012-05-14 19:58:06 +0000148
bsalomon@google.comad5e9372012-07-11 18:11:27 +0000149private:
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +0000150 const GrGLContextInfo& fContext;
151 GrGLUniformManager& fUniformManager;
tomhudson@google.comf9ad8862012-05-11 20:38:48 +0000152};
153
154#endif