1 /* 2 ----------------------------------------------------------------------------- 3 This source file is part of OGRE 4 (Object-oriented Graphics Rendering Engine) 5 For the latest info, see http://www.ogre3d.org 6 7 Copyright (c) 2000-2013 Torus Knot Software Ltd 8 Permission is hereby granted, free of charge, to any person obtaining a copy 9 of this software and associated documentation files (the "Software"), to deal 10 in the Software without restriction, including without limitation the rights 11 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 12 copies of the Software, and to permit persons to whom the Software is 13 furnished to do so, subject to the following conditions: 14 15 The above copyright notice and this permission notice shall be included in 16 all copies or substantial portions of the Software. 17 18 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 19 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 20 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 21 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 22 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 23 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 24 THE SOFTWARE. 25 ----------------------------------------------------------------------------- 26 */ 27 #include "OgreShaderExTriplanarTexturing.h" 28 #ifdef RTSHADER_SYSTEM_BUILD_EXT_SHADERS 29 #include "OgreShaderFFPRenderState.h" 30 #include "OgreShaderProgram.h" 31 #include "OgreShaderParameter.h" 32 #include "OgreShaderProgramSet.h" 33 34 namespace Ogre { 35 namespace RTShader { 36 37 String TriplanarTexturing::type = "SGX_TriplanarTexturing"; 38 39 //----------------------------------------------------------------------- 40 resolveParameters(ProgramSet * programSet)41 bool TriplanarTexturing::resolveParameters(ProgramSet* programSet) 42 { 43 Program* vsProgram = programSet->getCpuVertexProgram(); 44 Program* psProgram = programSet->getCpuFragmentProgram(); 45 Function* vsMain = vsProgram->getEntryPointFunction(); 46 Function* psMain = psProgram->getEntryPointFunction(); 47 48 // Resolve pixel shader output diffuse color. 49 mPSInDiffuse = vsMain->resolveInputParameter(Parameter::SPS_COLOR, 0, Parameter::SPC_COLOR_DIFFUSE, GCT_FLOAT4); 50 51 // Resolve input vertex shader normal. 52 mVSInNormal = vsMain->resolveInputParameter(Parameter::SPS_NORMAL, 0, Parameter::SPC_NORMAL_OBJECT_SPACE, GCT_FLOAT3); 53 54 // Resolve output vertex shader normal. 55 mVSOutNormal = vsMain->resolveOutputParameter(Parameter::SPS_TEXTURE_COORDINATES, -1, Parameter::SPC_NORMAL_VIEW_SPACE, GCT_FLOAT3); 56 57 // Resolve pixel shader output diffuse color. 58 mPSInDiffuse = psMain->resolveInputParameter(Parameter::SPS_COLOR, 0, Parameter::SPC_COLOR_DIFFUSE, GCT_FLOAT4); 59 60 // Resolve input pixel shader normal. 61 mPSInNormal = psMain->resolveInputParameter(Parameter::SPS_TEXTURE_COORDINATES, 62 mVSOutNormal->getIndex(), 63 mVSOutNormal->getContent(), 64 GCT_FLOAT3); 65 66 // Resolve input vertex shader normal. 67 mVSInPosition = vsMain->resolveInputParameter(Parameter::SPS_POSITION, 0, Parameter::SPC_POSITION_OBJECT_SPACE, GCT_FLOAT4); 68 69 mVSInPosition = vsMain->resolveInputParameter(Parameter::SPS_POSITION, 0, Parameter::SPC_POSITION_OBJECT_SPACE, GCT_FLOAT4); 70 mVSOutPosition = vsMain->resolveOutputParameter(Parameter::SPS_TEXTURE_COORDINATES, -1, Parameter::SPC_POSITION_OBJECT_SPACE, GCT_FLOAT4); 71 mPSInPosition = psMain->resolveInputParameter(Parameter::SPS_TEXTURE_COORDINATES, 72 mVSOutPosition->getIndex(), 73 mVSOutPosition->getContent(), 74 GCT_FLOAT4); 75 76 mSamplerFromX = psProgram->resolveParameter(GCT_SAMPLER2D, mTextureSamplerIndexFromX, (uint16)GPV_GLOBAL, "tp_sampler_from_x"); 77 if (mSamplerFromX.get() == NULL) 78 return false; 79 mSamplerFromY = psProgram->resolveParameter(GCT_SAMPLER2D, mTextureSamplerIndexFromY, (uint16)GPV_GLOBAL, "tp_sampler_from_y"); 80 if (mSamplerFromY.get() == NULL) 81 return false; 82 mSamplerFromZ = psProgram->resolveParameter(GCT_SAMPLER2D, mTextureSamplerIndexFromZ, (uint16)GPV_GLOBAL, "tp_sampler_from_z"); 83 if (mSamplerFromZ.get() == NULL) 84 return false; 85 86 mPSOutDiffuse = psMain->resolveOutputParameter(Parameter::SPS_COLOR, 0, Parameter::SPC_COLOR_DIFFUSE, GCT_FLOAT4); 87 if (mPSOutDiffuse.get() == NULL) 88 return false; 89 90 mPSTPParams = psProgram->resolveParameter(GCT_FLOAT3, -1, (uint16)GPV_GLOBAL, "gTPParams"); 91 if (mPSTPParams.get() == NULL) 92 return false; 93 return true; 94 } 95 96 //----------------------------------------------------------------------- resolveDependencies(ProgramSet * programSet)97 bool TriplanarTexturing::resolveDependencies(ProgramSet* programSet) 98 { 99 Program* psProgram = programSet->getCpuFragmentProgram(); 100 Program* vsProgram = programSet->getCpuVertexProgram(); 101 psProgram->addDependency("SGXLib_TriplanarTexturing"); 102 vsProgram->addDependency(FFP_LIB_COMMON); 103 return true; 104 } 105 106 //----------------------------------------------------------------------- addFunctionInvocations(ProgramSet * programSet)107 bool TriplanarTexturing::addFunctionInvocations(ProgramSet* programSet) 108 { 109 Program* psProgram = programSet->getCpuFragmentProgram(); 110 Function* psMain = psProgram->getEntryPointFunction(); 111 Program* vsProgram = programSet->getCpuVertexProgram(); 112 Function* vsMain = vsProgram->getEntryPointFunction(); 113 114 int internalCounter = 0; 115 116 FunctionInvocation *curFuncInvocation = OGRE_NEW FunctionInvocation(FFP_FUNC_ASSIGN, FFP_VS_TEXTURING, internalCounter++); 117 curFuncInvocation->pushOperand(mVSInNormal, Operand::OPS_IN); 118 curFuncInvocation->pushOperand(mVSOutNormal, Operand::OPS_OUT); 119 vsMain->addAtomInstance(curFuncInvocation); 120 121 curFuncInvocation = OGRE_NEW FunctionInvocation(FFP_FUNC_ASSIGN, FFP_VS_TEXTURING, internalCounter++); 122 curFuncInvocation->pushOperand(mVSInPosition, Operand::OPS_IN); 123 curFuncInvocation->pushOperand(mVSOutPosition, Operand::OPS_OUT); 124 vsMain->addAtomInstance(curFuncInvocation); 125 126 curFuncInvocation = OGRE_NEW FunctionInvocation(SGX_FUNC_TRIPLANAR_TEXTURING, FFP_PS_TEXTURING, internalCounter++); 127 curFuncInvocation->pushOperand(mPSInDiffuse, Operand::OPS_IN); 128 curFuncInvocation->pushOperand(mPSInNormal, Operand::OPS_IN); 129 curFuncInvocation->pushOperand(mPSInPosition, Operand::OPS_IN); 130 curFuncInvocation->pushOperand(mSamplerFromX, Operand::OPS_IN); 131 curFuncInvocation->pushOperand(mSamplerFromY, Operand::OPS_IN); 132 curFuncInvocation->pushOperand(mSamplerFromZ, Operand::OPS_IN); 133 curFuncInvocation->pushOperand(mPSTPParams, Operand::OPS_IN); 134 curFuncInvocation->pushOperand(mPSOutDiffuse, Operand::OPS_OUT); 135 psMain->addAtomInstance(curFuncInvocation); 136 137 return true; 138 } 139 140 //----------------------------------------------------------------------- getType() const141 const String& TriplanarTexturing::getType() const 142 { 143 return type; 144 } 145 146 //----------------------------------------------------------------------- getExecutionOrder() const147 int TriplanarTexturing::getExecutionOrder() const 148 { 149 return FFP_TEXTURING; 150 } 151 152 //----------------------------------------------------------------------- preAddToRenderState(const RenderState * renderState,Pass * srcPass,Pass * dstPass)153 bool TriplanarTexturing::preAddToRenderState(const RenderState* renderState, Pass* srcPass, Pass* dstPass ) 154 { 155 TextureUnitState* textureUnit; 156 157 // Create the mapping textures 158 textureUnit = dstPass->createTextureUnitState(); 159 textureUnit->setTextureName(mTextureNameFromX); 160 mTextureSamplerIndexFromX = dstPass->getNumTextureUnitStates() - 1; 161 162 textureUnit = dstPass->createTextureUnitState(); 163 textureUnit->setTextureName(mTextureNameFromY); 164 mTextureSamplerIndexFromY = dstPass->getNumTextureUnitStates() - 1; 165 166 textureUnit = dstPass->createTextureUnitState(); 167 textureUnit->setTextureName(mTextureNameFromZ); 168 mTextureSamplerIndexFromZ = dstPass->getNumTextureUnitStates() - 1; 169 return true; 170 } 171 172 //----------------------------------------------------------------------- copyFrom(const SubRenderState & rhs)173 void TriplanarTexturing::copyFrom(const SubRenderState& rhs) 174 { 175 const TriplanarTexturing& rhsTP = static_cast<const TriplanarTexturing&>(rhs); 176 177 mPSOutDiffuse = rhsTP.mPSOutDiffuse; 178 mPSInDiffuse = rhsTP.mPSInDiffuse; 179 180 mVSInPosition = rhsTP.mVSInPosition; 181 mVSOutPosition = rhsTP.mVSOutPosition; 182 183 mVSOutNormal = rhsTP.mVSOutNormal; 184 mVSInNormal = rhsTP.mVSInNormal; 185 mPSInNormal = rhsTP.mPSInNormal; 186 187 mVSOutPosition = rhsTP.mVSOutPosition; 188 mVSInPosition = rhsTP.mVSInPosition; 189 mPSInPosition = rhsTP.mPSInPosition; 190 191 mSamplerFromX = rhsTP.mSamplerFromX; 192 mSamplerFromY = rhsTP.mSamplerFromY; 193 mSamplerFromZ = rhsTP.mSamplerFromZ; 194 195 mPSTPParams = rhsTP.mPSTPParams; 196 mParameters = rhsTP.mParameters; 197 mTextureNameFromX = rhsTP.mTextureNameFromX; 198 mTextureNameFromY = rhsTP.mTextureNameFromY; 199 mTextureNameFromZ = rhsTP.mTextureNameFromZ; 200 } 201 202 //----------------------------------------------------------------------- updateGpuProgramsParams(Renderable * rend,Pass * pass,const AutoParamDataSource * source,const LightList * pLightList)203 void TriplanarTexturing::updateGpuProgramsParams(Renderable* rend, Pass* pass, const AutoParamDataSource* source, 204 const LightList* pLightList) 205 { 206 mPSTPParams->setGpuParameter(mParameters); 207 } 208 209 //----------------------------------------------------------------------- setParameters(const Vector3 & parameters)210 void TriplanarTexturing::setParameters(const Vector3 ¶meters) 211 { 212 mParameters = parameters; 213 } 214 215 //----------------------------------------------------------------------- setTextureNames(const String & textureNameFromX,const String & textureNameFromY,const String & textureNameFromZ)216 void TriplanarTexturing::setTextureNames(const String &textureNameFromX, const String &textureNameFromY, const String &textureNameFromZ) 217 { 218 mTextureNameFromX = textureNameFromX; 219 mTextureNameFromY = textureNameFromY; 220 mTextureNameFromZ = textureNameFromZ; 221 } 222 223 //----------------------------------------------------------------------- getType() const224 const String& TriplanarTexturingFactory::getType() const 225 { 226 return TriplanarTexturing::type; 227 } 228 229 //----------------------------------------------------------------------- createInstance(ScriptCompiler * compiler,PropertyAbstractNode * prop,Pass * pass,SGScriptTranslator * translator)230 SubRenderState* TriplanarTexturingFactory::createInstance(ScriptCompiler* compiler, 231 PropertyAbstractNode* prop, Pass* pass, SGScriptTranslator* translator) 232 { 233 if (prop->name == "triplanarTexturing") 234 { 235 if (prop->values.size() == 6) 236 { 237 SubRenderState* subRenderState = createOrRetrieveInstance(translator); 238 TriplanarTexturing* tpSubRenderState = static_cast<TriplanarTexturing*>(subRenderState); 239 240 AbstractNodeList::const_iterator it = prop->values.begin(); 241 float parameters[3]; 242 if (false == SGScriptTranslator::getFloat(*it, parameters)) 243 { 244 compiler->addError(ScriptCompiler::CE_INVALIDPARAMETERS, prop->file, prop->line); 245 return NULL; 246 } 247 it++; 248 if (false == SGScriptTranslator::getFloat(*it, parameters + 1)) 249 { 250 compiler->addError(ScriptCompiler::CE_INVALIDPARAMETERS, prop->file, prop->line); 251 return NULL; 252 } 253 it++; 254 if (false == SGScriptTranslator::getFloat(*it, parameters + 2)) 255 { 256 compiler->addError(ScriptCompiler::CE_INVALIDPARAMETERS, prop->file, prop->line); 257 return NULL; 258 } 259 Vector3 vParameters(parameters[0], parameters[1], parameters[2]); 260 tpSubRenderState->setParameters(vParameters); 261 262 String textureNameFromX, textureNameFromY, textureNameFromZ; 263 ++it; 264 if (false == SGScriptTranslator::getString(*it, &textureNameFromX)) 265 { 266 compiler->addError(ScriptCompiler::CE_INVALIDPARAMETERS, prop->file, prop->line); 267 return NULL; 268 } 269 ++it; 270 if (false == SGScriptTranslator::getString(*it, &textureNameFromY)) 271 { 272 compiler->addError(ScriptCompiler::CE_INVALIDPARAMETERS, prop->file, prop->line); 273 return NULL; 274 } 275 ++it; 276 if (false == SGScriptTranslator::getString(*it, &textureNameFromZ)) 277 { 278 compiler->addError(ScriptCompiler::CE_INVALIDPARAMETERS, prop->file, prop->line); 279 return NULL; 280 } 281 tpSubRenderState->setTextureNames(textureNameFromX, textureNameFromY, textureNameFromZ); 282 283 return subRenderState; 284 } 285 else 286 { 287 compiler->addError(ScriptCompiler::CE_INVALIDPARAMETERS, prop->file, prop->line); 288 } 289 } 290 return NULL; 291 } 292 293 //----------------------------------------------------------------------- createInstanceImpl()294 SubRenderState* TriplanarTexturingFactory::createInstanceImpl() 295 { 296 return OGRE_NEW TriplanarTexturing; 297 } 298 299 300 } 301 } 302 303 #endif 304