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.

288 lines
9.6 KiB

  1. //========= Copyright Valve Corporation, All rights reserved. ============//
  2. //
  3. // Purpose:
  4. //
  5. //=============================================================================
  6. #include "movieobjects/dmecamera.h"
  7. #include "tier0/dbg.h"
  8. #include "datamodel/dmelementfactoryhelper.h"
  9. #include "mathlib/vector.h"
  10. #include "movieobjects/dmetransform.h"
  11. #include "materialsystem/imaterialsystem.h"
  12. #include "movieobjects_interfaces.h"
  13. #include "tier2/tier2.h"
  14. // FIXME: REMOVE
  15. #include "istudiorender.h"
  16. // memdbgon must be the last include file in a .cpp file!!!
  17. #include "tier0/memdbgon.h"
  18. //-----------------------------------------------------------------------------
  19. // Expose this class to the scene database
  20. //-----------------------------------------------------------------------------
  21. IMPLEMENT_ELEMENT_FACTORY( DmeCamera, CDmeCamera );
  22. //-----------------------------------------------------------------------------
  23. // Purpose:
  24. //-----------------------------------------------------------------------------
  25. void CDmeCamera::OnConstruction()
  26. {
  27. m_fieldOfView.InitAndSet( this, "fieldOfView", 30.0f );
  28. // FIXME: This currently matches the client DLL for HL2
  29. // but we probably need a way of getting this state from the client DLL
  30. m_zNear.InitAndSet( this, "znear", 3.0f );
  31. m_zFar.InitAndSet( this, "zfar", 16384.0f * 1.73205080757f );
  32. m_fFocalDistance.InitAndSet( this, "focalDistance", 72.0f);
  33. m_fAperture.InitAndSet( this, "aperture", 0.2f);
  34. m_fShutterSpeed.InitAndSet( this, "shutterSpeed", 1.0f / 48.0f );
  35. m_fToneMapScale.InitAndSet( this, "toneMapScale", 1.0f );
  36. m_fBloomScale.InitAndSet( this, "bloomScale", 0.28f );
  37. m_nDoFQuality.InitAndSet( this, "depthOfFieldQuality", 0 );
  38. m_nMotionBlurQuality.InitAndSet( this, "motionBlurQuality", 0 );
  39. }
  40. void CDmeCamera::OnDestruction()
  41. {
  42. }
  43. //-----------------------------------------------------------------------------
  44. // Loads the material system view matrix based on the transform
  45. //-----------------------------------------------------------------------------
  46. void CDmeCamera::LoadViewMatrix( bool bUseEngineCoordinateSystem )
  47. {
  48. if ( !g_pMaterialSystem )
  49. return;
  50. CMatRenderContextPtr pRenderContext( g_pMaterialSystem );
  51. VMatrix view;
  52. GetViewMatrix( view, bUseEngineCoordinateSystem );
  53. pRenderContext->MatrixMode( MATERIAL_VIEW );
  54. pRenderContext->LoadMatrix( view );
  55. }
  56. //-----------------------------------------------------------------------------
  57. // Loads the material system projection matrix based on the fov, etc.
  58. //-----------------------------------------------------------------------------
  59. void CDmeCamera::LoadProjectionMatrix( int nDisplayWidth, int nDisplayHeight )
  60. {
  61. if ( !g_pMaterialSystem )
  62. return;
  63. CMatRenderContextPtr pRenderContext( g_pMaterialSystem );
  64. pRenderContext->MatrixMode( MATERIAL_PROJECTION );
  65. VMatrix proj;
  66. GetProjectionMatrix( proj, nDisplayWidth, nDisplayHeight );
  67. pRenderContext->LoadMatrix( proj );
  68. }
  69. //-----------------------------------------------------------------------------
  70. // Sets up studiorender camera state
  71. //-----------------------------------------------------------------------------
  72. void CDmeCamera::LoadStudioRenderCameraState()
  73. {
  74. // FIXME: Remove this! This should automatically happen in DrawModel
  75. // in studiorender.
  76. if ( !g_pStudioRender )
  77. return;
  78. matrix3x4_t transform;
  79. GetTransform()->GetTransform( transform );
  80. Vector vecOrigin, vecRight, vecUp, vecForward;
  81. MatrixGetColumn( transform, 0, vecRight );
  82. MatrixGetColumn( transform, 1, vecUp );
  83. MatrixGetColumn( transform, 2, vecForward );
  84. MatrixGetColumn( transform, 3, vecOrigin );
  85. g_pStudioRender->SetViewState( vecOrigin, vecRight, vecUp, vecForward );
  86. }
  87. //-----------------------------------------------------------------------------
  88. // Returns the x FOV (the full angle)
  89. //-----------------------------------------------------------------------------
  90. float CDmeCamera::GetFOVx() const
  91. {
  92. return m_fieldOfView;
  93. }
  94. void CDmeCamera::SetFOVx( float fov )
  95. {
  96. m_fieldOfView = fov;
  97. }
  98. //-----------------------------------------------------------------------------
  99. // Returns the focal distance in inches
  100. //-----------------------------------------------------------------------------
  101. float CDmeCamera::GetFocalDistance() const
  102. {
  103. return m_fFocalDistance;
  104. }
  105. //-----------------------------------------------------------------------------
  106. // Sets the focal distance in inches
  107. //-----------------------------------------------------------------------------
  108. void CDmeCamera::SetFocalDistance( const float &fFocalDistance )
  109. {
  110. m_fFocalDistance = fFocalDistance;
  111. }
  112. //-----------------------------------------------------------------------------
  113. // Returns the camera aperture in inches
  114. //-----------------------------------------------------------------------------
  115. float CDmeCamera::GetAperture() const
  116. {
  117. return m_fAperture;
  118. }
  119. //-----------------------------------------------------------------------------
  120. // Returns the camera aperture in inches
  121. //-----------------------------------------------------------------------------
  122. float CDmeCamera::GetShutterSpeed() const
  123. {
  124. return m_fShutterSpeed;
  125. }
  126. //-----------------------------------------------------------------------------
  127. // Returns the tone map scale
  128. //-----------------------------------------------------------------------------
  129. float CDmeCamera::GetToneMapScale() const
  130. {
  131. return m_fToneMapScale;
  132. }
  133. //-----------------------------------------------------------------------------
  134. // Returns the bloom scale
  135. //-----------------------------------------------------------------------------
  136. float CDmeCamera::GetBloomScale() const
  137. {
  138. return m_fBloomScale;
  139. }
  140. //-----------------------------------------------------------------------------
  141. // Returns the number of Depth of Field samples
  142. //-----------------------------------------------------------------------------
  143. int CDmeCamera::GetDepthOfFieldQuality() const
  144. {
  145. return m_nDoFQuality;
  146. }
  147. //-----------------------------------------------------------------------------
  148. // Returns the number of Motion Blur samples
  149. //-----------------------------------------------------------------------------
  150. int CDmeCamera::GetMotionBlurQuality() const
  151. {
  152. return m_nMotionBlurQuality;
  153. }
  154. //-----------------------------------------------------------------------------
  155. // Returns the view direction
  156. //-----------------------------------------------------------------------------
  157. void CDmeCamera::GetViewDirection( Vector *pDirection )
  158. {
  159. matrix3x4_t transform;
  160. GetTransform()->GetTransform( transform );
  161. MatrixGetColumn( transform, 2, *pDirection );
  162. // We look down the -z axis
  163. *pDirection *= -1.0f;
  164. }
  165. //-----------------------------------------------------------------------------
  166. // Sets up render state in the material system for rendering
  167. //-----------------------------------------------------------------------------
  168. void CDmeCamera::SetupRenderState( int nDisplayWidth, int nDisplayHeight, bool bUseEngineCoordinateSystem /* = false */ )
  169. {
  170. LoadViewMatrix( bUseEngineCoordinateSystem );
  171. LoadProjectionMatrix( nDisplayWidth, nDisplayHeight );
  172. LoadStudioRenderCameraState( );
  173. }
  174. //-----------------------------------------------------------------------------
  175. // accessors for generated matrices
  176. //-----------------------------------------------------------------------------
  177. void CDmeCamera::GetViewMatrix( VMatrix &view, bool bUseEngineCoordinateSystem /* = false */ )
  178. {
  179. matrix3x4_t transform, invTransform;
  180. CDmeTransform *pTransform = GetTransform();
  181. pTransform->GetTransform( transform );
  182. if ( bUseEngineCoordinateSystem )
  183. {
  184. VMatrix matRotate( transform );
  185. VMatrix matRotateZ;
  186. MatrixBuildRotationAboutAxis( matRotateZ, Vector(0,0,1), -90 );
  187. MatrixMultiply( matRotate, matRotateZ, matRotate );
  188. VMatrix matRotateX;
  189. MatrixBuildRotationAboutAxis( matRotateX, Vector(1,0,0), 90 );
  190. MatrixMultiply( matRotate, matRotateX, matRotate );
  191. transform = matRotate.As3x4();
  192. }
  193. MatrixInvert( transform, invTransform );
  194. view = invTransform;
  195. }
  196. void CDmeCamera::GetProjectionMatrix( VMatrix &proj, int width, int height )
  197. {
  198. float flFOV = m_fieldOfView.Get();
  199. float flZNear = m_zNear.Get();
  200. float flZFar = m_zFar.Get();
  201. float flApsectRatio = (float)width / (float)height;
  202. // MatrixBuildPerspective( proj, flFOV, flFOV * flApsectRatio, flZNear, flZFar );
  203. #if 1
  204. float halfWidth = tan( flFOV * M_PI / 360.0 );
  205. float halfHeight = halfWidth / flApsectRatio;
  206. #else
  207. float halfHeight = tan( flFOV * M_PI / 360.0 );
  208. float halfWidth = flApsectRatio * halfHeight;
  209. #endif
  210. memset( proj.Base(), 0, sizeof( proj ) );
  211. proj[0][0] = 1.0f / halfWidth;
  212. proj[1][1] = 1.0f / halfHeight;
  213. proj[2][2] = flZFar / ( flZNear - flZFar );
  214. proj[3][2] = -1.0f;
  215. proj[2][3] = flZNear * flZFar / ( flZNear - flZFar );
  216. }
  217. void CDmeCamera::GetViewProjectionInverse( VMatrix &viewprojinv, int width, int height )
  218. {
  219. VMatrix view, proj;
  220. GetViewMatrix( view );
  221. GetProjectionMatrix( proj, width, height );
  222. VMatrix viewproj;
  223. MatrixMultiply( proj, view, viewproj );
  224. bool success = MatrixInverseGeneral( viewproj, viewprojinv );
  225. if ( !success )
  226. {
  227. Assert( 0 );
  228. MatrixInverseTR( viewproj, viewprojinv );
  229. }
  230. }
  231. //-----------------------------------------------------------------------------
  232. // Computes the screen space position given a screen size
  233. //-----------------------------------------------------------------------------
  234. void CDmeCamera::ComputeScreenSpacePosition( const Vector &vecWorldPosition, int width, int height, Vector2D *pScreenPosition )
  235. {
  236. VMatrix view, proj, viewproj;
  237. GetViewMatrix( view );
  238. GetProjectionMatrix( proj, width, height );
  239. MatrixMultiply( proj, view, viewproj );
  240. Vector vecScreenPos;
  241. Vector3DMultiplyPositionProjective( viewproj, vecWorldPosition, vecScreenPos );
  242. pScreenPosition->x = ( vecScreenPos.x + 1.0f ) * width / 2.0f;
  243. pScreenPosition->y = ( -vecScreenPos.y + 1.0f ) * height / 2.0f;
  244. }