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.

220 lines
5.1 KiB

  1. //========= Copyright Valve Corporation, All rights reserved. ============//
  2. //
  3. // Purpose:
  4. //
  5. //=============================================================================//
  6. #include "cbase.h"
  7. #include "weapon_csbasegun.h"
  8. #if defined( CLIENT_DLL )
  9. #define CWeaponScout C_WeaponScout
  10. #include "c_cs_player.h"
  11. #else
  12. #include "cs_player.h"
  13. #include "KeyValues.h"
  14. #endif
  15. const int cScoutMidZoomFOV = 40;
  16. const int cScoutMaxZoomFOV = 15;
  17. class CWeaponScout : public CWeaponCSBaseGun
  18. {
  19. public:
  20. DECLARE_CLASS( CWeaponScout, CWeaponCSBaseGun );
  21. DECLARE_NETWORKCLASS();
  22. DECLARE_PREDICTABLE();
  23. CWeaponScout();
  24. virtual void PrimaryAttack();
  25. virtual void SecondaryAttack();
  26. virtual float GetInaccuracy() const;
  27. virtual float GetMaxSpeed() const;
  28. virtual bool Reload();
  29. virtual bool Deploy();
  30. virtual CSWeaponID GetWeaponID( void ) const { return WEAPON_SCOUT; }
  31. private:
  32. CWeaponScout( const CWeaponScout & );
  33. };
  34. IMPLEMENT_NETWORKCLASS_ALIASED( WeaponScout, DT_WeaponScout )
  35. BEGIN_NETWORK_TABLE( CWeaponScout, DT_WeaponScout )
  36. END_NETWORK_TABLE()
  37. BEGIN_PREDICTION_DATA( CWeaponScout )
  38. END_PREDICTION_DATA()
  39. LINK_ENTITY_TO_CLASS( weapon_scout, CWeaponScout );
  40. PRECACHE_WEAPON_REGISTER( weapon_scout );
  41. CWeaponScout::CWeaponScout()
  42. {
  43. }
  44. void CWeaponScout::SecondaryAttack()
  45. {
  46. const float kZoomTime = 0.10f;
  47. CCSPlayer *pPlayer = GetPlayerOwner();
  48. if (pPlayer == NULL)
  49. {
  50. Assert(pPlayer != NULL);
  51. return;
  52. }
  53. if (pPlayer->GetFOV() == pPlayer->GetDefaultFOV())
  54. {
  55. pPlayer->SetFOV( pPlayer, cScoutMidZoomFOV, kZoomTime );
  56. m_weaponMode = Secondary_Mode;
  57. m_fAccuracyPenalty += GetCSWpnData().m_fInaccuracyAltSwitch;
  58. }
  59. else if (pPlayer->GetFOV() == cScoutMidZoomFOV)
  60. {
  61. pPlayer->SetFOV( pPlayer, cScoutMaxZoomFOV, kZoomTime );
  62. m_weaponMode = Secondary_Mode;
  63. }
  64. else if (pPlayer->GetFOV() == cScoutMaxZoomFOV)
  65. {
  66. pPlayer->SetFOV( pPlayer, pPlayer->GetDefaultFOV(), kZoomTime );
  67. m_weaponMode = Primary_Mode;
  68. }
  69. m_flNextSecondaryAttack = gpGlobals->curtime + 0.3f;
  70. m_zoomFullyActiveTime = gpGlobals->curtime + 0.15; // The worst zoom time from above.
  71. #ifndef CLIENT_DLL
  72. // If this isn't guarded, the sound will be emitted twice, once by the server and once by the client.
  73. // Let the server play it since if only the client plays it, it's liable to get played twice cause of
  74. // a prediction error. joy.
  75. //=============================================================================
  76. // HPE_BEGIN:
  77. // [tj] Playing this from the player so that we don't try to play the sound outside the level.
  78. //=============================================================================
  79. if ( GetPlayerOwner() )
  80. {
  81. GetPlayerOwner()->EmitSound( "Default.Zoom" ); // zoom sound
  82. }
  83. //=============================================================================
  84. // HPE_END
  85. //=============================================================================
  86. // let the bots hear the rifle zoom
  87. IGameEvent * event = gameeventmanager->CreateEvent( "weapon_zoom" );
  88. if( event )
  89. {
  90. event->SetInt( "userid", pPlayer->GetUserID() );
  91. gameeventmanager->FireEvent( event );
  92. }
  93. #endif
  94. }
  95. float CWeaponScout::GetInaccuracy() const
  96. {
  97. if ( weapon_accuracy_model.GetInt() == 1 )
  98. {
  99. CCSPlayer *pPlayer = GetPlayerOwner();
  100. if (pPlayer == NULL)
  101. return 0.0f;
  102. float fSpread = 0.0f;
  103. if ( !FBitSet( pPlayer->GetFlags(), FL_ONGROUND ) )
  104. fSpread = 0.2f;
  105. else if (pPlayer->GetAbsVelocity().Length2D() > 170)
  106. fSpread = 0.075f;
  107. else if ( FBitSet( pPlayer->GetFlags(), FL_DUCKING ) )
  108. fSpread = 0.0f;
  109. else
  110. fSpread = 0.007f;
  111. // If we are not zoomed in, or we have very recently zoomed and are still transitioning, the bullet diverts more.
  112. if (pPlayer->GetFOV() == pPlayer->GetDefaultFOV() || (gpGlobals->curtime < m_zoomFullyActiveTime))
  113. {
  114. fSpread += 0.025;
  115. }
  116. return fSpread;
  117. }
  118. else
  119. return BaseClass::GetInaccuracy();
  120. }
  121. void CWeaponScout::PrimaryAttack( void )
  122. {
  123. CCSPlayer *pPlayer = GetPlayerOwner();
  124. if (pPlayer == NULL)
  125. return;
  126. if ( !CSBaseGunFire( GetCSWpnData().m_flCycleTime, m_weaponMode ) )
  127. return;
  128. if ( m_weaponMode == Secondary_Mode )
  129. {
  130. float midFOVdistance = fabs( pPlayer->GetFOV() - (float)cScoutMidZoomFOV );
  131. float farFOVdistance = fabs( pPlayer->GetFOV() - (float)cScoutMaxZoomFOV );
  132. if ( midFOVdistance < farFOVdistance )
  133. {
  134. pPlayer->m_iLastZoom = cScoutMidZoomFOV;
  135. }
  136. else
  137. {
  138. pPlayer->m_iLastZoom = cScoutMaxZoomFOV;
  139. }
  140. // #ifndef CLIENT_DLL
  141. pPlayer->m_bResumeZoom = true;
  142. pPlayer->SetFOV( pPlayer, pPlayer->GetDefaultFOV(), 0.05f );
  143. m_weaponMode = Primary_Mode;
  144. // #endif
  145. }
  146. QAngle angle = pPlayer->GetPunchAngle();
  147. angle.x -= 2;
  148. pPlayer->SetPunchAngle( angle );
  149. }
  150. float CWeaponScout::GetMaxSpeed() const
  151. {
  152. CCSPlayer *pPlayer = GetPlayerOwner();
  153. if (pPlayer == NULL)
  154. {
  155. Assert(pPlayer != NULL);
  156. return BaseClass::GetMaxSpeed();
  157. }
  158. if ( pPlayer->GetFOV() == pPlayer->GetDefaultFOV() )
  159. return BaseClass::GetMaxSpeed();
  160. else
  161. return 220; // zoomed in.
  162. }
  163. bool CWeaponScout::Reload()
  164. {
  165. m_weaponMode = Primary_Mode;
  166. return BaseClass::Reload();
  167. }
  168. bool CWeaponScout::Deploy()
  169. {
  170. m_weaponMode = Primary_Mode;
  171. return BaseClass::Deploy();
  172. }