diff --git a/docs/src/sentences.json b/docs/src/sentences.json index 55c060bca..e8ecfa916 100644 --- a/docs/src/sentences.json +++ b/docs/src/sentences.json @@ -4884,6 +4884,10 @@ { "english": "Scientist Zombie" }, +"monster_zombie::allow_headcrab": +{ +"english": "Headcrab can jump" +}, "monstermaker::classname": { "english": "Monster Maker" diff --git a/src/data/base/BaseZombie.json b/src/data/base/BaseZombie.json new file mode 100644 index 000000000..c09924b48 --- /dev/null +++ b/src/data/base/BaseZombie.json @@ -0,0 +1,22 @@ +{ + "$schema": "../schema.json", + "Class": "Base", + "data": + { + "allow_headcrab": + { + "variable": "choices", + "value": "1", + "choices": { + "0": { + "title": "No" + }, + "1": { + "title": "Yes" + } + }, + "title": "monster_zombie::allow_headcrab", + "description": "monster_zombie::allow_headcrab::description" + } + } +} \ No newline at end of file diff --git a/src/data/entities/monster_zombie.json b/src/data/entities/monster_zombie.json index 290328a3a..abae0c21d 100644 --- a/src/data/entities/monster_zombie.json +++ b/src/data/entities/monster_zombie.json @@ -2,6 +2,7 @@ "$schema": "../schema.json", "Class": "Point", "base": [ + "BaseZombie", "Monster", "Target", "RenderFields", diff --git a/src/data/entities/monster_zombie_barney.json b/src/data/entities/monster_zombie_barney.json index 7d0bd9511..31239750d 100644 --- a/src/data/entities/monster_zombie_barney.json +++ b/src/data/entities/monster_zombie_barney.json @@ -2,6 +2,7 @@ "$schema": "../schema.json", "Class": "Point", "base": [ + "BaseZombie", "Monster", "Target", "RenderFields", diff --git a/src/data/entities/monster_zombie_soldier.json b/src/data/entities/monster_zombie_soldier.json index 109caa374..066c0d79e 100644 --- a/src/data/entities/monster_zombie_soldier.json +++ b/src/data/entities/monster_zombie_soldier.json @@ -2,6 +2,7 @@ "$schema": "../schema.json", "Class": "Point", "base": [ + "BaseZombie", "Monster", "Target", "RenderFields", diff --git a/src/game/server/entities/NPCs/zombies/zombie.cpp b/src/game/server/entities/NPCs/zombies/zombie.cpp index f3d549109..a7e1a9642 100644 --- a/src/game/server/entities/NPCs/zombies/zombie.cpp +++ b/src/game/server/entities/NPCs/zombies/zombie.cpp @@ -18,11 +18,16 @@ #include "cbase.h" #include "zombie.h" +BEGIN_DATAMAP(CZombie) + DEFINE_FIELD(m_iAllowHeadcrab, FIELD_INTEGER), + DEFINE_FIELD(m_flDamageTaken, FIELD_FLOAT), +END_DATAMAP(); + LINK_ENTITY_TO_CLASS(monster_zombie, CZombie); void CZombie::OnCreate() { - CBaseMonster::OnCreate(); + BaseClass::OnCreate(); pev->health = GetSkillFloat("zombie_health"sv); pev->model = MAKE_STRING("models/zombie.mdl"); @@ -59,7 +64,7 @@ bool CZombie::TakeDamage(CBaseEntity* inflictor, CBaseEntity* attacker, float fl // HACK HACK -- until we fix this. if (IsAlive()) PainSound(); - return CBaseMonster::TakeDamage(inflictor, attacker, flDamage, bitsDamageType); + return BaseClass::TakeDamage(inflictor, attacker, flDamage, bitsDamageType); } void CZombie::PainSound() @@ -142,7 +147,7 @@ void CZombie::HandleAnimEvent(MonsterEvent_t* pEvent) break; default: - CBaseMonster::HandleAnimEvent(pEvent); + BaseClass::HandleAnimEvent(pEvent); break; } } @@ -156,7 +161,6 @@ void CZombie::Spawn() pev->solid = SOLID_SLIDEBOX; pev->movetype = MOVETYPE_STEP; - m_bloodColor = BLOOD_COLOR_GREEN; pev->view_ofs = VEC_VIEW; // position of the eyes relative to monster's origin. m_flFieldOfView = 0.5; // indicates the width of this monster's forward view cone ( as a dotproduct result ) m_MonsterState = MONSTERSTATE_NONE; @@ -167,6 +171,8 @@ void CZombie::Spawn() void CZombie::Precache() { + UTIL_PrecacheOther( "monster_headcrab" ); + PrecacheModel(STRING(pev->model)); PRECACHE_SOUND_ARRAY(pAttackHitSounds); @@ -179,7 +185,7 @@ void CZombie::Precache() int CZombie::IgnoreConditions() { - int iIgnore = CBaseMonster::IgnoreConditions(); + int iIgnore = BaseClass::IgnoreConditions(); if (m_Activity == ACT_MELEE_ATTACK1) { @@ -200,3 +206,42 @@ int CZombie::IgnoreConditions() return iIgnore; } + +void CZombie::TraceAttack(CBaseEntity* pAttacker, float flDamage, Vector vecDir, TraceResult* ptr, int bitsDamageType) +{ + if( m_iAllowHeadcrab == 1 && ptr->iHitgroup == 1 ) // check for headcrab shot + { + m_flDamageTaken += flDamage; // Store received damage + } + + m_bloodColor = ( ptr->iHitgroup == 1 ? BLOOD_COLOR_GREEN : BLOOD_COLOR_RED ); // If headshot drop green blood + + BaseClass::TraceAttack(pAttacker, flDamage, vecDir, ptr, bitsDamageType); +} + +void CZombie::Killed(CBaseEntity* pAttacker, int iGib) +{ + // Check if the stored received damage is less than a headcrab's HP + if( m_iAllowHeadcrab == 1 && m_flDamageTaken < GetSkillFloat("headcrab_health"sv) ) + { + SetBodygroup( 1, 1 ); + + CBaseEntity* pEntity = Create( "monster_headcrab", pev->origin + Vector( 0,0,72 ), pev->angles, this ); + + pEntity->pev->health = GetSkillFloat("headcrab_health"sv) - m_flDamageTaken; + } + BaseClass::Killed(pAttacker, iGib); +} + +bool CZombie::KeyValue(KeyValueData* pkvd) +{ + if( FStrEq( pkvd->szKeyName, "allow_headcrab" ) ) + { + m_iAllowHeadcrab = atoi( pkvd->szValue ); + } + else + { + return BaseClass::KeyValue(pkvd); + } + return true; +} diff --git a/src/game/server/entities/NPCs/zombies/zombie.h b/src/game/server/entities/NPCs/zombies/zombie.h index 14c9ce3cf..8468ba76e 100644 --- a/src/game/server/entities/NPCs/zombies/zombie.h +++ b/src/game/server/entities/NPCs/zombies/zombie.h @@ -23,6 +23,9 @@ class CZombie : public CBaseMonster { + DECLARE_CLASS( CZombie, CBaseMonster ); + DECLARE_DATAMAP(); + public: void OnCreate() override; void Spawn() override; @@ -84,6 +87,9 @@ class CZombie : public CBaseMonster bool CheckRangeAttack1(float flDot, float flDist) override { return false; } bool CheckRangeAttack2(float flDot, float flDist) override { return false; } bool TakeDamage(CBaseEntity* inflictor, CBaseEntity* attacker, float flDamage, int bitsDamageType) override; + void TraceAttack(CBaseEntity* pAttacker, float flDamage, Vector vecDir, TraceResult* ptr, int bitsDamageType) override; + void Killed(CBaseEntity* pAttacker, int iGib) override; + bool KeyValue(KeyValueData* pkvd) override; protected: virtual float GetOneSlashDamage(); @@ -93,4 +99,7 @@ class CZombie : public CBaseMonster // Take 30% damage from bullets by default virtual float GetBulletDamageFraction() const { return 0.3f; } + + int m_iAllowHeadcrab = 1; + float m_flDamageTaken = 0.0f; }; diff --git a/unity/models/zombie.mdl b/unity/models/zombie.mdl index c41a8a7af..7a9909767 100644 Binary files a/unity/models/zombie.mdl and b/unity/models/zombie.mdl differ diff --git a/unity/models/zombie_barney.mdl b/unity/models/zombie_barney.mdl index 985df2781..22668a4f0 100644 Binary files a/unity/models/zombie_barney.mdl and b/unity/models/zombie_barney.mdl differ diff --git a/unity/models/zombie_soldier.mdl b/unity/models/zombie_soldier.mdl index 5ef06097a..c616a42b4 100644 Binary files a/unity/models/zombie_soldier.mdl and b/unity/models/zombie_soldier.mdl differ