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.

407 lines
12 KiB

  1. //========= Copyright Valve Corporation, All rights reserved. ============//
  2. //
  3. // Purpose:
  4. //
  5. // $NoKeywords: $
  6. //
  7. //=============================================================================//
  8. #ifndef TRANSITION_TABLE_H
  9. #define TRANSITION_TABLE_H
  10. #ifdef _WIN32
  11. #pragma once
  12. #endif
  13. #include "utlvector.h"
  14. #include "shadershadowdx8.h"
  15. #include "UtlSortVector.h"
  16. #include "checksum_crc.h"
  17. #include "shaderapi/ishaderapi.h"
  18. // Required for DEBUG_BOARD_STATE
  19. #include "shaderapidx8_global.h"
  20. //-----------------------------------------------------------------------------
  21. // Forward declarations
  22. //-----------------------------------------------------------------------------
  23. struct IDirect3DStateBlock9;
  24. //-----------------------------------------------------------------------------
  25. // Enumeration for ApplyStateFunc_ts
  26. //-----------------------------------------------------------------------------
  27. // Any function that does not require a texture stage
  28. // NOTE: If you change this, change the function table s_pRenderFunctionTable[] below!!
  29. enum RenderStateFunc_t
  30. {
  31. RENDER_STATE_DepthTest = 0,
  32. RENDER_STATE_ZWriteEnable,
  33. RENDER_STATE_ColorWriteEnable,
  34. RENDER_STATE_AlphaTest,
  35. RENDER_STATE_FillMode,
  36. RENDER_STATE_Lighting,
  37. RENDER_STATE_SpecularEnable,
  38. RENDER_STATE_SRGBWriteEnable,
  39. RENDER_STATE_AlphaBlend,
  40. RENDER_STATE_SeparateAlphaBlend,
  41. RENDER_STATE_CullEnable,
  42. RENDER_STATE_VertexBlendEnable,
  43. RENDER_STATE_FogMode,
  44. RENDER_STATE_ActivateFixedFunction,
  45. RENDER_STATE_TextureEnable,
  46. RENDER_STATE_DiffuseMaterialSource,
  47. RENDER_STATE_DisableFogGammaCorrection,
  48. RENDER_STATE_EnableAlphaToCoverage,
  49. RENDER_STATE_COUNT,
  50. };
  51. // Any function that requires a texture stage
  52. // NOTE: If you change this, change the function table s_pTextureFunctionTable[] below!!
  53. enum TextureStateFunc_t
  54. {
  55. TEXTURE_STATE_TexCoordIndex = 0,
  56. TEXTURE_STATE_SRGBReadEnable,
  57. TEXTURE_STATE_Fetch4Enable,
  58. #ifdef DX_TO_GL_ABSTRACTION
  59. TEXTURE_STATE_ShadowFilterEnable,
  60. #endif
  61. // Fixed function states
  62. TEXTURE_STATE_ColorTextureStage,
  63. TEXTURE_STATE_AlphaTextureStage,
  64. TEXTURE_STATE_COUNT
  65. };
  66. //-----------------------------------------------------------------------------
  67. // Types related to transition table entries
  68. //-----------------------------------------------------------------------------
  69. typedef void (*ApplyStateFunc_t)( const ShadowState_t& shadowState, int arg );
  70. //-----------------------------------------------------------------------------
  71. // The DX8 implementation of the transition table
  72. //-----------------------------------------------------------------------------
  73. class CTransitionTable
  74. {
  75. public:
  76. struct CurrentTextureStageState_t
  77. {
  78. D3DTEXTUREOP m_ColorOp;
  79. int m_ColorArg1;
  80. int m_ColorArg2;
  81. D3DTEXTUREOP m_AlphaOp;
  82. int m_AlphaArg1;
  83. int m_AlphaArg2;
  84. };
  85. struct CurrentSamplerState_t
  86. {
  87. bool m_SRGBReadEnable;
  88. bool m_Fetch4Enable;
  89. bool m_ShadowFilterEnable;
  90. };
  91. struct CurrentState_t
  92. {
  93. // Everything in this 'CurrentState' structure is a state whose value we don't care about
  94. // under certain circumstances, (which therefore can diverge from the shadow state),
  95. // or states which we override in the dynamic pass.
  96. // Alpha state
  97. bool m_AlphaBlendEnable;
  98. D3DBLEND m_SrcBlend;
  99. D3DBLEND m_DestBlend;
  100. D3DBLENDOP m_BlendOp;
  101. // GR - Separate alpha state
  102. bool m_SeparateAlphaBlendEnable;
  103. D3DBLEND m_SrcBlendAlpha;
  104. D3DBLEND m_DestBlendAlpha;
  105. D3DBLENDOP m_BlendOpAlpha;
  106. // Depth testing states
  107. D3DZBUFFERTYPE m_ZEnable;
  108. D3DCMPFUNC m_ZFunc;
  109. PolygonOffsetMode_t m_ZBias;
  110. // Alpha testing states
  111. bool m_AlphaTestEnable;
  112. D3DCMPFUNC m_AlphaFunc;
  113. int m_AlphaRef;
  114. bool m_ForceDepthFuncEquals;
  115. bool m_bOverrideDepthEnable;
  116. D3DZBUFFERTYPE m_OverrideZWriteEnable;
  117. bool m_bOverrideAlphaWriteEnable;
  118. bool m_bOverriddenAlphaWriteValue;
  119. bool m_bOverrideColorWriteEnable;
  120. bool m_bOverriddenColorWriteValue;
  121. DWORD m_ColorWriteEnable;
  122. bool m_bLinearColorSpaceFrameBufferEnable;
  123. bool m_StencilEnable;
  124. D3DCMPFUNC m_StencilFunc;
  125. int m_StencilRef;
  126. int m_StencilMask;
  127. DWORD m_StencilFail;
  128. DWORD m_StencilZFail;
  129. DWORD m_StencilPass;
  130. int m_StencilWriteMask;
  131. // Texture stage state
  132. CurrentTextureStageState_t m_TextureStage[MAX_TEXTURE_STAGES];
  133. CurrentSamplerState_t m_SamplerState[MAX_SAMPLERS];
  134. };
  135. public:
  136. // constructor, destructor
  137. CTransitionTable( );
  138. virtual ~CTransitionTable();
  139. // Initialization, shutdown
  140. bool Init( );
  141. void Shutdown( );
  142. // Resets the snapshots...
  143. void Reset();
  144. // Takes a snapshot
  145. StateSnapshot_t TakeSnapshot( );
  146. // Take startup snapshot
  147. void TakeDefaultStateSnapshot( );
  148. // Makes the board state match the snapshot
  149. void UseSnapshot( StateSnapshot_t snapshotId );
  150. // Cause the board to match the default state snapshot
  151. void UseDefaultState();
  152. // Snapshotted state overrides
  153. void ForceDepthFuncEquals( bool bEnable );
  154. void OverrideDepthEnable( bool bEnable, bool bDepthEnable );
  155. void OverrideAlphaWriteEnable( bool bOverrideEnable, bool bAlphaWriteEnable );
  156. void OverrideColorWriteEnable( bool bOverrideEnable, bool bColorWriteEnable );
  157. void EnableLinearColorSpaceFrameBuffer( bool bEnable );
  158. // Returns a particular snapshot
  159. const ShadowState_t &GetSnapshot( StateSnapshot_t snapshotId ) const;
  160. const ShadowShaderState_t &GetSnapshotShader( StateSnapshot_t snapshotId ) const;
  161. // Gets the current shadow state
  162. const ShadowState_t *CurrentShadowState() const;
  163. const ShadowShaderState_t *CurrentShadowShaderState() const;
  164. // Return the current shapshot
  165. int CurrentSnapshot() const { return m_CurrentSnapshotId; }
  166. CurrentState_t& CurrentState() { return m_CurrentState; }
  167. #ifdef DEBUG_BOARD_STATE
  168. ShadowState_t& BoardState() { return m_BoardState; }
  169. ShadowShaderState_t& BoardShaderState() { return m_BoardShaderState; }
  170. #endif
  171. // The following are meant to be used by the transition table only
  172. public:
  173. // Applies alpha blending
  174. void ApplyAlphaBlend( const ShadowState_t& state );
  175. // GR - separate alpha blend
  176. void ApplySeparateAlphaBlend( const ShadowState_t& state );
  177. void ApplyAlphaTest( const ShadowState_t& state );
  178. void ApplyDepthTest( const ShadowState_t& state );
  179. // Applies alpha texture op
  180. void ApplyColorTextureStage( const ShadowState_t& state, int stage );
  181. void ApplyAlphaTextureStage( const ShadowState_t& state, int stage );
  182. void ApplySRGBWriteEnable( const ShadowState_t& state );
  183. private:
  184. enum
  185. {
  186. INVALID_TRANSITION_OP = 0xFFFFFF
  187. };
  188. typedef short ShadowStateId_t;
  189. // For the transition table
  190. struct TransitionList_t
  191. {
  192. unsigned int m_FirstOperation : 24;
  193. unsigned int m_NumOperations : 8;
  194. };
  195. union TransitionOp_t
  196. {
  197. unsigned char m_nBits;
  198. struct
  199. {
  200. unsigned char m_nOpCode : 7;
  201. unsigned char m_bIsTextureCode : 1;
  202. } m_nInfo;
  203. };
  204. struct SnapshotShaderState_t
  205. {
  206. ShadowShaderState_t m_ShaderState;
  207. ShadowStateId_t m_ShadowStateId;
  208. unsigned short m_nReserved; // Pad to 2 ints
  209. unsigned int m_nReserved2;
  210. };
  211. struct ShadowStateDictEntry_t
  212. {
  213. CRC32_t m_nChecksum;
  214. ShadowStateId_t m_nShadowStateId;
  215. };
  216. struct SnapshotDictEntry_t
  217. {
  218. CRC32_t m_nChecksum;
  219. StateSnapshot_t m_nSnapshot;
  220. };
  221. class ShadowStateDictLessFunc
  222. {
  223. public:
  224. bool Less( const ShadowStateDictEntry_t &src1, const ShadowStateDictEntry_t &src2, void *pCtx );
  225. };
  226. class SnapshotDictLessFunc
  227. {
  228. public:
  229. bool Less( const SnapshotDictEntry_t &src1, const SnapshotDictEntry_t &src2, void *pCtx );
  230. };
  231. class UniqueSnapshotLessFunc
  232. {
  233. public:
  234. bool Less( const TransitionList_t &src1, const TransitionList_t &src2, void *pCtx );
  235. };
  236. CurrentTextureStageState_t &TextureStage( int stage ) { return m_CurrentState.m_TextureStage[stage]; }
  237. const CurrentTextureStageState_t &TextureStage( int stage ) const { return m_CurrentState.m_TextureStage[stage]; }
  238. CurrentSamplerState_t &SamplerState( int stage ) { return m_CurrentState.m_SamplerState[stage]; }
  239. const CurrentSamplerState_t &SamplerState( int stage ) const { return m_CurrentState.m_SamplerState[stage]; }
  240. // creates state snapshots
  241. ShadowStateId_t CreateShadowState( const ShadowState_t &currentState );
  242. StateSnapshot_t CreateStateSnapshot( ShadowStateId_t shadowStateId, const ShadowShaderState_t& currentShaderState );
  243. // finds state snapshots
  244. ShadowStateId_t FindShadowState( const ShadowState_t& currentState ) const;
  245. StateSnapshot_t FindStateSnapshot( ShadowStateId_t id, const ShadowShaderState_t& currentState ) const;
  246. // Finds identical transition lists
  247. unsigned int FindIdenticalTransitionList( unsigned int firstElem,
  248. unsigned short numOps, unsigned int nFirstTest ) const;
  249. // Adds a transition
  250. void AddTransition( RenderStateFunc_t func );
  251. void AddTextureTransition( TextureStateFunc_t func, int stage );
  252. // Apply a transition
  253. void ApplyTransition( TransitionList_t& list, int snapshot );
  254. // Creates an entry in the transition table
  255. void CreateTransitionTableEntry( int to, int from );
  256. // Checks if a state is valid
  257. bool TestShadowState( const ShadowState_t& state, const ShadowShaderState_t &shaderState );
  258. // Perform state block overrides
  259. void PerformShadowStateOverrides( );
  260. // Applies the transition list
  261. void ApplyTransitionList( int snapshot, int nFirstOp, int nOpCount );
  262. // Apply shader state (stuff that doesn't lie in the transition table)
  263. void ApplyShaderState( const ShadowState_t &shadowState, const ShadowShaderState_t &shaderState );
  264. // Wrapper for the non-standard transitions for stateblock + non-stateblock cases
  265. int CreateNormalTransitions( const ShadowState_t& fromState, const ShadowState_t& toState, bool bForce );
  266. // State setting methods
  267. void SetZEnable( D3DZBUFFERTYPE nEnable );
  268. void SetZFunc( D3DCMPFUNC nCmpFunc );
  269. private:
  270. // Sets up the default state
  271. StateSnapshot_t m_DefaultStateSnapshot;
  272. TransitionList_t m_DefaultTransition;
  273. ShadowState_t m_DefaultShadowState;
  274. // The current snapshot id
  275. ShadowStateId_t m_CurrentShadowId;
  276. StateSnapshot_t m_CurrentSnapshotId;
  277. // Maintains a list of all used snapshot transition states
  278. CUtlVector< ShadowState_t > m_ShadowStateList;
  279. // Lookup table for fast snapshot finding
  280. CUtlSortVector< ShadowStateDictEntry_t, ShadowStateDictLessFunc > m_ShadowStateDict;
  281. // The snapshot transition table
  282. CUtlVector< CUtlVector< TransitionList_t > > m_TransitionTable;
  283. // List of unique transitions
  284. CUtlSortVector< TransitionList_t, UniqueSnapshotLessFunc > m_UniqueTransitions;
  285. // Stores all state transition operations
  286. CUtlVector< TransitionOp_t > m_TransitionOps;
  287. // Stores all state for a particular snapshot
  288. CUtlVector< SnapshotShaderState_t > m_SnapshotList;
  289. // Lookup table for fast snapshot finding
  290. CUtlSortVector< SnapshotDictEntry_t, SnapshotDictLessFunc > m_SnapshotDict;
  291. // The current board state.
  292. CurrentState_t m_CurrentState;
  293. #ifdef DEBUG_BOARD_STATE
  294. // Maintains the total shadow state
  295. ShadowState_t m_BoardState;
  296. ShadowShaderState_t m_BoardShaderState;
  297. #endif
  298. };
  299. //-----------------------------------------------------------------------------
  300. // Inline methods
  301. //-----------------------------------------------------------------------------
  302. inline const ShadowState_t &CTransitionTable::GetSnapshot( StateSnapshot_t snapshotId ) const
  303. {
  304. Assert( (snapshotId >= 0) && (snapshotId < m_SnapshotList.Count()) );
  305. return m_ShadowStateList[m_SnapshotList[snapshotId].m_ShadowStateId];
  306. }
  307. inline const ShadowShaderState_t &CTransitionTable::GetSnapshotShader( StateSnapshot_t snapshotId ) const
  308. {
  309. Assert( (snapshotId >= 0) && (snapshotId < m_SnapshotList.Count()) );
  310. return m_SnapshotList[snapshotId].m_ShaderState;
  311. }
  312. inline const ShadowState_t *CTransitionTable::CurrentShadowState() const
  313. {
  314. if ( m_CurrentShadowId == -1 )
  315. return NULL;
  316. Assert( (m_CurrentShadowId >= 0) && (m_CurrentShadowId < m_ShadowStateList.Count()) );
  317. return &m_ShadowStateList[m_CurrentShadowId];
  318. }
  319. inline const ShadowShaderState_t *CTransitionTable::CurrentShadowShaderState() const
  320. {
  321. if ( m_CurrentShadowId == -1 )
  322. return NULL;
  323. Assert( (m_CurrentShadowId >= 0) && (m_CurrentShadowId < m_ShadowStateList.Count()) );
  324. return &m_SnapshotList[m_CurrentShadowId].m_ShaderState;
  325. }
  326. #endif // TRANSITION_TABLE_H