//----------------------------------------------------------------------------- // Purpose: Detach the player from the "Buff Station." //----------------------------------------------------------------------------- void CObjectBuffStation::DetachPlayerByIndex( int nIndex ) { // Valid index? Assert( nIndex < BUFF_STATION_MAX_PLAYERS ); // Get the player. CBaseTFPlayer *pPlayer = m_hPlayers[nIndex].Get(); if ( !pPlayer ) { m_hPlayers.Set( nIndex, NULL ); return; } // Remove the damage modifier. m_aPlayerAttachInfo[nIndex].m_DamageModifier.RemoveModifier(); // Remove the rope (cable). if ( m_aPlayerAttachInfo[nIndex].m_hRope.Get() ) { m_aPlayerAttachInfo[nIndex].m_hRope->DetachPoint( 1 ); m_aPlayerAttachInfo[nIndex].m_hRope->DieAtNextRest(); } // Unconstrain the player movement. pPlayer->DeactivateMovementConstraint(); // Keep track of player events. g_pNotify->RemoveEntity( this, pPlayer ); // Reduce player count. m_nPlayerCount--; m_hPlayers.Set( nIndex, NULL ); }
static bool IsValidFn_PlayersWantingAssist( void *pUserData, int a ) { CSortBase *pSortBase = (CSortBase*)pUserData; CBaseTFPlayer *pPlayer = (CBaseTFPlayer*)pSortBase->m_pPlayer->GetTeam()->GetPlayer( a ); if ( !pPlayer->IsAlive() ) { // This guy sure could have used an assist but YOU'RE TOO SLOW!!! return false; } // Don't try to assist yourself... if ( pPlayer == pSortBase->m_pPlayer ) return false; // Make sure this guy was shot recently. if ( (gpGlobals->curtime - pPlayer->LastTimeDamagedByEnemy()) > COMMANDO_ASSIST_SHOT_DELAY ) return false; // Is the guy close enough? if ( pSortBase->m_pPlayer->GetAbsOrigin().DistToSqr( pPlayer->GetAbsOrigin() ) > COMMAND_ASSIST_DISTANCE_SQR ) return false; return true; }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- float CWeaponCombatBurstRifle::GetFireRate( void ) { if ( !inv_demo.GetFloat() ) { float flFireRate = ( SequenceDuration() * 0.6f ) + SHARED_RANDOMFLOAT( 0.0, 0.035f ); CBaseTFPlayer *pPlayer = static_cast<CBaseTFPlayer*>( GetOwner() ); if ( pPlayer ) { // Ducking players should fire more rapidly. if ( pPlayer->GetFlags() & FL_DUCKING ) { flFireRate *= weapon_combat_burstrifle_ducking_mod.GetFloat(); } } return flFireRate; } // Get the player and check to see if we are powered up. CBaseTFPlayer *pPlayer = ( CBaseTFPlayer* )GetOwner(); if ( pPlayer && pPlayer->HasPowerup( POWERUP_BOOST ) ) { return BURSTRIFLE_BOOSTED_FIRERATE; } return SHARED_RANDOMFLOAT( 0.075f, 0.15f ); }
//----------------------------------------------------------------------------- // New technologies: //----------------------------------------------------------------------------- void CWeaponCombat_ChargeablePlasma::GainedNewTechnology( CBaseTechnology *pTechnology ) { BaseClass::GainedNewTechnology( pTechnology ); CBaseTFPlayer *pPlayer = ToBaseTFPlayer( (CBaseEntity*)GetOwner() ); if ( pPlayer ) { // Charge-up mode? if ( pPlayer->HasNamedTechnology( "com_comboshield_charge" ) ) { m_bHasCharge = true; } else { m_bHasCharge = false; } // Burst shot mode? if ( pPlayer->HasNamedTechnology( "com_comboshield_tripleshot" ) ) { m_bHasBurstShot = true; } else { m_bHasBurstShot = false; } } }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CGrenadeRocket::MissileTouch( CBaseEntity *pOther ) { Assert( pOther ); if ( !pOther->IsSolid() ) return; Vector vecAbsOrigin = GetAbsOrigin(); CPASFilter filter( vecAbsOrigin ); te->Explosion( filter, 0.0, &vecAbsOrigin, g_sModelIndexFireball, 2.0, 15, TE_EXPLFLAG_NONE, 100, m_flDamage ); StopSound( "GrenadeRocket.FlyLoop" ); // Don't apply explosive damage if it hit a shield of any kind... bool bHittingShield = false; if (pOther->GetCollisionGroup() == TFCOLLISION_GROUP_SHIELD) { bHittingShield = true; } else if ( pOther->IsPlayer() ) { CBaseTFPlayer *pPlayer = static_cast<CBaseTFPlayer*>(pOther); trace_t tr; float flDamage = m_flDamage; bHittingShield = pPlayer->IsHittingShield( GetAbsVelocity(), &flDamage ); } if (!bHittingShield) { RadiusDamage( CTakeDamageInfo( this, m_pRealOwner, m_flDamage, DMG_BLAST ), vecAbsOrigin, 100, CLASS_NONE ); } UTIL_Remove( this ); }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CWeaponCombatLaserRifle::PrimaryAttack( void ) { CBaseTFPlayer *pPlayer = (CBaseTFPlayer*)GetOwner(); if (!pPlayer) return; WeaponSound(SINGLE); // Fire the bullets Vector vecSrc = pPlayer->Weapon_ShootPosition( ); Vector vecAiming; pPlayer->EyeVectors( &vecAiming ); PlayAttackAnimation( GetPrimaryAttackActivity() ); // Reduce the spread if the player's ducking Vector vecSpread = GetBulletSpread(); vecSpread *= m_flInaccuracy; TFGameRules()->FireBullets( CTakeDamageInfo( this, pPlayer, weapon_combat_laserrifle_damage.GetFloat(), DMG_PLASMA), 1, vecSrc, vecAiming, vecSpread, weapon_combat_laserrifle_range.GetFloat(), m_iPrimaryAmmoType, 0, entindex(), 0 ); m_flInaccuracy += 0.3; m_flInaccuracy = clamp(m_flInaccuracy, 0, 1); m_flNextPrimaryAttack = gpGlobals->curtime + GetFireRate(); m_iClip1 = m_iClip1 - 1; }
//----------------------------------------------------------------------------- // Purpose: Try and find an entity to lock onto //----------------------------------------------------------------------------- CBaseEntity *CWeaponCombat_ChargeablePlasma::GetLockTarget( void ) { CBaseTFPlayer *pPlayer = (CBaseTFPlayer*)GetOwner(); if ( !pPlayer ) return NULL; Vector vecSrc = pPlayer->Weapon_ShootPosition( ); Vector vecAiming; pPlayer->EyeVectors( &vecAiming ); Vector vecEnd = vecSrc + vecAiming * MAX_TRACE_LENGTH; trace_t tr; TFGameRules()->WeaponTraceLine( vecSrc, vecEnd, MASK_SHOT, pPlayer, GetDamageType(), &tr ); if ( (tr.fraction < 1.0f) && tr.m_pEnt ) { CBaseEntity *pTargetEntity = tr.m_pEnt; // Don't guide on same team or on anything other than players, objects, and NPCs if ( pTargetEntity->InSameTeam(pPlayer) || (!pTargetEntity->IsPlayer() && (pTargetEntity->MyNPCPointer() == NULL)) ) return NULL; // Compute the target offset relative to the target Vector vecWorldOffset; VectorSubtract( tr.endpos, pTargetEntity->GetAbsOrigin(), vecWorldOffset ); VectorIRotate( vecWorldOffset, pTargetEntity->EntityToWorldTransform(), m_vecTargetOffset ); m_flLockedAt = gpGlobals->curtime + 0.2; return pTargetEntity; } return NULL; }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CWeaponBuilder::ItemPostFrame( void ) { CBaseTFPlayer *pOwner = ToBaseTFPlayer( GetOwner() ); if ( !pOwner ) return; // Ignore input while the player's building anything if ( pOwner->IsBuilding() ) return; // Switch away if I'm not in placement mode if ( m_iBuildState != BS_PLACING && m_iBuildState != BS_PLACING_INVALID ) { pOwner->SwitchToNextBestWeapon( NULL ); return; } if (( pOwner->m_nButtons & IN_ATTACK ) && (m_flNextPrimaryAttack <= gpGlobals->curtime) ) { PrimaryAttack(); } // Allow shield post frame AllowShieldPostFrame( true ); WeaponIdle(); }
//----------------------------------------------------------------------------- // Purpose: Place the combat object //----------------------------------------------------------------------------- void CWeaponBaseCombatObject::PrimaryAttack( void ) { CBaseTFPlayer *pPlayer = dynamic_cast<CBaseTFPlayer*>((CBaseEntity*)GetOwner()); if ( !pPlayer ) return; if ( pPlayer->GetAmmoCount(m_iPrimaryAmmoType) <= 0 ) return; m_flNextPrimaryAttack = gpGlobals->curtime + GetFireRate(); Vector vecPlaceOrigin; QAngle angPlaceAngles; if ( GetPlacePosition( pPlayer, &vecPlaceOrigin, &angPlaceAngles ) == false ) { WeaponSound( DOUBLE ); return; } // Place the combat object PlaceCombatObject( pPlayer, vecPlaceOrigin, angPlaceAngles ); WeaponSound( SINGLE ); pPlayer->RemoveAmmo( 1, m_iPrimaryAmmoType ); // If I'm now out of ammo, switch away if ( !HasPrimaryAmmo() ) { pPlayer->SelectLastItem(); } }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CWeaponCombatPlasmaGrenadeLauncher::PrimaryAttack( void ) { CBaseTFPlayer *pPlayer = (CBaseTFPlayer*)GetOwner(); if (!pPlayer) return; WeaponSound(SINGLE); // Fire the bullets Vector vecSrc = pPlayer->Weapon_ShootPosition( ); PlayAttackAnimation( GetPrimaryAttackActivity() ); // Launch the grenade Vector vecForward; pPlayer->EyeVectors( &vecForward ); Vector vecOrigin = pPlayer->EyePosition(); vecOrigin += (vecForward); #if !defined( CLIENT_DLL ) float flSpeed = 1200; CGrenadeAntiPersonnel* pGrenade = CGrenadeAntiPersonnel::Create(vecOrigin, vecForward * flSpeed, pPlayer ); pGrenade->SetModel( "models/weapons/w_grenade.mdl" ); pGrenade->SetBounceSound( "PlasmaGrenade.Bounce" ); pGrenade->SetDamage( weapon_combat_plasmagrenadelauncher_damage.GetFloat() ); pGrenade->SetDamageRadius( weapon_combat_plasmagrenadelauncher_radius.GetFloat() ); pGrenade->SetExplodeOnContact( true ); #endif m_flNextPrimaryAttack = gpGlobals->curtime + GetFireRate(); m_iClip1 = m_iClip1 - 1; }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CPlayerClassCommando::BullRushTouch( CBaseEntity *pTouched ) { if ( pTouched->IsPlayer() && !pTouched->InSameTeam( m_pPlayer ) ) { // Get the player. CBaseTFPlayer *pTFPlayer = ( CBaseTFPlayer* )pTouched; // Check to see if we have "touched" this player already this bullrush cycle. if ( m_aHitPlayers.Find( pTFPlayer ) != -1 ) return; // Hitting the player now. m_aHitPlayers.AddToTail( pTFPlayer ); // ROBIN: Bullrush now instantly kills again float flDamage = 200; // Calculate the damage a player takes based on distance(time). //float flDamage = 1.0f - ( ( COMMANDO_BULLRUSH_TIME - m_ClassData.m_flBullRushTime ) * ( 1.0f / COMMANDO_BULLRUSH_TIME ) ); //flDamage *= 115.0f; // max bullrush damage trace_t tr = m_pPlayer->GetTouchTrace(); CTakeDamageInfo info( m_pPlayer, m_pPlayer, flDamage, DMG_CLUB, DMG_KILL_BULLRUSH ); CalculateMeleeDamageForce( &info, (tr.endpos - tr.startpos), tr.endpos ); pTFPlayer->TakeDamage( info ); CPASAttenuationFilter filter( m_pPlayer, "Commando.BullRushFlesh" ); CBaseEntity::EmitSound( filter, m_pPlayer->entindex(), "Commando.BullRushFlesh" ); pTFPlayer->Touch( m_pPlayer ); } }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CBaseTFVehicle::FinishedBuilding( void ) { BaseClass::FinishedBuilding(); // See if we've finished building on a vehicle that has a passenger slot assigned to my buildpoint. CBaseObject *pParent = GetParentObject(); if ( pParent && pParent->IsAVehicle() ) { CBaseTFVehicle *pVehicle = static_cast<CBaseTFVehicle*>(pParent); int iRole = pVehicle->GetChildVehicleRole( this ); if ( iRole != -1 ) { // Is there a player in the role assigned to this buildpoint? CBaseTFPlayer *pExistingPlayer = static_cast<CBaseTFPlayer*>( pVehicle->GetPassenger( iRole ) ); if ( pExistingPlayer ) { // Remove the player from my parent vehicle and put them in me pExistingPlayer->LeaveVehicle(); // Get in the vehicle. pExistingPlayer->GetInVehicle( this, VEHICLE_DRIVER ); } } } }
//----------------------------------------------------------------------------- // Purpose: Check to see if our target has moved beyond our length //----------------------------------------------------------------------------- void CHarpoon::ConstrainThink( void ) { if ( !GetImpaledTarget() || !m_hLinkedHarpoon.Get() ) return; // Moved too far away? float flDistSq = m_hLinkedHarpoon->GetAbsOrigin().DistToSqr( GetImpaledTarget()->GetAbsOrigin() ); if ( flDistSq > m_flConstrainLength ) { // Break the rope if ( m_hRope ) { m_hRope->DetachPoint(1); m_hRope->DieAtNextRest(); m_hRope = NULL; } // If we're impaling a player, remove his movement constraint if ( GetImpaledTarget()->IsPlayer() ) { CBaseTFPlayer *pPlayer = (CBaseTFPlayer *)GetImpaledTarget(); pPlayer->DeactivateMovementConstraint(); } SetThink( NULL ); } else { SetNextThink( gpGlobals->curtime + 0.1f ); } }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CWeaponCombatLaserRifle::RecalculateAccuracy( void ) { CBaseTFPlayer *pPlayer = (CBaseTFPlayer*)GetOwner(); if (!pPlayer) return; m_flAccuracyTime += gpGlobals->frametime; while ( m_flAccuracyTime > 0.05 ) { if ( !(pPlayer->GetFlags() & FL_ONGROUND) ) { m_flInaccuracy += 0.05; } else if ( pPlayer->GetFlags() & FL_DUCKING ) { m_flInaccuracy -= 0.08; } /* else if ( pPlayer->GetLocalVelocity().LengthSqr() > (100*100) ) { // Never get worse than 1/2 accuracy from running if ( m_flInaccuracy < 0.25 ) { m_flInaccuracy += 0.01; if ( m_flInaccuracy > 0.5 ) { m_flInaccuracy = 0.5; } } else if ( m_flInaccuracy > 0.25 ) { m_flInaccuracy -= 0.01; } } */ else { m_flInaccuracy -= 0.04; } // Crouching prevents accuracy ever going beyond a point if ( pPlayer->GetFlags() & FL_DUCKING ) { m_flInaccuracy = clamp(m_flInaccuracy, 0, 0.8); } else { m_flInaccuracy = clamp(m_flInaccuracy, 0, 1); } m_flAccuracyTime -= 0.05; #ifndef CLIENT_DLL //if ( m_flInaccuracy ) //Msg("Inaccuracy %.2f (%.2f)\n", m_flInaccuracy, gpGlobals->curtime ); #endif } }
/* =========== ClientPutInServer called each time a player is spawned into the game ============ */ void ClientPutInServer( edict_t *pEdict, const char *playername ) { // Allocate a CBaseTFPlayer for pev, and call spawn CBaseTFPlayer *pPlayer = CBaseTFPlayer::CreatePlayer( "player", pEdict ); pPlayer->InitialSpawn(); pPlayer->SetPlayerName( playername ); pPlayer->Spawn(); }
//----------------------------------------------------------------------------- // Purpose: This is called pre player movement and copies all the data necessary // from the player for movement. (Server-side, the client-side version // of this code can be found in prediction.cpp.) //----------------------------------------------------------------------------- void CTFPlayerMove::SetupMove( CBasePlayer *player, CUserCmd *ucmd, IMoveHelper *pHelper, CMoveData *move ) { // Call the default SetupMove code. BaseClass::SetupMove( player, ucmd, pHelper, move ); // // Convert to TF2 data. // CBaseTFPlayer *pTFPlayer = static_cast<CBaseTFPlayer*>( player ); Assert( pTFPlayer ); CTFMoveData *pTFMove = static_cast<CTFMoveData*>( move ); Assert( pTFMove ); // // Player movement data. // // Copy the position delta. pTFMove->m_vecPosDelta = pTFPlayer->m_vecPosDelta; // Copy the momentum data. pTFMove->m_iMomentumHead = pTFPlayer->m_iMomentumHead; for ( int iMomentum = 0; iMomentum < CTFMoveData::MOMENTUM_MAXSIZE; iMomentum++ ) { pTFMove->m_aMomentum[iMomentum] = pTFPlayer->m_aMomentum[iMomentum]; } pTFMove->m_nClassID = pTFPlayer->PlayerClass(); IVehicle *pVehicle = player->GetVehicle(); if (!pVehicle) { // Handle player class specific setup. switch( pTFPlayer->PlayerClass() ) { case TFCLASS_RECON: { SetupMoveRecon( pTFPlayer, ucmd, pHelper, pTFMove ); break; } case TFCLASS_COMMANDO: { SetupMoveCommando( pTFPlayer, ucmd, pHelper, pTFMove ); break; } default: { // pTFMove->m_nClassID = TFCLASS_UNDECIDED; break; } } } else { pVehicle->SetupMove( player, ucmd, pHelper, move ); } }
//----------------------------------------------------------------------------- // Purpose: Check to see if we've got a linked harpoon, and see if we should constrain something //----------------------------------------------------------------------------- void CHarpoon::CheckLinkedHarpoon( void ) { if ( m_hLinkedHarpoon ) { CHarpoon *pPlayerHarpoon = NULL; CHarpoon *pNonMovingHarpoon = NULL; // Find out if either of us has impaled something if ( GetImpaledTarget() && m_hLinkedHarpoon->GetImpaledTarget() ) { // Only care about players for now. One of the targets must be a player. CBaseTFPlayer *pPlayer = NULL; CBaseEntity *pOtherTarget = NULL; if ( GetImpaledTarget()->IsPlayer() ) { pPlayer = (CBaseTFPlayer*)GetImpaledTarget(); pPlayerHarpoon = this; pNonMovingHarpoon = m_hLinkedHarpoon; } else if ( m_hLinkedHarpoon->GetImpaledTarget()->IsPlayer() ) { pPlayer = (CBaseTFPlayer*)m_hLinkedHarpoon->GetImpaledTarget(); pNonMovingHarpoon = this; pPlayerHarpoon = m_hLinkedHarpoon; } // Found a player? if ( pPlayer ) { pOtherTarget = pNonMovingHarpoon->GetImpaledTarget(); // For now, we have to be linked to a non-moving target. Eventually we could support linked moving targets. // pOtherTarget == NULL means the harpoon's buried in the world. if ( pOtherTarget->IsBSPModel() || pOtherTarget->GetMoveType() == MOVETYPE_NONE ) { // Add a little slack m_flConstrainLength = ( m_hLinkedHarpoon->GetAbsOrigin() - GetAbsOrigin() ).Length() + 150; pPlayer->ActivateMovementConstraint( NULL, pNonMovingHarpoon->GetAbsOrigin(), m_flConstrainLength, 150.0f, 0.1f ); // Square it for later checking m_flConstrainLength *= m_flConstrainLength; // Start checking the length pPlayerHarpoon->m_flConstrainLength = m_flConstrainLength; pPlayerHarpoon->SetThink( ConstrainThink ); pPlayerHarpoon->SetNextThink( gpGlobals->curtime + 0.1f ); // Make the rope taught, and prevent it resizing if ( m_hRope ) { m_hRope->m_RopeFlags &= ~ROPE_RESIZE; m_hRope->RecalculateLength(); } } } } } }
//----------------------------------------------------------------------------- // Purpose: Handle deploying, undeploying, firing, etc. // TODO: Add a deploy to the firing! Currently no reloading! //----------------------------------------------------------------------------- void CWeaponRocketLauncher::ItemPostFrame( void ) { // Get the player. CBaseTFPlayer *pPlayer = ToBaseTFPlayer( GetOwner() ); if ( !pPlayer ) return; if ( UsesClipsForAmmo1() ) { CheckReload(); } #if !defined( CLIENT_DLL ) if ( !HasPrimaryAmmo() && ( m_flNextPrimaryAttack <= gpGlobals->curtime ) ) { pPlayer->SwitchToNextBestWeapon( NULL ); } #endif // Handle Firing if ( GetShieldState() == SS_DOWN && !m_bInReload ) { // Attempting to fire. if ( ( pPlayer->m_nButtons & IN_ATTACK ) && ( m_flNextPrimaryAttack <= gpGlobals->curtime ) ) { if ( m_iClip1 > 0 ) { PrimaryAttack(); } else { Reload(); } } // Reload button (or fire button when we're out of ammo) if ( m_flNextPrimaryAttack <= gpGlobals->curtime ) { if ( pPlayer->m_nButtons & IN_RELOAD ) { Reload(); } else if ( !((pPlayer->m_nButtons & IN_ATTACK) || (pPlayer->m_nButtons & IN_ATTACK2) || (pPlayer->m_nButtons & IN_RELOAD)) ) { if ( !m_iClip1 && HasPrimaryAmmo() ) { Reload(); } } } } // Prevent shield post frame if we're not ready to attack, or we're charging AllowShieldPostFrame( m_flNextPrimaryAttack <= gpGlobals->curtime || m_bInReload ); }
//----------------------------------------------------------------------------- // Purpose: Figure out if I should be using an attached item rather than this vehicle itself. //----------------------------------------------------------------------------- bool CBaseTFVehicle::UseAttachedItem( CBaseEntity *pActivator, CBaseEntity *pCaller, USE_TYPE useType, float value ) { CBaseTFPlayer* pPlayer = dynamic_cast<CBaseTFPlayer*>(pActivator); if ( !pPlayer || !InSameTeam(pPlayer) ) return false; Vector vecPlayerOrigin = pPlayer->GetAbsOrigin(); int nBestBuildPoint = -1; float fBestDistance = FLT_MAX; // Get the closest regular entry point: int nRole = LocateEntryPoint( pPlayer, &fBestDistance ); // Iterate through each of the build points, if any, and see which we are closest to. int nBuildPoints = GetNumBuildPoints(); for( int i = 0; i < nBuildPoints; i++ ) { CBaseObject* pObject = GetBuildPointObject(i); // If there's something in the build point that isn't in the process of being built or placed: if( pObject && !pObject->IsPlacing() && !pObject->IsBuilding() ) { Vector vecOrigin; QAngle vecAngles; // If the build point is the default point for this role, just take it if (GetBuildPointPassenger(i) == nRole) { nBestBuildPoint = i; break; } // And I can get the build point. if( GetBuildPoint( i, vecOrigin, vecAngles ) ) { float fLength2dSqr = (vecOrigin - vecPlayerOrigin).AsVector2D().LengthSqr(); if( fLength2dSqr < fBestDistance ) { nBestBuildPoint = i; fBestDistance = fLength2dSqr; } } } } if( nBestBuildPoint >= 0 ) { // They're using an item on me, so push out the deterioration time ResetDeteriorationTime(); GetBuildPointObject(nBestBuildPoint)->Use( pActivator, pCaller, useType, value ); return true; } return false; }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CWeaponBuilder::UpdateOnRemove( void ) { // Tell the player he's lost his build weapon CBaseTFPlayer *pOwner = ToBaseTFPlayer( GetOwner() ); if ( pOwner && pOwner->GetWeaponBuilder() == this ) { pOwner->SetWeaponBuilder( NULL ); } // Chain at end to mimic destructor unwind order BaseClass::UpdateOnRemove(); }
//----------------------------------------------------------------------------- // Purpose: Run through all the Bots in the game and let them think. //----------------------------------------------------------------------------- void Bot_RunAll( void ) { for ( int i = 1; i <= gpGlobals->maxClients; i++ ) { CBaseTFPlayer *pPlayer = ToBaseTFPlayer( UTIL_PlayerByIndex( i ) ); if ( pPlayer && (pPlayer->GetFlags() & FL_FAKECLIENT) ) { Bot_Think( pPlayer ); } } }
//----------------------------------------------------------------------------- // Boost those attached to me as long as I'm not EMPed //----------------------------------------------------------------------------- void CObjectBuffStation::BoostPlayerThink( void ) { // Are we emped? bool bIsEmped = HasPowerup( POWERUP_EMP ); // Get range (squared = faster test). float flMaxRangeSq = obj_buff_station_range.GetFloat(); flMaxRangeSq *= flMaxRangeSq; // Boost all attached players and objects. for ( int iPlayer = 0; iPlayer < BUFF_STATION_MAX_PLAYERS; iPlayer++ ) { // Clean up dangling pointers + dead players, subversion, disconnection CBaseTFPlayer *pPlayer = m_hPlayers[iPlayer].Get(); if ( !pPlayer || !pPlayer->IsAlive() || !InSameTeam( pPlayer ) || !pPlayer->PlayerClass() ) { DetachPlayerByIndex( iPlayer ); continue; } // Check for out of range. float flDistSq = GetAbsOrigin().DistToSqr( pPlayer->GetAbsOrigin() ); if ( flDistSq > flMaxRangeSq ) { DetachPlayerByIndex( iPlayer ); continue; } bool bBoosted = false; if ( !bIsEmped ) { float flHealAmount = obj_buff_station_heal_rate.GetFloat() * BUFF_STATION_BOOST_PLAYER_THINK_INTERVAL; bBoosted = pPlayer->AttemptToPowerup( POWERUP_BOOST, 0, flHealAmount, this, &m_aPlayerAttachInfo[iPlayer].m_DamageModifier ); } if ( !bBoosted ) { m_aPlayerAttachInfo[iPlayer].m_DamageModifier.RemoveModifier(); } } // Set next think time. if ( m_nPlayerCount > 0 ) { SetNextThink( gpGlobals->curtime + BUFF_STATION_BOOST_PLAYER_THINK_INTERVAL, BUFF_STATION_BOOST_PLAYER_THINK_CONTEXT ); } else { SetNextThink( gpGlobals->curtime + 1.0f, BUFF_STATION_BOOST_PLAYER_THINK_CONTEXT ); } }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CWeaponMortar::MortarDestroyed( void ) { CBaseTFPlayer *pPlayer = ToBaseTFPlayer( GetOwner() ); if ( pPlayer ) { ClientPrint( pPlayer, HUD_PRINTCENTER, "\n\n\n\n\n\n\n\n\n\nMortar Destroyed!" ); } if ( pPlayer && pPlayer->GetActiveWeapon() == this ) { SendWeaponAnim( ACT_SLAM_TRIPMINE_DRAW ); } MortarObjectRemoved(); }
//----------------------------------------------------------------------------- // Purpose: My player has just died //----------------------------------------------------------------------------- void CPlayerClass::PlayerDied( CBaseEntity *pAttacker ) { if ( pAttacker ) { CBaseTFPlayer *pAttackerPlayer = dynamic_cast< CBaseTFPlayer* >( pAttacker ); if ( pAttackerPlayer ) { CPlayerClass *pAttackerClass = pAttackerPlayer->GetPlayerClass(); if ( pAttackerClass ) { int iStatGroup = GetStatGroupFor( pAttackerPlayer ); g_PlayerClassStats[ iStatGroup ].m_InterClassStats[GetTFClass()].m_nKills++; } } } }
//----------------------------------------------------------------------------- // Purpose: Records that a player has left the zone, and updates it's state // according, maybe starting to change team. // Input : *pOther - the entity that left the zone //----------------------------------------------------------------------------- void CControlZone::EndTouch( CBaseEntity *pOther ) { CBaseTFPlayer *pl = ToBaseTFPlayer( pOther ); if ( !pl ) return; CHandle< CBaseTFPlayer > hHandle; hHandle = pl; m_ZonePlayerList.FindAndRemove( hHandle ); ReevaluateControllingTeam(); // Unset this player's current zone if it's this one if ( pl->GetCurrentZone() == this ) pl->SetCurrentZone( NULL ); }
//----------------------------------------------------------------------------- // Purpose: Records that a player has entered the zone, and updates it's state // according, maybe starting to change team. // Input : *pOther - the entity that left the zone //----------------------------------------------------------------------------- void CControlZone::StartTouch( CBaseEntity *pOther ) { CBaseTFPlayer *pl = ToBaseTFPlayer( pOther ); if ( !pl ) return; CHandle< CBaseTFPlayer > hHandle; hHandle = pl; m_ZonePlayerList.AddToTail( hHandle ); ReevaluateControllingTeam(); // Set this player's current zone to this zone pl->SetCurrentZone( this ); }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- float CWeaponCombatLaserRifle::GetFireRate( void ) { float flFireRate = ( SequenceDuration() * 0.4 ) + SHARED_RANDOMFLOAT( 0.0, 0.035f ); CBaseTFPlayer *pPlayer = static_cast<CBaseTFPlayer*>( GetOwner() ); if ( pPlayer ) { // Ducking players should fire more rapidly. if ( pPlayer->GetFlags() & FL_DUCKING ) { flFireRate *= weapon_combat_laserrifle_ducking_mod.GetFloat(); } } return flFireRate; }
//----------------------------------------------------------------------------- // Purpose: Called every frame by postthink //----------------------------------------------------------------------------- void CPlayerClassCommando::ClassThink( void ) { // Check bullrush m_ClassData.m_bCanBullRush = true; // Do the init thing here! if ( m_bOldBullRush != m_ClassData.m_bBullRush ) { if ( m_ClassData.m_bBullRush ) { PreBullRush(); } else { PostBullRush(); } m_bOldBullRush = (bool)m_ClassData.m_bBullRush; } // Check for melee attack if ( m_bCanBoot && m_pPlayer->IsAlive() && m_flNextBootCheck < gpGlobals->curtime ) { m_flNextBootCheck = gpGlobals->curtime + 0.2; CBaseEntity *pEntity = NULL; Vector vecSrc = m_pPlayer->Weapon_ShootPosition( ); Vector vecDir = m_pPlayer->BodyDirection2D( ); Vector vecTarget = vecSrc + (vecDir * 48); for ( CEntitySphereQuery sphere( vecTarget, 16 ); pEntity = sphere.GetCurrentEntity(); sphere.NextEntity() ) { if ( pEntity->IsPlayer() && (pEntity != m_pPlayer) ) { CBaseTFPlayer *pPlayer = (CBaseTFPlayer *)pEntity; // Target needs to be on the enemy team if ( !pPlayer->IsClass( TFCLASS_UNDECIDED ) && pPlayer->IsAlive() && pPlayer->InSameTeam( m_pPlayer ) == false ) { Boot( pPlayer ); m_flNextBootCheck = gpGlobals->curtime + 1.5; } } } } BaseClass::ClassThink(); }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- bool CWeaponCombatShield::Holster( CBaseCombatWeapon *pSwitchingTo ) { CBaseTFPlayer *player = ToBaseTFPlayer( GetOwner() ); if ( player ) { player->SetBlocking( false ); player->SetParrying( false ); if ( m_iShieldState != SS_DOWN && m_iShieldState != SS_UNAVAILABLE ) { SetShieldState( SS_LOWERING ); } } return true; }
//----------------------------------------------------------------------------- // Purpose: The player holding this weapon has just gained new technology. // Check to see if it affects the mortar //----------------------------------------------------------------------------- void CWeaponMortar::GainedNewTechnology( CBaseTechnology *pTechnology ) { CBaseTFPlayer *pPlayer = ToBaseTFPlayer( GetOwner() ); if ( pPlayer ) { // Range upgraded? if ( pPlayer->HasNamedTechnology("mortar_range") ) m_bRangeUpgraded = true; else m_bRangeUpgraded = false; // Accuracy upgraded? if ( pPlayer->HasNamedTechnology("mortar_accuracy") ) m_bAccuracyUpgraded = true; else m_bAccuracyUpgraded = false; } }