⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 hl1_npc_apache.cpp

📁 hl2 source code. Do not use it illegal.
💻 CPP
📖 第 1 页 / 共 2 页
字号:
// Purpose :
// Input   :
// Output  :
//------------------------------------------------------------------------------

#define CHOPPER_AP_GUN_TIP			0
#define CHOPPER_AP_GUN_BASE			1

#define CHOPPER_BC_GUN_YAW			0
#define CHOPPER_BC_GUN_PITCH		1
#define CHOPPER_BC_POD_PITCH		2

bool CNPC_Apache::FireGun( )
{
	Vector vForward, vRight, vUp;

	AngleVectors( GetAbsAngles(), &vForward, &vUp, &vRight );
		
	Vector posGun;
	QAngle angGun;
	GetAttachment( 1, posGun, angGun );

	Vector vecTarget = (m_vecTargetPosition - posGun);

	VectorNormalize( vecTarget );

	Vector vecOut;

	vecOut.x = DotProduct( vForward, vecTarget );
	vecOut.y = -DotProduct( vUp, vecTarget );
	vecOut.z = DotProduct( vRight, vecTarget );

	QAngle angles;

	VectorAngles( vecOut, angles );
	
	angles.x = -angles.x;
	if (angles.y > 180)
		angles.y = angles.y - 360;
	if (angles.y < -180)
		angles.y = angles.y + 360;
	if (angles.x > 180)
		angles.x = angles.x - 360;
	if (angles.x < -180)
		angles.x = angles.x + 360;

	if (angles.x > m_angGun.x)
		m_angGun.x = min( angles.x, m_angGun.x + 12 );
	if (angles.x < m_angGun.x)
		m_angGun.x = max( angles.x, m_angGun.x - 12 );
	if (angles.y > m_angGun.y)
		m_angGun.y = min( angles.y, m_angGun.y + 12 );
	if (angles.y < m_angGun.y)
		m_angGun.y = max( angles.y, m_angGun.y - 12 );

	m_angGun.y = SetBoneController( 0, m_angGun.y );
	m_angGun.x = SetBoneController( 1, -m_angGun.x );

	Vector posBarrel;
	QAngle angBarrel;
	GetAttachment( 2, posBarrel, angBarrel );
	Vector vecGun = (posGun - posBarrel);
	
	VectorNormalize( vecGun );

//	NDebugOverlay::Line( posBarrel, posBarrel + vecGun * 4098, 0,255,0, false, 0.1);

	if ( DotProduct( vecGun, vecTarget ) > 0.98 )
	{
		CPASAttenuationFilter filter( this, 0.2f );

		enginesound->EmitSound( filter, entindex(), CHAN_WEAPON, "turret/tu_fire1.wav", 1.0, 0.2 );//<<TEMP>>temp sound
		FireBullets( 1, posBarrel, vecGun, VECTOR_CONE_2DEGREES, 8192, m_iAmmoType, 2 );
		return true;
	}

	return false;
}

void CNPC_Apache::FireRocket( void )
{
	static float side = 1.0;
	static int count;
	Vector vForward, vRight, vUp;


	AngleVectors( GetAbsAngles(), &vForward, &vRight, &vUp );
	Vector vecSrc = GetAbsOrigin() + 1.5 * ( vForward * 21 + vRight * 70 * side + vUp * -79 );

	// pick firing pod to launch from
	switch( m_iRockets % 5)
	{
	case 0:	vecSrc = vecSrc + vRight * 10; break;
	case 1: vecSrc = vecSrc - vRight * 10; break;
	case 2: vecSrc = vecSrc + vUp * 10; break;
	case 3: vecSrc = vecSrc - vUp * 10; break;
	case 4: break;
	}

	Vector vTargetDir = m_vecTargetPosition - GetAbsOrigin();
	VectorNormalize ( vTargetDir );
	LaunchRocket( vTargetDir, 100, 150, vecSrc);

	m_iRockets--;

	side = - side;
}
void CNPC_Apache::AimRocketGun( void )
{
	Vector vForward, vRight, vUp;
	
	if (m_iRockets <= 0)
		return;
	
	Vector vTargetDir = m_vecTargetPosition - GetAbsOrigin();
	VectorNormalize ( vTargetDir );

	AngleVectors( GetAbsAngles(), &vForward, &vRight, &vUp );
	Vector vecEst = ( vForward * 800 + GetAbsVelocity());
	VectorNormalize ( vecEst );

	trace_t tr1;
	UTIL_TraceLine( GetAbsOrigin(), GetAbsOrigin() + vecEst * 4096, MASK_ALL, this, COLLISION_GROUP_NONE, &tr1);

//	NDebugOverlay::Line(GetAbsOrigin(), tr1.endpos, 255,255,0, false, 0.1);

	UTIL_TraceLine( GetAbsOrigin(), GetAbsOrigin() + vTargetDir * 4096, MASK_ALL, this, COLLISION_GROUP_NONE, &tr1);

//	NDebugOverlay::Line(GetAbsOrigin(), tr1.endpos, 0,255,0, false, 0.1);

	// ALERT( at_console, "%d %d %d %4.2f\n", GetAbsAngles().x < 0, DotProduct( pev->velocity, gpGlobals->v_forward ) > -100, m_flNextRocket < gpGlobals->curtime, DotProduct( m_vecTarget, vecEst ) );

	if ((m_iRockets % 2) == 1)
	{
		FireRocket( );
		m_flNextRocket = gpGlobals->curtime + 0.5;
		if (m_iRockets <= 0)
		{
			m_flNextRocket = gpGlobals->curtime + 10;
			m_iRockets = 10;
		}
	}
	else if (DotProduct( GetAbsVelocity(), vForward ) > -100 && m_flNextRocket < gpGlobals->curtime)
	{
		if (m_flLastSeen + 60 > gpGlobals->curtime)
		{
			if (GetEnemy() != NULL)
			{
				// make sure it's a good shot
				//if (DotProduct( vTargetDir, vecEst) > 0.5)
				{
					trace_t tr;
					
					UTIL_TraceLine( GetAbsOrigin(), GetAbsOrigin() + vecEst * 4096, MASK_ALL, this, COLLISION_GROUP_NONE, &tr);

			//		NDebugOverlay::Line(GetAbsOrigin(), tr.endpos, 255,0,255, false, 5);

//					if ((tr.endpos - m_vecTargetPosition).Length() < 512)
					if ((tr.endpos - m_vecTargetPosition).Length() < 1024)
						FireRocket( );
				}
			}
			else
			{
				trace_t tr;
				
				UTIL_TraceLine( GetAbsOrigin(), GetAbsOrigin() + vecEst * 4096, MASK_ALL, this, COLLISION_GROUP_NONE, &tr);
				// just fire when close
				if ((tr.endpos - m_vecTargetPosition).Length() < 512)
					FireRocket( );
			}
		}
	}
}

