This repository has been archived on 2024-06-13. You can view files and clone it, but cannot push or open issues or pull requests.
2020-08-04 13:13:01 -04:00

369 lines
13 KiB
C++

//========= Copyright Valve Corporation, All rights reserved. ============//
//
// Purpose:
//
// $NoKeywords: $
//=============================================================================//
#ifndef TAKEDAMAGEINFO_H
#define TAKEDAMAGEINFO_H
#ifdef _WIN32
#pragma once
#endif
#include "networkvar.h" // todo: change this when DECLARE_CLASS is moved into a better location.
// Used to initialize m_flBaseDamage to something that we know pretty much for
// sure hasn't been modified by a user.
#define BASEDAMAGE_NOT_SPECIFIED FLT_MAX
class CBaseEntity;
class CTakeDamageInfo {
public:
DECLARE_CLASS_NOBASE(CTakeDamageInfo);
CTakeDamageInfo();
CTakeDamageInfo(CBaseEntity *pInflictor, CBaseEntity *pAttacker,
float flDamage, int bitsDamageType, int iKillType = 0);
CTakeDamageInfo(CBaseEntity *pInflictor, CBaseEntity *pAttacker,
CBaseEntity *pWeapon, float flDamage, int bitsDamageType,
int iKillType = 0);
CTakeDamageInfo(CBaseEntity *pInflictor, CBaseEntity *pAttacker,
const Vector &damageForce, const Vector &damagePosition,
float flDamage, int bitsDamageType, int iKillType = 0,
Vector *reportedPosition = NULL);
CTakeDamageInfo(CBaseEntity *pInflictor, CBaseEntity *pAttacker,
CBaseEntity *pWeapon, const Vector &damageForce,
const Vector &damagePosition, float flDamage,
int bitsDamageType, int iKillType = 0,
Vector *reportedPosition = NULL);
// Inflictor is the weapon or rocket (or player) that is dealing the damage.
CBaseEntity *GetInflictor() const;
void SetInflictor(CBaseEntity *pInflictor);
// Weapon is the weapon that did the attack.
// For hitscan weapons, it'll be the same as the inflictor. For projectile
// weapons, the projectile is the inflictor, and this contains the weapon
// that created the projectile.
CBaseEntity *GetWeapon() const;
void SetWeapon(CBaseEntity *pWeapon);
// Attacker is the character who originated the attack (like a player or an
// AI).
CBaseEntity *GetAttacker() const;
void SetAttacker(CBaseEntity *pAttacker);
float GetDamage() const;
void SetDamage(float flDamage);
float GetMaxDamage() const;
void SetMaxDamage(float flMaxDamage);
void ScaleDamage(float flScaleAmount);
void AddDamage(float flAddAmount);
void SubtractDamage(float flSubtractAmount);
float GetDamageBonus() const;
CBaseEntity *GetDamageBonusProvider() const;
void SetDamageBonus(float flBonus, CBaseEntity *pProvider = NULL);
float GetBaseDamage() const;
bool BaseDamageIsValid() const;
Vector GetDamageForce() const;
void SetDamageForce(const Vector &damageForce);
void ScaleDamageForce(float flScaleAmount);
float GetDamageForForceCalc() const;
void SetDamageForForceCalc(const float flScaleAmount);
Vector GetDamagePosition() const;
void SetDamagePosition(const Vector &damagePosition);
Vector GetReportedPosition() const;
void SetReportedPosition(const Vector &reportedPosition);
int GetDamageType() const;
void SetDamageType(int bitsDamageType);
void AddDamageType(int bitsDamageType);
int GetDamageCustom(void) const;
void SetDamageCustom(int iDamageCustom);
int GetDamageStats(void) const;
void SetDamageStats(int iDamageStats);
void SetForceFriendlyFire(bool bValue) { m_bForceFriendlyFire = bValue; }
bool IsForceFriendlyFire(void) const { return m_bForceFriendlyFire; }
int GetAmmoType() const;
void SetAmmoType(int iAmmoType);
const char *GetAmmoName() const;
int GetPlayerPenetrationCount() const { return m_iPlayerPenetrationCount; }
void SetPlayerPenetrationCount(int iPlayerPenetrationCount) {
m_iPlayerPenetrationCount = iPlayerPenetrationCount;
}
int GetDamagedOtherPlayers() const { return m_iDamagedOtherPlayers; }
void SetDamagedOtherPlayers(int iVal) { m_iDamagedOtherPlayers = iVal; }
void Set(CBaseEntity *pInflictor, CBaseEntity *pAttacker, float flDamage,
int bitsDamageType, int iKillType = 0);
void Set(CBaseEntity *pInflictor, CBaseEntity *pAttacker,
CBaseEntity *pWeapon, float flDamage, int bitsDamageType,
int iKillType = 0);
void Set(CBaseEntity *pInflictor, CBaseEntity *pAttacker,
const Vector &damageForce, const Vector &damagePosition,
float flDamage, int bitsDamageType, int iKillType = 0,
Vector *reportedPosition = NULL);
void Set(CBaseEntity *pInflictor, CBaseEntity *pAttacker,
CBaseEntity *pWeapon, const Vector &damageForce,
const Vector &damagePosition, float flDamage, int bitsDamageType,
int iKillType = 0, Vector *reportedPosition = NULL);
void AdjustPlayerDamageInflictedForSkillLevel();
void AdjustPlayerDamageTakenForSkillLevel();
// Given a damage type (composed of the #defines above), fill out a string
// with the appropriate text. For designer debug output.
static void DebugGetDamageTypeString(unsigned int DamageType, char *outbuf,
int outbuflength);
// private:
void CopyDamageToBaseDamage();
protected:
void Init(CBaseEntity *pInflictor, CBaseEntity *pAttacker,
CBaseEntity *pWeapon, const Vector &damageForce,
const Vector &damagePosition, const Vector &reportedPosition,
float flDamage, int bitsDamageType, int iKillType);
Vector m_vecDamageForce;
Vector m_vecDamagePosition;
Vector m_vecReportedPosition; // Position players are told damage is coming
// from
EHANDLE m_hInflictor;
EHANDLE m_hAttacker;
EHANDLE m_hWeapon;
float m_flDamage;
float m_flMaxDamage;
float m_flBaseDamage; // The damage amount before skill leve adjustments
// are made. Used to get uniform damage forces.
int m_bitsDamageType;
int m_iDamageCustom;
int m_iDamageStats;
int m_iAmmoType; // AmmoType of the weapon used to cause this damage, if
// any
int m_iDamagedOtherPlayers;
int m_iPlayerPenetrationCount;
float m_flDamageBonus; // Anything that increases damage (crit) - store the
// delta
EHANDLE
m_hDamageBonusProvider; // Who gave us the ability to do extra damage?
bool m_bForceFriendlyFire; // Ideally this would be a dmg type, but we
// can't add more
float m_flDamageForForce;
DECLARE_SIMPLE_DATADESC();
};
//-----------------------------------------------------------------------------
// Purpose: Multi damage. Used to collect multiple damages in the same frame
// (i.e. shotgun pellets)
//-----------------------------------------------------------------------------
class CMultiDamage : public CTakeDamageInfo {
DECLARE_CLASS(CMultiDamage, CTakeDamageInfo);
public:
CMultiDamage();
bool IsClear(void) { return (m_hTarget == NULL); }
CBaseEntity *GetTarget() const;
void SetTarget(CBaseEntity *pTarget);
void Init(CBaseEntity *pTarget, CBaseEntity *pInflictor,
CBaseEntity *pAttacker, CBaseEntity *pWeapon,
const Vector &damageForce, const Vector &damagePosition,
const Vector &reportedPosition, float flDamage,
int bitsDamageType, int iKillType);
protected:
EHANDLE m_hTarget;
DECLARE_SIMPLE_DATADESC();
};
extern CMultiDamage g_MultiDamage;
// Multidamage accessors
void ClearMultiDamage(void);
void ApplyMultiDamage(void);
void AddMultiDamage(const CTakeDamageInfo &info, CBaseEntity *pEntity);
//-----------------------------------------------------------------------------
// Purpose: Utility functions for physics damage force calculation
//-----------------------------------------------------------------------------
float ImpulseScale(float flTargetMass, float flDesiredSpeed);
void CalculateExplosiveDamageForce(CTakeDamageInfo *info, const Vector &vecDir,
const Vector &vecForceOrigin,
float flScale = 1.0);
void CalculateBulletDamageForce(CTakeDamageInfo *info, int iBulletType,
const Vector &vecBulletDir,
const Vector &vecForceOrigin,
float flScale = 1.0);
void CalculateMeleeDamageForce(CTakeDamageInfo *info, const Vector &vecMeleeDir,
const Vector &vecForceOrigin,
float flScale = 1.0);
void GuessDamageForce(CTakeDamageInfo *info, const Vector &vecForceDir,
const Vector &vecForceOrigin, float flScale = 1.0);
// --------------------------------------------------------------------------------------------------
// // Inlines.
// --------------------------------------------------------------------------------------------------
// //
inline CBaseEntity *CTakeDamageInfo::GetInflictor() const {
return m_hInflictor;
}
inline void CTakeDamageInfo::SetInflictor(CBaseEntity *pInflictor) {
m_hInflictor = pInflictor;
}
inline CBaseEntity *CTakeDamageInfo::GetAttacker() const { return m_hAttacker; }
inline void CTakeDamageInfo::SetAttacker(CBaseEntity *pAttacker) {
m_hAttacker = pAttacker;
}
inline CBaseEntity *CTakeDamageInfo::GetWeapon() const { return m_hWeapon; }
inline void CTakeDamageInfo::SetWeapon(CBaseEntity *pWeapon) {
m_hWeapon = pWeapon;
}
inline float CTakeDamageInfo::GetDamage() const { return m_flDamage; }
inline void CTakeDamageInfo::SetDamage(float flDamage) {
m_flDamage = flDamage;
}
inline float CTakeDamageInfo::GetMaxDamage() const { return m_flMaxDamage; }
inline void CTakeDamageInfo::SetMaxDamage(float flMaxDamage) {
m_flMaxDamage = flMaxDamage;
}
inline void CTakeDamageInfo::ScaleDamage(float flScaleAmount) {
m_flDamage *= flScaleAmount;
}
inline void CTakeDamageInfo::AddDamage(float flAddAmount) {
m_flDamage += flAddAmount;
}
inline void CTakeDamageInfo::SubtractDamage(float flSubtractAmount) {
m_flDamage -= flSubtractAmount;
}
inline float CTakeDamageInfo::GetDamageBonus() const { return m_flDamageBonus; }
inline CBaseEntity *CTakeDamageInfo::GetDamageBonusProvider() const {
return m_hDamageBonusProvider;
}
inline void CTakeDamageInfo::SetDamageBonus(float flBonus,
CBaseEntity *pProvider /*= NULL*/) {
m_flDamageBonus = flBonus;
m_hDamageBonusProvider = pProvider;
}
inline float CTakeDamageInfo::GetBaseDamage() const {
if (BaseDamageIsValid()) return m_flBaseDamage;
// No one ever specified a base damage, so just return damage.
return m_flDamage;
}
inline bool CTakeDamageInfo::BaseDamageIsValid() const {
return (m_flBaseDamage != BASEDAMAGE_NOT_SPECIFIED);
}
inline Vector CTakeDamageInfo::GetDamageForce() const {
return m_vecDamageForce;
}
inline void CTakeDamageInfo::SetDamageForce(const Vector &damageForce) {
m_vecDamageForce = damageForce;
}
inline void CTakeDamageInfo::ScaleDamageForce(float flScaleAmount) {
m_vecDamageForce *= flScaleAmount;
}
inline float CTakeDamageInfo::GetDamageForForceCalc() const {
return m_flDamageForForce;
}
inline void CTakeDamageInfo::SetDamageForForceCalc(float flDamage) {
m_flDamageForForce = flDamage;
}
inline Vector CTakeDamageInfo::GetDamagePosition() const {
return m_vecDamagePosition;
}
inline void CTakeDamageInfo::SetDamagePosition(const Vector &damagePosition) {
m_vecDamagePosition = damagePosition;
}
inline Vector CTakeDamageInfo::GetReportedPosition() const {
return m_vecReportedPosition;
}
inline void CTakeDamageInfo::SetReportedPosition(
const Vector &reportedPosition) {
m_vecReportedPosition = reportedPosition;
}
inline void CTakeDamageInfo::SetDamageType(int bitsDamageType) {
m_bitsDamageType = bitsDamageType;
}
inline int CTakeDamageInfo::GetDamageType() const { return m_bitsDamageType; }
inline void CTakeDamageInfo::AddDamageType(int bitsDamageType) {
m_bitsDamageType |= bitsDamageType;
}
inline int CTakeDamageInfo::GetDamageCustom() const { return m_iDamageCustom; }
inline void CTakeDamageInfo::SetDamageCustom(int iDamageCustom) {
m_iDamageCustom = iDamageCustom;
}
inline int CTakeDamageInfo::GetDamageStats() const { return m_iDamageCustom; }
inline void CTakeDamageInfo::SetDamageStats(int iDamageCustom) {
m_iDamageCustom = iDamageCustom;
}
inline int CTakeDamageInfo::GetAmmoType() const { return m_iAmmoType; }
inline void CTakeDamageInfo::SetAmmoType(int iAmmoType) {
m_iAmmoType = iAmmoType;
}
inline void CTakeDamageInfo::CopyDamageToBaseDamage() {
m_flBaseDamage = m_flDamage;
}
// --------------------------------------------------------------------------------------------------
// // Inlines.
// --------------------------------------------------------------------------------------------------
// //
inline CBaseEntity *CMultiDamage::GetTarget() const { return m_hTarget; }
inline void CMultiDamage::SetTarget(CBaseEntity *pTarget) {
m_hTarget = pTarget;
}
#endif // TAKEDAMAGEINFO_H