Counter Strike : Global Offensive Source Code
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.

312 lines
12 KiB

  1. //========= Copyright � 1996-2007, Valve Corporation, All rights reserved. ============//
  2. #include "BaseVSShader.h"
  3. #include "mathlib/VMatrix.h"
  4. #include "lightshafts_helper.h"
  5. #include "convar.h"
  6. // Auto generated inc files
  7. #include "lightshafts_vs30.inc"
  8. #include "lightshafts_ps30.inc"
  9. // NOTE: This has to be the last file included!
  10. #include "tier0/memdbgon.h"
  11. void InitParamsLightShafts( CBaseVSShader *pShader, IMaterialVar** params, const char *pMaterialName, LightShaftsVars_t &info )
  12. {
  13. // Set material flags
  14. SET_FLAGS( MATERIAL_VAR_TRANSLUCENT );
  15. SET_FLAGS( MATERIAL_VAR_NOCULL );
  16. SET_PARAM_INT_IF_NOT_DEFINED( info.m_nCookieFrameNum, 0 );
  17. SET_PARAM_FLOAT_IF_NOT_DEFINED( info.m_nTime, 0.0f );
  18. }
  19. void InitLightShafts( CBaseVSShader *pShader, IMaterialVar** params, LightShaftsVars_t &info )
  20. {
  21. // Load textures
  22. if ( (info.m_nCookieTexture != -1) && params[info.m_nCookieTexture]->IsDefined() )
  23. {
  24. pShader->LoadTexture( info.m_nCookieTexture );
  25. }
  26. if ( (info.m_nShadowDepthTexture != -1) && params[info.m_nShadowDepthTexture]->IsDefined() )
  27. {
  28. pShader->LoadTexture( info.m_nShadowDepthTexture );
  29. }
  30. if ( (info.m_nNoiseTexture != -1) && params[info.m_nNoiseTexture]->IsDefined() )
  31. {
  32. pShader->LoadTexture( info.m_nNoiseTexture );
  33. }
  34. }
  35. void DrawLightShafts( CBaseVSShader *pShader, IMaterialVar** params, IShaderDynamicAPI *pShaderAPI,
  36. IShaderShadow* pShaderShadow, LightShaftsVars_t &info, VertexCompressionType_t vertexCompression )
  37. {
  38. SHADOW_STATE
  39. {
  40. // Set stream format (note that this shader supports compression)
  41. unsigned int flags = VERTEX_POSITION;
  42. pShaderShadow->VertexShaderVertexFormat( flags, 0, NULL, 0 ); // no texture coordinates needed
  43. DECLARE_STATIC_VERTEX_SHADER( lightshafts_vs30 );
  44. SET_STATIC_VERTEX_SHADER( lightshafts_vs30 );
  45. DECLARE_STATIC_PIXEL_SHADER( lightshafts_ps30 );
  46. SET_STATIC_PIXEL_SHADER_COMBO( FLASHLIGHTDEPTHFILTERMODE, IsPC() ? g_pHardwareConfig->GetShadowFilterMode( false /* bForceLowQuality */, true /* bPS30 */ ) : SHADOWFILTERMODE_DEFAULT );
  47. SET_STATIC_PIXEL_SHADER( lightshafts_ps30 );
  48. pShaderShadow->EnableTexture( SHADER_SAMPLER0, true ); // Cookie texture
  49. pShaderShadow->EnableSRGBRead( SHADER_SAMPLER0, true );
  50. pShaderShadow->EnableTexture( SHADER_SAMPLER1, true ); // Shadow depth texture
  51. pShaderShadow->EnableSRGBRead( SHADER_SAMPLER1, false );
  52. //pShaderShadow->SetShadowDepthFiltering( SHADER_SAMPLER1 );
  53. pShaderShadow->EnableTexture( SHADER_SAMPLER2, true ); // Screen-space noise map for shadow filtering
  54. pShaderShadow->EnableSRGBRead( SHADER_SAMPLER2, false );
  55. pShaderShadow->EnableTexture( SHADER_SAMPLER3, true ); // Projective noise map used for non-uniform atmospherics
  56. pShaderShadow->EnableSRGBRead( SHADER_SAMPLER3, false );
  57. pShaderShadow->EnableSRGBWrite( true );
  58. pShader->EnableAlphaBlending( SHADER_BLEND_ONE, SHADER_BLEND_ONE ); // Additive blending
  59. pShaderShadow->EnableAlphaWrites( false );
  60. }
  61. DYNAMIC_STATE
  62. {
  63. DECLARE_DYNAMIC_VERTEX_SHADER( lightshafts_vs30 );
  64. SET_DYNAMIC_VERTEX_SHADER( lightshafts_vs30 );
  65. //
  66. // Read material vars into relevant members of flashlightState...kinda icky and verbose...
  67. //
  68. VMatrix worldToTexture;
  69. FlashlightState_t flashlightState;
  70. if ( (info.m_nWorldToTexture != -1) && params[info.m_nWorldToTexture]->IsDefined() )
  71. {
  72. const VMatrix &mat = params[info.m_nWorldToTexture]->GetMatrixValue();
  73. worldToTexture = mat;
  74. }
  75. if ( (info.m_nFlashlightColor != -1) && params[info.m_nFlashlightColor]->IsDefined() )
  76. {
  77. params[info.m_nFlashlightColor]->GetVecValue( &(flashlightState.m_Color[0]), 4 );
  78. }
  79. else
  80. {
  81. flashlightState.m_Color[0] = flashlightState.m_Color[1] = flashlightState.m_Color[2] = flashlightState.m_Color[3] = 1.0f;
  82. }
  83. // Pre-modulate with intensity factor
  84. if ( (info.m_nVolumetricIntensity != -1) && params[info.m_nVolumetricIntensity]->IsDefined() )
  85. {
  86. float flVolumetricIntensity = params[info.m_nVolumetricIntensity]->GetFloatValue();
  87. flashlightState.m_Color[0] *= flVolumetricIntensity;
  88. flashlightState.m_Color[1] *= flVolumetricIntensity;
  89. flashlightState.m_Color[2] *= flVolumetricIntensity;
  90. }
  91. SetFlashLightColorFromState( flashlightState, pShaderAPI, false, PSREG_FLASHLIGHT_COLOR );
  92. if ( (info.m_nAttenFactors != -1) && params[info.m_nAttenFactors]->IsDefined() )
  93. {
  94. float v[4];
  95. params[info.m_nAttenFactors]->GetVecValue( v, 4 );
  96. flashlightState.m_fConstantAtten = v[0];
  97. flashlightState.m_fLinearAtten = v[1];
  98. flashlightState.m_fQuadraticAtten = v[2];
  99. flashlightState.m_FarZAtten = v[3];
  100. }
  101. if ( (info.m_nOriginFarZ != -1) && params[info.m_nOriginFarZ]->IsDefined() )
  102. {
  103. float v[4];
  104. params[info.m_nOriginFarZ]->GetVecValue( v, 4 );
  105. flashlightState.m_vecLightOrigin[0] = v[0];
  106. flashlightState.m_vecLightOrigin[1] = v[1];
  107. flashlightState.m_vecLightOrigin[2] = v[2];
  108. flashlightState.m_FarZ = v[3];
  109. }
  110. if ( (info.m_nQuatOrientation != -1) && params[info.m_nQuatOrientation]->IsDefined() )
  111. {
  112. params[info.m_nQuatOrientation]->GetVecValue( flashlightState.m_quatOrientation.Base(), 4 );
  113. }
  114. if ( (info.m_nShadowFilterSize != -1) && params[info.m_nShadowFilterSize]->IsDefined() )
  115. {
  116. flashlightState.m_flShadowFilterSize = params[info.m_nShadowFilterSize]->GetFloatValue();
  117. }
  118. if ( (info.m_nShadowAtten != -1) && params[info.m_nShadowAtten]->IsDefined() )
  119. {
  120. flashlightState.m_flShadowAtten = params[info.m_nShadowAtten]->GetFloatValue();
  121. }
  122. if ( (info.m_nShadowJitterSeed != -1) && params[info.m_nShadowJitterSeed]->IsDefined() )
  123. {
  124. flashlightState.m_flShadowJitterSeed = params[info.m_nShadowJitterSeed]->GetFloatValue();
  125. }
  126. if ( (info.m_nFlashlightTime != -1) && params[info.m_nFlashlightTime]->IsDefined() )
  127. {
  128. flashlightState.m_flFlashlightTime = params[info.m_nFlashlightTime]->GetFloatValue();
  129. }
  130. if ( (info.m_nNumPlanes != -1) && params[info.m_nNumPlanes]->IsDefined() )
  131. {
  132. flashlightState.m_nNumPlanes = params[info.m_nNumPlanes]->GetIntValue();
  133. }
  134. if ( (info.m_nUberlight != -1) && params[info.m_nUberlight]->IsDefined() )
  135. {
  136. flashlightState.m_bUberlight = ( params[info.m_nUberlight]->GetIntValue() != 0 );
  137. }
  138. if ( (info.m_nEnableShadows != -1) && params[info.m_nEnableShadows]->IsDefined() )
  139. {
  140. flashlightState.m_bEnableShadows = ( params[info.m_nEnableShadows]->GetIntValue() != 0 );
  141. }
  142. if ( (info.m_nNoiseStrength != -1) && params[info.m_nNoiseStrength]->IsDefined() )
  143. {
  144. flashlightState.m_flNoiseStrength = params[info.m_nNoiseStrength]->GetFloatValue();
  145. }
  146. if ( (info.m_nCookieTexture != -1) && params[info.m_nCookieTexture]->IsDefined() )
  147. {
  148. ITexture *pCookieTexture = params[info.m_nCookieTexture]->GetTextureValue();
  149. int nFrameNumber = params[info.m_nCookieFrameNum]->GetIntValue();
  150. pShader->BindTexture( SHADER_SAMPLER0, TEXTURE_BINDFLAGS_SRGBREAD, pCookieTexture, nFrameNumber );
  151. }
  152. ITexture *pFlashlightDepthTexture = NULL;
  153. if( (info.m_nShadowDepthTexture != -1) && params[info.m_nShadowDepthTexture]->IsDefined() &&
  154. g_pConfig->ShadowDepthTexture() && flashlightState.m_bEnableShadows )
  155. {
  156. pFlashlightDepthTexture = params[info.m_nShadowDepthTexture]->GetTextureValue();
  157. pShader->BindTexture( SHADER_SAMPLER1, TEXTURE_BINDFLAGS_SHADOWDEPTH, pFlashlightDepthTexture );
  158. pShaderAPI->BindStandardTexture( SHADER_SAMPLER2, TEXTURE_BINDFLAGS_NONE, TEXTURE_SHADOW_NOISE_2D );
  159. }
  160. if( (info.m_nNoiseTexture != -1) && params[info.m_nNoiseTexture]->IsDefined() )
  161. {
  162. ITexture *pNoiseTexture = params[info.m_nNoiseTexture]->GetTextureValue();
  163. pShader->BindTexture( SHADER_SAMPLER3, TEXTURE_BINDFLAGS_NONE, pNoiseTexture );
  164. }
  165. //
  166. // Now that we've packed the flashlightState structure from our material vars, we can set constants and draw as normal
  167. //
  168. float atten[4], pos[4], tweaks[4], packedParams[4], noiseScroll[4];
  169. atten[0] = flashlightState.m_fConstantAtten; // Set the flashlight attenuation factors
  170. atten[1] = flashlightState.m_fLinearAtten;
  171. atten[2] = flashlightState.m_fQuadraticAtten;
  172. atten[3] = flashlightState.m_FarZAtten;
  173. pShaderAPI->SetPixelShaderConstant( PSREG_FLASHLIGHT_ATTENUATION, atten, 1 );
  174. pos[0] = flashlightState.m_vecLightOrigin[0]; // Set the flashlight origin
  175. pos[1] = flashlightState.m_vecLightOrigin[1];
  176. pos[2] = flashlightState.m_vecLightOrigin[2];
  177. pos[3] = flashlightState.m_FarZ;
  178. pShaderAPI->SetPixelShaderConstant( PSREG_FLASHLIGHT_POSITION_RIM_BOOST, pos, 1 ); // steps on rim boost
  179. // Coefficient for projective noise
  180. packedParams[0] = flashlightState.m_flNoiseStrength;
  181. packedParams[1] = 64.0f / (float) flashlightState.m_nNumPlanes;
  182. packedParams[2] = 0.0f;
  183. packedParams[3] = 0.0f;
  184. pShaderAPI->SetPixelShaderConstant( 0, packedParams, 1 );
  185. // Directions for projective noise
  186. noiseScroll[0] = fmodf( flashlightState.m_flFlashlightTime * 0.043f * 0.394, 1.0f); // UV offset for noise in red
  187. noiseScroll[1] = fmodf( flashlightState.m_flFlashlightTime * 0.043f * 0.919, 1.0f);
  188. noiseScroll[2] = fmodf( flashlightState.m_flFlashlightTime * 0.039f * -0.781, 1.0f); // UV offset for noise in green
  189. noiseScroll[3] = fmodf( flashlightState.m_flFlashlightTime * 0.039f * 0.625, 1.0f);
  190. pShaderAPI->SetPixelShaderConstant( 1, noiseScroll, 1 );
  191. // Tweaks associated with a given flashlight
  192. tweaks[0] = ShadowFilterFromState( flashlightState );
  193. tweaks[1] = ShadowAttenFromState( flashlightState );
  194. pShader->HashShadow2DJitter( flashlightState.m_flShadowJitterSeed, &tweaks[2], &tweaks[3] );
  195. pShaderAPI->SetPixelShaderConstant( PSREG_ENVMAP_TINT__SHADOW_TWEAKS, tweaks, 1 );
  196. pShaderAPI->SetVertexShaderConstant( VERTEX_SHADER_SHADER_SPECIFIC_CONST_0, worldToTexture.Base(), 4 );
  197. if ( flashlightState.m_bUberlight )
  198. {
  199. // No shear supported at present
  200. flashlightState.m_uberlightState.m_fShearx = 0.0f;
  201. flashlightState.m_uberlightState.m_fSheary = 0.0f;
  202. if ( (info.m_nUberNearFar != -1) && params[info.m_nUberNearFar]->IsDefined() )
  203. {
  204. float v[4];
  205. params[info.m_nUberNearFar]->GetVecValue( v, 4 );
  206. flashlightState.m_uberlightState.m_fNearEdge = v[0];
  207. flashlightState.m_uberlightState.m_fFarEdge = v[1];
  208. flashlightState.m_uberlightState.m_fCutOn = v[2];
  209. flashlightState.m_uberlightState.m_fCutOff = v[3];
  210. }
  211. if ( (info.m_nUberHeightWidth != -1) && params[info.m_nUberHeightWidth]->IsDefined() )
  212. {
  213. float v[4];
  214. params[info.m_nUberHeightWidth]->GetVecValue( v, 4 );
  215. flashlightState.m_uberlightState.m_fWidth = v[0];
  216. flashlightState.m_uberlightState.m_fWedge = v[1];
  217. flashlightState.m_uberlightState.m_fHeight = v[2];
  218. flashlightState.m_uberlightState.m_fHedge = v[3];
  219. }
  220. if ( (info.m_nUberRoundness != -1) && params[info.m_nUberRoundness]->IsDefined() )
  221. {
  222. flashlightState.m_uberlightState.m_fRoundness = params[info.m_nUberRoundness]->GetFloatValue();
  223. }
  224. SetupUberlightFromState( pShaderAPI, flashlightState );
  225. QAngle angles;
  226. QuaternionAngles( flashlightState.m_quatOrientation, angles );
  227. // World to Light's View matrix
  228. matrix3x4_t viewMatrix, viewMatrixInverse;
  229. AngleMatrix( angles, flashlightState.m_vecLightOrigin, viewMatrixInverse );
  230. MatrixInvert( viewMatrixInverse, viewMatrix );
  231. pShaderAPI->SetVertexShaderConstant( VERTEX_SHADER_SHADER_SPECIFIC_CONST_4, worldToTexture.Base(), 4 );
  232. }
  233. else
  234. {
  235. matrix3x4_t identityMatrix;
  236. SetIdentityMatrix( identityMatrix );
  237. pShaderAPI->SetVertexShaderConstant( VERTEX_SHADER_SHADER_SPECIFIC_CONST_4, identityMatrix.Base(), 4 );
  238. }
  239. // Dimensions of screen, used for screen-space noise map sampling
  240. float vScreenScale[4] = {1280.0f / 32.0f, 720.0f / 32.0f, 0, 0};
  241. int nWidth, nHeight;
  242. pShaderAPI->GetBackBufferDimensions( nWidth, nHeight );
  243. int nTexWidth, nTexHeight;
  244. pShaderAPI->GetStandardTextureDimensions( &nTexWidth, &nTexHeight, TEXTURE_SHADOW_NOISE_2D );
  245. vScreenScale[0] = (float) nWidth / nTexWidth;
  246. vScreenScale[1] = (float) nHeight / nTexHeight;
  247. pShaderAPI->SetPixelShaderConstant( PSREG_FLASHLIGHT_SCREEN_SCALE, vScreenScale, 1 );
  248. DECLARE_DYNAMIC_PIXEL_SHADER( lightshafts_ps30 );
  249. SET_DYNAMIC_PIXEL_SHADER_COMBO( FLASHLIGHTSHADOWS, flashlightState.m_bEnableShadows && ( pFlashlightDepthTexture != NULL ) );
  250. SET_DYNAMIC_PIXEL_SHADER_COMBO( UBERLIGHT, flashlightState.m_bUberlight );
  251. SET_DYNAMIC_PIXEL_SHADER( lightshafts_ps30 );
  252. }
  253. pShader->Draw();
  254. }