//----------------------------------------------------------------------------- // Purpose: Attaches the grub to the surface underneath its abdomen //----------------------------------------------------------------------------- void CNPC_AntlionGrub::AttachToSurface( void ) { // Get our downward direction Vector vecForward, vecRight, vecDown; GetVectors( &vecForward, &vecRight, &vecDown ); vecDown.Negate(); // Trace down to find a surface trace_t tr; UTIL_TraceLine( WorldSpaceCenter(), WorldSpaceCenter() + (vecDown*256.0f), MASK_NPCSOLID, this, COLLISION_GROUP_NONE, &tr ); if ( tr.fraction < 1.0f ) { // Move there UTIL_SetOrigin( this, tr.endpos, false ); } }
Vector CWeaponTFCBase::GetSoundEmissionOrigin() const { CBasePlayer *pPlayer = GetPlayerOwner(); if ( pPlayer ) return pPlayer->WorldSpaceCenter(); else return WorldSpaceCenter(); }
void CASW_Simple_Alien::DrawDebugGeometryOverlays() { BaseClass::DrawDebugGeometryOverlays(); // draw route if ((m_debugOverlays & OVERLAY_NPC_ROUTE_BIT)) { if ( m_bMoving ) { Vector vecDiff = m_vecMoveTarget - GetAbsOrigin(); NDebugOverlay::Line(WorldSpaceCenter(), WorldSpaceCenter() + vecDiff,0,0,255,true,0.0); } if (GetEnemy()) { NDebugOverlay::Line(WorldSpaceCenter(), GetEnemy()->WorldSpaceCenter(),255,0,0,true,0.0); } } }
bool CNPC_Zombine::AllowedToSprint( void ) { if ( IsOnFire() ) return false; //If you're sprinting then there's no reason to sprint again. if ( IsSprinting() ) return false; int iChance = SPRINT_CHANCE_VALUE; //Secobmod FixMe ?? also changed to HL2MPRules CHL2_Player *pPlayer = dynamic_cast <CHL2_Player*> ( UTIL_GetNearestPlayer(GetAbsOrigin() )); //CHL2MP_Player *pPlayer = dynamic_cast<CHL2MP_Player *>( UTIL_GetNearestPlayer(GetAbsOrigin() ); if ( pPlayer ) { #ifdef MFS if ( HL2MPRules()->IsAlyxInDarknessMode() && pPlayer->FlashlightIsOn() == false ) #else if (IsAlyxInDarknessMode() && pPlayer->FlashlightIsOn() == false) #endif { iChance = SPRINT_CHANCE_VALUE_DARKNESS; } //Bigger chance of this happening if the player is not looking at the zombie if ( pPlayer->FInViewCone( this ) == false ) { iChance *= 2; } } if ( HasGrenade() ) { iChance *= 4; } //Below 25% health they'll always sprint if ( ( GetHealth() > GetMaxHealth() * 0.5f ) ) { if ( IsStrategySlotRangeOccupied( SQUAD_SLOT_ZOMBINE_SPRINT1, SQUAD_SLOT_ZOMBINE_SPRINT2 ) == true ) return false; if ( random->RandomInt( 0, 100 ) > iChance ) return false; if ( m_flSprintRestTime > gpGlobals->curtime ) return false; } float flLength = ( GetEnemy()->WorldSpaceCenter() - WorldSpaceCenter() ).Length(); if ( flLength > MAX_SPRINT_DISTANCE ) return false; return true; }
bool C_Func_LOD::LODTest() { if(!lod_Enable.GetInt()) return true; float transitionDist = m_fDisappearDist; float disappearDist = m_fDisappearDist + lod_TransitionDist.GetFloat(); float dist = (CurrentViewOrigin() - WorldSpaceCenter()).Length(); if(dist < transitionDist) { // Always visible between 0 and transitionDist. m_LastRegion = Visible; m_bLastDrawn = true; } else if(dist < disappearDist) { // In the transition range. First, figure out if we want to transition at all. bool bTransition = false; // See if they're rotating their view fast enough. if(r_DoCovertTransitions.GetInt()) { bTransition = true; } else { // FIXME: Should we use the surrounding box here? // Since this is a brushmodel which isn't rotating, it should be close enough... Vector vCenter = (WorldSpaceSurroundingMins() + WorldSpaceSurroundingMaxs()) * 0.5f; float radius = (WorldSpaceSurroundingMaxs() - vCenter).Length(); bTransition = R_CullSphere(view->GetFrustum(), 5, &vCenter, radius); } if(bTransition) { // Ok, do the transition while they're not looking. if(m_LastRegion == Visible && m_bLastDrawn) { // Make it invisible. m_bLastDrawn = false; } else if(m_LastRegion == Invisible && !m_bLastDrawn) { // Make it visible. m_bLastDrawn = true; } } } else { // Never visible from disappearDist+. m_LastRegion = Invisible; m_bLastDrawn = false; } return m_bLastDrawn; }
//----------------------------------------------------------------------------- //----------------------------------------------------------------------------- Vector CPropAPC::BodyTarget( const Vector &posSrc, bool bNoisy ) { if( g_pGameRules->GetAutoAimMode() == AUTOAIM_ON_CONSOLE ) { return WorldSpaceCenter(); } return BaseClass::BodyTarget( posSrc, bNoisy ); }
//----------------------------------------------------------------------------- //----------------------------------------------------------------------------- Vector CPropAPC::BodyTarget( const Vector &posSrc, bool bNoisy ) { if ( IsXbox() ) { return WorldSpaceCenter(); } return BaseClass::BodyTarget( posSrc, bNoisy ); }
void CFlechette::DoAOEDamage() { CBaseEntity *ppEnts[256]; Vector vecCenter = WorldSpaceCenter(); float flRadius = flechette_radius.GetFloat(); vecCenter.z -= flRadius * 0.8f; int nEntCount = UTIL_EntitiesInSphere( ppEnts, 256, vecCenter, flRadius, 0 ); int i; for ( i = 0; i < nEntCount; i++ ) { if ( ppEnts[i] == NULL ) continue; bool bDoDamage = true; if(ppEnts[i]->IsPlayer() || ppEnts[i]->IsNPC()) { CBasePlayer *pOtherPlayer = ToBasePlayer(ppEnts[i]); CBasePlayer *pPlayer = ToBasePlayer(GetOwnerEntity()); if(pOtherPlayer != NULL && pPlayer != NULL) { if((HL2MPRules()->IsTeamplay() && (pPlayer->GetTeamNumber() == pOtherPlayer->GetTeamNumber())) || HL2MPRules()->GetGameType() == GAME_COOP) { const int oldHealth = pOtherPlayer->GetHealth(); pOtherPlayer->TakeHealth( HEAL_AMOUNT, DMG_GENERIC ); bDoDamage = false; if(oldHealth <= HEAL_AMOUNT) pOtherPlayer->PlayAutovocal(HEALED,0); if(oldHealth != pOtherPlayer->GetHealth()) // Si on a vraiment heal pOtherPlayer->EmitSound("Tranqu.Heal"); } } if(bDoDamage && ppEnts[i] != GetOwnerEntity()) { int iApplyDamage = 0; if(ppEnts[i]->IsNPC()) iApplyDamage = 70; else { if(ppEnts[i]->GetHealth() < m_iDamage + 10) iApplyDamage = 100; else iApplyDamage = ppEnts[i]->GetHealth() - m_iDamage; } CTakeDamageInfo dmgInfo( this, GetOwnerEntity(), GetOwnerEntity(), iApplyDamage, DMG_POISON | DMG_NEVERGIB ); //CalculateMeleeDamageForce( &dmgInfo, vecNormalizedVel, tr.endpos, 0.7f ); dmgInfo.SetDamagePosition( vecCenter ); ppEnts[i]->TakeDamage(dmgInfo); //ppEnts[i]->DispatchTraceAttack( dmgInfo, vecNormalizedVel, &tr ); } } ApplyMultiDamage(); } }
//----------------------------------------------------------------------------- // Purpose: // Input : &info - // Output : Returns true on success, false on failure. //----------------------------------------------------------------------------- void CNPC_CombineShot::Event_Killed(const CTakeDamageInfo &info) { // Don't bother if we've been told not to, or the player has a megaphyscannon if ( combine_shot_spawn_health.GetBool() == false || PlayerHasMegaPhysCannon() ) { BaseClass::Event_Killed( info ); return; } CBasePlayer *pPlayer = ToBasePlayer( info.GetAttacker() ); if ( !pPlayer ) { CPropVehicleDriveable *pVehicle = dynamic_cast<CPropVehicleDriveable *>( info.GetAttacker() ) ; if ( pVehicle && pVehicle->GetDriver() && pVehicle->GetDriver()->IsPlayer() ) { pPlayer = assert_cast<CBasePlayer *>( pVehicle->GetDriver() ); } } if ( pPlayer != NULL ) { CHalfLife2 *pHL2GameRules = static_cast<CHalfLife2 *>(g_pGameRules); // Attempt to drop health if ( pHL2GameRules->NPC_ShouldDropHealth( pPlayer ) ) { DropItem( "item_healthvial", WorldSpaceCenter()+RandomVector(-4,4), RandomAngle(0,360) ); pHL2GameRules->NPC_DroppedHealth(); } if ( HasSpawnFlags( SF_COMBINE_NO_GRENADEDROP ) == false ) { // Attempt to drop a grenade if ( pHL2GameRules->NPC_ShouldDropGrenade( pPlayer ) ) { DropItem( "weapon_frag", WorldSpaceCenter()+RandomVector(-4,4), RandomAngle(0,360) ); pHL2GameRules->NPC_DroppedGrenade(); } } } BaseClass::Event_Killed( info ); }
//----------------------------------------------------------------------------- // Create, initialize, and distribute all blob elements //----------------------------------------------------------------------------- void CNPC_Blob::InitializeElements() { // Squirt all of the elements out into a circle int i; QAngle angDistributor( 0, 0, 0 ); int iNumElements = blob_numelements.GetInt(); float step = 360.0f / ((float)iNumElements); for( i = 0 ; i < iNumElements ; i++ ) { Vector vecDir; Vector vecDest; AngleVectors( angDistributor, &vecDir, NULL, NULL ); vecDest = WorldSpaceCenter() + vecDir * 64.0f; CBlobElement *pElement = CreateNewElement(); if( !pElement ) { Msg("Blob could not create all elements!!\n"); return; } trace_t tr; UTIL_TraceLine( vecDest, vecDest + Vector (0, 0, MIN_COORD_FLOAT), MASK_SHOT, pElement, COLLISION_GROUP_NONE, &tr ); pElement->SetAbsOrigin( tr.endpos + Vector( 0, 0, 1 ) ); angDistributor.y += step; } CBaseEntity *pEntity = gEntList.FindEntityByClassname( NULL, "info_target" ); for( i = 0 ; i < BLOB_MAX_AVOID_ORIGINS ; i++ ) { if( pEntity ) { if( pEntity->NameMatches("avoid") ) { m_vecAvoidOrigin[ i ] = pEntity->GetAbsOrigin(); m_flAvoidRadiusSqr = Square( 120.0f ); m_iNumAvoidOrigins++; } pEntity = gEntList.FindEntityByClassname( pEntity, "info_target" ); } else { break; } } Msg("%d avoid origins\n", m_iNumAvoidOrigins ); RecomputeIdealElementDist(); }
//----------------------------------------------------------------------------- // Purpose: Try to encourage Alyx not to use her weapon at point blank range, // but don't prevent her from defending herself if cornered. // Input : flDot - // flDist - // Output : int //----------------------------------------------------------------------------- int CWeaponAlyxGun::WeaponRangeAttack1Condition( float flDot, float flDist ) { #ifdef HL2_EPISODIC if( flDist < m_fMinRange1 ) { // If Alyx is not able to fire because an enemy is too close, start a timer. // If the condition persists, allow her to ignore it and defend herself. The idea // is to stop Alyx being content to fire point blank at enemies if she's able to move // away, without making her defenseless if she's not able to move. float flTime; if( m_flTooCloseTimer == TOOCLOSETIMER_OFF ) { m_flTooCloseTimer = gpGlobals->curtime; } flTime = gpGlobals->curtime - m_flTooCloseTimer; if( flTime > ALYX_TOOCLOSETIMER ) { // Fake the range to allow Alyx to shoot. flDist = m_fMinRange1 + 1.0f; } } else { m_flTooCloseTimer = TOOCLOSETIMER_OFF; } int nBaseCondition = BaseClass::WeaponRangeAttack1Condition( flDot, flDist ); // While in a vehicle, we extend our aiming cone (this relies on COND_NOT_FACING_ATTACK // TODO: This needs to be rolled in at the animation level if ( GetOwner()->IsInAVehicle() ) { Vector vecRoughDirection = ( GetOwner()->GetEnemy()->WorldSpaceCenter() - WorldSpaceCenter() ); Vector vecRight; GetVectors( NULL, &vecRight, NULL ); bool bRightSide = ( DotProduct( vecRoughDirection, vecRight ) > 0.0f ); float flTargetDot = ( bRightSide ) ? -0.7f : 0.0f; if ( nBaseCondition == COND_NOT_FACING_ATTACK && flDot >= flTargetDot ) { nBaseCondition = COND_CAN_RANGE_ATTACK1; } } return nBaseCondition; #else return BaseClass::WeaponRangeAttack1Condition( flDot, flDist ); #endif//HL2_EPISODIC }
void CAI_DynamicLinkController::GenerateLinksFromVolume() { Assert( m_ControlledLinks.Count() == 0 ); int nNodes = g_pBigAINet->NumNodes(); CAI_Node **ppNodes = g_pBigAINet->AccessNodes(); const float MinDistCareSq = Square(MAX_NODE_LINK_DIST + 0.1); const Vector &origin = WorldSpaceCenter(); Vector vAbsMins, vAbsMaxs; CollisionProp()->WorldSpaceAABB( &vAbsMins, &vAbsMaxs ); vAbsMins -= Vector( 1, 1, 1 ); vAbsMaxs += Vector( 1, 1, 1 ); for ( int i = 0; i < nNodes; i++ ) { CAI_Node *pNode = ppNodes[i]; const Vector &nodeOrigin = pNode->GetOrigin(); if ( origin.DistToSqr(nodeOrigin) < MinDistCareSq ) { int nLinks = pNode->NumLinks(); for ( int j = 0; j < nLinks; j++ ) { CAI_Link *pLink = pNode->GetLinkByIndex( j ); int iLinkDest = pLink->DestNodeID( i ); if ( iLinkDest > i ) { const Vector &originOther = ppNodes[iLinkDest]->GetOrigin(); if ( origin.DistToSqr(originOther) < MinDistCareSq ) { if ( IsBoxIntersectingRay( vAbsMins, vAbsMaxs, nodeOrigin, originOther - nodeOrigin ) ) { Assert( IsBoxIntersectingRay( vAbsMins, vAbsMaxs, originOther, nodeOrigin - originOther ) ); CAI_DynamicLink *pLink = (CAI_DynamicLink *)CreateEntityByName( "info_node_link" ); pLink->m_nSrcID = i; pLink->m_nDestID = iLinkDest; pLink->m_nSrcEditID = g_pAINetworkManager->GetEditOps()->GetWCIdFromNodeId( pLink->m_nSrcID ); pLink->m_nDestEditID = g_pAINetworkManager->GetEditOps()->GetWCIdFromNodeId( pLink->m_nDestID ); pLink->m_nLinkState = m_nLinkState; pLink->m_strAllowUse = m_strAllowUse; pLink->m_bFixedUpIds = true; pLink->m_bNotSaved = true; pLink->Spawn(); m_ControlledLinks.AddToTail( pLink ); } } } } } } }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CNPC_AntlionGrub::Squash( CBaseEntity *pOther ) { SpawnSquashedGrub(); AddEffects( EF_NODRAW ); AddSolidFlags( FSOLID_NOT_SOLID ); EmitSound( "NPC_AntlionGrub.Squash" ); BroadcastAlert(); Vector vecUp; AngleVectors( GetAbsAngles(), NULL, NULL, &vecUp ); trace_t tr; for ( int i = 0; i < 4; i++ ) { tr.endpos = WorldSpaceCenter(); tr.endpos[0] += random->RandomFloat( -16.0f, 16.0f ); tr.endpos[1] += random->RandomFloat( -16.0f, 16.0f ); tr.endpos += vecUp * 8.0f; MakeDamageBloodDecal( 2, 0.8f, &tr, -vecUp ); } SetTouch( NULL ); m_bSquashed = true; // Temp squash effect CEffectData data; data.m_fFlags = 0; data.m_vOrigin = WorldSpaceCenter(); data.m_vNormal = vecUp; VectorAngles( vecUp, data.m_vAngles ); data.m_flScale = random->RandomFloat( 5, 7 ); data.m_fFlags |= FX_WATER_IN_SLIME; DispatchEffect( "watersplash", data ); }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CItem_DynamicResupply::FindPotentialItems( int nCount, DynamicResupplyItems_t *pItems, int iDebug, SpawnInfo_t *pSpawnInfo ) { int i; for ( i = 0; i < nCount; ++i ) { pSpawnInfo[i].m_iPotentialItems = 0; } // Count the potential addition of items in the PVS CBaseEntity *pEntity = NULL; while ( (pEntity = UTIL_EntitiesInPVS( this, pEntity )) != NULL ) { if ( pEntity->WorldSpaceCenter().DistToSqr( WorldSpaceCenter() ) > (POTENTIAL_ITEM_RADIUS * POTENTIAL_ITEM_RADIUS) ) continue; for ( i = 0; i < nCount; ++i ) { if ( !FClassnameIs( pEntity, pItems[i].sEntityName ) ) continue; if ( iDebug == 2 ) { NDebugOverlay::Line( WorldSpaceCenter(), pEntity->WorldSpaceCenter(), 0,255,0, true, 20.0 ); } ++pSpawnInfo[i].m_iPotentialItems; break; } } if ( iDebug ) { Msg("Searching the PVS:\n"); for ( int i = 0; i < nCount; i++ ) { Msg(" Found %d '%s' in the PVS.\n", pSpawnInfo[i].m_iPotentialItems, pItems[i].sEntityName ); } } }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- Vector CUnitBase::BodyTarget( const Vector &posSrc, bool bNoisy ) { Vector result; if( m_bBodyTargetOriginBased ) { Vector vUpdatedWorldSpaceCenter = GetAbsOrigin(); vUpdatedWorldSpaceCenter.z = GetAbsOrigin().z + (CollisionProp()->OBBMaxs().z / 2.0f); Vector low = vUpdatedWorldSpaceCenter - ( vUpdatedWorldSpaceCenter - GetAbsOrigin() ) * .25; Vector high = EyePosition(); Vector delta = high - low; if ( bNoisy ) { // bell curve float rand1 = random->RandomFloat( 0.0, 0.5 ); float rand2 = random->RandomFloat( 0.0, 0.5 ); result = low + delta * rand1 + delta * rand2; } else result = low + delta * 0.5; } else { Vector low = WorldSpaceCenter() - ( WorldSpaceCenter() - GetAbsOrigin() ) * .25; Vector high = EyePosition(); Vector delta = high - low; if ( bNoisy ) { // bell curve float rand1 = random->RandomFloat( 0.0, 0.5 ); float rand2 = random->RandomFloat( 0.0, 0.5 ); result = low + delta * rand1 + delta * rand2; } else result = low + delta * 0.5; } return result; }
//----------------------------------------------------------------------------- // Create a corpse //----------------------------------------------------------------------------- void CPropAPC::CreateCorpse( ) { m_lifeState = LIFE_DEAD; for ( int i = 0; i < APC_MAX_GIBS; ++i ) { CPhysicsProp *pGib = assert_cast<CPhysicsProp*>(CreateEntityByName( "prop_physics" )); pGib->SetAbsOrigin( GetAbsOrigin() ); pGib->SetAbsAngles( GetAbsAngles() ); pGib->SetAbsVelocity( GetAbsVelocity() ); pGib->SetModel( s_pGibModelName[i] ); pGib->Spawn(); pGib->SetMoveType( MOVETYPE_VPHYSICS ); float flMass = pGib->GetMass(); if ( flMass < 200 ) { Vector vecVelocity; pGib->GetMassCenter( &vecVelocity ); vecVelocity -= WorldSpaceCenter(); vecVelocity.z = fabs(vecVelocity.z); VectorNormalize( vecVelocity ); // Apply a force that would make a 100kg mass travel 150 - 300 m/s float flRandomVel = random->RandomFloat( 150, 300 ); vecVelocity *= (100 * flRandomVel) / flMass; vecVelocity.z += 100.0f; AngularImpulse angImpulse = RandomAngularImpulse( -500, 500 ); IPhysicsObject *pObj = pGib->VPhysicsGetObject(); if ( pObj != NULL ) { pObj->AddVelocity( &vecVelocity, &angImpulse ); } pGib->SetCollisionGroup( COLLISION_GROUP_DEBRIS ); } if( hl2_episodic.GetBool() ) { // EP1 perf hit pGib->Ignite( 6, false ); } else { pGib->Ignite( 60, false ); } } AddSolidFlags( FSOLID_NOT_SOLID ); AddEffects( EF_NODRAW ); UTIL_Remove( this ); }
//----------------------------------------------------------------------------- // Aims the secondary weapon at a target //----------------------------------------------------------------------------- void CPropAPC::AimSecondaryWeaponAt( CBaseEntity *pTarget ) { m_hRocketTarget = pTarget; // Update the rocket target CreateAPCLaserDot(); if ( m_hRocketTarget ) { m_hLaserDot->SetAbsOrigin( m_hRocketTarget->BodyTarget( WorldSpaceCenter(), false ) ); } SetLaserDotTarget( m_hLaserDot, m_hRocketTarget ); EnableLaserDot( m_hLaserDot, m_hRocketTarget != NULL ); }
void CPropAPC2::AimSecondaryWeapon(Vector &vecWorldTarget ) { //m_hRocketTarget = vecWorldTarget; // Update the rocket target CreateAPCLaserDot(); if ( m_hRocketTarget ) { m_hLaserDot->SetAbsOrigin( m_hRocketTarget->BodyTarget( WorldSpaceCenter(), false ) ); } SetLaserDotTarget( m_hLaserDot, m_hRocketTarget ); EnableLaserDot( m_hLaserDot, m_hRocketTarget != NULL ); }
//----------------------------------------------------------------------------- // Purpose: Will hurt others based on how fast the brush is spinning. // Input : pOther - //----------------------------------------------------------------------------- void CFuncRotating::HurtTouch ( CBaseEntity *pOther ) { // we can't hurt this thing, so we're not concerned with it if ( !pOther->m_takedamage ) return; // calculate damage based on rotation speed m_flBlockDamage = GetLocalAngularVelocity().Length() / 10; pOther->TakeDamage( CTakeDamageInfo( this, this, m_flBlockDamage, DMG_CRUSH ) ); Vector vecNewVelocity = pOther->GetAbsOrigin() - WorldSpaceCenter(); VectorNormalize(vecNewVelocity); vecNewVelocity *= m_flBlockDamage; pOther->SetAbsVelocity( vecNewVelocity ); }
//----------------------------------------------------------------------------- // Purpose: // Input: // Output: //----------------------------------------------------------------------------- bool CASW_Boomer::CorpseGib( const CTakeDamageInfo &info ) { CEffectData data; m_LagCompensation.UndoLaggedPosition(); data.m_vOrigin = WorldSpaceCenter(); data.m_vNormal = data.m_vOrigin - info.GetDamagePosition(); VectorNormalize( data.m_vNormal ); data.m_flScale = RemapVal( m_iHealth, 0, 3, 0.5f, 2 ); data.m_nColor = m_nSkin; data.m_fFlags = IsOnFire() ? ASW_GIBFLAG_ON_FIRE : 0; return true; }
bool CASW_Simple_Alien::CorpseGib( const CTakeDamageInfo &info ) { CEffectData data; data.m_vOrigin = WorldSpaceCenter(); data.m_vNormal = data.m_vOrigin - info.GetDamagePosition(); VectorNormalize( data.m_vNormal ); data.m_flScale = RemapVal( m_iHealth, 0, -500, 1, 3 ); data.m_flScale = clamp( data.m_flScale, 1, 3 ); data.m_nColor = m_nSkin; //DispatchEffect( "DroneGib", data ); return true; }
//----------------------------------------------------------------------------- // Purpose: Return true if this object is powerable //----------------------------------------------------------------------------- bool CObjectBuffStation::IsWithinBuffRange( CBaseObject *pObject ) { if ( ( pObject->GetAbsOrigin() - GetAbsOrigin() ).LengthSqr() < BUFF_STATION_BUFF_RANGE ) { // Can I see it? // Ignore things we're attached to trace_t tr; CTraceFilterWorldAndPropsOnly buffFilter; UTIL_TraceLine( WorldSpaceCenter(), pObject->WorldSpaceCenter(), MASK_SOLID_BRUSHONLY, &buffFilter, &tr ); CBaseEntity *pEntity = tr.m_pEnt; if ( ( tr.fraction == 1.0 ) || ( pEntity == pObject ) ) return true; } return false; }
//----------------------------------------------------------------------------- // Purpose: Allows us to make damage exceptions that are breakable-specific. //----------------------------------------------------------------------------- int CBreakable::OnTakeDamage( const CTakeDamageInfo &info ) { Vector vecTemp; CTakeDamageInfo subInfo = info; // If attacker can't do at least the min required damage to us, don't take any damage from them if ( m_takedamage == DAMAGE_NO || info.GetDamage() < m_iMinHealthDmg ) return 0; // Check our damage filter if ( !PassesDamageFilter(subInfo) ) { m_bTookPhysicsDamage = false; return 1; } vecTemp = subInfo.GetInflictor()->GetAbsOrigin() - WorldSpaceCenter(); if (!IsBreakable()) return 0; float flPropDamage = GetBreakableDamage( subInfo, assert_cast<IBreakableWithPropData*>(this) ); subInfo.SetDamage( flPropDamage ); int iPrevHealth = m_iHealth; BaseClass::OnTakeDamage( subInfo ); // HACK: slam health back to what it was so UpdateHealth can do its thing int iNewHealth = m_iHealth; m_iHealth = iPrevHealth; if ( !UpdateHealth( iNewHealth, info.GetAttacker() ) ) return 1; // Make a shard noise each time func breakable is hit, if it's capable of taking damage if ( m_takedamage == DAMAGE_YES ) { // Don't play shard noise if being burned. // Don't play shard noise if cbreakable actually died. if ( ( subInfo.GetDamageType() & DMG_BURN ) == false ) { DamageSound(); } } return 1; }
//------------------------------------------------------------------------------ void CNPC_EnemyFinder::PrescheduleThink() { BaseClass::PrescheduleThink(); bool bHasEnemies = GetEnemies()->NumEnemies() > 0; if ( GetEnemies()->NumEnemies() > 0 ) { //If I haven't seen my enemy in half a second then we'll assume he's gone. if ( gpGlobals->curtime - GetEnemyLastTimeSeen() >= 0.5f ) { bHasEnemies = false; } } if ( m_bEnemyStatus != bHasEnemies ) { if ( bHasEnemies ) { m_OnAcquireEnemies.FireOutput( this, this ); } else { m_OnLostEnemies.FireOutput( this, this ); } m_bEnemyStatus = bHasEnemies; } if( ai_debug_enemyfinders.GetBool() ) { m_debugOverlays |= OVERLAY_BBOX_BIT; if( IsInSquad() && GetSquad()->NumMembers() > 1 ) { AISquadIter_t iter; CAI_BaseNPC *pSquadmate = m_pSquad ? m_pSquad->GetFirstMember( &iter ) : NULL; while ( pSquadmate ) { NDebugOverlay::Line( WorldSpaceCenter(), pSquadmate->EyePosition(), 255, 255, 0, false, 0.1f ); pSquadmate = m_pSquad->GetNextMember( &iter ); } } } }
void QUA_helicopter::CreateCorpse( ) { m_lifeState = LIFE_DEAD; for ( int i = 0; i < HELICOPTER_MAX_GIBS; ++i ) { CPhysicsProp *pGib = assert_cast<CPhysicsProp*>(CreateEntityByName( "prop_physics_multiplayer" )); pGib->SetAbsOrigin( GetAbsOrigin() ); pGib->SetAbsAngles( GetAbsAngles() ); pGib->SetAbsVelocity( GetAbsVelocity() ); pGib->SetModel( s_pGibModelName[i] ); pGib->Spawn(); pGib->SetMoveType( MOVETYPE_VPHYSICS ); float flMass = pGib->GetMass(); /*if ( flMass < 200 ) {*/ Vector vecVelocity; pGib->GetMassCenter( &vecVelocity ); vecVelocity -= WorldSpaceCenter(); vecVelocity.z = fabs(vecVelocity.z); VectorNormalize( vecVelocity ); // Apply a force that would make a 100kg mass travel 150 - 300 m/s float flRandomVel = random->RandomFloat( 150, 300 ); vecVelocity *= (100 * flRandomVel) / flMass; vecVelocity.z += 100.0f; AngularImpulse angImpulse = RandomAngularImpulse( -500, 500 ); IPhysicsObject *pObj = pGib->VPhysicsGetObject(); if ( pObj != NULL ) { pObj->AddVelocity( &vecVelocity, &angImpulse ); } pGib->SetCollisionGroup( COLLISION_GROUP_DEBRIS ); /*}*/ pGib->Ignite( 60, false ); pGib->Dissolve( NULL, gpGlobals->curtime, false, ENTITY_DISSOLVE_NORMAL ); } AddSolidFlags( FSOLID_NOT_SOLID ); AddEffects( EF_NODRAW ); UTIL_RemoveImmediate( this ); }
//------------------------------------------------------------------------------ // Purpose : // Input : // Output : //------------------------------------------------------------------------------ void CGrenadeHomer::Launch( CBaseEntity* pOwner, CBaseEntity* pTarget, const Vector& vInitVelocity, float flHomingSpeed, float flGravity, int nRocketTrailType) { SetOwnerEntity( pOwner ); m_hTarget = pTarget; SetAbsVelocity( vInitVelocity ); m_flHomingSpeed = flHomingSpeed; SetGravity( flGravity ); m_nRocketTrailType = nRocketTrailType; // ---------------------------- // Initialize homing parameters // ---------------------------- m_flHomingLaunchTime = gpGlobals->curtime; // ------------- // Smoke trail. // ------------- if ( (m_nRocketTrailType == HOMER_SMOKE_TRAIL_ON) || (m_nRocketTrailType == HOMER_SMOKE_TRAIL_ALIEN) ) { StartRocketTrail(); } SetUse( &CGrenadeHomer::DetonateUse ); SetTouch( &CGrenadeHomer::GrenadeHomerTouch ); SetThink( &CGrenadeHomer::AimThink ); AimThink(); SetNextThink( gpGlobals->curtime ); // Issue danger! if ( pTarget ) { // Figure out how long it'll take for me to reach the target. float flDist = ( pTarget->WorldSpaceCenter() - WorldSpaceCenter() ).Length(); float flTime = MAX( 0.5, flDist / GetAbsVelocity().Length() ); CSoundEnt::InsertSound ( SOUND_DANGER, m_hTarget->GetAbsOrigin(), 300, flTime, pOwner ); } }
int CASW_Boomer::OnTakeDamage_Alive( const CTakeDamageInfo &info ) { CTakeDamageInfo infoNew( info ); if ( infoNew.GetAttacker() && info.GetAttacker()->Classify() == CLASS_ASW_MARINE ) { EHANDLE hAttacker = infoNew.GetAttacker(); if ( m_hMarineAttackers.Find( hAttacker ) == m_hMarineAttackers.InvalidIndex() ) { m_hMarineAttackers.AddToTail( hAttacker ); } if ( infoNew.GetAttacker()->WorldSpaceCenter().DistTo( WorldSpaceCenter() ) < 40 ) { // Stuck inside! Kill it good! infoNew.ScaleDamage( 8 ); } } return BaseClass::OnTakeDamage_Alive( infoNew ); }
void CDODPlayer::CheckProneMoveSound( int groundspeed, bool onground ) { #ifdef CLIENT_DLL bool bShouldPlay = (groundspeed > 10) && (onground == true) && m_Shared.IsProne() && IsAlive(); if ( m_bPlayingProneMoveSound && !bShouldPlay ) { StopSound( "Player.MoveProne" ); m_bPlayingProneMoveSound= false; } else if ( !m_bPlayingProneMoveSound && bShouldPlay ) { CRecipientFilter filter; filter.AddRecipientsByPAS( WorldSpaceCenter() ); EmitSound( filter, entindex(), "Player.MoveProne" ); m_bPlayingProneMoveSound = true; } #endif }
//----------------------------------------------------------------------------- // Purpose: Emits sparks at random intervals. //----------------------------------------------------------------------------- void CEnvSpark::SparkThink(void) { SetNextThink( gpGlobals->curtime + 0.1 + random->RandomFloat(0, m_flDelay) ); Vector vecDir = vec3_origin; if ( FBitSet( m_spawnflags, SF_SPARK_DIRECTIONAL ) ) { AngleVectors( GetAbsAngles(), &vecDir ); } DoSpark( this, WorldSpaceCenter(), m_nMagnitude, m_nTrailLength, !( m_spawnflags & SF_SPARK_SILENT ), vecDir ); m_OnSpark.FireOutput( this, this ); if (FBitSet(m_spawnflags, SF_SPARK_GLOW)) { CPVSFilter filter( GetAbsOrigin() ); te->GlowSprite( filter, 0.0, &GetAbsOrigin(), m_nGlowSpriteIndex, 0.2, 1.5, 25 ); } }
bool CASW_Parasite::CorpseGib( const CTakeDamageInfo &info ) { CEffectData data; data.m_vOrigin = WorldSpaceCenter(); data.m_vNormal = data.m_vOrigin - info.GetDamagePosition(); VectorNormalize( data.m_vNormal ); data.m_flScale = RemapVal( m_iHealth, 0, -500, 1, 3 ); data.m_flScale = clamp( data.m_flScale, 1, 3 ); data.m_fFlags = IsOnFire() ? ASW_GIBFLAG_ON_FIRE : 0; if (m_bDefanged) DispatchEffect( "HarvesiteGib", data ); else DispatchEffect( "ParasiteGib", data ); return true; }