summaryrefslogtreecommitdiff
path: root/game/shared/hl2mp/weapon_hl2mpbase_machinegun.cpp
diff options
context:
space:
mode:
authorFluorescentCIAAfricanAmerican <[email protected]>2020-04-22 12:56:21 -0400
committerFluorescentCIAAfricanAmerican <[email protected]>2020-04-22 12:56:21 -0400
commit3bf9df6b2785fa6d951086978a3e66f49427166a (patch)
tree2c0f1f0c63c4832882bc93814ebd2c2b1c6224e5 /game/shared/hl2mp/weapon_hl2mpbase_machinegun.cpp
downloadarchived-source-engine-2018-hl2-src-master.tar.xz
archived-source-engine-2018-hl2-src-master.zip
Diffstat (limited to 'game/shared/hl2mp/weapon_hl2mpbase_machinegun.cpp')
-rw-r--r--game/shared/hl2mp/weapon_hl2mpbase_machinegun.cpp242
1 files changed, 242 insertions, 0 deletions
diff --git a/game/shared/hl2mp/weapon_hl2mpbase_machinegun.cpp b/game/shared/hl2mp/weapon_hl2mpbase_machinegun.cpp
new file mode 100644
index 0000000..b5a0040
--- /dev/null
+++ b/game/shared/hl2mp/weapon_hl2mpbase_machinegun.cpp
@@ -0,0 +1,242 @@
+//========= Copyright Valve Corporation, All rights reserved. ============//
+//
+// Purpose:
+//
+//=============================================================================//
+
+#include "cbase.h"
+
+#if defined( CLIENT_DLL )
+ #include "c_hl2mp_player.h"
+#else
+ #include "hl2mp_player.h"
+#endif
+
+#include "weapon_hl2mpbase_machinegun.h"
+#include "in_buttons.h"
+
+// memdbgon must be the last include file in a .cpp file!!!
+#include "tier0/memdbgon.h"
+
+IMPLEMENT_NETWORKCLASS_ALIASED( HL2MPMachineGun, DT_HL2MPMachineGun )
+
+BEGIN_NETWORK_TABLE( CHL2MPMachineGun, DT_HL2MPMachineGun )
+END_NETWORK_TABLE()
+
+BEGIN_PREDICTION_DATA( CHL2MPMachineGun )
+END_PREDICTION_DATA()
+
+//=========================================================
+// >> CHLSelectFireMachineGun
+//=========================================================
+BEGIN_DATADESC( CHL2MPMachineGun )
+
+ DEFINE_FIELD( m_nShotsFired, FIELD_INTEGER ),
+ DEFINE_FIELD( m_flNextSoundTime, FIELD_TIME ),
+
+END_DATADESC()
+
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+CHL2MPMachineGun::CHL2MPMachineGun( void )
+{
+}
+
+const Vector &CHL2MPMachineGun::GetBulletSpread( void )
+{
+ static Vector cone = VECTOR_CONE_3DEGREES;
+ return cone;
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//
+//
+//-----------------------------------------------------------------------------
+void CHL2MPMachineGun::PrimaryAttack( void )
+{
+ // Only the player fires this way so we can cast
+ CBasePlayer *pPlayer = ToBasePlayer( GetOwner() );
+ if (!pPlayer)
+ return;
+
+ // Abort here to handle burst and auto fire modes
+ if ( (UsesClipsForAmmo1() && m_iClip1 == 0) || ( !UsesClipsForAmmo1() && !pPlayer->GetAmmoCount(m_iPrimaryAmmoType) ) )
+ return;
+
+ m_nShotsFired++;
+
+ pPlayer->DoMuzzleFlash();
+
+ // To make the firing framerate independent, we may have to fire more than one bullet here on low-framerate systems,
+ // especially if the weapon we're firing has a really fast rate of fire.
+ int iBulletsToFire = 0;
+ float fireRate = GetFireRate();
+
+ while ( m_flNextPrimaryAttack <= gpGlobals->curtime )
+ {
+ // MUST call sound before removing a round from the clip of a CHLMachineGun
+ WeaponSound(SINGLE, m_flNextPrimaryAttack);
+ m_flNextPrimaryAttack = m_flNextPrimaryAttack + fireRate;
+ iBulletsToFire++;
+ }
+
+ // Make sure we don't fire more than the amount in the clip, if this weapon uses clips
+ if ( UsesClipsForAmmo1() )
+ {
+ if ( iBulletsToFire > m_iClip1 )
+ iBulletsToFire = m_iClip1;
+ m_iClip1 -= iBulletsToFire;
+ }
+
+ CHL2MP_Player *pHL2MPPlayer = ToHL2MPPlayer( pPlayer );
+
+ // Fire the bullets
+ FireBulletsInfo_t info;
+ info.m_iShots = iBulletsToFire;
+ info.m_vecSrc = pHL2MPPlayer->Weapon_ShootPosition( );
+ info.m_vecDirShooting = pPlayer->GetAutoaimVector( AUTOAIM_5DEGREES );
+ info.m_vecSpread = pHL2MPPlayer->GetAttackSpread( this );
+ info.m_flDistance = MAX_TRACE_LENGTH;
+ info.m_iAmmoType = m_iPrimaryAmmoType;
+ info.m_iTracerFreq = 2;
+ FireBullets( info );
+
+ //Factor in the view kick
+ AddViewKick();
+
+ if (!m_iClip1 && pPlayer->GetAmmoCount(m_iPrimaryAmmoType) <= 0)
+ {
+ // HEV suit - indicate out of ammo condition
+ pPlayer->SetSuitUpdate("!HEV_AMO0", FALSE, 0);
+ }
+
+ SendWeaponAnim( GetPrimaryAttackActivity() );
+ pPlayer->SetAnimation( PLAYER_ATTACK1 );
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+// Input : &info -
+//-----------------------------------------------------------------------------
+void CHL2MPMachineGun::FireBullets( const FireBulletsInfo_t &info )
+{
+ if(CBasePlayer *pPlayer = ToBasePlayer ( GetOwner() ) )
+ {
+ pPlayer->FireBullets(info);
+ }
+}
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+void CHL2MPMachineGun::DoMachineGunKick( CBasePlayer *pPlayer, float dampEasy, float maxVerticleKickAngle, float fireDurationTime, float slideLimitTime )
+{
+ #define KICK_MIN_X 0.2f //Degrees
+ #define KICK_MIN_Y 0.2f //Degrees
+ #define KICK_MIN_Z 0.1f //Degrees
+
+ QAngle vecScratch;
+ int iSeed = CBaseEntity::GetPredictionRandomSeed() & 255;
+
+ //Find how far into our accuracy degradation we are
+ float duration = ( fireDurationTime > slideLimitTime ) ? slideLimitTime : fireDurationTime;
+ float kickPerc = duration / slideLimitTime;
+
+ // do this to get a hard discontinuity, clear out anything under 10 degrees punch
+ pPlayer->ViewPunchReset( 10 );
+
+ //Apply this to the view angles as well
+ vecScratch.x = -( KICK_MIN_X + ( maxVerticleKickAngle * kickPerc ) );
+ vecScratch.y = -( KICK_MIN_Y + ( maxVerticleKickAngle * kickPerc ) ) / 3;
+ vecScratch.z = KICK_MIN_Z + ( maxVerticleKickAngle * kickPerc ) / 8;
+
+ RandomSeed( iSeed );
+
+ //Wibble left and right
+ if ( RandomInt( -1, 1 ) >= 0 )
+ vecScratch.y *= -1;
+
+ iSeed++;
+
+ //Wobble up and down
+ if ( RandomInt( -1, 1 ) >= 0 )
+ vecScratch.z *= -1;
+
+ //Clip this to our desired min/max
+ UTIL_ClipPunchAngleOffset( vecScratch, pPlayer->m_Local.m_vecPunchAngle, QAngle( 24.0f, 3.0f, 1.0f ) );
+
+ //Add it to the view punch
+ // NOTE: 0.5 is just tuned to match the old effect before the punch became simulated
+ pPlayer->ViewPunch( vecScratch * 0.5 );
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Reset our shots fired
+//-----------------------------------------------------------------------------
+bool CHL2MPMachineGun::Deploy( void )
+{
+ m_nShotsFired = 0;
+
+ return BaseClass::Deploy();
+}
+
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Make enough sound events to fill the estimated think interval
+// returns: number of shots needed
+//-----------------------------------------------------------------------------
+int CHL2MPMachineGun::WeaponSoundRealtime( WeaponSound_t shoot_type )
+{
+ int numBullets = 0;
+
+ // ran out of time, clamp to current
+ if (m_flNextSoundTime < gpGlobals->curtime)
+ {
+ m_flNextSoundTime = gpGlobals->curtime;
+ }
+
+ // make enough sound events to fill up the next estimated think interval
+ float dt = clamp( m_flAnimTime - m_flPrevAnimTime, 0, 0.2 );
+ if (m_flNextSoundTime < gpGlobals->curtime + dt)
+ {
+ WeaponSound( SINGLE_NPC, m_flNextSoundTime );
+ m_flNextSoundTime += GetFireRate();
+ numBullets++;
+ }
+ if (m_flNextSoundTime < gpGlobals->curtime + dt)
+ {
+ WeaponSound( SINGLE_NPC, m_flNextSoundTime );
+ m_flNextSoundTime += GetFireRate();
+ numBullets++;
+ }
+
+ return numBullets;
+}
+
+
+
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+void CHL2MPMachineGun::ItemPostFrame( void )
+{
+ CBasePlayer *pOwner = ToBasePlayer( GetOwner() );
+
+ if ( pOwner == NULL )
+ return;
+
+ // Debounce the recoiling counter
+ if ( ( pOwner->m_nButtons & IN_ATTACK ) == false )
+ {
+ m_nShotsFired = 0;
+ }
+
+ BaseClass::ItemPostFrame();
+}
+
+