#define MISSILE_HOMING_STRENGTH		0.3
#define MISSILE_HOMING_DELAY		5.0
#define MISSILE_HOMING_RAMP_UP		0.5
#define MISSILE_HOMING_DURATION		1.0
#define MISSILE_HOMING_RAMP_DOWN	0.5

void CNPC_Apache::LaunchRocket( Vector &viewDir, int damage, int radius, Vector vecLaunchPoint )
{

	CGrenadeHomer *pGrenade = CGrenadeHomer::CreateGrenadeHomer( MAKE_STRING("models/weapons/w_missile.mdl"), MAKE_STRING("weapons/stinger_fire1.wav"), vecLaunchPoint, vec3_angle, edict() );
	pGrenade->Spawn( );
	pGrenade->SetHoming(MISSILE_HOMING_STRENGTH, MISSILE_HOMING_DELAY,
						MISSILE_HOMING_RAMP_UP,	MISSILE_HOMING_DURATION,
						MISSILE_HOMING_RAMP_DOWN);
	pGrenade->SetDamage( damage );
	pGrenade->m_DmgRadius = radius;

	pGrenade->Launch( this, GetEnemy(), viewDir * 1500, 500, 0, HOMER_SMOKE_TRAIL_ON );

}


//-----------------------------------------------------------------------------
// Purpose:	Lame, temporary death
//-----------------------------------------------------------------------------
void CNPC_Apache::DyingThink( void )
{
	StudioFrameAdvance( );
	SetNextThink( gpGlobals->curtime + 0.1f );

	if( random->RandomInt( 0, 50 ) == 1 )
	{
		Vector vecSize = Vector( 60, 60, 30 );
		CPVSFilter filter( GetAbsOrigin() );
		te->BreakModel( filter, 0.0, &GetAbsOrigin(), &vecSize, &vec3_origin, m_nDebrisModel, 100, 0, 2.5, BREAK_METAL );
	}

	QAngle angVel = GetLocalAngularVelocity();
	if( angVel.y < 400 )
	{
		angVel.y *= 1.1;
		SetLocalAngularVelocity( angVel );
	}
	Vector vecImpulse( 0, 0, 0 );
	// add gravity
	vecImpulse.z -= 38.4; // 32ft/sec
	ApplyAbsVelocityImpulse( vecImpulse );

}





//**************************************************************************************
class CApacheHVR : public CHL1BaseGrenade
{
	DECLARE_CLASS( CApacheHVR, CHL1BaseGrenade );

	void Spawn( void );
	void Precache( void );
	void IgniteThink( void );
	void AccelerateThink( void );
	void StartRocketTrail( void );
	void Detonate( CBaseEntity *pOther );

	DECLARE_DATADESC();

	int m_iTrail;
	Vector m_vecForward;

	float m_flDamage;
	EHANDLE		m_hSmokeTrail[2];
};
LINK_ENTITY_TO_CLASS( hvr_rocket, CApacheHVR );

BEGIN_DATADESC( CApacheHVR )
//	DEFINE_FIELD( CApacheHVR, m_iTrail, FIELD_INTEGER ),	// Dont' save, precache
	DEFINE_FIELD( CApacheHVR, m_vecForward, FIELD_VECTOR ),
	DEFINE_FUNCTION( CApacheHVR, IgniteThink ),
	DEFINE_FUNCTION( CApacheHVR, AccelerateThink ),
	DEFINE_FUNCTION( CApacheHVR, Detonate ),
