Team Fortress 2 Source Code as on 22/4/2020
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1791 lines
53 KiB

  1. //========= Copyright Valve Corporation, All rights reserved. ============//
  2. //
  3. // Purpose:
  4. //
  5. //=====================================================================================//
  6. #include "shaderlib/BaseShader.h"
  7. #include "shaderlib/ShaderDLL.h"
  8. #include "tier0/dbg.h"
  9. #include "shaderDLL_Global.h"
  10. #include "IShaderSystem.h"
  11. #include "materialsystem/imaterial.h"
  12. #include "materialsystem/itexture.h"
  13. #include "materialsystem/ishaderapi.h"
  14. #include "materialsystem/materialsystem_config.h"
  15. #include "shaderlib/cshader.h"
  16. #include "mathlib/vmatrix.h"
  17. #include "tier1/strtools.h"
  18. #include "convar.h"
  19. #include "tier0/vprof.h"
  20. // NOTE: This must be the last include file in a .cpp file!
  21. #include "tier0/memdbgon.h"
  22. //-----------------------------------------------------------------------------
  23. // Globals
  24. //-----------------------------------------------------------------------------
  25. const char *CBaseShader::s_pTextureGroupName = NULL;
  26. IMaterialVar **CBaseShader::s_ppParams;
  27. IShaderShadow *CBaseShader::s_pShaderShadow;
  28. IShaderDynamicAPI *CBaseShader::s_pShaderAPI;
  29. IShaderInit *CBaseShader::s_pShaderInit;
  30. int CBaseShader::s_nModulationFlags;
  31. CMeshBuilder *CBaseShader::s_pMeshBuilder;
  32. static ConVar mat_fullbright( "mat_fullbright","0", FCVAR_CHEAT );
  33. bool g_shaderConfigDumpEnable = false; //true; //DO NOT CHECK IN ENABLED FIXME
  34. //-----------------------------------------------------------------------------
  35. // constructor
  36. //-----------------------------------------------------------------------------
  37. CBaseShader::CBaseShader()
  38. {
  39. GetShaderDLL()->InsertShader( this );
  40. }
  41. //-----------------------------------------------------------------------------
  42. // Shader parameter info
  43. //-----------------------------------------------------------------------------
  44. // Look in BaseShader.h for the enumeration for these.
  45. // Update there if you update here.
  46. static ShaderParamInfo_t s_StandardParams[NUM_SHADER_MATERIAL_VARS] =
  47. {
  48. { "$flags", "flags", SHADER_PARAM_TYPE_INTEGER, "0", SHADER_PARAM_NOT_EDITABLE },
  49. { "$flags_defined", "flags_defined", SHADER_PARAM_TYPE_INTEGER, "0", SHADER_PARAM_NOT_EDITABLE },
  50. { "$flags2", "flags2", SHADER_PARAM_TYPE_INTEGER, "0", SHADER_PARAM_NOT_EDITABLE },
  51. { "$flags_defined2", "flags2_defined", SHADER_PARAM_TYPE_INTEGER, "0", SHADER_PARAM_NOT_EDITABLE },
  52. { "$color", "color", SHADER_PARAM_TYPE_COLOR, "[1 1 1]", 0 },
  53. { "$alpha", "alpha", SHADER_PARAM_TYPE_FLOAT, "1.0", 0 },
  54. { "$basetexture", "Base Texture with lighting built in", SHADER_PARAM_TYPE_TEXTURE, "shadertest/BaseTexture", 0 },
  55. { "$frame", "Animation Frame", SHADER_PARAM_TYPE_INTEGER, "0", 0 },
  56. { "$basetexturetransform", "Base Texture Texcoord Transform",SHADER_PARAM_TYPE_MATRIX, "center .5 .5 scale 1 1 rotate 0 translate 0 0", 0 },
  57. { "$flashlighttexture", "flashlight spotlight shape texture", SHADER_PARAM_TYPE_TEXTURE, "effects/flashlight001", SHADER_PARAM_NOT_EDITABLE },
  58. { "$flashlighttextureframe", "Animation Frame for $flashlight", SHADER_PARAM_TYPE_INTEGER, "0", SHADER_PARAM_NOT_EDITABLE },
  59. { "$color2", "color2", SHADER_PARAM_TYPE_COLOR, "[1 1 1]", 0 },
  60. { "$srgbtint", "tint value to be applied when running on new-style srgb parts", SHADER_PARAM_TYPE_COLOR, "[1 1 1]", 0 },
  61. };
  62. //-----------------------------------------------------------------------------
  63. // Gets the standard shader parameter names
  64. // FIXME: Turn this into one function?
  65. //-----------------------------------------------------------------------------
  66. int CBaseShader::GetNumParams( ) const
  67. {
  68. return NUM_SHADER_MATERIAL_VARS;
  69. }
  70. char const* CBaseShader::GetParamName( int nParamIndex ) const
  71. {
  72. Assert( nParamIndex < NUM_SHADER_MATERIAL_VARS );
  73. return s_StandardParams[nParamIndex].m_pName;
  74. }
  75. const char *CBaseShader::GetParamHelp( int nParamIndex ) const
  76. {
  77. Assert( nParamIndex < NUM_SHADER_MATERIAL_VARS );
  78. return s_StandardParams[nParamIndex].m_pHelp;
  79. }
  80. ShaderParamType_t CBaseShader::GetParamType( int nParamIndex ) const
  81. {
  82. Assert( nParamIndex < NUM_SHADER_MATERIAL_VARS );
  83. return s_StandardParams[nParamIndex].m_Type;
  84. }
  85. const char *CBaseShader::GetParamDefault( int nParamIndex ) const
  86. {
  87. Assert( nParamIndex < NUM_SHADER_MATERIAL_VARS );
  88. return s_StandardParams[nParamIndex].m_pDefaultValue;
  89. }
  90. int CBaseShader::GetParamFlags( int nParamIndex ) const
  91. {
  92. Assert( nParamIndex < NUM_SHADER_MATERIAL_VARS );
  93. return s_StandardParams[nParamIndex].m_nFlags;
  94. }
  95. //-----------------------------------------------------------------------------
  96. // Necessary to snag ahold of some important data for the helper methods
  97. //-----------------------------------------------------------------------------
  98. void CBaseShader::InitShaderParams( IMaterialVar** ppParams, const char *pMaterialName )
  99. {
  100. // Re-entrancy check
  101. Assert( !s_ppParams );
  102. s_ppParams = ppParams;
  103. OnInitShaderParams( ppParams, pMaterialName );
  104. s_ppParams = NULL;
  105. }
  106. void CBaseShader::InitShaderInstance( IMaterialVar** ppParams, IShaderInit *pShaderInit, const char *pMaterialName, const char *pTextureGroupName )
  107. {
  108. // Re-entrancy check
  109. Assert( !s_ppParams );
  110. s_ppParams = ppParams;
  111. s_pShaderInit = pShaderInit;
  112. s_pTextureGroupName = pTextureGroupName;
  113. OnInitShaderInstance( ppParams, pShaderInit, pMaterialName );
  114. s_pTextureGroupName = NULL;
  115. s_ppParams = NULL;
  116. s_pShaderInit = NULL;
  117. }
  118. void CBaseShader::DrawElements( IMaterialVar **ppParams, int nModulationFlags,
  119. IShaderShadow* pShaderShadow, IShaderDynamicAPI* pShaderAPI, VertexCompressionType_t vertexCompression, CBasePerMaterialContextData **pContextDataPtr )
  120. {
  121. VPROF("CBaseShader::DrawElements");
  122. // Re-entrancy check
  123. Assert( !s_ppParams );
  124. s_ppParams = ppParams;
  125. s_pShaderAPI = pShaderAPI;
  126. s_pShaderShadow = pShaderShadow;
  127. s_nModulationFlags = nModulationFlags;
  128. s_pMeshBuilder = pShaderAPI ? pShaderAPI->GetVertexModifyBuilder() : NULL;
  129. if ( IsSnapshotting() )
  130. {
  131. // Set up the shadow state
  132. SetInitialShadowState( );
  133. }
  134. OnDrawElements( ppParams, pShaderShadow, pShaderAPI, vertexCompression, pContextDataPtr );
  135. s_nModulationFlags = 0;
  136. s_ppParams = NULL;
  137. s_pShaderAPI = NULL;
  138. s_pShaderShadow = NULL;
  139. s_pMeshBuilder = NULL;
  140. }
  141. //-----------------------------------------------------------------------------
  142. // Sets the default shadow state
  143. //-----------------------------------------------------------------------------
  144. void CBaseShader::SetInitialShadowState( )
  145. {
  146. // Set the default state
  147. s_pShaderShadow->SetDefaultState();
  148. // Init the standard states...
  149. int flags = s_ppParams[FLAGS]->GetIntValue();
  150. if (flags & MATERIAL_VAR_IGNOREZ)
  151. {
  152. s_pShaderShadow->EnableDepthTest( false );
  153. s_pShaderShadow->EnableDepthWrites( false );
  154. }
  155. if (flags & MATERIAL_VAR_DECAL)
  156. {
  157. s_pShaderShadow->EnablePolyOffset( SHADER_POLYOFFSET_DECAL );
  158. s_pShaderShadow->EnableDepthWrites( false );
  159. }
  160. if (flags & MATERIAL_VAR_NOCULL)
  161. {
  162. s_pShaderShadow->EnableCulling( false );
  163. }
  164. if (flags & MATERIAL_VAR_ZNEARER)
  165. {
  166. s_pShaderShadow->DepthFunc( SHADER_DEPTHFUNC_NEARER );
  167. }
  168. if (flags & MATERIAL_VAR_WIREFRAME)
  169. {
  170. s_pShaderShadow->PolyMode( SHADER_POLYMODEFACE_FRONT_AND_BACK, SHADER_POLYMODE_LINE );
  171. }
  172. // Set alpha to coverage
  173. if (flags & MATERIAL_VAR_ALLOWALPHATOCOVERAGE)
  174. {
  175. // Force the bit on and then check against alpha blend and test states in CShaderShadowDX8::ComputeAggregateShadowState()
  176. s_pShaderShadow->EnableAlphaToCoverage( true );
  177. }
  178. }
  179. //-----------------------------------------------------------------------------
  180. // Draws a snapshot
  181. //-----------------------------------------------------------------------------
  182. void CBaseShader::Draw( bool bMakeActualDrawCall )
  183. {
  184. if ( IsSnapshotting() )
  185. {
  186. // Turn off transparency if we're asked to....
  187. if (g_pConfig->bNoTransparency &&
  188. ((s_ppParams[FLAGS]->GetIntValue() & MATERIAL_VAR_NO_DEBUG_OVERRIDE) == 0))
  189. {
  190. s_pShaderShadow->EnableDepthWrites( true );
  191. s_pShaderShadow->EnableBlending( false );
  192. }
  193. GetShaderSystem()->TakeSnapshot();
  194. }
  195. else
  196. {
  197. GetShaderSystem()->DrawSnapshot( bMakeActualDrawCall );
  198. }
  199. }
  200. //-----------------------------------------------------------------------------
  201. // Finds a particular parameter (works because the lowest parameters match the shader)
  202. //-----------------------------------------------------------------------------
  203. int CBaseShader::FindParamIndex( const char *pName ) const
  204. {
  205. int numParams = GetNumParams();
  206. for( int i = 0; i < numParams; i++ )
  207. {
  208. if( Q_strnicmp( GetParamName( i ), pName, 64 ) == 0 )
  209. {
  210. return i;
  211. }
  212. }
  213. return -1;
  214. }
  215. //-----------------------------------------------------------------------------
  216. // Are we using graphics?
  217. //-----------------------------------------------------------------------------
  218. bool CBaseShader::IsUsingGraphics()
  219. {
  220. return GetShaderSystem()->IsUsingGraphics();
  221. }
  222. //-----------------------------------------------------------------------------
  223. // Are we using graphics?
  224. //-----------------------------------------------------------------------------
  225. bool CBaseShader::CanUseEditorMaterials()
  226. {
  227. return GetShaderSystem()->CanUseEditorMaterials();
  228. }
  229. //-----------------------------------------------------------------------------
  230. // Gets the builder...
  231. //-----------------------------------------------------------------------------
  232. CMeshBuilder* CBaseShader::MeshBuilder()
  233. {
  234. return s_pMeshBuilder;
  235. }
  236. //-----------------------------------------------------------------------------
  237. // Loads a texture
  238. //-----------------------------------------------------------------------------
  239. void CBaseShader::LoadTexture( int nTextureVar, int nAdditionalCreationFlags /* = 0 */ )
  240. {
  241. if ((!s_ppParams) || (nTextureVar == -1))
  242. return;
  243. IMaterialVar* pNameVar = s_ppParams[nTextureVar];
  244. if( pNameVar && pNameVar->IsDefined() )
  245. {
  246. s_pShaderInit->LoadTexture( pNameVar, s_pTextureGroupName, nAdditionalCreationFlags );
  247. }
  248. }
  249. //-----------------------------------------------------------------------------
  250. // Loads a bumpmap
  251. //-----------------------------------------------------------------------------
  252. void CBaseShader::LoadBumpMap( int nTextureVar )
  253. {
  254. if ((!s_ppParams) || (nTextureVar == -1))
  255. return;
  256. IMaterialVar* pNameVar = s_ppParams[nTextureVar];
  257. if( pNameVar && pNameVar->IsDefined() )
  258. {
  259. s_pShaderInit->LoadBumpMap( pNameVar, s_pTextureGroupName );
  260. }
  261. }
  262. //-----------------------------------------------------------------------------
  263. // Loads a cubemap
  264. //-----------------------------------------------------------------------------
  265. void CBaseShader::LoadCubeMap( int nTextureVar, int nAdditionalCreationFlags /* = 0 */ )
  266. {
  267. if ((!s_ppParams) || (nTextureVar == -1))
  268. return;
  269. IMaterialVar* pNameVar = s_ppParams[nTextureVar];
  270. if( pNameVar && pNameVar->IsDefined() )
  271. {
  272. s_pShaderInit->LoadCubeMap( s_ppParams, pNameVar, nAdditionalCreationFlags );
  273. }
  274. }
  275. ShaderAPITextureHandle_t CBaseShader::GetShaderAPITextureBindHandle( int nTextureVar, int nFrameVar, int nTextureChannel )
  276. {
  277. // Assert( !IsSnapshotting() );
  278. Assert( nTextureVar != -1 );
  279. Assert ( s_ppParams );
  280. IMaterialVar* pTextureVar = s_ppParams[nTextureVar];
  281. IMaterialVar* pFrameVar = (nFrameVar != -1) ? s_ppParams[nFrameVar] : NULL;
  282. int nFrame = pFrameVar ? pFrameVar->GetIntValue() : 0;
  283. return GetShaderSystem()->GetShaderAPITextureBindHandle( pTextureVar->GetTextureValue(), nFrame, nTextureChannel );
  284. }
  285. //-----------------------------------------------------------------------------
  286. // Four different flavors of BindTexture(), handling the two-sampler
  287. // case as well as ITexture* versus textureVar forms
  288. //-----------------------------------------------------------------------------
  289. void CBaseShader::BindTexture( Sampler_t sampler1, int nTextureVar, int nFrameVar /* = -1 */ )
  290. {
  291. BindTexture( sampler1, (Sampler_t) -1, nTextureVar, nFrameVar );
  292. }
  293. void CBaseShader::BindTexture( Sampler_t sampler1, Sampler_t sampler2, int nTextureVar, int nFrameVar /* = -1 */ )
  294. {
  295. Assert( !IsSnapshotting() );
  296. Assert( nTextureVar != -1 );
  297. Assert ( s_ppParams );
  298. IMaterialVar* pTextureVar = s_ppParams[nTextureVar];
  299. IMaterialVar* pFrameVar = (nFrameVar != -1) ? s_ppParams[nFrameVar] : NULL;
  300. if (pTextureVar)
  301. {
  302. int nFrame = pFrameVar ? pFrameVar->GetIntValue() : 0;
  303. if ( sampler2 == Sampler_t(-1) )
  304. {
  305. GetShaderSystem()->BindTexture( sampler1, pTextureVar->GetTextureValue(), nFrame );
  306. }
  307. else
  308. {
  309. GetShaderSystem()->BindTexture( sampler1, sampler2, pTextureVar->GetTextureValue(), nFrame );
  310. }
  311. }
  312. }
  313. void CBaseShader::BindTexture( Sampler_t sampler1, ITexture *pTexture, int nFrame /* = 0 */ )
  314. {
  315. BindTexture( sampler1, (Sampler_t) -1, pTexture, nFrame );
  316. }
  317. void CBaseShader::BindTexture( Sampler_t sampler1, Sampler_t sampler2, ITexture *pTexture, int nFrame /* = 0 */ )
  318. {
  319. Assert( !IsSnapshotting() );
  320. if ( sampler2 == Sampler_t(-1 ) )
  321. {
  322. GetShaderSystem()->BindTexture( sampler1, pTexture, nFrame );
  323. }
  324. else
  325. {
  326. GetShaderSystem()->BindTexture( sampler1, sampler2, pTexture, nFrame );
  327. }
  328. }
  329. void CBaseShader::GetTextureDimensions( float* pOutWidth, float* pOutHeight, int nTextureVar )
  330. {
  331. Assert( pOutWidth && pOutHeight ); // Outputs must be provided.
  332. Assert( nTextureVar != -1 );
  333. IMaterialVar* pTextureVar = s_ppParams[nTextureVar];
  334. if (pTextureVar && pTextureVar->GetTextureValue())
  335. {
  336. *pOutWidth = (float) (pTextureVar->GetTextureValue()->GetActualWidth());
  337. *pOutHeight = (float) (pTextureVar->GetTextureValue()->GetActualHeight());
  338. }
  339. }
  340. //-----------------------------------------------------------------------------
  341. // Does the texture store translucency in its alpha channel?
  342. //-----------------------------------------------------------------------------
  343. bool CBaseShader::TextureIsTranslucent( int textureVar, bool isBaseTexture )
  344. {
  345. if (textureVar < 0)
  346. return false;
  347. IMaterialVar** params = s_ppParams;
  348. if (params[textureVar]->GetType() == MATERIAL_VAR_TYPE_TEXTURE)
  349. {
  350. if (!isBaseTexture)
  351. {
  352. return params[textureVar]->GetTextureValue()->IsTranslucent();
  353. }
  354. else
  355. {
  356. // Override translucency settings if this flag is set.
  357. if (IS_FLAG_SET(MATERIAL_VAR_OPAQUETEXTURE))
  358. return false;
  359. if ( (CurrentMaterialVarFlags() & (MATERIAL_VAR_SELFILLUM | MATERIAL_VAR_BASEALPHAENVMAPMASK)) == 0)
  360. {
  361. if ((CurrentMaterialVarFlags() & MATERIAL_VAR_TRANSLUCENT) ||
  362. (CurrentMaterialVarFlags() & MATERIAL_VAR_ALPHATEST))
  363. {
  364. return params[textureVar]->GetTextureValue()->IsTranslucent();
  365. }
  366. }
  367. }
  368. }
  369. return false;
  370. }
  371. //-----------------------------------------------------------------------------
  372. //
  373. // Helper methods for color modulation
  374. //
  375. //-----------------------------------------------------------------------------
  376. //-----------------------------------------------------------------------------
  377. // Are we alpha or color modulating?
  378. //-----------------------------------------------------------------------------
  379. bool CBaseShader::IsAlphaModulating()
  380. {
  381. return (s_nModulationFlags & SHADER_USING_ALPHA_MODULATION) != 0;
  382. }
  383. bool CBaseShader::IsColorModulating()
  384. {
  385. return (s_nModulationFlags & SHADER_USING_COLOR_MODULATION) != 0;
  386. }
  387. void CBaseShader::GetColorParameter( IMaterialVar **params, float *pColorOut ) const
  388. {
  389. float flColor2[3];
  390. params[COLOR]->GetVecValue( pColorOut, 3 );
  391. params[COLOR2]->GetVecValue( flColor2, 3 );
  392. pColorOut[0] *= flColor2[0];
  393. pColorOut[1] *= flColor2[1];
  394. pColorOut[2] *= flColor2[2];
  395. if ( g_pHardwareConfig->UsesSRGBCorrectBlending() )
  396. {
  397. float flSRGBTint[3];
  398. params[SRGBTINT]->GetVecValue( flSRGBTint, 3 );
  399. pColorOut[0] *= flSRGBTint[0];
  400. pColorOut[1] *= flSRGBTint[1];
  401. pColorOut[2] *= flSRGBTint[2];
  402. }
  403. }
  404. //-----------------------------------------------------------------------------
  405. // FIXME: Figure out a better way to do this?
  406. //-----------------------------------------------------------------------------
  407. int CBaseShader::ComputeModulationFlags( IMaterialVar** params, IShaderDynamicAPI* pShaderAPI )
  408. {
  409. s_pShaderAPI = pShaderAPI;
  410. int mod = 0;
  411. if ( GetAlpha(params) < 1.0f )
  412. {
  413. mod |= SHADER_USING_ALPHA_MODULATION;
  414. }
  415. float color[3];
  416. GetColorParameter( params, color );
  417. if ((color[0] != 1.0) || (color[1] != 1.0) || (color[2] != 1.0))
  418. {
  419. mod |= SHADER_USING_COLOR_MODULATION;
  420. }
  421. if( UsingFlashlight(params) )
  422. {
  423. mod |= SHADER_USING_FLASHLIGHT;
  424. }
  425. if ( UsingEditor(params) )
  426. {
  427. mod |= SHADER_USING_EDITOR;
  428. }
  429. if( IS_FLAG2_SET( MATERIAL_VAR2_USE_FIXED_FUNCTION_BAKED_LIGHTING ) )
  430. {
  431. AssertOnce( IS_FLAG2_SET( MATERIAL_VAR2_NEEDS_BAKED_LIGHTING_SNAPSHOTS ) );
  432. if( IS_FLAG2_SET( MATERIAL_VAR2_NEEDS_BAKED_LIGHTING_SNAPSHOTS ) )
  433. {
  434. mod |= SHADER_USING_FIXED_FUNCTION_BAKED_LIGHTING;
  435. }
  436. }
  437. s_pShaderAPI = NULL;
  438. return mod;
  439. }
  440. //-----------------------------------------------------------------------------
  441. //
  442. //-----------------------------------------------------------------------------
  443. bool CBaseShader::NeedsPowerOfTwoFrameBufferTexture( IMaterialVar **params, bool bCheckSpecificToThisFrame ) const
  444. {
  445. return CShader_IsFlag2Set( params, MATERIAL_VAR2_NEEDS_POWER_OF_TWO_FRAME_BUFFER_TEXTURE );
  446. }
  447. //-----------------------------------------------------------------------------
  448. //
  449. //-----------------------------------------------------------------------------
  450. bool CBaseShader::NeedsFullFrameBufferTexture( IMaterialVar **params, bool bCheckSpecificToThisFrame ) const
  451. {
  452. return CShader_IsFlag2Set( params, MATERIAL_VAR2_NEEDS_FULL_FRAME_BUFFER_TEXTURE );
  453. }
  454. //-----------------------------------------------------------------------------
  455. //
  456. //-----------------------------------------------------------------------------
  457. bool CBaseShader::IsTranslucent( IMaterialVar **params ) const
  458. {
  459. return IS_FLAG_SET( MATERIAL_VAR_TRANSLUCENT );
  460. }
  461. //-----------------------------------------------------------------------------
  462. // Returns the translucency...
  463. //-----------------------------------------------------------------------------
  464. float CBaseShader::GetAlpha( IMaterialVar** ppParams )
  465. {
  466. if ( !ppParams )
  467. {
  468. ppParams = s_ppParams;
  469. }
  470. if (!ppParams)
  471. return 1.0f;
  472. if ( ppParams[FLAGS]->GetIntValue() & MATERIAL_VAR_NOALPHAMOD )
  473. return 1.0f;
  474. float flAlpha = ppParams[ALPHA]->GetFloatValue();
  475. return clamp( flAlpha, 0.0f, 1.0f );
  476. }
  477. //-----------------------------------------------------------------------------
  478. // Sets the color + transparency
  479. //-----------------------------------------------------------------------------
  480. void CBaseShader::SetColorState( int colorVar, bool setAlpha )
  481. {
  482. Assert( !IsSnapshotting() );
  483. if ( !s_ppParams )
  484. return;
  485. // Use tint instead of color if it was specified...
  486. IMaterialVar* pColorVar = (colorVar != -1) ? s_ppParams[colorVar] : 0;
  487. float color[4] = { 1.0, 1.0, 1.0, 1.0 };
  488. if (pColorVar)
  489. {
  490. if (pColorVar->GetType() == MATERIAL_VAR_TYPE_VECTOR)
  491. {
  492. pColorVar->GetVecValue( color, 3 );
  493. }
  494. else
  495. {
  496. color[0] = color[1] = color[2] = pColorVar->GetFloatValue();
  497. }
  498. if ( !g_pHardwareConfig->SupportsPixelShaders_1_4() ) // Clamp 0..1 for ps_1_1 and below
  499. {
  500. color[0] = clamp( color[0], 0.0f, 1.0f );
  501. color[1] = clamp( color[1], 0.0f, 1.0f );
  502. color[2] = clamp( color[2], 0.0f, 1.0f );
  503. }
  504. else if ( !g_pHardwareConfig->SupportsPixelShaders_2_0() ) // Clamp 0..8 for ps_1_4
  505. {
  506. color[0] = clamp( color[0], 0.0f, 8.0f );
  507. color[1] = clamp( color[1], 0.0f, 8.0f );
  508. color[2] = clamp( color[2], 0.0f, 8.0f );
  509. }
  510. }
  511. ApplyColor2Factor( color );
  512. color[3] = setAlpha ? GetAlpha() : 1.0f;
  513. s_pShaderAPI->Color4fv( color );
  514. }
  515. void CBaseShader::SetModulationShadowState( int tintVar )
  516. {
  517. // Have have no control over the tint var...
  518. bool doModulation = (tintVar != -1);
  519. // We activate color modulating when we're alpha or color modulating
  520. doModulation = doModulation || IsAlphaModulating() || IsColorModulating();
  521. s_pShaderShadow->EnableConstantColor( doModulation );
  522. }
  523. void CBaseShader::SetModulationDynamicState( int tintVar )
  524. {
  525. if (tintVar != -1)
  526. {
  527. SetColorState( tintVar, true );
  528. }
  529. else
  530. {
  531. SetColorState( COLOR, true );
  532. }
  533. }
  534. void CBaseShader::ApplyColor2Factor( float *pColorOut ) const // (*pColorOut) *= COLOR2
  535. {
  536. IMaterialVar* pColor2Var = s_ppParams[COLOR2];
  537. if (pColor2Var->GetType() == MATERIAL_VAR_TYPE_VECTOR)
  538. {
  539. float flColor2[3];
  540. pColor2Var->GetVecValue( flColor2, 3 );
  541. pColorOut[0] *= flColor2[0];
  542. pColorOut[1] *= flColor2[1];
  543. pColorOut[2] *= flColor2[2];
  544. }
  545. if ( g_pHardwareConfig->UsesSRGBCorrectBlending() )
  546. {
  547. IMaterialVar* pSRGBVar = s_ppParams[SRGBTINT];
  548. if (pSRGBVar->GetType() == MATERIAL_VAR_TYPE_VECTOR)
  549. {
  550. float flSRGB[3];
  551. pSRGBVar->GetVecValue( flSRGB, 3 );
  552. pColorOut[0] *= flSRGB[0];
  553. pColorOut[1] *= flSRGB[1];
  554. pColorOut[2] *= flSRGB[2];
  555. }
  556. }
  557. }
  558. void CBaseShader::ComputeModulationColor( float* color )
  559. {
  560. Assert( !IsSnapshotting() );
  561. if (!s_ppParams)
  562. return;
  563. IMaterialVar* pColorVar = s_ppParams[COLOR];
  564. if (pColorVar->GetType() == MATERIAL_VAR_TYPE_VECTOR)
  565. {
  566. pColorVar->GetVecValue( color, 3 );
  567. }
  568. else
  569. {
  570. color[0] = color[1] = color[2] = pColorVar->GetFloatValue();
  571. }
  572. ApplyColor2Factor( color );
  573. if( !g_pConfig->bShowDiffuse )
  574. {
  575. color[0] = color[1] = color[2] = 0.0f;
  576. }
  577. if( mat_fullbright.GetInt() == 2 )
  578. {
  579. color[0] = color[1] = color[2] = 1.0f;
  580. }
  581. color[3] = GetAlpha();
  582. }
  583. //-----------------------------------------------------------------------------
  584. //
  585. // Helper methods for alpha blending....
  586. //
  587. //-----------------------------------------------------------------------------
  588. void CBaseShader::EnableAlphaBlending( ShaderBlendFactor_t src, ShaderBlendFactor_t dst )
  589. {
  590. Assert( IsSnapshotting() );
  591. s_pShaderShadow->EnableBlending( true );
  592. s_pShaderShadow->BlendFunc( src, dst );
  593. s_pShaderShadow->EnableDepthWrites(false);
  594. }
  595. void CBaseShader::DisableAlphaBlending()
  596. {
  597. Assert( IsSnapshotting() );
  598. s_pShaderShadow->EnableBlending( false );
  599. }
  600. void CBaseShader::SetNormalBlendingShadowState( int textureVar, bool isBaseTexture )
  601. {
  602. Assert( IsSnapshotting() );
  603. // Either we've got a constant modulation
  604. bool isTranslucent = IsAlphaModulating();
  605. // Or we've got a vertex alpha
  606. isTranslucent = isTranslucent || (CurrentMaterialVarFlags() & MATERIAL_VAR_VERTEXALPHA);
  607. // Or we've got a texture alpha
  608. isTranslucent = isTranslucent || ( TextureIsTranslucent( textureVar, isBaseTexture ) &&
  609. !(CurrentMaterialVarFlags() & MATERIAL_VAR_ALPHATEST ) );
  610. if (isTranslucent)
  611. {
  612. EnableAlphaBlending( SHADER_BLEND_SRC_ALPHA, SHADER_BLEND_ONE_MINUS_SRC_ALPHA );
  613. }
  614. else
  615. {
  616. DisableAlphaBlending();
  617. }
  618. }
  619. //ConVar mat_debug_flashlight_only( "mat_debug_flashlight_only", "0" );
  620. void CBaseShader::SetAdditiveBlendingShadowState( int textureVar, bool isBaseTexture )
  621. {
  622. Assert( IsSnapshotting() );
  623. // Either we've got a constant modulation
  624. bool isTranslucent = IsAlphaModulating();
  625. // Or we've got a vertex alpha
  626. isTranslucent = isTranslucent || (CurrentMaterialVarFlags() & MATERIAL_VAR_VERTEXALPHA);
  627. // Or we've got a texture alpha
  628. isTranslucent = isTranslucent || ( TextureIsTranslucent( textureVar, isBaseTexture ) &&
  629. !(CurrentMaterialVarFlags() & MATERIAL_VAR_ALPHATEST ) );
  630. /*
  631. if ( mat_debug_flashlight_only.GetBool() )
  632. {
  633. if (isTranslucent)
  634. {
  635. EnableAlphaBlending( SHADER_BLEND_SRC_ALPHA, SHADER_BLEND_ONE_MINUS_SRC_ALPHA);
  636. //s_pShaderShadow->EnableAlphaTest( true );
  637. //s_pShaderShadow->AlphaFunc( SHADER_ALPHAFUNC_GREATER, 0.99f );
  638. }
  639. else
  640. {
  641. EnableAlphaBlending( SHADER_BLEND_ONE, SHADER_BLEND_ZERO);
  642. }
  643. }
  644. else
  645. */
  646. {
  647. if (isTranslucent)
  648. {
  649. EnableAlphaBlending( SHADER_BLEND_SRC_ALPHA, SHADER_BLEND_ONE );
  650. }
  651. else
  652. {
  653. EnableAlphaBlending( SHADER_BLEND_ONE, SHADER_BLEND_ONE );
  654. }
  655. }
  656. }
  657. void CBaseShader::SetDefaultBlendingShadowState( int textureVar, bool isBaseTexture )
  658. {
  659. if ( CurrentMaterialVarFlags() & MATERIAL_VAR_ADDITIVE )
  660. {
  661. SetAdditiveBlendingShadowState( textureVar, isBaseTexture );
  662. }
  663. else
  664. {
  665. SetNormalBlendingShadowState( textureVar, isBaseTexture );
  666. }
  667. }
  668. void CBaseShader::SetBlendingShadowState( BlendType_t nMode )
  669. {
  670. switch ( nMode )
  671. {
  672. case BT_NONE:
  673. DisableAlphaBlending();
  674. break;
  675. case BT_BLEND:
  676. EnableAlphaBlending( SHADER_BLEND_SRC_ALPHA, SHADER_BLEND_ONE_MINUS_SRC_ALPHA );
  677. break;
  678. case BT_ADD:
  679. EnableAlphaBlending( SHADER_BLEND_ONE, SHADER_BLEND_ONE );
  680. break;
  681. case BT_BLENDADD:
  682. EnableAlphaBlending( SHADER_BLEND_SRC_ALPHA, SHADER_BLEND_ONE );
  683. break;
  684. }
  685. }
  686. //-----------------------------------------------------------------------------
  687. // Sets lightmap blending mode for single texturing
  688. //-----------------------------------------------------------------------------
  689. void CBaseShader::SingleTextureLightmapBlendMode( )
  690. {
  691. Assert( IsSnapshotting() );
  692. s_pShaderShadow->EnableBlending( true );
  693. s_pShaderShadow->BlendFunc( SHADER_BLEND_DST_COLOR, SHADER_BLEND_SRC_COLOR );
  694. }
  695. //-----------------------------------------------------------------------------
  696. // Loads the identity transform into a matrix
  697. //-----------------------------------------------------------------------------
  698. void CBaseShader::LoadIdentity( MaterialMatrixMode_t matrixMode )
  699. {
  700. Assert( !IsSnapshotting() );
  701. s_pShaderAPI->MatrixMode( matrixMode );
  702. s_pShaderAPI->LoadIdentity( );
  703. }
  704. //-----------------------------------------------------------------------------
  705. // Loads the camera to world transform into a matrix
  706. //-----------------------------------------------------------------------------
  707. void CBaseShader::LoadCameraToWorldTransform( MaterialMatrixMode_t matrixMode )
  708. {
  709. s_pShaderAPI->MatrixMode( matrixMode );
  710. s_pShaderAPI->LoadCameraToWorld();
  711. }
  712. void CBaseShader::LoadCameraSpaceSphereMapTransform( MaterialMatrixMode_t matrixMode )
  713. {
  714. static float mat[4][4] =
  715. {
  716. { 0.5f, 0.0f, 0.0f, 0.0f },
  717. { 0.0f, -0.5f, 0.0f, 0.0f },
  718. { 0.0f, 0.0f, 0.0f, 0.0f },
  719. { 0.5f, -0.5f, 0.0f, 1.0f },
  720. };
  721. s_pShaderAPI->MatrixMode( matrixMode );
  722. s_pShaderAPI->LoadMatrix( (float*)mat );
  723. }
  724. //-----------------------------------------------------------------------------
  725. //
  726. // Sets a texture translation transform
  727. //
  728. //-----------------------------------------------------------------------------
  729. void CBaseShader::SetFixedFunctionTextureTranslation( MaterialMatrixMode_t textureTransform, int translationVar )
  730. {
  731. Assert( !IsSnapshotting() );
  732. // handle scrolling of base texture
  733. Vector2D vDelta( 0, 0 );
  734. if (translationVar != -1)
  735. {
  736. s_ppParams[translationVar]->GetVecValue( vDelta.Base(), 2 );
  737. }
  738. if( vDelta[0] != 0.0f || vDelta[1] != 0.0f )
  739. {
  740. s_pShaderAPI->MatrixMode( textureTransform );
  741. // only do the upper 3x3 since this is a 2D matrix
  742. float mat[16];
  743. mat[0] = 1.0f; mat[1] = 0.0f; mat[2] = 0.0f;
  744. mat[4] = 0.0f; mat[5] = 1.0f; mat[6] = 0.0f;
  745. mat[8] = vDelta[0]; mat[9] = vDelta[1]; mat[10] = 1.0f;
  746. // Better set the stuff we don't set with some sort of value!
  747. mat[3] = mat[7] = mat[11] = 0;
  748. mat[12] = mat[13] = mat[14] = 0;
  749. mat[15] = 1;
  750. s_pShaderAPI->LoadMatrix( mat );
  751. }
  752. else
  753. {
  754. LoadIdentity( textureTransform );
  755. }
  756. }
  757. void CBaseShader::SetFixedFunctionTextureScale( MaterialMatrixMode_t textureTransform, int scaleVar )
  758. {
  759. Assert( !IsSnapshotting() );
  760. // handle scrolling of base texture
  761. Vector2D vScale;
  762. s_ppParams[scaleVar]->GetVecValue( vScale.Base(), 2 );
  763. if( vScale[0] != 0.0f || vScale[1] != 0.0f )
  764. {
  765. s_pShaderAPI->MatrixMode( textureTransform );
  766. // only do the upper 3x3 since this is a 2D matrix
  767. float mat[16];
  768. mat[0] = vScale[0]; mat[1] = 0.0f; mat[2] = 0.0f;
  769. mat[4] = 0.0f; mat[5] = vScale[1]; mat[6] = 0.0f;
  770. mat[8] = 0.0f; mat[9] = 0.0f; mat[10] = 1.0f;
  771. // Better set the stuff we don't set with some sort of value!
  772. mat[3] = mat[7] = mat[11] = 0;
  773. mat[12] = mat[13] = mat[14] = 0;
  774. mat[15] = 1;
  775. s_pShaderAPI->LoadMatrix( mat );
  776. }
  777. else
  778. {
  779. LoadIdentity( textureTransform );
  780. }
  781. }
  782. void CBaseShader::SetFixedFunctionTextureTransform( MaterialMatrixMode_t textureTransform, int transformVar )
  783. {
  784. Assert( !IsSnapshotting() );
  785. IMaterialVar* pTransformationVar = s_ppParams[transformVar];
  786. if (pTransformationVar && (pTransformationVar->GetType() == MATERIAL_VAR_TYPE_MATRIX))
  787. {
  788. s_pShaderAPI->MatrixMode( textureTransform );
  789. const VMatrix &transformation = pTransformationVar->GetMatrixValue();
  790. // only do the upper 3x3 since this is a 2D matrix
  791. float mat[16];
  792. mat[0] = transformation[0][0]; mat[1] = transformation[1][0]; mat[2] = transformation[3][0];
  793. mat[4] = transformation[0][1]; mat[5] = transformation[1][1]; mat[6] = transformation[3][1];
  794. mat[8] = transformation[0][3]; mat[9] = transformation[1][3]; mat[10] = transformation[3][3];
  795. // Better set the stuff we don't set with some sort of value!
  796. mat[3] = mat[7] = mat[11] = 0;
  797. mat[12] = mat[13] = mat[14] = 0;
  798. mat[15] = 1;
  799. s_pShaderAPI->LoadMatrix( mat );
  800. }
  801. else
  802. {
  803. LoadIdentity( textureTransform );
  804. }
  805. }
  806. void CBaseShader::SetFixedFunctionTextureScaledTransform( MaterialMatrixMode_t textureTransform,
  807. int transformVar, int scaleVar )
  808. {
  809. Assert( !IsSnapshotting() );
  810. float mat[16];
  811. IMaterialVar* pTransformationVar = s_ppParams[transformVar];
  812. if (pTransformationVar && (pTransformationVar->GetType() == MATERIAL_VAR_TYPE_MATRIX))
  813. {
  814. Vector2D scale( 1, 1 );
  815. IMaterialVar* pScaleVar = s_ppParams[scaleVar];
  816. if (pScaleVar)
  817. {
  818. if (pScaleVar->GetType() == MATERIAL_VAR_TYPE_VECTOR)
  819. pScaleVar->GetVecValue( scale.Base(), 2 );
  820. else if (pScaleVar->IsDefined())
  821. scale[0] = scale[1] = pScaleVar->GetFloatValue();
  822. }
  823. s_pShaderAPI->MatrixMode( textureTransform );
  824. const VMatrix &transformation = pTransformationVar->GetMatrixValue();
  825. // only do the upper 3x3 since this is a 2D matrix
  826. mat[0] = transformation[0][0] * scale[0]; mat[1] = transformation[1][0] * scale[0]; mat[2] = transformation[3][0] * scale[0];
  827. mat[4] = transformation[0][1] * scale[1]; mat[5] = transformation[1][1] * scale[1]; mat[6] = transformation[3][1] * scale[1];
  828. mat[8] = transformation[0][3]; mat[9] = transformation[1][3]; mat[10] = transformation[3][3];
  829. // Better set the stuff we don't set with some sort of value!
  830. mat[3] = mat[7] = mat[11] = 0;
  831. mat[12] = mat[13] = mat[14] = 0;
  832. mat[15] = 1;
  833. s_pShaderAPI->LoadMatrix( mat );
  834. }
  835. else
  836. {
  837. SetFixedFunctionTextureScale( textureTransform, scaleVar );
  838. }
  839. }
  840. //-----------------------------------------------------------------------------
  841. //
  842. // Helper methods for fog
  843. //
  844. //-----------------------------------------------------------------------------
  845. void CBaseShader::FogToOOOverbright( void )
  846. {
  847. Assert( IsSnapshotting() );
  848. if (( CurrentMaterialVarFlags() & MATERIAL_VAR_NOFOG ) == 0)
  849. {
  850. s_pShaderShadow->FogMode( SHADER_FOGMODE_OO_OVERBRIGHT );
  851. }
  852. else
  853. {
  854. s_pShaderShadow->FogMode( SHADER_FOGMODE_DISABLED );
  855. }
  856. }
  857. void CBaseShader::FogToWhite( void )
  858. {
  859. Assert( IsSnapshotting() );
  860. if (( CurrentMaterialVarFlags() & MATERIAL_VAR_NOFOG ) == 0)
  861. {
  862. s_pShaderShadow->FogMode( SHADER_FOGMODE_WHITE );
  863. }
  864. else
  865. {
  866. s_pShaderShadow->FogMode( SHADER_FOGMODE_DISABLED );
  867. }
  868. }
  869. void CBaseShader::FogToBlack( void )
  870. {
  871. Assert( IsSnapshotting() );
  872. if (( CurrentMaterialVarFlags() & MATERIAL_VAR_NOFOG ) == 0)
  873. {
  874. s_pShaderShadow->FogMode( SHADER_FOGMODE_BLACK );
  875. }
  876. else
  877. {
  878. s_pShaderShadow->FogMode( SHADER_FOGMODE_DISABLED );
  879. }
  880. }
  881. void CBaseShader::FogToGrey( void )
  882. {
  883. Assert( IsSnapshotting() );
  884. if (( CurrentMaterialVarFlags() & MATERIAL_VAR_NOFOG ) == 0)
  885. {
  886. s_pShaderShadow->FogMode( SHADER_FOGMODE_GREY );
  887. }
  888. else
  889. {
  890. s_pShaderShadow->FogMode( SHADER_FOGMODE_DISABLED );
  891. }
  892. }
  893. void CBaseShader::FogToFogColor( void )
  894. {
  895. Assert( IsSnapshotting() );
  896. if (( CurrentMaterialVarFlags() & MATERIAL_VAR_NOFOG ) == 0)
  897. {
  898. s_pShaderShadow->FogMode( SHADER_FOGMODE_FOGCOLOR );
  899. }
  900. else
  901. {
  902. s_pShaderShadow->FogMode( SHADER_FOGMODE_DISABLED );
  903. }
  904. }
  905. void CBaseShader::DisableFog( void )
  906. {
  907. Assert( IsSnapshotting() );
  908. s_pShaderShadow->FogMode( SHADER_FOGMODE_DISABLED );
  909. }
  910. void CBaseShader::DefaultFog( void )
  911. {
  912. if ( CurrentMaterialVarFlags() & MATERIAL_VAR_ADDITIVE )
  913. {
  914. FogToBlack();
  915. }
  916. else
  917. {
  918. FogToFogColor();
  919. }
  920. }
  921. //-----------------------------------------------------------------------------
  922. // Fixed function multiply by detail texture pass
  923. //-----------------------------------------------------------------------------
  924. void CBaseShader::FixedFunctionMultiplyByDetailPass( int baseTextureVar, int frameVar,
  925. int textureTransformVar, int detailVar, int detailScaleVar )
  926. {
  927. IMaterialVar** params = s_ppParams;
  928. if (!params[detailVar]->IsDefined())
  929. return;
  930. if (IsSnapshotting())
  931. {
  932. SetInitialShadowState();
  933. s_pShaderShadow->EnableAlphaTest( IS_FLAG_SET(MATERIAL_VAR_ALPHATEST) );
  934. bool translucentTexture = TextureIsTranslucent( baseTextureVar, true ) ||
  935. IS_FLAG_SET(MATERIAL_VAR_ALPHATEST);
  936. s_pShaderShadow->EnableTexture( SHADER_SAMPLER0, true );
  937. s_pShaderShadow->EnableTexture( SHADER_SAMPLER1, true );
  938. s_pShaderShadow->EnableTexGen( SHADER_TEXTURE_STAGE0, false );
  939. s_pShaderShadow->EnableTexGen( SHADER_TEXTURE_STAGE1, false );
  940. // Mod 2x blend here
  941. EnableAlphaBlending( SHADER_BLEND_DST_COLOR, SHADER_BLEND_SRC_COLOR );
  942. s_pShaderShadow->EnableCustomPixelPipe( true );
  943. s_pShaderShadow->CustomTextureStages( 2 );
  944. // We need to blend towards grey based on alpha...
  945. // We can never get the perfect alpha (vertex alpha * cc alpha * texture alpha)
  946. // so we'll just choose to use cc alpha * texture alpha
  947. int flags = SHADER_DRAW_POSITION | SHADER_DRAW_TEXCOORD1;
  948. // Compute alpha, stage 0 is used, stage 1 isn't.
  949. if ( translucentTexture )
  950. {
  951. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  952. SHADER_TEXCHANNEL_ALPHA, SHADER_TEXOP_MODULATE,
  953. SHADER_TEXARG_TEXTURE, SHADER_TEXARG_CONSTANTCOLOR );
  954. flags |= SHADER_DRAW_TEXCOORD0;
  955. }
  956. else
  957. {
  958. bool hasVertexAlpha = (CurrentMaterialVarFlags() & MATERIAL_VAR_VERTEXALPHA) != 0;
  959. if (hasVertexAlpha)
  960. {
  961. flags |= SHADER_DRAW_COLOR;
  962. }
  963. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  964. SHADER_TEXCHANNEL_ALPHA, hasVertexAlpha ? SHADER_TEXOP_MODULATE : SHADER_TEXOP_SELECTARG1,
  965. SHADER_TEXARG_CONSTANTCOLOR, SHADER_TEXARG_VERTEXCOLOR );
  966. }
  967. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE1,
  968. SHADER_TEXCHANNEL_ALPHA, SHADER_TEXOP_SELECTARG1,
  969. SHADER_TEXARG_PREVIOUSSTAGE, SHADER_TEXARG_NONE );
  970. // This here will perform color = vertex light * alpha + 0.5f * (1 - alpha)
  971. // Stage 0 really doesn't do anything
  972. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  973. SHADER_TEXCHANNEL_COLOR, SHADER_TEXOP_SELECTARG1,
  974. SHADER_TEXARG_TEXTURE, SHADER_TEXARG_CONSTANTCOLOR );
  975. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE1,
  976. SHADER_TEXCHANNEL_COLOR, SHADER_TEXOP_BLEND_PREVIOUSSTAGEALPHA,
  977. SHADER_TEXARG_TEXTURE, SHADER_TEXARG_CONSTANTCOLOR );
  978. s_pShaderShadow->DrawFlags( flags );
  979. FogToGrey();
  980. Draw( );
  981. s_pShaderShadow->EnableCustomPixelPipe( false );
  982. DisableAlphaBlending();
  983. }
  984. else
  985. {
  986. if (TextureIsTranslucent( baseTextureVar, true ) )
  987. {
  988. SetFixedFunctionTextureTransform( MATERIAL_TEXTURE0, textureTransformVar );
  989. BindTexture( SHADER_SAMPLER0, baseTextureVar, frameVar );
  990. }
  991. else
  992. {
  993. // Unnecessary... but we get strange colors if we don't put something on stage 0
  994. BindTexture( SHADER_SAMPLER0, detailVar, frameVar );
  995. }
  996. BindTexture( SHADER_SAMPLER1, detailVar, frameVar );
  997. SetFixedFunctionTextureScaledTransform( MATERIAL_TEXTURE1, textureTransformVar, detailScaleVar );
  998. float alpha = GetAlpha();
  999. s_pShaderAPI->Color4ub( 128, 128, 128, 255 * alpha );
  1000. Draw( );
  1001. }
  1002. }
  1003. //-----------------------------------------------------------------------------
  1004. // Multiply by lightmap pass
  1005. //-----------------------------------------------------------------------------
  1006. void CBaseShader::FixedFunctionMultiplyByLightmapPass( int baseTextureVar,
  1007. int frameVar, int baseTextureTransformVar, float alphaOverride )
  1008. {
  1009. if (IsSnapshotting())
  1010. {
  1011. SetInitialShadowState();
  1012. s_pShaderShadow->EnableAlphaTest( false );
  1013. s_pShaderShadow->EnableBlending( true );
  1014. SingleTextureLightmapBlendMode();
  1015. s_pShaderShadow->EnableTexture( SHADER_SAMPLER0, true );
  1016. s_pShaderShadow->EnableTexture( SHADER_SAMPLER1, true );
  1017. s_pShaderShadow->EnableTexGen( SHADER_TEXTURE_STAGE0, false );
  1018. s_pShaderShadow->EnableTexGen( SHADER_TEXTURE_STAGE1, false );
  1019. s_pShaderShadow->EnableCustomPixelPipe( true );
  1020. s_pShaderShadow->CustomTextureStages( 2 );
  1021. // Stage zero color is not used, this op doesn't matter
  1022. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  1023. SHADER_TEXCHANNEL_COLOR, SHADER_TEXOP_SELECTARG1,
  1024. SHADER_TEXARG_CONSTANTCOLOR, SHADER_TEXARG_CONSTANTCOLOR );
  1025. // This here will perform color = lightmap * (cc alpha) + 1 * (1- cc alpha)
  1026. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE1,
  1027. SHADER_TEXCHANNEL_COLOR, SHADER_TEXOP_BLEND_PREVIOUSSTAGEALPHA,
  1028. SHADER_TEXARG_TEXTURE, SHADER_TEXARG_CONSTANTCOLOR );
  1029. int flags = SHADER_DRAW_POSITION | SHADER_DRAW_LIGHTMAP_TEXCOORD1;
  1030. // Multiply the constant alpha by the texture alpha for total alpha
  1031. if (TextureIsTranslucent(baseTextureVar, true))
  1032. {
  1033. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  1034. SHADER_TEXCHANNEL_ALPHA, SHADER_TEXOP_MODULATE,
  1035. SHADER_TEXARG_TEXTURE, SHADER_TEXARG_CONSTANTCOLOR );
  1036. flags |= SHADER_DRAW_TEXCOORD0;
  1037. }
  1038. else
  1039. {
  1040. s_pShaderShadow->EnableTexture( SHADER_SAMPLER0, false );
  1041. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  1042. SHADER_TEXCHANNEL_ALPHA, SHADER_TEXOP_SELECTARG2,
  1043. SHADER_TEXARG_TEXTURE, SHADER_TEXARG_CONSTANTCOLOR );
  1044. }
  1045. // Alpha isn't used, it doesn't matter what we set it to.
  1046. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE1,
  1047. SHADER_TEXCHANNEL_ALPHA, SHADER_TEXOP_SELECTARG1,
  1048. SHADER_TEXARG_PREVIOUSSTAGE, SHADER_TEXARG_NONE );
  1049. s_pShaderShadow->DrawFlags( flags );
  1050. FogToOOOverbright();
  1051. Draw();
  1052. s_pShaderShadow->EnableCustomPixelPipe( false );
  1053. }
  1054. else
  1055. {
  1056. s_pShaderAPI->SetDefaultState();
  1057. // Put the alpha in the color channel to modulate the color down....
  1058. float alpha = (alphaOverride < 0) ? GetAlpha() : alphaOverride;
  1059. // NOTE: 128 is a more exact OO_OVERBRIGHT; it prevents some artifacts
  1060. // s_pShaderAPI->Color4f( OO_OVERBRIGHT, OO_OVERBRIGHT, OO_OVERBRIGHT, alpha );
  1061. s_pShaderAPI->Color4ub( 128, 128, 128, (int)(alpha * 255));
  1062. if (TextureIsTranslucent(baseTextureVar, true))
  1063. {
  1064. SetFixedFunctionTextureTransform( MATERIAL_TEXTURE0, baseTextureTransformVar );
  1065. BindTexture( SHADER_SAMPLER0, baseTextureVar, frameVar );
  1066. }
  1067. LoadIdentity( MATERIAL_TEXTURE1 );
  1068. s_pShaderAPI->BindStandardTexture( SHADER_SAMPLER1, TEXTURE_LIGHTMAP );
  1069. Draw();
  1070. }
  1071. }
  1072. //-----------------------------------------------------------------------------
  1073. // Fixed function Self illumination pass
  1074. //-----------------------------------------------------------------------------
  1075. void CBaseShader::FixedFunctionSelfIlluminationPass( Sampler_t sampler,
  1076. int baseTextureVar, int frameVar, int baseTextureTransformVar, int selfIllumTintVar )
  1077. {
  1078. // IMaterialVar** params = s_ppParams;
  1079. if ( IsSnapshotting() )
  1080. {
  1081. SetInitialShadowState();
  1082. // A little setup for self illum here...
  1083. SetModulationShadowState( selfIllumTintVar );
  1084. s_pShaderShadow->EnableTexture( sampler, true );
  1085. // No overbrighting
  1086. s_pShaderShadow->OverbrightValue( SHADER_TEXTURE_STAGE0, 1.0f );
  1087. s_pShaderShadow->OverbrightValue( SHADER_TEXTURE_STAGE1, 1.0f );
  1088. // Don't bother with z writes here...
  1089. s_pShaderShadow->EnableDepthWrites( false );
  1090. // We're always blending
  1091. EnableAlphaBlending( SHADER_BLEND_SRC_ALPHA, SHADER_BLEND_ONE_MINUS_SRC_ALPHA );
  1092. int flags = SHADER_DRAW_POSITION;
  1093. if ( sampler == SHADER_SAMPLER0 )
  1094. flags |= SHADER_DRAW_TEXCOORD0;
  1095. else
  1096. flags |= SHADER_DRAW_TEXCOORD1;
  1097. s_pShaderShadow->DrawFlags( flags );
  1098. FogToFogColor();
  1099. }
  1100. else
  1101. {
  1102. s_pShaderAPI->SetDefaultState();
  1103. SetFixedFunctionTextureTransform(
  1104. (sampler == SHADER_SAMPLER0) ? MATERIAL_TEXTURE0 : MATERIAL_TEXTURE1,
  1105. baseTextureTransformVar );
  1106. BindTexture( sampler, baseTextureVar, frameVar );
  1107. // NOTE: Texture + texture offset are set from BaseTimesLightmap
  1108. SetModulationDynamicState( selfIllumTintVar );
  1109. }
  1110. Draw();
  1111. }
  1112. //-----------------------------------------------------------------------------
  1113. // Fixed function Base * detail pass
  1114. //-----------------------------------------------------------------------------
  1115. void CBaseShader::FixedFunctionBaseTimesDetailPass( int baseTextureVar,
  1116. int frameVar, int baseTextureTransformVar, int detailVar, int detailScaleVar )
  1117. {
  1118. IMaterialVar** params = s_ppParams;
  1119. // We can't do this one one pass if CC and VC are both active...
  1120. bool hasDetail = (detailVar != -1) && params[detailVar]->IsDefined();
  1121. bool detailInSecondPass = hasDetail && IsColorModulating() &&
  1122. (IS_FLAG_SET(MATERIAL_VAR_VERTEXCOLOR) || IS_FLAG_SET(MATERIAL_VAR_VERTEXALPHA));
  1123. if (IsSnapshotting())
  1124. {
  1125. s_pShaderShadow->EnableTexGen( SHADER_TEXTURE_STAGE0, false );
  1126. s_pShaderShadow->EnableTexGen( SHADER_TEXTURE_STAGE1, false );
  1127. // alpha test
  1128. s_pShaderShadow->EnableAlphaTest( IS_FLAG_SET(MATERIAL_VAR_ALPHATEST) );
  1129. // Alpha blending
  1130. SetDefaultBlendingShadowState( baseTextureVar, true );
  1131. // independently configure alpha and color
  1132. s_pShaderShadow->EnableAlphaPipe( true );
  1133. // Here's the color states (NOTE: SHADER_DRAW_COLOR == use Vertex Color)
  1134. s_pShaderShadow->EnableConstantColor( IsColorModulating() );
  1135. s_pShaderShadow->EnableTexture( SHADER_SAMPLER0, true );
  1136. int flags = SHADER_DRAW_POSITION | SHADER_DRAW_TEXCOORD0;
  1137. // Detail texture..
  1138. if (hasDetail && (!detailInSecondPass))
  1139. {
  1140. s_pShaderShadow->EnableTexture( SHADER_SAMPLER1, true );
  1141. // Force mod2x
  1142. s_pShaderShadow->OverbrightValue( SHADER_TEXTURE_STAGE1, 2.0f );
  1143. flags |= SHADER_DRAW_TEXCOORD1;
  1144. }
  1145. // Here's the alpha states
  1146. s_pShaderShadow->EnableConstantAlpha( IsAlphaModulating() );
  1147. s_pShaderShadow->EnableVertexAlpha( IS_FLAG_SET(MATERIAL_VAR_VERTEXALPHA) );
  1148. s_pShaderShadow->EnableTextureAlpha( SHADER_TEXTURE_STAGE0, TextureIsTranslucent(baseTextureVar, true) );
  1149. if (IS_FLAG_SET(MATERIAL_VAR_VERTEXCOLOR))
  1150. flags |= SHADER_DRAW_COLOR;
  1151. s_pShaderShadow->DrawFlags( flags );
  1152. DefaultFog();
  1153. Draw();
  1154. s_pShaderShadow->EnableAlphaPipe( false );
  1155. }
  1156. else
  1157. {
  1158. SetFixedFunctionTextureTransform( MATERIAL_TEXTURE0, baseTextureTransformVar );
  1159. BindTexture( SHADER_SAMPLER0, baseTextureVar, frameVar );
  1160. // Detail texture..
  1161. if (hasDetail && (!detailInSecondPass))
  1162. {
  1163. BindTexture( SHADER_SAMPLER1, detailVar, frameVar );
  1164. SetFixedFunctionTextureScaledTransform( MATERIAL_TEXTURE1, baseTextureTransformVar, detailScaleVar );
  1165. }
  1166. SetModulationDynamicState();
  1167. Draw();
  1168. }
  1169. if (detailInSecondPass)
  1170. {
  1171. FixedFunctionMultiplyByDetailPass( baseTextureVar, frameVar, baseTextureTransformVar, detailVar, detailScaleVar );
  1172. }
  1173. }
  1174. //-----------------------------------------------------------------------------
  1175. // Helpers for environment mapping...
  1176. //-----------------------------------------------------------------------------
  1177. int CBaseShader::SetShadowEnvMappingState( int envMapMaskVar, int tintVar )
  1178. {
  1179. Assert( IsSnapshotting() );
  1180. IMaterialVar** params = s_ppParams;
  1181. int varFlags = params[FLAGS]->GetIntValue();
  1182. s_pShaderShadow->EnableAlphaTest( false );
  1183. // envmap on stage 0
  1184. s_pShaderShadow->EnableTexture( SHADER_SAMPLER0, true );
  1185. s_pShaderShadow->EnableTexGen( SHADER_TEXTURE_STAGE0, true );
  1186. if ( (varFlags & MATERIAL_VAR_ENVMAPSPHERE) == 0 )
  1187. s_pShaderShadow->TexGen( SHADER_TEXTURE_STAGE0, SHADER_TEXGENPARAM_CAMERASPACEREFLECTIONVECTOR );
  1188. else
  1189. s_pShaderShadow->TexGen( SHADER_TEXTURE_STAGE0, SHADER_TEXGENPARAM_SPHERE_MAP );
  1190. int flags = SHADER_DRAW_POSITION | SHADER_DRAW_NORMAL;
  1191. // mask on stage 1
  1192. if (params[envMapMaskVar]->IsDefined() || (varFlags & MATERIAL_VAR_BASEALPHAENVMAPMASK))
  1193. {
  1194. s_pShaderShadow->EnableTexture( SHADER_SAMPLER1, true );
  1195. flags |= SHADER_DRAW_TEXCOORD1;
  1196. }
  1197. else
  1198. {
  1199. s_pShaderShadow->EnableTexture( SHADER_SAMPLER1, false );
  1200. }
  1201. if (varFlags & MATERIAL_VAR_BASEALPHAENVMAPMASK)
  1202. {
  1203. s_pShaderShadow->EnableCustomPixelPipe( true );
  1204. s_pShaderShadow->CustomTextureStages( 2 );
  1205. // Color = base texture * envmaptint * (1 - mask alpha)
  1206. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  1207. SHADER_TEXCHANNEL_COLOR, SHADER_TEXOP_MODULATE, SHADER_TEXARG_TEXTURE, SHADER_TEXARG_CONSTANTCOLOR );
  1208. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE1,
  1209. SHADER_TEXCHANNEL_COLOR, SHADER_TEXOP_MODULATE, SHADER_TEXARG_PREVIOUSSTAGE, SHADER_TEXARG_INVTEXTUREALPHA );
  1210. // Use alpha modulation * vertex alpha * env map alpha
  1211. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  1212. SHADER_TEXCHANNEL_ALPHA, SHADER_TEXOP_MODULATE, SHADER_TEXARG_VERTEXCOLOR, SHADER_TEXARG_TEXTURE );
  1213. s_pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE1,
  1214. SHADER_TEXCHANNEL_ALPHA, SHADER_TEXOP_SELECTARG1, SHADER_TEXARG_PREVIOUSSTAGE, SHADER_TEXARG_CONSTANTCOLOR );
  1215. }
  1216. else
  1217. {
  1218. s_pShaderShadow->EnableAlphaPipe( true );
  1219. // Color = base texture * envmaptint * mask
  1220. s_pShaderShadow->EnableConstantColor( tintVar >= 0 );
  1221. // Alpha = vertex alpha * constant alpha * env map alpha * mask alpha (only if it's not a base alpha mask)
  1222. s_pShaderShadow->EnableConstantAlpha( IsAlphaModulating() );
  1223. s_pShaderShadow->EnableVertexAlpha( (varFlags & MATERIAL_VAR_VERTEXALPHA) != 0 );
  1224. s_pShaderShadow->EnableTextureAlpha( SHADER_TEXTURE_STAGE0, true );
  1225. s_pShaderShadow->EnableTextureAlpha( SHADER_TEXTURE_STAGE1, params[envMapMaskVar]->IsTexture() );
  1226. }
  1227. return flags;
  1228. }
  1229. void CBaseShader::SetDynamicEnvMappingState( int envMapVar, int envMapMaskVar,
  1230. int baseTextureVar, int envMapFrameVar, int envMapMaskFrameVar, int frameVar,
  1231. int maskOffsetVar, int maskScaleVar, int tintVar )
  1232. {
  1233. Assert( !IsSnapshotting() );
  1234. IMaterialVar** params = s_ppParams;
  1235. int varFlags = params[FLAGS]->GetIntValue();
  1236. if( (varFlags & MATERIAL_VAR_ENVMAPSPHERE) == 0 )
  1237. {
  1238. if ( (varFlags & MATERIAL_VAR_ENVMAPCAMERASPACE) == 0 )
  1239. {
  1240. LoadCameraToWorldTransform( MATERIAL_TEXTURE0 );
  1241. }
  1242. else
  1243. {
  1244. LoadIdentity( MATERIAL_TEXTURE0 );
  1245. }
  1246. }
  1247. else
  1248. {
  1249. LoadCameraSpaceSphereMapTransform( MATERIAL_TEXTURE0 );
  1250. }
  1251. BindTexture( SHADER_SAMPLER0, envMapVar, envMapFrameVar );
  1252. if (params[envMapMaskVar]->IsTexture())
  1253. {
  1254. SetFixedFunctionTextureScaledTransform( MATERIAL_TEXTURE1,
  1255. maskOffsetVar, maskScaleVar );
  1256. BindTexture( SHADER_SAMPLER1, envMapMaskVar, envMapMaskFrameVar );
  1257. }
  1258. else if (varFlags & MATERIAL_VAR_BASEALPHAENVMAPMASK)
  1259. {
  1260. SetFixedFunctionTextureScaledTransform( MATERIAL_TEXTURE1,
  1261. maskOffsetVar, maskScaleVar );
  1262. BindTexture( SHADER_SAMPLER1, baseTextureVar, frameVar );
  1263. }
  1264. SetModulationDynamicState( tintVar );
  1265. }
  1266. //-----------------------------------------------------------------------------
  1267. // Masked environment map
  1268. //-----------------------------------------------------------------------------
  1269. void CBaseShader::FixedFunctionMaskedEnvmapPass( int envMapVar, int envMapMaskVar,
  1270. int baseTextureVar, int envMapFrameVar, int envMapMaskFrameVar,
  1271. int frameVar, int maskOffsetVar, int maskScaleVar, int envMapTintVar )
  1272. {
  1273. // IMaterialVar** params = ShaderState().m_ppParams;
  1274. if (IsSnapshotting())
  1275. {
  1276. // Alpha blending
  1277. SetDefaultBlendingShadowState( envMapMaskVar, false );
  1278. // Disable overbright
  1279. s_pShaderShadow->OverbrightValue( SHADER_TEXTURE_STAGE0, 1.0f );
  1280. s_pShaderShadow->OverbrightValue( SHADER_TEXTURE_STAGE1, 1.0f );
  1281. int flags = SetShadowEnvMappingState( envMapMaskVar, envMapTintVar );
  1282. s_pShaderShadow->DrawFlags( flags );
  1283. DefaultFog();
  1284. Draw();
  1285. s_pShaderShadow->EnableCustomPixelPipe( false );
  1286. s_pShaderShadow->EnableAlphaPipe( false );
  1287. }
  1288. else
  1289. {
  1290. SetDynamicEnvMappingState( envMapVar, envMapMaskVar, baseTextureVar,
  1291. envMapFrameVar, envMapMaskFrameVar, frameVar,
  1292. maskOffsetVar, maskScaleVar, envMapTintVar );
  1293. Draw();
  1294. }
  1295. }
  1296. //-----------------------------------------------------------------------------
  1297. // Add masked environment map
  1298. //-----------------------------------------------------------------------------
  1299. void CBaseShader::FixedFunctionAdditiveMaskedEnvmapPass( int envMapVar, int envMapMaskVar,
  1300. int baseTextureVar, int envMapFrameVar, int envMapMaskFrameVar,
  1301. int frameVar, int maskOffsetVar, int maskScaleVar, int envMapTintVar )
  1302. {
  1303. // IMaterialVar** params = ShaderState().m_ppParams;
  1304. if (IsSnapshotting())
  1305. {
  1306. SetInitialShadowState();
  1307. // Alpha blending
  1308. SetAdditiveBlendingShadowState( envMapMaskVar, false );
  1309. // Disable overbright
  1310. s_pShaderShadow->OverbrightValue( SHADER_TEXTURE_STAGE0, 1.0f );
  1311. s_pShaderShadow->OverbrightValue( SHADER_TEXTURE_STAGE1, 1.0f );
  1312. // Don't bother with z writes here...
  1313. s_pShaderShadow->EnableDepthWrites( false );
  1314. int flags = SetShadowEnvMappingState( envMapMaskVar, envMapTintVar );
  1315. s_pShaderShadow->DrawFlags( flags );
  1316. FogToBlack();
  1317. Draw();
  1318. s_pShaderShadow->EnableCustomPixelPipe( false );
  1319. s_pShaderShadow->EnableAlphaPipe( false );
  1320. }
  1321. else
  1322. {
  1323. SetDynamicEnvMappingState( envMapVar, envMapMaskVar, baseTextureVar,
  1324. envMapFrameVar, envMapMaskFrameVar, frameVar,
  1325. maskOffsetVar, maskScaleVar, envMapTintVar );
  1326. Draw();
  1327. }
  1328. }
  1329. void CBaseShader::CleanupDynamicStateFixedFunction( )
  1330. {
  1331. Assert( !IsSnapshotting() );
  1332. LoadIdentity( MATERIAL_TEXTURE0 );
  1333. }
  1334. bool CBaseShader::UsingFlashlight( IMaterialVar **params ) const
  1335. {
  1336. if( IsSnapshotting() )
  1337. {
  1338. return CShader_IsFlag2Set( params, MATERIAL_VAR2_USE_FLASHLIGHT );
  1339. }
  1340. else
  1341. {
  1342. return s_pShaderAPI->InFlashlightMode();
  1343. }
  1344. }
  1345. bool CBaseShader::UsingEditor( IMaterialVar **params ) const
  1346. {
  1347. if( IsSnapshotting() )
  1348. {
  1349. return CShader_IsFlag2Set( params, MATERIAL_VAR2_USE_EDITOR );
  1350. }
  1351. else
  1352. {
  1353. return s_pShaderAPI->InEditorMode();
  1354. }
  1355. }
  1356. void CBaseShader::DrawFlashlight_dx70(
  1357. IMaterialVar** params, IShaderDynamicAPI *pShaderAPI, IShaderShadow* pShaderShadow,
  1358. int flashlightTextureVar, int flashlightTextureFrameVar,
  1359. bool suppress_lighting )
  1360. {
  1361. SHADOW_STATE
  1362. {
  1363. SET_FLAGS2( MATERIAL_VAR2_NEEDS_FIXED_FUNCTION_FLASHLIGHT );
  1364. pShaderShadow->EnableDepthWrites( false );
  1365. pShaderShadow->EnableAlphaWrites( false );
  1366. // Alpha test
  1367. // pShaderShadow->EnableAlphaTest( IS_FLAG_SET( MATERIAL_VAR_ALPHATEST ) );
  1368. bool bIsAlphaTested = IS_FLAG_SET( MATERIAL_VAR_ALPHATEST ) != 0;
  1369. if( bIsAlphaTested )
  1370. {
  1371. // disable alpha test and use the zfunc zequals since alpha isn't guaranteed to
  1372. // be the same on both the regular pass and the flashlight pass.
  1373. s_pShaderShadow->EnableAlphaTest( false );
  1374. s_pShaderShadow->DepthFunc( SHADER_DEPTHFUNC_EQUAL );
  1375. }
  1376. // Alpha blend
  1377. SetAdditiveBlendingShadowState( BASETEXTURE, true );
  1378. int flags = SHADER_DRAW_POSITION | SHADER_DRAW_TEXCOORD1 | SHADER_DRAW_COLOR | SHADER_DRAW_NORMAL;
  1379. pShaderShadow->DrawFlags( flags );
  1380. FogToBlack();
  1381. if ( !suppress_lighting )
  1382. pShaderShadow->EnableLighting( true );
  1383. pShaderShadow->EnableCustomPixelPipe( true );
  1384. pShaderShadow->CustomTextureStages( 2 );
  1385. // color stage 0
  1386. // projected texture * vertex color (lighting)
  1387. pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  1388. SHADER_TEXCHANNEL_COLOR,
  1389. SHADER_TEXOP_MODULATE,
  1390. SHADER_TEXARG_TEXTURE,
  1391. SHADER_TEXARG_VERTEXCOLOR );
  1392. // color stage 1
  1393. // * base texture
  1394. pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE1,
  1395. SHADER_TEXCHANNEL_COLOR,
  1396. SHADER_TEXOP_MODULATE,
  1397. SHADER_TEXARG_TEXTURE, SHADER_TEXARG_PREVIOUSSTAGE );
  1398. // alpha stage 0
  1399. // get alpha from constant alpha
  1400. pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE0,
  1401. SHADER_TEXCHANNEL_ALPHA,
  1402. SHADER_TEXOP_SELECTARG1,
  1403. SHADER_TEXARG_CONSTANTCOLOR, SHADER_TEXARG_NONE );
  1404. // alpha stage 1
  1405. // get alpha from $basetexture
  1406. pShaderShadow->CustomTextureOperation( SHADER_TEXTURE_STAGE1,
  1407. SHADER_TEXCHANNEL_ALPHA,
  1408. SHADER_TEXOP_MODULATE,
  1409. SHADER_TEXARG_TEXTURE, SHADER_TEXARG_PREVIOUSSTAGE );
  1410. pShaderShadow->EnableTexture( SHADER_SAMPLER0, true );
  1411. pShaderShadow->EnableTexture( SHADER_SAMPLER1, true );
  1412. // Shove the view position into texcoord 0 before the texture matrix.
  1413. pShaderShadow->TexGen( SHADER_TEXTURE_STAGE0, SHADER_TEXGENPARAM_EYE_LINEAR );
  1414. pShaderShadow->EnableTexGen( SHADER_TEXTURE_STAGE0, true );
  1415. }
  1416. DYNAMIC_STATE
  1417. {
  1418. SetFlashlightFixedFunctionTextureTransform( MATERIAL_TEXTURE0 );
  1419. // NOTE: This has to come after the loadmatrix since the loadmatrix screws with the
  1420. // transform flags!!!!!!
  1421. // Specify that we have XYZ texcoords that need to be divided by W before the pixel shader.
  1422. // NOTE Tried to divide XY by Z, but doesn't work.
  1423. pShaderAPI->SetTextureTransformDimension( SHADER_TEXTURE_STAGE0, 3, true );
  1424. BindTexture( SHADER_SAMPLER0, flashlightTextureVar, flashlightTextureFrameVar );
  1425. if( params[BASETEXTURE]->IsTexture() )
  1426. {
  1427. BindTexture( SHADER_SAMPLER1, BASETEXTURE, FRAME );
  1428. }
  1429. else
  1430. {
  1431. pShaderAPI->BindStandardTexture( SHADER_SAMPLER1, TEXTURE_GREY );
  1432. }
  1433. SetModulationDynamicState();
  1434. }
  1435. Draw();
  1436. }
  1437. void CBaseShader::SetFlashlightFixedFunctionTextureTransform( MaterialMatrixMode_t matrix )
  1438. {
  1439. VMatrix worldToTexture;
  1440. s_pShaderAPI->GetFlashlightState( worldToTexture );
  1441. VMatrix worldToView, viewToWorld, viewToTexture;
  1442. s_pShaderAPI->GetMatrix( MATERIAL_VIEW, &worldToView[0][0] );
  1443. // The matrix that we get back from the shader api is transposed. . . yuck.
  1444. MatrixTranspose( worldToView, worldToView );
  1445. MatrixInverseGeneral( worldToView, viewToWorld );
  1446. MatrixMultiply( worldToTexture, viewToWorld, viewToTexture );
  1447. s_pShaderAPI->MatrixMode( matrix );
  1448. // tranpose before going into the shaderapi. . . suck
  1449. MatrixTranspose( viewToTexture, viewToTexture );
  1450. s_pShaderAPI->LoadMatrix( &viewToTexture[0][0] );
  1451. }
  1452. bool CBaseShader::IsHDREnabled( void )
  1453. {
  1454. // HDRFIXME! Need to fix this for vgui materials
  1455. HDRType_t hdr_mode=g_pHardwareConfig->GetHDRType();
  1456. switch(hdr_mode)
  1457. {
  1458. case HDR_TYPE_NONE:
  1459. return false;
  1460. case HDR_TYPE_INTEGER:
  1461. return true;
  1462. case HDR_TYPE_FLOAT:
  1463. {
  1464. ITexture *pRT = s_pShaderAPI->GetRenderTargetEx( 0 );
  1465. if( pRT && pRT->GetImageFormat() == IMAGE_FORMAT_RGBA16161616F )
  1466. {
  1467. return true;
  1468. }
  1469. }
  1470. }
  1471. return false;
  1472. }