Portable Half-Life SDK. GoldSource and Xash3D. Crossplatform.
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.

717 lines
19 KiB

7 years ago
/***
*
* Copyright (c) 1996-2002, Valve LLC. All rights reserved.
*
* This product contains software technology licensed from Id
* Software, Inc. ("Id Technology"). Id Technology (c) 1996 Id Software, Inc.
* All Rights Reserved.
*
* Use, distribution, and modification of this source code and/or resulting
* object code is restricted to non-commercial enhancements to products from
* Valve LLC. All other use, distribution, or modification is prohibited
* without written permission from Valve LLC.
*
****/
#if !OEM_BUILD
7 years ago
#include "extdll.h"
#include "util.h"
#include "cbase.h"
#include "monsters.h"
#include "weapons.h"
#include "nodes.h"
#include "player.h"
#include "gamerules.h"
8 years ago
enum rpg_e
{
7 years ago
RPG_IDLE = 0,
RPG_FIDGET,
RPG_RELOAD, // to reload
RPG_FIRE2, // to empty
RPG_HOLSTER1, // loaded
RPG_DRAW1, // loaded
RPG_HOLSTER2, // unloaded
RPG_DRAW_UL, // unloaded
RPG_IDLE_UL, // unloaded idle
RPG_FIDGET_UL // unloaded fidget
7 years ago
};
LINK_ENTITY_TO_CLASS( weapon_rpg, CRpg )
7 years ago
4 years ago
#if !CLIENT_DLL
7 years ago
LINK_ENTITY_TO_CLASS( laser_spot, CLaserSpot )
7 years ago
//=========================================================
//=========================================================
CLaserSpot *CLaserSpot::CreateSpot( void )
{
CLaserSpot *pSpot = GetClassPtr( (CLaserSpot *)NULL );
pSpot->Spawn();
8 years ago
pSpot->pev->classname = MAKE_STRING( "laser_spot" );
7 years ago
return pSpot;
}
//=========================================================
//=========================================================
CLaserSpot *CLaserSpot::CreateSpot( const char* spritename )
{
CLaserSpot *pSpot = CreateSpot();
SET_MODEL(ENT(pSpot->pev), spritename);
return pSpot;
}
//=========================================================
//=========================================================
void CLaserSpot::Spawn( void )
{
8 years ago
Precache();
7 years ago
pev->movetype = MOVETYPE_NONE;
pev->solid = SOLID_NOT;
pev->rendermode = kRenderGlow;
pev->renderfx = kRenderFxNoDissipation;
pev->renderamt = 255;
8 years ago
SET_MODEL( ENT( pev ), "sprites/laserdot.spr" );
7 years ago
UTIL_SetOrigin( this, pev->origin );
};
//=========================================================
// Suspend- make the laser sight invisible.
//=========================================================
void CLaserSpot::Suspend( float flSuspendTime )
{
pev->effects |= EF_NODRAW;
8 years ago
7 years ago
//LRC: -1 means suspend indefinitely
if (flSuspendTime == -1)
{
SetThink( NULL );
}
else
{
9 years ago
SetThink( &CLaserSpot::Revive );
7 years ago
SetNextThink( flSuspendTime );
}
}
//=========================================================
// Revive - bring a suspended laser sight back.
//=========================================================
void CLaserSpot::Revive( void )
{
pev->effects &= ~EF_NODRAW;
SetThink( NULL );
}
void CLaserSpot::Precache( void )
{
8 years ago
PRECACHE_MODEL( "sprites/laserdot.spr" );
}
7 years ago
LINK_ENTITY_TO_CLASS( rpg_rocket, CRpgRocket )
7 years ago
//=========================================================
//=========================================================
CRpgRocket *CRpgRocket::CreateRpgRocket( Vector vecOrigin, Vector vecAngles, CBaseEntity *pOwner, CRpg *pLauncher )
{
CRpgRocket *pRocket = GetClassPtr( (CRpgRocket *)NULL );
UTIL_SetOrigin( pRocket, vecOrigin );
pRocket->pev->angles = vecAngles;
pRocket->Spawn();
9 years ago
pRocket->SetTouch( &CRpgRocket::RocketTouch );
pRocket->m_hLauncher = pLauncher;// remember what RPG fired me.
pLauncher->m_cActiveRockets++;// register this missile as active for the launcher
7 years ago
pRocket->pev->owner = pOwner->edict();
return pRocket;
}
//=========================================================
//=========================================================
8 years ago
void CRpgRocket::Spawn( void )
7 years ago
{
8 years ago
Precache();
7 years ago
// motor
pev->movetype = MOVETYPE_BOUNCE;
pev->solid = SOLID_BBOX;
8 years ago
SET_MODEL( ENT( pev ), "models/rpgrocket.mdl" );
UTIL_SetSize( pev, Vector( 0, 0, 0 ), Vector( 0, 0, 0 ) );
7 years ago
UTIL_SetOrigin( this, pev->origin );
8 years ago
pev->classname = MAKE_STRING( "rpg_rocket" );
7 years ago
9 years ago
SetThink( &CRpgRocket::IgniteThink );
7 years ago
SetTouch(&CRpgRocket :: ExplodeTouch );
pev->angles.x -= 30.0f;
7 years ago
UTIL_MakeVectors( pev->angles );
pev->angles.x = -( pev->angles.x + 30.0f );
7 years ago
pev->velocity = gpGlobals->v_forward * 250.0f;
pev->gravity = 0.5f;
7 years ago
SetNextThink( 0.4f );
7 years ago
pev->dmg = gSkillData.plrDmgRPG;
}
//=========================================================
//=========================================================
8 years ago
void CRpgRocket::RocketTouch( CBaseEntity *pOther )
7 years ago
{
if( CRpg* pLauncher = (CRpg*)( (CBaseEntity*)( m_hLauncher ) ) )
7 years ago
{
// my launcher is still around, tell it I'm dead.
pLauncher->m_cActiveRockets--;
7 years ago
}
STOP_SOUND( edict(), CHAN_VOICE, "weapons/rocket1.wav" );
ExplodeTouch( pOther );
// initialize a vector that finds the center of the RPG models hitbox
Vector vecSpot = pev->origin + ( pev->mins + pev->maxs ) * 0.5;
MESSAGE_BEGIN( MSG_PVS, SVC_TEMPENTITY, vecSpot );
WRITE_BYTE( TE_SPRITE );//additive sprite plays though once
WRITE_COORD( vecSpot.x );//where to make the sprite appear on x axis
WRITE_COORD( vecSpot.y );//where to make the sprite appear on y axis
WRITE_COORD( vecSpot.z + 128 );//Creates sprite 128 units above model's center
WRITE_SHORT( m_iExplode );//Name of the sprite to use, as defined at begining of tut
WRITE_BYTE( 60 ); // scale in .1 units --by comparison the player is 72 units tall
WRITE_BYTE( 255 ); // brightness (this is as bright as it gets)
MESSAGE_END();
// Big Plume of Smoke
MESSAGE_BEGIN( MSG_PVS, SVC_TEMPENTITY, vecSpot );
WRITE_BYTE( TE_SMOKE );//alphablended sprite
WRITE_COORD( vecSpot.x );
WRITE_COORD( vecSpot.y );
WRITE_COORD( vecSpot.z + 256 );
WRITE_SHORT( g_sModelIndexSmoke );//This is Defined in weapons.cpp and weapons.h
WRITE_BYTE( 125 ); //scale in .1 units
WRITE_BYTE( 5 ); // framerate to playback sprite
MESSAGE_END();
// blast circle "The Infamous Disc of Death"
MESSAGE_BEGIN( MSG_PVS, SVC_TEMPENTITY, pev->origin );
WRITE_BYTE( TE_BEAMCYLINDER );
WRITE_COORD( pev->origin.x );//center of effect on x axis
WRITE_COORD( pev->origin.y );//center of effect on y axis
WRITE_COORD( pev->origin.z );//center of effect on z axis
WRITE_COORD( pev->origin.x );//axis of effect on x axis
WRITE_COORD( pev->origin.y );//axis of effect on y axis
WRITE_COORD( pev->origin.z + 320 ); // z axis and Radius of effect
WRITE_SHORT( m_iSpriteTexture );//Name of the sprite to use, as defined at begining of tut
WRITE_BYTE( 0 ); // startframe
WRITE_BYTE( 0 ); //framerate in 0.1's
WRITE_BYTE( 4 ); //Life in 0.1's
WRITE_BYTE( 32 ); //Line Width in .1 units
WRITE_BYTE( 0 ); //Noise Amplitude in 0.01's
WRITE_BYTE( 255 ); // Red Color Value
WRITE_BYTE( 255 ); // Green Color Value
WRITE_BYTE( 192 ); // Blue Color Value
WRITE_BYTE( 128 ); // brightness
WRITE_BYTE( 0 ); // speed
MESSAGE_END();
// insane glow
MESSAGE_BEGIN( MSG_PVS, SVC_TEMPENTITY, pev->origin );
WRITE_BYTE( TE_GLOWSPRITE );//Big Flare Effect
WRITE_COORD( pev->origin.x ); //where to make the sprite appear on x axis
WRITE_COORD( pev->origin.y );//where to make the sprite appear on y axis
WRITE_COORD( pev->origin.z );//where to make the sprite appear on zaxis
WRITE_SHORT( m_iGlow ); //Name of the sprite to use, as defined at begining of tut
WRITE_BYTE( 20 ); //Life in 0.1's
WRITE_BYTE( 128 ); //Size in 0.1's
WRITE_BYTE( 190 ); // brightness
MESSAGE_END();
EMIT_SOUND( ENT( pev ), CHAN_STATIC, "weapons/bfg_fire_sunofgod.wav", 1.0, 0.3 );
UTIL_ScreenShake( pev->origin, 25.0, 150.0, 1.0, 1080 );
RadiusDamage( pev->origin, pev, pev, 150, CLASS_NONE, DMG_BLAST | DMG_RADIATION );
entvars_t *pevOwner; // defines owner
if( pev->owner )
pevOwner = VARS( pev->owner );
else
pevOwner = NULL;
pev->owner = NULL; // can't traceline attack owner if this is set
pev->effects |= EF_NODRAW; // stop showing the model!!
pev->velocity = g_vecZero; // set velocity to "0"
SetThink( &CRpgRocket::AfterGlow );
pev->nextthink = gpGlobals->time + 0.7f; // set next think into future
}
void CRpgRocket::AfterGlow( void )
{
// aftermath glow
MESSAGE_BEGIN( MSG_PAS, SVC_TEMPENTITY, pev->origin );
WRITE_BYTE( TE_GLOWSPRITE );//Like the AfterGlow from the Gauss
WRITE_COORD( pev->origin.x); //where to make the sprite appear on x axis
WRITE_COORD( pev->origin.y); //where to make the sprite appear on y axis
WRITE_COORD( pev->origin.z); //where to make the sprite appear on z axis
WRITE_SHORT( m_iGlow ); //Name of the sprite to use, as defined at begining of tut
WRITE_BYTE( 60 ); //Life in 0.1's
WRITE_BYTE( 64 ); //Size in 0.1's
WRITE_BYTE( 200 ); // brightness
MESSAGE_END();
/*insert radiation think for 2nd tutorial later,
for now just get rid of this damn thing.*/
UTIL_Remove( this );
7 years ago
}
//=========================================================
//=========================================================
8 years ago
void CRpgRocket::Precache( void )
7 years ago
{
8 years ago
PRECACHE_MODEL( "models/rpgrocket.mdl" );
m_iTrail = PRECACHE_MODEL( "sprites/smoke.spr" );
m_iSpriteTexture = PRECACHE_MODEL( "sprites/white.spr" );
m_iExplode = PRECACHE_MODEL( "sprites/fexplo.spr" );
m_iGlow = PRECACHE_MODEL( "sprites/hotglow.spr" );
8 years ago
PRECACHE_SOUND( "weapons/rocket1.wav" );
PRECACHE_SOUND( "weapons/bfg_fire_sunofgod.wav" );
7 years ago
}
8 years ago
void CRpgRocket::IgniteThink( void )
7 years ago
{
// pev->movetype = MOVETYPE_TOSS;
pev->movetype = MOVETYPE_FLY;
pev->effects |= EF_LIGHT;
// make rocket sound
EMIT_SOUND( ENT( pev ), CHAN_VOICE, "weapons/rocket1.wav", 1, 0.5f );
7 years ago
// rocket trail
MESSAGE_BEGIN( MSG_BROADCAST, SVC_TEMPENTITY );
WRITE_BYTE( TE_BEAMFOLLOW );
8 years ago
WRITE_SHORT( entindex() ); // entity
WRITE_SHORT( m_iTrail ); // model
7 years ago
WRITE_BYTE( 40 ); // life
WRITE_BYTE( 5 ); // width
WRITE_BYTE( 224 ); // r, g, b
WRITE_BYTE( 224 ); // r, g, b
WRITE_BYTE( 255 ); // r, g, b
WRITE_BYTE( 255 ); // brightness
MESSAGE_END(); // move PHS/PVS data sending into here (SEND_ALL, SEND_PVS, SEND_PHS)
m_flIgniteTime = gpGlobals->time;
// set to follow laser spot
9 years ago
SetThink( &CRpgRocket::FollowThink );
SetNextThink( 0.1f );
7 years ago
}
8 years ago
void CRpgRocket::FollowThink( void )
7 years ago
{
CBaseEntity *pOther = NULL;
Vector vecTarget;
Vector vecDir;
float flDist, flMax, flDot;
TraceResult tr;
UTIL_MakeAimVectors( pev->angles );
vecTarget = gpGlobals->v_forward;
flMax = 4096;
// Examine all entities within a reasonable radius
8 years ago
while( ( pOther = UTIL_FindEntityByClassname( pOther, "laser_spot" ) ) != NULL )
7 years ago
{
8 years ago
UTIL_TraceLine( pev->origin, pOther->pev->origin, dont_ignore_monsters, ENT( pev ), &tr );
7 years ago
// ALERT( at_console, "%f\n", tr.flFraction );
if( tr.flFraction >= 0.9f )
7 years ago
{
vecDir = pOther->pev->origin - pev->origin;
8 years ago
flDist = vecDir.Length();
vecDir = vecDir.Normalize();
7 years ago
flDot = DotProduct( gpGlobals->v_forward, vecDir );
8 years ago
if( ( flDot > 0 ) && ( flDist * ( 1 - flDot ) < flMax ) )
7 years ago
{
8 years ago
flMax = flDist * ( 1 - flDot );
7 years ago
vecTarget = vecDir;
}
}
}
pev->angles = UTIL_VecToAngles( vecTarget );
// this acceleration and turning math is totally wrong, but it seems to respond well so don't change it.
float flSpeed = pev->velocity.Length();
if( gpGlobals->time - m_flIgniteTime < 1.0f )
7 years ago
{
pev->velocity = pev->velocity * 0.2f + vecTarget * ( flSpeed * 0.8f + 400 );
if( pev->waterlevel == 3 && pev->watertype > CONTENT_FLYFIELD )
7 years ago
{
// go slow underwater
if( pev->velocity.Length() > 300.0f )
7 years ago
{
pev->velocity = pev->velocity.Normalize() * 300.0f;
7 years ago
}
UTIL_BubbleTrail( pev->origin - pev->velocity * 0.1f, pev->origin, 4 );
7 years ago
}
else
{
if( pev->velocity.Length() > 2000.0f )
7 years ago
{
pev->velocity = pev->velocity.Normalize() * 2000.0f;
7 years ago
}
}
}
else
{
8 years ago
if( pev->effects & EF_LIGHT )
7 years ago
{
pev->effects = 0;
8 years ago
STOP_SOUND( ENT( pev ), CHAN_VOICE, "weapons/rocket1.wav" );
7 years ago
}
pev->velocity = pev->velocity * 0.2f + vecTarget * flSpeed * 0.798f;
if( ( pev->waterlevel == 0 || pev->watertype == CONTENT_FOG ) && pev->velocity.Length() < 1500.0f )
7 years ago
{
if( CRpg *pLauncher = (CRpg*)( (CBaseEntity*)( m_hLauncher ) ) )
{
// my launcher is still around, tell it I'm dead.
pLauncher->m_cActiveRockets--;
}
8 years ago
Detonate();
7 years ago
}
}
// ALERT( at_console, "%.0f\n", flSpeed );
SetNextThink( 0.1f );
7 years ago
}
#endif
void CRpg::Reload( void )
{
int iResult = 0;
// don't bother with any of this if don't need to reload.
if( m_pPlayer->m_rgAmmo[m_iPrimaryAmmoType] <= 0 || m_iClip == RPG_MAX_CLIP )
7 years ago
return;
// because the RPG waits to autoreload when no missiles are active while the LTD is on, the
// weapons code is constantly calling into this function, but is often denied because
// a) missiles are in flight, but the LTD is on
// or
// b) player is totally out of ammo and has nothing to switch to, and should be allowed to
// shine the designator around
//
// Set the next attack time into the future so that WeaponIdle will get called more often
// than reload, allowing the RPG LTD to be updated
m_flNextPrimaryAttack = GetNextAttackDelay( 0.5f );
7 years ago
8 years ago
if( m_cActiveRockets && m_fSpotActive )
7 years ago
{
// no reloading when there are active missiles tracking the designator.
// ward off future autoreload attempts by setting next attack time into the future for a bit.
return;
}
4 years ago
#if !CLIENT_DLL
8 years ago
if( m_pSpot && m_fSpotActive )
7 years ago
{
m_pSpot->Suspend( 2.1f );
m_flNextSecondaryAttack = UTIL_WeaponTimeBase() + 2.1f;
7 years ago
}
#endif
8 years ago
if( m_iClip == 0 )
7 years ago
iResult = DefaultReload( RPG_MAX_CLIP, RPG_RELOAD, 2 );
8 years ago
if( iResult )
7 years ago
m_flTimeWeaponIdle = UTIL_WeaponTimeBase() + UTIL_SharedRandomFloat( m_pPlayer->random_seed, 10, 15 );
}
8 years ago
void CRpg::Spawn()
7 years ago
{
8 years ago
Precache();
7 years ago
m_iId = WEAPON_RPG;
8 years ago
SET_MODEL( ENT( pev ), "models/w_rpg.mdl" );
7 years ago
m_fSpotActive = 1;
4 years ago
#if CLIENT_DLL
8 years ago
if( bIsMultiplayer() )
7 years ago
#else
8 years ago
if( g_pGameRules->IsMultiplayer() )
7 years ago
#endif
{
// more default ammo in multiplay.
m_iDefaultAmmo = RPG_DEFAULT_GIVE * 2;
}
else
{
m_iDefaultAmmo = RPG_DEFAULT_GIVE;
}
FallInit();// get ready to fall down.
}
void CRpg::Precache( void )
{
8 years ago
PRECACHE_MODEL( "models/w_rpg.mdl" );
PRECACHE_MODEL( "models/v_rpg.mdl" );
PRECACHE_MODEL( "models/p_rpg.mdl" );
7 years ago
8 years ago
PRECACHE_SOUND( "items/9mmclip1.wav" );
7 years ago
UTIL_PrecacheOther( "laser_spot" );
UTIL_PrecacheOther( "rpg_rocket" );
8 years ago
PRECACHE_SOUND( "weapons/rocketfire1.wav" );
PRECACHE_SOUND( "weapons/glauncher.wav" ); // alternative fire sound
7 years ago
8 years ago
m_usRpg = PRECACHE_EVENT( 1, "events/rpg.sc" );
7 years ago
}
8 years ago
int CRpg::GetItemInfo( ItemInfo *p )
7 years ago
{
8 years ago
p->pszName = STRING( pev->classname );
7 years ago
p->pszAmmo1 = "rockets";
p->iMaxAmmo1 = ROCKET_MAX_CARRY;
p->pszAmmo2 = NULL;
p->iMaxAmmo2 = -1;
p->iMaxClip = RPG_MAX_CLIP;
p->iSlot = 5;
7 years ago
p->iPosition = 0;
p->iId = m_iId = WEAPON_RPG;
p->iFlags = 0;
p->iWeight = RPG_WEIGHT;
p->weaponName = "Rocket Grenade Launcher Nuke";
7 years ago
return 1;
}
int CRpg::AddToPlayer( CBasePlayer *pPlayer )
{
8 years ago
if( CBasePlayerWeapon::AddToPlayer( pPlayer ) )
7 years ago
{
MESSAGE_BEGIN( MSG_ONE, gmsgWeapPickup, NULL, pPlayer->pev );
WRITE_BYTE( m_iId );
MESSAGE_END();
return TRUE;
}
return FALSE;
}
8 years ago
BOOL CRpg::Deploy()
7 years ago
{
8 years ago
if( m_iClip == 0 )
7 years ago
{
return DefaultDeploy( "models/v_rpg.mdl", "models/p_rpg.mdl", RPG_DRAW_UL, "rpg" );
}
return DefaultDeploy( "models/v_rpg.mdl", "models/p_rpg.mdl", RPG_DRAW1, "rpg" );
}
BOOL CRpg::CanHolster( void )
{
8 years ago
if( m_fSpotActive && m_cActiveRockets )
7 years ago
{
// can't put away while guiding a missile.
return FALSE;
}
return TRUE;
}
void CRpg::Holster( int skiplocal /* = 0 */ )
{
m_fInReload = FALSE;// cancel any reload in progress.
m_pPlayer->m_flNextAttack = UTIL_WeaponTimeBase() + 0.5f;
8 years ago
7 years ago
SendWeaponAnim( RPG_HOLSTER1 );
4 years ago
#if !CLIENT_DLL
8 years ago
if( m_pSpot )
7 years ago
{
m_pSpot->Killed( NULL, GIB_NEVER );
m_pSpot = NULL;
}
#endif
}
void CRpg::PrimaryAttack()
{
8 years ago
if( m_iClip )
7 years ago
{
m_pPlayer->m_iWeaponVolume = LOUD_GUN_VOLUME;
m_pPlayer->m_iWeaponFlash = BRIGHT_GUN_FLASH;
4 years ago
#if !CLIENT_DLL
7 years ago
// player "shoot" animation
m_pPlayer->SetAnimation( PLAYER_ATTACK1 );
UTIL_MakeVectors( m_pPlayer->pev->v_angle );
Vector vecSrc = m_pPlayer->GetGunPosition() + gpGlobals->v_forward * 16.0f + gpGlobals->v_right * 8.0f + gpGlobals->v_up * -8.0f;
8 years ago
7 years ago
CRpgRocket *pRocket = CRpgRocket::CreateRpgRocket( vecSrc, m_pPlayer->pev->v_angle, m_pPlayer, this );
UTIL_MakeVectors( m_pPlayer->pev->v_angle );// RpgRocket::Create stomps on globals, so remake.
pRocket->pev->velocity = pRocket->pev->velocity + gpGlobals->v_forward * DotProduct( m_pPlayer->pev->velocity, gpGlobals->v_forward );
#endif
// firing RPG no longer turns on the designator. ALT fire is a toggle switch for the LTD.
// Ken signed up for this as a global change (sjb)
int flags;
#if CLIENT_WEAPONS
7 years ago
flags = FEV_NOTHOST;
#else
flags = 0;
#endif
PLAYBACK_EVENT( flags, m_pPlayer->edict(), m_usRpg );
m_iClip--;
8 years ago
m_flNextPrimaryAttack = GetNextAttackDelay( 1.5f );
m_flTimeWeaponIdle = UTIL_WeaponTimeBase() + 1.5f;
ResetEmptySound();
7 years ago
}
else
{
8 years ago
PlayEmptySound();
m_flNextPrimaryAttack = UTIL_WeaponTimeBase() + 0.2f;
7 years ago
}
8 years ago
UpdateSpot();
7 years ago
}
void CRpg::SecondaryAttack()
{
8 years ago
m_fSpotActive = !m_fSpotActive;
7 years ago
4 years ago
#if !CLIENT_DLL
8 years ago
if( !m_fSpotActive && m_pSpot )
7 years ago
{
m_pSpot->Killed( NULL, GIB_NORMAL );
m_pSpot = NULL;
}
#endif
m_flNextSecondaryAttack = UTIL_WeaponTimeBase() + 0.2f;
7 years ago
}
void CRpg::WeaponIdle( void )
{
8 years ago
UpdateSpot();
7 years ago
8 years ago
if( m_flTimeWeaponIdle > UTIL_WeaponTimeBase() )
7 years ago
return;
8 years ago
if( m_pPlayer->m_rgAmmo[m_iPrimaryAmmoType] )
7 years ago
{
ResetEmptySound();
7 years ago
int iAnim;
float flRand = UTIL_SharedRandomFloat( m_pPlayer->random_seed, 0.0f, 1.0f );
if( flRand <= 0.75f || m_fSpotActive )
7 years ago
{
8 years ago
if( m_iClip == 0 )
7 years ago
iAnim = RPG_IDLE_UL;
else
iAnim = RPG_IDLE;
m_flTimeWeaponIdle = UTIL_WeaponTimeBase() + 90.0f / 15.0f;
7 years ago
}
else
{
8 years ago
if( m_iClip == 0 )
7 years ago
iAnim = RPG_FIDGET_UL;
else
iAnim = RPG_FIDGET;
m_flTimeWeaponIdle = UTIL_WeaponTimeBase() + 3.0f;
7 years ago
}
SendWeaponAnim( iAnim );
}
else
{
m_flTimeWeaponIdle = UTIL_WeaponTimeBase() + 1.0f;
7 years ago
}
}
void CRpg::UpdateSpot( void )
{
4 years ago
#if !CLIENT_DLL
8 years ago
if( m_fSpotActive )
7 years ago
{
if (m_pPlayer->pev->viewmodel == 0)
return;
8 years ago
if( !m_pSpot )
7 years ago
{
m_pSpot = CLaserSpot::CreateSpot();
}
UTIL_MakeVectors( m_pPlayer->pev->v_angle );
8 years ago
Vector vecSrc = m_pPlayer->GetGunPosition();
7 years ago
Vector vecAiming = gpGlobals->v_forward;
TraceResult tr;
UTIL_TraceLine( vecSrc, vecSrc + vecAiming * 8192.0f, dont_ignore_monsters, ENT( m_pPlayer->pev ), &tr );
8 years ago
7 years ago
UTIL_SetOrigin( m_pSpot, tr.vecEndPos );
}
#endif
}
class CRpgAmmo : public CBasePlayerAmmo
{
void Spawn( void )
8 years ago
{
Precache();
SET_MODEL( ENT( pev ), "models/w_rpgammo.mdl" );
CBasePlayerAmmo::Spawn();
7 years ago
}
void Precache( void )
{
8 years ago
PRECACHE_MODEL( "models/w_rpgammo.mdl" );
PRECACHE_SOUND( "items/9mmclip1.wav" );
7 years ago
}
BOOL AddAmmo( CBaseEntity *pOther )
{
int iGive;
4 years ago
#if CLIENT_DLL
8 years ago
if( bIsMultiplayer() )
7 years ago
#else
8 years ago
if( g_pGameRules->IsMultiplayer() )
7 years ago
#endif
{
// hand out more ammo per rocket in multiplayer.
iGive = AMMO_RPGCLIP_GIVE * 2;
}
else
{
iGive = AMMO_RPGCLIP_GIVE;
}
8 years ago
if( pOther->GiveAmmo( iGive, "rockets", ROCKET_MAX_CARRY ) != -1 )
7 years ago
{
8 years ago
EMIT_SOUND( ENT( pev ), CHAN_ITEM, "items/9mmclip1.wav", 1, ATTN_NORM );
7 years ago
return TRUE;
}
return FALSE;
}
};
LINK_ENTITY_TO_CLASS( ammo_rpgclip, CRpgAmmo )
7 years ago
#endif