END_DATADESC()


void CApacheHVR::StartRocketTrail( void )
{
	SmokeTrail *pSmokeTrail =  SmokeTrail::CreateSmokeTrail();

	if( pSmokeTrail )
	{
		pSmokeTrail->m_SpawnRate = 500;
		pSmokeTrail->m_ParticleLifetime = HOMER_TRAIL0_LIFE;
		pSmokeTrail->m_StartColor.Init(0.7, 0.7, 0.7);
		pSmokeTrail->m_EndColor.Init(0.5,0.5,0.5);
		pSmokeTrail->m_StartSize = 10;
		pSmokeTrail->m_EndSize = 10;
		pSmokeTrail->m_SpawnRadius = 1;
		pSmokeTrail->m_MinSpeed = 15;
		pSmokeTrail->m_MaxSpeed = 25;
		pSmokeTrail->SetLifetime(12);
		pSmokeTrail->FollowEntity(ENTINDEX(pev));

		m_hSmokeTrail[0] = pSmokeTrail;
	}

	pSmokeTrail = SmokeTrail::CreateSmokeTrail();

	if( pSmokeTrail )
	{
		pSmokeTrail->m_SpawnRate = 150;
		pSmokeTrail->m_ParticleLifetime = HOMER_TRAIL2_LIFE;
		pSmokeTrail->m_StartColor.Init(0.7, 0.7, 0.7);
		pSmokeTrail->m_EndColor.Init(0.5,0.5,0.5);
		pSmokeTrail->m_StartSize = 12;
		pSmokeTrail->m_EndSize = 20;
		pSmokeTrail->m_SpawnRadius = 1;
		pSmokeTrail->m_MinSpeed = 15;
		pSmokeTrail->m_MaxSpeed = 25;
		pSmokeTrail->SetLifetime(12);
		pSmokeTrail->FollowEntity(ENTINDEX(pev));

		m_hSmokeTrail[1] = pSmokeTrail;
	}
}

void CApacheHVR :: Detonate ( CBaseEntity *pOther )
{
	for ( int i = 0; i < 2; i++ )
	{
		if( m_hSmokeTrail[i] )
		  ((SmokeTrail*)(CBaseEntity*)m_hSmokeTrail[i])->SetEmit(false);
	}	

	ExplodeTouch( pOther );
	
}
void CApacheHVR :: Spawn( void )
{
	Precache( );
	// motor
	SetSolid( SOLID_BBOX );
	SetMoveType( MOVETYPE_FLY );

	SetModel( "models/HVR.mdl" );
	UTIL_SetSize(this, Vector( 0, 0, 0), Vector(0, 0, 0));
	UTIL_SetOrigin( this, GetAbsOrigin() );

	SetThink( IgniteThink );
	SetTouch( Detonate );

	
	AngleVectors( GetAbsAngles(), &m_vecForward );
	SetGravity( 0.5 );

	SetNextThink( gpGlobals->curtime + 0.1f );

	m_flDamage = 150;
}


void CApacheHVR :: Precache( void )
{
	engine->PrecacheModel( "models/HVR.mdl" );
	m_iTrail = engine->PrecacheModel( "sprites/smoke.spr" );
	enginesound->PrecacheSound ( "weapons/rocket1.wav" );
}

void TE_BeamFollow( int msg_dest, float delay, const Vector *origin, const edict_t *recipient, int iEntIndex,
	int modelIndex, int haloIndex, float haloScale, float life, float width, float endWidth, 
	float fadeLength,float r, float g, float b, float a, float brightness );

void CApacheHVR :: IgniteThink( void  )
{
	// make rocket sound
	CPASAttenuationFilter filter( this, 0.5f );
	enginesound->EmitSound( filter, entindex(), CHAN_VOICE, "weapons/rocket1.wav", 1, 0.5 );

	StartRocketTrail();

	// set to accelerate
	SetThink( AccelerateThink );
	SetNextThink( gpGlobals->curtime + 0.1f );
}


void CApacheHVR :: AccelerateThink( void  )
{
	// check world boundaries
	if ( GetAbsOrigin().x < -4096 || GetAbsOrigin().x > 4096 || GetAbsOrigin().y < -4096 || GetAbsOrigin().y > 4096 || GetAbsOrigin().z < -4096 || GetAbsOrigin().z > 4096 )
	{
		 UTIL_Remove( this );
		 return;
	}

	// accelerate
	float flSpeed = GetAbsVelocity().Length();

	if ( flSpeed < 1800 )
	{
		 SetAbsVelocity( GetAbsVelocity() + m_vecForward * 200 );
	}

	Vector vVel = GetAbsVelocity();
	VectorNormalize ( vVel );

	QAngle angTmp;
	VectorAngles( vVel, angTmp );
	SetAbsAngles( angTmp );

	SetNextThink( gpGlobals->curtime + 0.1f );
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -