void CDestructibleModel::DoExplosion(char* pTargetName)
{
	CWeapons weapons;
	weapons.Init(m_hObject);
	weapons.ObtainWeapon(m_nExplosionWeaponId);
	weapons.ChangeWeapon(m_nExplosionWeaponId);

	CWeapon* pWeapon = weapons.GetCurWeapon();
	if (!pWeapon) return;

	weapons.SetAmmo(pWeapon->GetAmmoId());

	pWeapon->SetDamageFactor(m_fDamageFactor);

	LTRotation rRot;
	g_pLTServer->GetObjectRotation(m_hObject, &rRot);

	LTVector vF, vPos;
	g_pLTServer->GetObjectPos(m_hObject, &vPos);
	vF = rRot.Forward();

	// Just blow up in place if we're not supposed to fire along
	// forward vector and we don't have a target...

	if (!m_bFireAlongForward)
	{
		pWeapon->SetLifetime(0.0f);
		VEC_SET(vF, 0.0f, -1.0f, 0.0f);  // Fire down
	}

	// See if we have a target...If so, point at it.

	if (pTargetName)
	{
		ObjArray <HOBJECT, MAX_OBJECT_ARRAY_SIZE> objArray;
		g_pLTServer->FindNamedObjects(pTargetName, objArray);

		if (objArray.NumObjects())
		{
			LTVector vObjPos;
			g_pLTServer->GetObjectPos(objArray.GetObject(0), &vObjPos);
			vF = vObjPos - vPos;
			vF.Normalize();

			rRot = LTRotation(vF, LTVector(0.0f, 1.0f, 0.0f));
			g_pLTServer->SetObjectRotation(m_hObject, &rRot);
		}
	}

	WeaponFireInfo weaponFireInfo;
	weaponFireInfo.hFiredFrom	= m_hObject;
	weaponFireInfo.vPath		= vF;
	weaponFireInfo.vFirePos	= vPos;
	weaponFireInfo.vFlashPos	= vPos;

	pWeapon->Fire(weaponFireInfo);
}
LTBOOL CAIHelicopterStrategyShoot::Update()
{
	if ( !CAIHelicopterStrategy::Update() )
	{
        return LTFALSE;
	}

	if ( !m_hTarget )
	{
        return LTFALSE;
	}

	for ( int iWeapon = 0 ; iWeapon < GetAI()->GetNumWeapons() ; iWeapon++ )
	{
		CWeapon* pWeapon = GetAI()->GetWeapon(iWeapon);

		if ( m_aBursts[iWeapon].m_bFired && m_aBursts[iWeapon].m_bActive )
		{
			UpdateFiring(pWeapon, &m_aBursts[iWeapon]);

			m_aBursts[iWeapon].m_bFired = LTFALSE;
		}
		else
		{
			UpdateAiming(pWeapon, &m_aBursts[iWeapon]);
		}

		if ( 0 == pWeapon->GetAmmoInClip() )
		{
            pWeapon->ReloadClip(LTFALSE);
		}

		if ( 0 == pWeapon->GetParent()->GetAmmoCount(pWeapon->GetAmmoId()) )
		{
			pWeapon->GetParent()->AddAmmo(pWeapon->GetAmmoId(), 999999);
		}
	}

    return LTTRUE;
}
Exemple #3
0
bool CTronPlayerObj::HandleMessageProjectile( HOBJECT hSender,
                                              ILTMessage_Read *pMsg )
{
	// to check the results of engine functions
	LTRESULT ltResult;

	// get the projectile message's subtype
	uint8 nProjectileMessageSubType = pMsg->Readuint8();

	switch ( nProjectileMessageSubType )
	{
		//case MPROJ_RETURNED:
		// the place where the ammo gets incremented is in CWeapons


		case MPROJ_START_SWAT_BLOCK:
		case MPROJ_START_HOLD_BLOCK:
		case MPROJ_START_ARM_BLOCK:
		{
			// get the rest of the info

			// get the weapon id
			uint8 cAmmoId = pMsg->Readuint8();

			// get the timestamp
			uint32 nDefendTimestamp = pMsg->Readuint8();

			// get the animation length
			uint32 nDefendDuration = pMsg->Readuint8();

			// make sure the current weapon is the weapon
			// being blocked with
			CWeapon* pWeapon = m_pPlayerAttachments->GetWeapon();
			if ( pWeapon->GetAmmoId() != cAmmoId )
			{
				// Tut tut, no cheating!
				//
				// The weapon the user is trying to block with is
				// different from the current weapon.
				ASSERT( 0 );

				return true;
			}

			if ( TRONPLAYEROBJ_NO_DEFEND != m_cDefendType )
			{
				// we are already handling a block, check
				// if the new one is valid
				if ( ( m_nDefendClientTimeStarted + m_nDefendDuration ) >
					 static_cast< int >( nDefendTimestamp ) )
				{
					// Tut, tut, no cheating!
					//
					// The timestamp passed by the client is faster
					// than is allowed.  If this assert is hit check,
					// to make sure a defensive animation isn't getting
					// nixed prematurely.
					ASSERT( 0 );

					return true;
				}
			}

			// we're ok with the new block, setup the info
			m_cDefendType = nProjectileMessageSubType;
			m_nDefendClientTimeStarted = nDefendTimestamp;
			m_nDefendServerTimeStarted =
				static_cast< int >(
					g_pLTServer->GetTime() * 1000.0f
				);
			m_nDefendDuration = nDefendDuration;
			m_cDefendAmmoId = cAmmoId;

			return true;
		}
		break;

		case MPROJ_END_HOLD_BLOCK:
		{
			// get the rest of the info

			// get the weapon id
			uint8 cAmmoId = pMsg->Readuint8();

			// get the timestamp
			uint32 nDefendTimestamp = pMsg->Readuint8();

			// get the animation length
			uint32 nDefendDuration = pMsg->Readuint8();

			// make sure the current weapon is the weapon
			// being blocked with
			CWeapon* pWeapon = m_pPlayerAttachments->GetWeapon();
			if ( pWeapon->GetAmmoId() != cAmmoId )
			{
				// Tut tut, no cheating!
				//
				// The weapon the user is trying to block with is
				// different from the current weapon.
				ASSERT( 0 );

				return true;
			}

			if ( MPROJ_START_HOLD_BLOCK != m_cDefendType )
			{
				// Woa!  We can't end the hold block until
				// after it starts!  Something is out of
				// order, or there's some cheating going on!
				ASSERT( 0 );

				return true;
			}

			if ( ( m_nDefendClientTimeStarted + m_nDefendDuration ) >
				 static_cast< int >( nDefendTimestamp ) )
			{
				// Tut, tut, no cheating!
				//
				// The timestamp passed by the client is faster
				// than is allowed.  If this assert is hit check,
				// to make sure a defensive animation isn't getting
				// nixed prematurely.
				ASSERT( 0 );

				return true;
			}

			// we're ok with the new block, setup the info
			m_cDefendType = nProjectileMessageSubType;
			m_nDefendClientTimeStarted = nDefendTimestamp;
			m_nDefendServerTimeStarted =
				static_cast< int >(
					g_pLTServer->GetTime() * 1000.0f
				);
			m_nDefendDuration = nDefendDuration;
			m_cDefendAmmoId = cAmmoId;

			return true;
		}
		break;

		default:
		{
			// the message will be forwarded through the chain, eventually
			// to the CWeapon attachment where we want it to go

			// reset the message, we don't want to alter it
			pMsg->SeekTo(0);

			// return false, this did NOT handle the message
			return false;
		}
		break;
	};
}