shaderFeature.h
Engine/source/shaderGen/shaderFeature.h
Classes:
Detailed Description
1 2//----------------------------------------------------------------------------- 3// Copyright (c) 2012 GarageGames, LLC 4// 5// Permission is hereby granted, free of charge, to any person obtaining a copy 6// of this software and associated documentation files (the "Software"), to 7// deal in the Software without restriction, including without limitation the 8// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or 9// sell copies of the Software, and to permit persons to whom the Software is 10// furnished to do so, subject to the following conditions: 11// 12// The above copyright notice and this permission notice shall be included in 13// all copies or substantial portions of the Software. 14// 15// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 20// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS 21// IN THE SOFTWARE. 22//----------------------------------------------------------------------------- 23#ifndef _SHADERFEATURE_H_ 24#define _SHADERFEATURE_H_ 25 26#ifndef _MATERIALDEFINITION_H_ 27#include "materials/materialDefinition.h" 28#endif 29#ifndef _SHADERCOMP_H_ 30#include "shaderGen/shaderComp.h" 31#endif 32#ifndef _SHADER_DEPENDENCY_H_ 33#include "shaderGen/shaderDependency.h" 34#endif 35 36class MultiLine; 37struct LangElement; 38struct MaterialFeatureData; 39class GFXShaderConstBuffer; 40struct RenderPassData; 41struct SceneData; 42class SceneRenderState; 43class GFXShader; 44class GFXVertexFormat; 45 46 47/// 48class ShaderFeatureConstHandles 49{ 50public: 51 52 virtual ~ShaderFeatureConstHandles() { } 53 54 virtual void init( GFXShader *shader ) = 0; 55 56 virtual void setConsts( SceneRenderState *state, 57 const SceneData &sgData, 58 GFXShaderConstBuffer *buffer ) = 0; 59}; 60 61//************************************************************************** 62/*! 63 The ShaderFeature class is the base class for every procedurally generated 64 feature. Each feature the engine recognizes is part of the MaterialFeatureType 65 enum. That structure is used to indicate which features are present in a shader 66 to be generated. This is useful as many ShaderFeatures will output different 67 code depending on what other features are going to be in the shader. 68 69 Shaders are generated using the ShaderFeature interface, so all of the 70 descendants interact pretty much the same way. 71 72*/ 73//************************************************************************** 74 75 76//************************************************************************** 77// Shader Feature 78//************************************************************************** 79class ShaderFeature 80{ 81public: 82 83 // Bitfield which allows a shader feature to say which render targets it outputs 84 // data to (could be more than one). 85 enum OutputTarget 86 { 87 DefaultTarget = 1 << 0, 88 RenderTarget1 = 1 << 1, 89 RenderTarget2 = 1 << 2, 90 RenderTarget3 = 1 << 3, 91 }; 92 93protected: 94 95 LangElement *output; 96 97 /// The list of unique shader dependencies. 98 Vector<const ShaderDependency*> mDependencies; 99 100 /// 101 S32 mProcessIndex; 102 103public: 104 105 // TODO: Make this protected and give it a proper API. 106 const GFXVertexFormat *mVertexFormat; 107 108 // TODO: Make this protected and give it a proper API. 109 GFXVertexFormat *mInstancingFormat; 110 111public: 112 113 //************************************************************************** 114 /*! 115 The Resources structure is used by ShaderFeature to indicate how many 116 hardware "resources" it needs. Resources are things such as how 117 many textures it uses and how many texture registers it needs to pass 118 information from the vertex to the pixel shader. 119 120 The Resources data can change depending what hardware is available. For 121 instance, pixel 1.x level hardware may need more texture registers than 122 pixel 2.0+ hardware because each texture register can only be used with 123 its respective texture sampler. 124 125 The data in Resources is used to determine how many features can be 126 squeezed into a singe shader. If a feature requires too many resources 127 to fit into the current shader, it will be put into another pass. 128 */ 129 //************************************************************************** 130 struct Resources 131 { 132 U32 numTex; 133 U32 numTexReg; 134 135 Resources() 136 { 137 dMemset( this, 0, sizeof( Resources ) ); 138 } 139 }; 140 141 142 //----------------------------------------------------------------------- 143 // Base functions 144 //----------------------------------------------------------------------- 145 146 ShaderFeature() 147 : output( NULL ), 148 mProcessIndex( 0 ), 149 mInstancingFormat( NULL ), 150 mVertexFormat( NULL ) 151 { 152 } 153 154 virtual ~ShaderFeature() {} 155 156 /// returns output from a processed vertex or pixel shader 157 LangElement* getOutput() const { return output; } 158 159 /// 160 void setProcessIndex( S32 index ) { mProcessIndex = index; } 161 162 /// 163 S32 getProcessIndex() const { return mProcessIndex; } 164 165 //----------------------------------------------------------------------- 166 // Virtual Functions 167 //----------------------------------------------------------------------- 168 169 /// Get the incoming base texture coords - useful for bumpmap and detail maps 170 virtual Var* getVertTexCoord( const String &name ) = 0; 171 172 /// Set up a texture space matrix - to pass into pixel shader 173 virtual LangElement * setupTexSpaceMat( Vector<ShaderComponent*> &componentList, 174 Var **texSpaceMat ) = 0; 175 176 /// Expand and assign a normal map. This takes care of compressed normal maps as well. 177 virtual LangElement * expandNormalMap( LangElement *sampleNormalOp, 178 LangElement *normalDecl, LangElement *normalVar, const MaterialFeatureData &fd ) = 0; 179 180 /// Helper function for applying the color to shader output. 181 /// 182 /// @param elem The rbg or rgba color to assign. 183 /// 184 /// @param blend The type of blending to perform. 185 /// 186 /// @param lerpElem The optional lerp parameter when doing a LerpAlpha blend, 187 /// if not set then the elem is used. 188 /// 189 virtual LangElement* assignColor( LangElement *elem, 190 Material::BlendOp blend, 191 LangElement *lerpElem = NULL, 192 ShaderFeature::OutputTarget outputTarget = ShaderFeature::DefaultTarget ) = 0; 193 194 195 //----------------------------------------------------------------------- 196 /*! 197 Process vertex shader - This function is used by each feature to 198 generate a list of LangElements that can be traversed and "printed" 199 to generate the actual shader code. The 'output' member is the head 200 of that list. 201 202 The componentList is used mostly for access to the "Connector" 203 structure which is used to pass data from the vertex to the pixel 204 shader. 205 206 The MaterialFeatureData parameter is used to determine what other 207 features are present for the shader being generated. 208 */ 209 //----------------------------------------------------------------------- 210 virtual void processVert( Vector<ShaderComponent*> &componentList, 211 const MaterialFeatureData &fd ) 212 { output = NULL; } 213 214 //----------------------------------------------------------------------- 215 /*! 216 Process pixel shader - This function is used by each feature to 217 generate a list of LangElements that can be traversed and "printed" 218 to generate the actual shader code. The 'output' member is the head 219 of that list. 220 221 The componentList is used mostly for access to the "Connector" 222 structure which is used to pass data from the vertex to the pixel 223 shader. 224 225 The MaterialFeatureData parameter is used to determine what other 226 features are present for the shader being generated. 227 */ 228 //----------------------------------------------------------------------- 229 virtual void processPix( Vector<ShaderComponent*> &componentList, 230 const MaterialFeatureData &fd ) 231 { output = NULL; } 232 233 /// Allows the feature to add macros to pixel shader compiles. 234 virtual void processPixMacros( Vector<GFXShaderMacro> ¯os, const MaterialFeatureData &fd ) {}; 235 236 /// Allows the feature to add macros to vertex shader compiles. 237 virtual void processVertMacros( Vector<GFXShaderMacro> ¯os, const MaterialFeatureData &fd ) {}; 238 239 /// Identifies what type of blending a feature uses. This is used to 240 /// group features with the same blend operation together in a multipass 241 /// situation. 242 virtual Material::BlendOp getBlendOp() { return Material::Add; } 243 244 /// Returns the resource requirements of this feature based on what 245 /// other features are present. The "resources" are things such as 246 /// texture units, and texture registers of which there can be 247 /// very limited numbers. The resources can vary depending on hardware 248 /// and what other features are present. 249 virtual Resources getResources( const MaterialFeatureData &fd ); 250 251 /// Fills texture related info in RenderPassData for this feature. It 252 /// takes into account the current pass (passData) as well as what other 253 /// data is available to the material stage (stageDat). 254 /// 255 /// For instance, ReflectCubeFeatHLSL would like to modulate its output 256 /// by the alpha channel of another texture. If the current pass does 257 /// not contain a diffuse or bump texture, but the Material does, then 258 /// this function allows it to use one of those textures in the current 259 /// pass. 260 virtual void setTexData( Material::StageData &stageDat, 261 const MaterialFeatureData &fd, 262 RenderPassData &passData, 263 U32 &texIndex ){}; 264 265 /// Returns the name of this feature. 266 virtual String getName() = 0; 267 268 /// Adds a dependency to this shader feature. 269 virtual void addDependency( const ShaderDependency *depends ); 270 271 /// Gets the dependency list for this shader feature. 272 virtual const Vector<const ShaderDependency*> &getDependencies() const { return mDependencies; } 273 274 /// Returns the output variable name for this feature if it applies. 275 virtual const char* getOutputVarName() const { return NULL; } 276 277 /// Gets the render target this shader feature is assigning data to. 278 virtual U32 getOutputTargets( const MaterialFeatureData &fd ) const { return DefaultTarget; } 279 280 /// Returns the name of output targer var. 281 const char* getOutputTargetVarName( OutputTarget target = DefaultTarget ) const; 282 283 // Called from ProcessedShaderMaterial::determineFeatures to enable/disable features. 284 virtual void determineFeature( Material *material, 285 const GFXVertexFormat *vertexFormat, 286 U32 stageNum, 287 const FeatureType &type, 288 const FeatureSet &features, 289 MaterialFeatureData *outFeatureData ) { } 290 291 // 292 virtual ShaderFeatureConstHandles* createConstHandles( GFXShader *shader, SimObject *userObject ) { return NULL; } 293 294 /// Called after processing the vertex and processing the pixel 295 /// to cleanup any temporary structures stored in the feature. 296 virtual void reset() { output = NULL; mProcessIndex = 0; mInstancingFormat = NULL; mVertexFormat = NULL; } 297 298 /// A simpler helper function which either finds 299 /// the existing local var or creates one. 300 static Var* findOrCreateLocal( const char *name, 301 const char *type, 302 MultiLine *multi ); 303 // Set the instancing format 304 void setInstancingFormat(GFXVertexFormat *format); 305}; 306 307#endif // _SHADERFEATURE_H_ 308
