/* ================ TraceAttack ================ */ void CBaseEntity::TraceAttack(entvars_t *pevAttacker, float flDamage, Vector vecDir, TraceResult *ptr, int bitsDamageType) { Vector vecOrigin = ptr->vecEndPos - vecDir * 4; if ( pev->takedamage ) { AddMultiDamage( pevAttacker, this, flDamage, bitsDamageType ); int blood = BloodColor(); if ( blood != DONT_BLEED ) { SpawnBlood(vecOrigin, blood, flDamage);// a little surface blood. TraceBleed( flDamage, vecDir, ptr, bitsDamageType ); } } }
//========================================================= // TraceAttack //========================================================= void CAGrunt :: TraceAttack( entvars_t *pevAttacker, float flDamage, Vector vecDir, TraceResult *ptr, int bitsDamageType) { if ( ptr->iHitgroup == 10 && (bitsDamageType & (DMG_BULLET | DMG_SLASH | DMG_CLUB))) { // hit armor if ( pev->dmgtime != gpGlobals->time || (RANDOM_LONG(0,10) < 1) ) { UTIL_Ricochet( ptr->vecEndPos, RANDOM_FLOAT( 1, 2) ); pev->dmgtime = gpGlobals->time; } if ( RANDOM_LONG( 0, 1 ) == 0 ) { Vector vecTracerDir = vecDir; vecTracerDir.x += RANDOM_FLOAT( -0.3, 0.3 ); vecTracerDir.y += RANDOM_FLOAT( -0.3, 0.3 ); vecTracerDir.z += RANDOM_FLOAT( -0.3, 0.3 ); vecTracerDir = vecTracerDir * -512; MESSAGE_BEGIN( MSG_PVS, SVC_TEMPENTITY, ptr->vecEndPos ); WRITE_BYTE( TE_TRACER ); WRITE_COORD( ptr->vecEndPos.x ); WRITE_COORD( ptr->vecEndPos.y ); WRITE_COORD( ptr->vecEndPos.z ); WRITE_COORD( vecTracerDir.x ); WRITE_COORD( vecTracerDir.y ); WRITE_COORD( vecTracerDir.z ); MESSAGE_END(); } flDamage -= 20; if (flDamage <= 0) flDamage = 0.1;// don't hurt the monster much, but allow bits_COND_LIGHT_DAMAGE to be generated } else { SpawnBlood(ptr->vecEndPos, BloodColor(), flDamage);// a little surface blood. TraceBleed( flDamage, vecDir, ptr, bitsDamageType ); } AddMultiDamage( pevAttacker, this, flDamage, bitsDamageType ); }
void CNPC_AlienGrunt::TraceAttack( const CTakeDamageInfo &info, const Vector &vecDir, trace_t *ptr ) { CTakeDamageInfo ainfo = info; float flDamage = ainfo.GetDamage(); if ( ptr->hitgroup == 10 && (ainfo.GetDamageType() & (DMG_BULLET | DMG_SLASH | DMG_CLUB))) { // hit armor if ( m_flDamageTime != gpGlobals->curtime || (random->RandomInt(0,10) < 1) ) { CPVSFilter filter( ptr->endpos ); te->ArmorRicochet( filter, 0.0, &ptr->endpos, &ptr->plane.normal ); m_flDamageTime = gpGlobals->curtime; } if ( random->RandomInt( 0, 1 ) == 0 ) { Vector vecTracerDir = vecDir; vecTracerDir.x += random->RandomFloat( -0.3, 0.3 ); vecTracerDir.y += random->RandomFloat( -0.3, 0.3 ); vecTracerDir.z += random->RandomFloat( -0.3, 0.3 ); vecTracerDir = vecTracerDir * -512; Vector vEndPos = ptr->endpos + vecTracerDir; UTIL_Tracer( ptr->endpos, vEndPos, ENTINDEX( edict() ) ); } flDamage -= 20; if (flDamage <= 0) flDamage = 0.1;// don't hurt the monster much, but allow bits_COND_LIGHT_DAMAGE to be generated ainfo.SetDamage( flDamage ); } else { SpawnBlood( ptr->endpos, vecDir, BloodColor(), flDamage);// a little surface blood. TraceBleed( flDamage, vecDir, ptr, ainfo.GetDamageType() ); } AddMultiDamage( ainfo, this ); }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CUnitBase::TraceAttack( const CTakeDamageInfo &info, const Vector &vecDir, trace_t *ptr ) { Vector vecOrigin = ptr->endpos - vecDir * 4; if ( m_takedamage ) { AddMultiDamage( info, this ); // Must always be called from the client to save data #ifdef CLIENT_DLL int blood = BloodColor(); if ( blood != DONT_BLEED ) { SpawnBlood( vecOrigin, vecDir, blood, info.GetDamage() );// a little surface blood. TraceBleed( info.GetDamage(), vecDir, ptr, info.GetDamageType() ); } #endif // CLIENT_DLL } }
//----------------------------------------------------------------------------- // Purpose: // Input : *pAttacker - // flDamage - // &vecDir - // *ptr - // bitsDamageType - //----------------------------------------------------------------------------- void CNPC_Bullseye::TraceAttack( const CTakeDamageInfo &info, const Vector &vecDir, trace_t *ptr ) { //If specified, we must be the enemy of the target if ( m_spawnflags & SF_BULLSEYE_ENEMYDAMAGEONLY ) { CAI_BaseNPC *pInstigator = info.GetAttacker()->MyNPCPointer(); if ( pInstigator == NULL ) return; if ( pInstigator->GetEnemy() != this ) return; } //We can bleed if we want to, we can leave decals behind... if ( ( m_spawnflags & SF_BULLSEYE_BLEED ) && ( m_takedamage == DAMAGE_NO ) ) { TraceBleed( info.GetDamage(), vecDir, ptr, info.GetDamageType() ); } BaseClass::TraceAttack( info, vecDir, ptr ); }
void C_SDKRagdoll::ImpactTrace( trace_t *pTrace, int iDamageType, char *pCustomImpactName ) { // DevMsg("C_SDKRagDoll::ImpactTrace: %i\n", iDamageType); IPhysicsObject *pPhysicsObject = VPhysicsGetObject(); if( !pPhysicsObject ) return; Vector dir = pTrace->endpos - pTrace->startpos; if ( iDamageType == DMG_BLAST ) { dir *= 4000; // adjust impact strength // apply force at object mass center pPhysicsObject->ApplyForceCenter( dir ); } else { Vector hitpos; VectorMA( pTrace->startpos, pTrace->fraction, dir, hitpos ); VectorNormalize( dir ); // Blood spray! FX_BloodSpray( hitpos, dir, 3, 72, 0, 0, FX_BLOODSPRAY_ALL ); dir *= 4000; // adjust impact strenght // apply force where we hit it pPhysicsObject->ApplyForceOffset( dir, hitpos ); //Tony; throw in some bleeds! - just use a generic value for damage. TraceBleed( 40, dir, pTrace, iDamageType ); } m_pRagdoll->ResetRagdollSleepAfterTime(); }
//========================================================= // TraceAttack //========================================================= void CBaseMonster :: TraceAttack( entvars_t *pevAttacker, float flDamage, Vector vecDir, TraceResult *ptr, int bitsDamageType) { if ( pev->takedamage ) { m_LastHitGroup = ptr->iHitgroup; switch ( ptr->iHitgroup ) { case HITGROUP_GENERIC: break; case HITGROUP_HEAD: flDamage *= gSkillData.monHead; break; case HITGROUP_CHEST: flDamage *= gSkillData.monChest; break; case HITGROUP_STOMACH: flDamage *= gSkillData.monStomach; break; case HITGROUP_LEFTARM: case HITGROUP_RIGHTARM: flDamage *= gSkillData.monArm; break; case HITGROUP_LEFTLEG: case HITGROUP_RIGHTLEG: flDamage *= gSkillData.monLeg; break; default: break; } SpawnBlood(ptr->vecEndPos, BloodColor(), flDamage);// a little surface blood. TraceBleed( flDamage, vecDir, ptr, bitsDamageType ); AddMultiDamage( pevAttacker, this, flDamage, bitsDamageType ); } }
// make the bleeding more pronounced void CASW_Zombie::TraceAttack( const CTakeDamageInfo &info, const Vector &vecDir, trace_t *ptr ) { m_fNoDamageDecal = false; if ( m_takedamage == DAMAGE_NO ) return; CTakeDamageInfo subInfo = info; SetLastHitGroup( ptr->hitgroup ); m_nForceBone = ptr->physicsbone; // save this bone for physics forces Assert( m_nForceBone > -255 && m_nForceBone < 256 ); bool bDebug = showhitlocation.GetBool(); switch ( ptr->hitgroup ) { case HITGROUP_GENERIC: if( bDebug ) DevMsg("Hit Location: Generic\n"); break; // hit gear, react but don't bleed case HITGROUP_GEAR: subInfo.SetDamage( 0.01 ); ptr->hitgroup = HITGROUP_GENERIC; if( bDebug ) DevMsg("Hit Location: Gear\n"); break; case HITGROUP_HEAD: subInfo.ScaleDamage( GetHitgroupDamageMultiplier(ptr->hitgroup, info) ); if( bDebug ) DevMsg("Hit Location: Head\n"); break; case HITGROUP_CHEST: subInfo.ScaleDamage( GetHitgroupDamageMultiplier(ptr->hitgroup, info) ); if( bDebug ) DevMsg("Hit Location: Chest\n"); break; case HITGROUP_STOMACH: subInfo.ScaleDamage( GetHitgroupDamageMultiplier(ptr->hitgroup, info) ); if( bDebug ) DevMsg("Hit Location: Stomach\n"); break; case HITGROUP_LEFTARM: case HITGROUP_RIGHTARM: subInfo.ScaleDamage( GetHitgroupDamageMultiplier(ptr->hitgroup, info) ); if( bDebug ) DevMsg("Hit Location: Left/Right Arm\n"); break ; case HITGROUP_LEFTLEG: case HITGROUP_RIGHTLEG: subInfo.ScaleDamage( GetHitgroupDamageMultiplier(ptr->hitgroup, info) ); if( bDebug ) DevMsg("Hit Location: Left/Right Leg\n"); break; default: if( bDebug ) DevMsg("Hit Location: UNKNOWN\n"); break; } if ( subInfo.GetDamage() >= 1.0 && !(subInfo.GetDamageType() & DMG_SHOCK ) ) { if( !IsPlayer() || ( IsPlayer() && gpGlobals->maxClients > 1 ) ) { // NPC's always bleed. Players only bleed in multiplayer. //SpawnBlood( ptr->endpos, vecDir, BloodColor(), subInfo.GetDamage() );// a little surface blood. //UTIL_ASW_DroneBleed( ptr->endpos, vecDir, 4 ); UTIL_ASW_BloodDrips( GetAbsOrigin()+Vector(0,0,60)+vecDir*3, vecDir, BloodColor(), 5 ); } TraceBleed( subInfo.GetDamage(), vecDir, ptr, subInfo.GetDamageType() ); if ( ptr->hitgroup == HITGROUP_HEAD && m_iHealth - subInfo.GetDamage() > 0 ) { m_fNoDamageDecal = true; } } // Airboat gun will impart major force if it's about to kill him.... if ( info.GetDamageType() & DMG_AIRBOAT ) { if ( subInfo.GetDamage() >= GetHealth() ) { float flMagnitude = subInfo.GetDamageForce().Length(); if ( (flMagnitude != 0.0f) && (flMagnitude < 400.0f * 65.0f) ) { subInfo.ScaleDamageForce( 400.0f * 65.0f / flMagnitude ); } } } if( info.GetInflictor() ) { subInfo.SetInflictor( info.GetInflictor() ); } else { subInfo.SetInflictor( info.GetAttacker() ); } AddMultiDamage( subInfo, this ); }