From e5a41a135821d48e65f460979b6f566c02ccc2fd Mon Sep 17 00:00:00 2001 From: MajorCooke Date: Sat, 20 Dec 2014 16:57:00 -0600 Subject: [PATCH 1/4] - Added name filtering to all A_Damage/Kill/Remove functions. - A_DamageChildren(20,"Normal",0,"DoomImp") for example will only target actors of DoomImp specifically. --- src/thingdef/thingdef_codeptr.cpp | 158 +++++++++++++++++++++++------- wadsrc/static/actors/actor.txt | 34 +++---- 2 files changed, 138 insertions(+), 54 deletions(-) diff --git a/src/thingdef/thingdef_codeptr.cpp b/src/thingdef/thingdef_codeptr.cpp index 98451795b..23fe031c7 100644 --- a/src/thingdef/thingdef_codeptr.cpp +++ b/src/thingdef/thingdef_codeptr.cpp @@ -5068,12 +5068,15 @@ static void DoDamage(AActor *dmgtarget, AActor *self, int amount, FName DamageTy //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSelf) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); + ACTION_PARAM_CLASS(filter, 3); - DoDamage(self, self, amount, DamageType, flags); + const PClass *c1 = self->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoDamage(self, self, amount, DamageType, flags); } //=========================================================================== @@ -5083,12 +5086,18 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSelf) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTarget) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); + ACTION_PARAM_CLASS(filter, 3); - if (self->target != NULL) DoDamage(self->target, self, amount, DamageType, flags); + if (self->target != NULL) + { + const PClass *c1 = self->target->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoDamage(self->target, self, amount, DamageType, flags); + } } //=========================================================================== @@ -5098,12 +5107,18 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTarget) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTracer) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); + ACTION_PARAM_CLASS(filter, 3); - if (self->tracer != NULL) DoDamage(self->tracer, self, amount, DamageType, flags); + if (self->tracer != NULL) + { + const PClass *c1 = self->tracer->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoDamage(self->tracer, self, amount, DamageType, flags); + } } //=========================================================================== @@ -5113,12 +5128,18 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTracer) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageMaster) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); + ACTION_PARAM_CLASS(filter, 3); - if (self->master != NULL) DoDamage(self->master, self, amount, DamageType, flags); + if (self->master != NULL) + { + const PClass *c1 = self->master->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoDamage(self->master, self, amount, DamageType, flags); + } } //=========================================================================== @@ -5128,17 +5149,23 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageMaster) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageChildren) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); + ACTION_PARAM_CLASS(filter, 3); TThinkerIterator it; AActor * mo; while ( (mo = it.Next()) ) { - if (mo->master == self) DoDamage(mo, self, amount, DamageType, flags); + if (mo->master == self) + { + const PClass *c1 = mo->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoDamage(mo, self, amount, DamageType, flags); + } } } @@ -5149,10 +5176,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageChildren) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSiblings) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); + ACTION_PARAM_CLASS(filter, 3); TThinkerIterator it; AActor * mo; @@ -5161,7 +5189,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSiblings) { while ((mo = it.Next())) { - if (mo->master == self->master && mo != self) DoDamage(mo, self, amount, DamageType, flags); + if (mo->master == self->master && mo != self) + { + const PClass *c1 = mo->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoDamage(mo, self, amount, DamageType, flags); + } } } } @@ -5214,11 +5247,17 @@ static void DoKill(AActor *killtarget, AActor *self, FName damagetype, int flags //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTarget) { - ACTION_PARAM_START(2); + ACTION_PARAM_START(3); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); + ACTION_PARAM_CLASS(filter, 2); - if (self->target != NULL) DoKill(self->target, self, damagetype, flags); + if (self->target != NULL) + { + const PClass *c1 = self->target->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoKill(self->target, self, damagetype, flags); + } } //=========================================================================== @@ -5228,11 +5267,17 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTarget) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTracer) { - ACTION_PARAM_START(2); + ACTION_PARAM_START(3); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); + ACTION_PARAM_CLASS(filter, 2); - if (self->tracer != NULL) DoKill(self->tracer, self, damagetype, flags); + if (self->tracer != NULL) + { + const PClass *c1 = self->tracer->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoKill(self->tracer, self, damagetype, flags); + } } //=========================================================================== @@ -5242,11 +5287,17 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTracer) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillMaster) { - ACTION_PARAM_START(2); + ACTION_PARAM_START(3); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); + ACTION_PARAM_CLASS(filter, 2); - if (self->master != NULL) DoKill(self->master, self, damagetype, flags); + if (self->master != NULL) + { + const PClass *c1 = self->master->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoKill(self->master, self, damagetype, flags); + } } //=========================================================================== @@ -5256,16 +5307,22 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillMaster) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillChildren) { - ACTION_PARAM_START(2); + ACTION_PARAM_START(3); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); + ACTION_PARAM_CLASS(filter, 2); TThinkerIterator it; AActor *mo; while ( (mo = it.Next()) ) { - if (mo->master == self) DoKill(mo, self, damagetype, flags); + if (mo->master == self) + { + const PClass *c1 = mo->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoKill(mo, self, damagetype, flags); + } } } @@ -5276,9 +5333,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillChildren) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillSiblings) { - ACTION_PARAM_START(2); + ACTION_PARAM_START(3); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); + ACTION_PARAM_CLASS(filter, 2); TThinkerIterator it; AActor *mo; @@ -5287,7 +5345,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillSiblings) { while ( (mo = it.Next()) ) { - if (mo->master == self->master && mo != self) DoKill(mo, self, damagetype, flags); + if (mo->master == self->master && mo != self) + { + const PClass *c1 = mo->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoKill(mo, self, damagetype, flags); + } } } } @@ -5333,11 +5396,15 @@ static void DoRemove(AActor *removetarget, int flags) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTarget) { - ACTION_PARAM_START(1); + ACTION_PARAM_START(2); ACTION_PARAM_INT(flags, 0); - if (self->master != NULL) + ACTION_PARAM_CLASS(filter, 1); + + if (self->target != NULL) { - DoRemove(self->target, flags); + const PClass *c1 = self->target->GetClass(); + if ((filter && (c1 == filter)) || (filter == NULL) || !(filter)) + DoRemove(self->target, flags); } } @@ -5348,11 +5415,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTarget) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTracer) { - ACTION_PARAM_START(1); + ACTION_PARAM_START(2); ACTION_PARAM_INT(flags, 0); - if (self->master != NULL) + ACTION_PARAM_CLASS(filter, 1); + + if (self->tracer != NULL) { - DoRemove(self->tracer, flags); + const PClass *c1 = self->tracer->GetClass(); + if ((filter && (c1 == filter)) || (filter == NULL) || !(filter)) + DoRemove(self->tracer, flags); } } @@ -5363,11 +5434,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTracer) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveMaster) { - ACTION_PARAM_START(1); + ACTION_PARAM_START(2); ACTION_PARAM_INT(flags, 0); + ACTION_PARAM_CLASS(filter, 1); + if (self->master != NULL) { - DoRemove(self->master, flags); + const PClass *c1 = self->master->GetClass(); + if ((filter && (c1 == filter)) || (filter == NULL) || !(filter)) + DoRemove(self->master, flags); } } @@ -5380,15 +5455,19 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveChildren) { TThinkerIterator it; AActor *mo; - ACTION_PARAM_START(2); + ACTION_PARAM_START(3); ACTION_PARAM_BOOL(removeall, 0); ACTION_PARAM_INT(flags, 1); + ACTION_PARAM_CLASS(filter, 2); + while ((mo = it.Next()) != NULL) { if (mo->master == self && (mo->health <= 0 || removeall)) { - DoRemove(mo, flags); + const PClass *c1 = mo->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoRemove(mo, flags); } } } @@ -5402,9 +5481,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) { TThinkerIterator it; AActor *mo; - ACTION_PARAM_START(2); + ACTION_PARAM_START(3); ACTION_PARAM_BOOL(removeall, 0); ACTION_PARAM_INT(flags, 1); + ACTION_PARAM_CLASS(filter, 2); if (self->master != NULL) { @@ -5412,7 +5492,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) { if (mo->master == self->master && mo != self && (mo->health <= 0 || removeall)) { - DoRemove(mo, flags); + const PClass *c1 = mo->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoRemove(mo, flags); } } } @@ -5425,15 +5507,17 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Remove) { - ACTION_PARAM_START(2); + ACTION_PARAM_START(3); ACTION_PARAM_INT(removee, 0); ACTION_PARAM_INT(flags, 1); + ACTION_PARAM_CLASS(filter, 2); AActor *reference = COPY_AAPTR(self, removee); - if (reference != NULL) { - DoRemove(reference, flags); + const PClass *c1 = reference->GetClass(); + if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) + DoRemove(reference, flags); } } diff --git a/wadsrc/static/actors/actor.txt b/wadsrc/static/actors/actor.txt index cd718b1c0..910bd0778 100644 --- a/wadsrc/static/actors/actor.txt +++ b/wadsrc/static/actors/actor.txt @@ -237,12 +237,6 @@ ACTOR Actor native //: Thinker action native A_ChangeFlag(string flagname, bool value); action native A_CheckFlag(string flagname, state label, int check_pointer = AAPTR_DEFAULT); action native A_JumpIf(bool expression, state label); - action native A_RemoveMaster(int flags = 0); - action native A_RemoveChildren(bool removeall = false, int flags = 0); - action native A_RemoveSiblings(bool removeall = false, int flags = 0); - action native A_KillMaster(name damagetype = "none", int flags = 0); - action native A_KillChildren(name damagetype = "none", int flags = 0); - action native A_KillSiblings(name damagetype = "none", int flags = 0); action native A_RaiseMaster(bool copy = 0); action native A_RaiseChildren(bool copy = 0); action native A_RaiseSiblings(bool copy = 0); @@ -278,9 +272,6 @@ ACTOR Actor native //: Thinker action native A_CheckLOF(state jump, int flags = 0, float range = 0, float minrange = 0, float angle = 0, float pitch = 0, float offsetheight = 0, float offsetwidth = 0, int ptr_target = AAPTR_DEFAULT); action native A_JumpIfTargetInLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); action native A_JumpIfInTargetLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); - action native A_DamageMaster(int amount, name damagetype = "none", int flags = 0); - action native A_DamageChildren(int amount, name damagetype = "none", int flags = 0); - action native A_DamageSiblings(int amount, name damagetype = "none", int flags = 0); action native A_SelectWeapon(class whichweapon); action native A_Punch(); action native A_Feathers(); @@ -307,14 +298,23 @@ ACTOR Actor native //: Thinker action native A_SetDamageType(name damagetype); action native A_DropItem(class item, int dropamount = -1, int chance = 256); action native A_SetSpeed(float speed); - action native A_DamageSelf(int amount, name damagetype = "none", int flags = 0); - action native A_DamageTarget(int amount, name damagetype = "none", int flags = 0); - action native A_DamageTracer(int amount, name damagetype = "none", int flags = 0); - action native A_KillTarget(name damagetype = "none", int flags = 0); - action native A_KillTracer(name damagetype = "none", int flags = 0); - action native A_RemoveTarget(int flags = 0); - action native A_RemoveTracer(int flags = 0); - action native A_Remove(int removee, int flags = 0); + action native A_DamageSelf(int amount, name damagetype = "none", int flags = 0, class filter); + action native A_DamageTarget(int amount, name damagetype = "none", int flags = 0, class filter); + action native A_DamageMaster(int amount, name damagetype = "none", int flags = 0, class filter); + action native A_DamageTracer(int amount, name damagetype = "none", int flags = 0, class filter); + action native A_DamageChildren(int amount, name damagetype = "none", int flags = 0, class filter); + action native A_DamageSiblings(int amount, name damagetype = "none", int flags = 0, class filter); + action native A_KillTarget(name damagetype = "none", int flags = 0, class filter); + action native A_KillMaster(name damagetype = "none", int flags = 0, class filter); + action native A_KillTracer(name damagetype = "none", int flags = 0, class filter); + action native A_KillChildren(name damagetype = "none", int flags = 0, class filter); + action native A_KillSiblings(name damagetype = "none", int flags = 0, class filter); + action native A_RemoveTarget(int flags = 0, class filter); + action native A_RemoveMaster(int flags = 0, class filter); + action native A_RemoveTracer(int flags = 0, class filter); + action native A_RemoveChildren(bool removeall = false, int flags = 0, class filter); + action native A_RemoveSiblings(bool removeall = false, int flags = 0, class filter); + action native A_Remove(int removee, int flags = 0, class filter); action native A_GiveToChildren(class itemtype, int amount = 0); action native A_GiveToSiblings(class itemtype, int amount = 0); action native A_TakeFromChildren(class itemtype, int amount = 0); From c168761edacc5aa69bf89f21e3eeb8e769c91c61 Mon Sep 17 00:00:00 2001 From: MajorCooke Date: Sat, 20 Dec 2014 22:51:43 -0600 Subject: [PATCH 2/4] - Couple additional fixes: - The wiki said the minimum distance to teleport defaults to 0, actor.txt on the other hand said otherwise. I was wondering why it was still broken somewhat... - Prevent stickiness from happening, a.k.a. getting stuck in ceiling or floor and letting the engine unstick the actor. This caused velocity loss. --- src/thingdef/thingdef_codeptr.cpp | 21 ++++++++++++++------- wadsrc/static/actors/actor.txt | 2 +- 2 files changed, 15 insertions(+), 8 deletions(-) diff --git a/src/thingdef/thingdef_codeptr.cpp b/src/thingdef/thingdef_codeptr.cpp index 23fe031c7..485db3d86 100644 --- a/src/thingdef/thingdef_codeptr.cpp +++ b/src/thingdef/thingdef_codeptr.cpp @@ -4199,16 +4199,23 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Teleport) fixed_t prevX = self->x; fixed_t prevY = self->y; fixed_t prevZ = self->z; + fixed_t aboveFloor = spot->z - spot->floorz; + fixed_t finalz = spot->floorz + aboveFloor; + + if (spot->z + self->height > spot->ceilingz) + finalz = spot->ceilingz - self->height; + else if (spot->z < spot->floorz) + finalz = spot->floorz; + //Take precedence and cooperate with telefragging first. - bool teleResult = P_TeleportMove(self, spot->x, spot->y, spot->z, Flags & TF_TELEFRAG); - - if ((!(teleResult)) && (Flags & TF_FORCED)) - { - //If for some reason the original move didn't work, regardless of telefrag, force it to move. - self->SetOrigin(spot->x, spot->y, spot->z); - teleResult = true; + bool teleResult = P_TeleportMove(self, spot->x, spot->y, finalz, Flags & TF_TELEFRAG); + if (Flags & TF_FORCED) + { + //If for some reason the original move didn't work, regardless of telefrag, force it to move. + self->SetOrigin(spot->x, spot->y, finalz); + teleResult = true; } if (teleResult) diff --git a/wadsrc/static/actors/actor.txt b/wadsrc/static/actors/actor.txt index 910bd0778..7bc6b8df4 100644 --- a/wadsrc/static/actors/actor.txt +++ b/wadsrc/static/actors/actor.txt @@ -244,7 +244,7 @@ ACTOR Actor native //: Thinker action native A_CheckCeiling(state label); action native A_PlayerSkinCheck(state label); action native A_BasicAttack(int meleedamage, sound meleesound, class missiletype, float missileheight); - action native A_Teleport(state teleportstate = "", class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 128, float maxdist = 0); + action native A_Teleport(state teleportstate = "", class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 0); action native A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, state success_state = ""); action native A_ThrowGrenade(class itemtype, float zheight = 0, float xyvel = 0, float zvel = 0, bool useammo = true); action native A_Weave(int xspeed, int yspeed, float xdist, float ydist); From 5a472e815b9df50079bebbc38c157d3256ace894 Mon Sep 17 00:00:00 2001 From: MajorCooke Date: Sun, 21 Dec 2014 09:31:24 -0600 Subject: [PATCH 3/4] - Added species checking. - Added two more flags for each of the functions, EXFILTER and EXSPECIES. - Stands for "exclude filter/species" and makes the function not take them into account. - Cleaned up the code and placed all the checking in their own subfunctions. --- src/thingdef/thingdef_codeptr.cpp | 213 ++++++++++++++++------------- wadsrc/static/actors/actor.txt | 34 ++--- wadsrc/static/actors/constants.txt | 6 + 3 files changed, 138 insertions(+), 115 deletions(-) diff --git a/src/thingdef/thingdef_codeptr.cpp b/src/thingdef/thingdef_codeptr.cpp index 485db3d86..e61f33ea4 100644 --- a/src/thingdef/thingdef_codeptr.cpp +++ b/src/thingdef/thingdef_codeptr.cpp @@ -5023,6 +5023,18 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpeed) self->Speed = speed; } +static bool DoCheckSpecies(AActor *mo, FName species, bool exclude) +{ + FName spec = mo->Species; + return (!(species) || !(stricmp(species, "")) || (species && ((exclude) ? (spec != species) : (spec == species)))); +} + +static bool DoCheckFilter(AActor *mo, const PClass *filter, bool exclude) +{ + const PClass *c1 = mo->GetClass(); + return (!(filter) || (filter == NULL) || (filter && ((exclude) ? (c1 != filter) : (c1 == filter)))); +} + //=========================================================================== // // Common A_Damage handler @@ -5040,9 +5052,11 @@ enum DMSS DMSS_NOFACTOR = 8, DMSS_FOILBUDDHA = 16, DMSS_NOPROTECT = 32, + DMSS_EXFILTER = 64, + DMSS_EXSPECIES = 128, }; -static void DoDamage(AActor *dmgtarget, AActor *self, int amount, FName DamageType, int flags) +static void DoDamage(AActor *dmgtarget, AActor *self, int amount, FName DamageType, int flags, const PClass *filter, FName species) { int dmgFlags = 0; if (flags & DMSS_FOILINVUL) @@ -5058,13 +5072,19 @@ static void DoDamage(AActor *dmgtarget, AActor *self, int amount, FName DamageTy if (flags & DMSS_NOPROTECT) //Ignore PowerProtection. dmgFlags += DMG_NO_PROTECT; - if (amount > 0) - P_DamageMobj(dmgtarget, self, self, amount, DamageType, dmgFlags); //Should wind up passing them through just fine. - - else if (amount < 0) + bool filterpass = DoCheckFilter(dmgtarget, filter, (flags & DMSS_EXFILTER) ? true : false), + speciespass = DoCheckSpecies(dmgtarget, species, (flags & DMSS_EXSPECIES) ? true : false); + + if (filterpass && speciespass) { - amount = -amount; - P_GiveBody(dmgtarget, amount); + if (amount > 0) + P_DamageMobj(dmgtarget, self, self, amount, DamageType, dmgFlags); //Should wind up passing them through just fine. + + else if (amount < 0) + { + amount = -amount; + P_GiveBody(dmgtarget, amount); + } } } @@ -5075,15 +5095,14 @@ static void DoDamage(AActor *dmgtarget, AActor *self, int amount, FName DamageTy //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSelf) { - ACTION_PARAM_START(4); + ACTION_PARAM_START(5); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); ACTION_PARAM_CLASS(filter, 3); + ACTION_PARAM_NAME(species, 4); - const PClass *c1 = self->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoDamage(self, self, amount, DamageType, flags); + DoDamage(self, self, amount, DamageType, flags, filter, species); } //=========================================================================== @@ -5093,17 +5112,16 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSelf) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTarget) { - ACTION_PARAM_START(4); + ACTION_PARAM_START(5); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); ACTION_PARAM_CLASS(filter, 3); + ACTION_PARAM_NAME(species, 4); if (self->target != NULL) { - const PClass *c1 = self->target->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoDamage(self->target, self, amount, DamageType, flags); + DoDamage(self->target, self, amount, DamageType, flags, filter, species); } } @@ -5114,17 +5132,16 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTarget) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTracer) { - ACTION_PARAM_START(4); + ACTION_PARAM_START(5); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); ACTION_PARAM_CLASS(filter, 3); + ACTION_PARAM_NAME(species, 4); if (self->tracer != NULL) { - const PClass *c1 = self->tracer->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoDamage(self->tracer, self, amount, DamageType, flags); + DoDamage(self->tracer, self, amount, DamageType, flags, filter, species); } } @@ -5135,17 +5152,16 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTracer) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageMaster) { - ACTION_PARAM_START(4); + ACTION_PARAM_START(5); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); ACTION_PARAM_CLASS(filter, 3); + ACTION_PARAM_NAME(species, 4); if (self->master != NULL) { - const PClass *c1 = self->master->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoDamage(self->master, self, amount, DamageType, flags); + DoDamage(self->master, self, amount, DamageType, flags, filter, species); } } @@ -5156,11 +5172,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageMaster) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageChildren) { - ACTION_PARAM_START(4); + ACTION_PARAM_START(5); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); ACTION_PARAM_CLASS(filter, 3); + ACTION_PARAM_NAME(species, 4); TThinkerIterator it; AActor * mo; @@ -5169,9 +5186,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageChildren) { if (mo->master == self) { - const PClass *c1 = mo->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoDamage(mo, self, amount, DamageType, flags); + DoDamage(mo, self, amount, DamageType, flags, filter, species); } } } @@ -5183,11 +5198,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageChildren) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSiblings) { - ACTION_PARAM_START(4); + ACTION_PARAM_START(5); ACTION_PARAM_INT(amount, 0); ACTION_PARAM_NAME(DamageType, 1); ACTION_PARAM_INT(flags, 2); ACTION_PARAM_CLASS(filter, 3); + ACTION_PARAM_NAME(species, 4); TThinkerIterator it; AActor * mo; @@ -5198,9 +5214,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSiblings) { if (mo->master == self->master && mo != self) { - const PClass *c1 = mo->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoDamage(mo, self, amount, DamageType, flags); + DoDamage(mo, self, amount, DamageType, flags, filter, species); } } } @@ -5218,9 +5232,11 @@ enum KILS KILS_KILLMISSILES = 1 << 1, KILS_NOMONSTERS = 1 << 2, KILS_FOILBUDDHA = 1 << 3, + KILS_EXFILTER = 1 << 4, + KILS_EXSPECIES = 1 << 5, }; -static void DoKill(AActor *killtarget, AActor *self, FName damagetype, int flags) +static void DoKill(AActor *killtarget, AActor *self, FName damagetype, int flags, const PClass *filter, FName species) { int dmgFlags = DMG_NO_ARMOR + DMG_NO_FACTOR; @@ -5229,20 +5245,25 @@ static void DoKill(AActor *killtarget, AActor *self, FName damagetype, int flags if (KILS_FOILBUDDHA) dmgFlags += DMG_FOILBUDDHA; - if ((killtarget->flags & MF_MISSILE) && (flags & KILS_KILLMISSILES)) + bool filterpass = DoCheckFilter(killtarget, filter, (flags & KILS_EXFILTER) ? true : false), + speciespass = DoCheckSpecies(killtarget, species, (flags & KILS_EXSPECIES) ? true : false); + if (filterpass && speciespass) //Check this first. I think it'll save the engine a lot more time this way. { - //[MC] Now that missiles can set masters, lets put in a check to properly destroy projectiles. BUT FIRST! New feature~! - //Check to see if it's invulnerable. Disregarded if foilinvul is on, but never works on a missile with NODAMAGE - //since that's the whole point of it. - if ((!(killtarget->flags2 & MF2_INVULNERABLE) || (flags & KILS_FOILINVUL)) && - (!(killtarget->flags2 & MF7_BUDDHA) || (flags & KILS_FOILBUDDHA)) && !(killtarget->flags5 & MF5_NODAMAGE)) + if ((killtarget->flags & MF_MISSILE) && (flags & KILS_KILLMISSILES)) { - P_ExplodeMissile(killtarget, NULL, NULL); + //[MC] Now that missiles can set masters, lets put in a check to properly destroy projectiles. BUT FIRST! New feature~! + //Check to see if it's invulnerable. Disregarded if foilinvul is on, but never works on a missile with NODAMAGE + //since that's the whole point of it. + if ((!(killtarget->flags2 & MF2_INVULNERABLE) || (flags & KILS_FOILINVUL)) && + (!(killtarget->flags2 & MF7_BUDDHA) || (flags & KILS_FOILBUDDHA)) && !(killtarget->flags5 & MF5_NODAMAGE)) + { + P_ExplodeMissile(killtarget, NULL, NULL); + } } - } - if (!(flags & KILS_NOMONSTERS)) - { + if (!(flags & KILS_NOMONSTERS)) + { P_DamageMobj(killtarget, self, self, killtarget->health, damagetype, dmgFlags); + } } } @@ -5254,16 +5275,15 @@ static void DoKill(AActor *killtarget, AActor *self, FName damagetype, int flags //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTarget) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); ACTION_PARAM_CLASS(filter, 2); + ACTION_PARAM_NAME(species, 3); if (self->target != NULL) { - const PClass *c1 = self->target->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoKill(self->target, self, damagetype, flags); + DoKill(self->target, self, damagetype, flags, filter, species); } } @@ -5274,16 +5294,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTarget) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTracer) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); ACTION_PARAM_CLASS(filter, 2); + ACTION_PARAM_NAME(species, 3); if (self->tracer != NULL) { - const PClass *c1 = self->tracer->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoKill(self->tracer, self, damagetype, flags); + DoKill(self->tracer, self, damagetype, flags, filter, species); } } @@ -5294,16 +5313,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTracer) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillMaster) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); ACTION_PARAM_CLASS(filter, 2); + ACTION_PARAM_NAME(species, 3); if (self->master != NULL) { - const PClass *c1 = self->master->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoKill(self->master, self, damagetype, flags); + DoKill(self->master, self, damagetype, flags, filter, species); } } @@ -5314,10 +5332,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillMaster) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillChildren) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); ACTION_PARAM_CLASS(filter, 2); + ACTION_PARAM_NAME(species, 3); TThinkerIterator it; AActor *mo; @@ -5326,9 +5345,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillChildren) { if (mo->master == self) { - const PClass *c1 = mo->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoKill(mo, self, damagetype, flags); + DoKill(mo, self, damagetype, flags, filter, species); } } } @@ -5340,10 +5357,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillChildren) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillSiblings) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_NAME(damagetype, 0); ACTION_PARAM_INT(flags, 1); ACTION_PARAM_CLASS(filter, 2); + ACTION_PARAM_NAME(species, 3); TThinkerIterator it; AActor *mo; @@ -5354,9 +5372,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillSiblings) { if (mo->master == self->master && mo != self) { - const PClass *c1 = mo->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoKill(mo, self, damagetype, flags); + DoKill(mo, self, damagetype, flags, filter, species); } } } @@ -5374,25 +5390,32 @@ enum RMVF_flags RMVF_NOMONSTERS = 1 << 1, RMVF_MISC = 1 << 2, RMVF_EVERYTHING = 1 << 3, + RMVF_EXFILTER = 1 << 4, + RMVF_EXSPECIES = 1 << 5, }; -static void DoRemove(AActor *removetarget, int flags) +static void DoRemove(AActor *removetarget, int flags, const PClass *filter, FName species) { - if ((flags & RMVF_EVERYTHING)) + bool filterpass = DoCheckFilter(removetarget, filter, (flags & RMVF_EXFILTER) ? true : false), + speciespass = DoCheckSpecies(removetarget, species, (flags & RMVF_EXSPECIES) ? true : false); + if (filterpass && speciespass) { - P_RemoveThing(removetarget); - } - if ((flags & RMVF_MISC) && !((removetarget->flags3 & MF3_ISMONSTER) && (removetarget->flags & MF_MISSILE))) - { - P_RemoveThing(removetarget); - } - if ((removetarget->flags3 & MF3_ISMONSTER) && !(flags & RMVF_NOMONSTERS)) - { - P_RemoveThing(removetarget); - } - if ((removetarget->flags & MF_MISSILE) && (flags & RMVF_MISSILES)) - { - P_RemoveThing(removetarget); + if ((flags & RMVF_EVERYTHING)) + { + P_RemoveThing(removetarget); + } + if ((flags & RMVF_MISC) && !((removetarget->flags3 & MF3_ISMONSTER) && (removetarget->flags & MF_MISSILE))) + { + P_RemoveThing(removetarget); + } + if ((removetarget->flags3 & MF3_ISMONSTER) && !(flags & RMVF_NOMONSTERS)) + { + P_RemoveThing(removetarget); + } + if ((removetarget->flags & MF_MISSILE) && (flags & RMVF_MISSILES)) + { + P_RemoveThing(removetarget); + } } } @@ -5406,12 +5429,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTarget) ACTION_PARAM_START(2); ACTION_PARAM_INT(flags, 0); ACTION_PARAM_CLASS(filter, 1); + ACTION_PARAM_NAME(species, 2); if (self->target != NULL) { - const PClass *c1 = self->target->GetClass(); - if ((filter && (c1 == filter)) || (filter == NULL) || !(filter)) - DoRemove(self->target, flags); + DoRemove(self->target, flags, filter, species); } } @@ -5425,12 +5447,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTracer) ACTION_PARAM_START(2); ACTION_PARAM_INT(flags, 0); ACTION_PARAM_CLASS(filter, 1); + ACTION_PARAM_NAME(species, 2); if (self->tracer != NULL) { - const PClass *c1 = self->tracer->GetClass(); - if ((filter && (c1 == filter)) || (filter == NULL) || !(filter)) - DoRemove(self->tracer, flags); + DoRemove(self->tracer, flags, filter, species); } } @@ -5444,12 +5465,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveMaster) ACTION_PARAM_START(2); ACTION_PARAM_INT(flags, 0); ACTION_PARAM_CLASS(filter, 1); + ACTION_PARAM_NAME(species, 2); if (self->master != NULL) { - const PClass *c1 = self->master->GetClass(); - if ((filter && (c1 == filter)) || (filter == NULL) || !(filter)) - DoRemove(self->master, flags); + DoRemove(self->master, flags, filter, species); } } @@ -5462,19 +5482,18 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveChildren) { TThinkerIterator it; AActor *mo; - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_BOOL(removeall, 0); ACTION_PARAM_INT(flags, 1); ACTION_PARAM_CLASS(filter, 2); + ACTION_PARAM_NAME(species, 3); while ((mo = it.Next()) != NULL) { if (mo->master == self && (mo->health <= 0 || removeall)) { - const PClass *c1 = mo->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoRemove(mo, flags); + DoRemove(mo, flags, filter, species); } } } @@ -5488,10 +5507,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) { TThinkerIterator it; AActor *mo; - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_BOOL(removeall, 0); ACTION_PARAM_INT(flags, 1); ACTION_PARAM_CLASS(filter, 2); + ACTION_PARAM_NAME(species, 3); if (self->master != NULL) { @@ -5499,9 +5519,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) { if (mo->master == self->master && mo != self && (mo->health <= 0 || removeall)) { - const PClass *c1 = mo->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoRemove(mo, flags); + DoRemove(mo, flags, filter, species); } } } @@ -5514,17 +5532,16 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Remove) { - ACTION_PARAM_START(3); + ACTION_PARAM_START(4); ACTION_PARAM_INT(removee, 0); ACTION_PARAM_INT(flags, 1); ACTION_PARAM_CLASS(filter, 2); + ACTION_PARAM_NAME(species, 3); AActor *reference = COPY_AAPTR(self, removee); if (reference != NULL) { - const PClass *c1 = reference->GetClass(); - if (!(filter) || (filter == NULL) || (filter && (c1 == filter))) - DoRemove(reference, flags); + DoRemove(reference, flags, filter, species); } } diff --git a/wadsrc/static/actors/actor.txt b/wadsrc/static/actors/actor.txt index 7bc6b8df4..19260ae7e 100644 --- a/wadsrc/static/actors/actor.txt +++ b/wadsrc/static/actors/actor.txt @@ -298,23 +298,23 @@ ACTOR Actor native //: Thinker action native A_SetDamageType(name damagetype); action native A_DropItem(class item, int dropamount = -1, int chance = 256); action native A_SetSpeed(float speed); - action native A_DamageSelf(int amount, name damagetype = "none", int flags = 0, class filter); - action native A_DamageTarget(int amount, name damagetype = "none", int flags = 0, class filter); - action native A_DamageMaster(int amount, name damagetype = "none", int flags = 0, class filter); - action native A_DamageTracer(int amount, name damagetype = "none", int flags = 0, class filter); - action native A_DamageChildren(int amount, name damagetype = "none", int flags = 0, class filter); - action native A_DamageSiblings(int amount, name damagetype = "none", int flags = 0, class filter); - action native A_KillTarget(name damagetype = "none", int flags = 0, class filter); - action native A_KillMaster(name damagetype = "none", int flags = 0, class filter); - action native A_KillTracer(name damagetype = "none", int flags = 0, class filter); - action native A_KillChildren(name damagetype = "none", int flags = 0, class filter); - action native A_KillSiblings(name damagetype = "none", int flags = 0, class filter); - action native A_RemoveTarget(int flags = 0, class filter); - action native A_RemoveMaster(int flags = 0, class filter); - action native A_RemoveTracer(int flags = 0, class filter); - action native A_RemoveChildren(bool removeall = false, int flags = 0, class filter); - action native A_RemoveSiblings(bool removeall = false, int flags = 0, class filter); - action native A_Remove(int removee, int flags = 0, class filter); + action native A_DamageSelf(int amount, name damagetype = "none", int flags = 0, class filter, name species); + action native A_DamageTarget(int amount, name damagetype = "none", int flags = 0, class filter, name species); + action native A_DamageMaster(int amount, name damagetype = "none", int flags = 0, class filter, name species); + action native A_DamageTracer(int amount, name damagetype = "none", int flags = 0, class filter, name species); + action native A_DamageChildren(int amount, name damagetype = "none", int flags = 0, class filter, name species); + action native A_DamageSiblings(int amount, name damagetype = "none", int flags = 0, class filter, name species); + action native A_KillTarget(name damagetype = "none", int flags = 0, class filter, name species); + action native A_KillMaster(name damagetype = "none", int flags = 0, class filter, name species); + action native A_KillTracer(name damagetype = "none", int flags = 0, class filter, name species); + action native A_KillChildren(name damagetype = "none", int flags = 0, class filter, name species); + action native A_KillSiblings(name damagetype = "none", int flags = 0, class filter, name species); + action native A_RemoveTarget(int flags = 0, class filter, name species); + action native A_RemoveMaster(int flags = 0, class filter, name species); + action native A_RemoveTracer(int flags = 0, class filter, name species); + action native A_RemoveChildren(bool removeall = false, int flags = 0, class filter, name species); + action native A_RemoveSiblings(bool removeall = false, int flags = 0, class filter, name species); + action native A_Remove(int removee, int flags = 0, class filter, name species); action native A_GiveToChildren(class itemtype, int amount = 0); action native A_GiveToSiblings(class itemtype, int amount = 0); action native A_TakeFromChildren(class itemtype, int amount = 0); diff --git a/wadsrc/static/actors/constants.txt b/wadsrc/static/actors/constants.txt index 756fae981..1d4252188 100644 --- a/wadsrc/static/actors/constants.txt +++ b/wadsrc/static/actors/constants.txt @@ -401,6 +401,8 @@ const int KILS_FOILINVUL = 1; const int KILS_KILLMISSILES = 2; const int KILS_NOMONSTERS = 4; const int KILS_FOILBUDDHA = 8; +const int KILS_EXFILTER = 16; +const int KILS_EXSPECIES = 32; // Flags for A_Damage (Master/Target/Tracer/Children/Siblings/Self) series const int DMSS_FOILINVUL = 1; @@ -409,6 +411,8 @@ const int DMSS_KILL = 4; const int DMSS_NOFACTOR = 8; const int DMSS_FOILBUDDHA = 16; const int DMSS_NOPROTECT = 32; +const int DMSS_EXFILTER = 64; +const int DMSS_EXSPECIES = 128; // Flags for A_AlertMonsters const int AMF_TARGETEMITTER = 1; @@ -422,6 +426,8 @@ enum RMVF_NOMONSTERS = 1 << 1, RMVF_MISC = 1 << 2, RMVF_EVERYTHING = 1 << 3, + RMVF_EXFILTER = 1 << 4, + RMVF_EXSPECIES = 1 << 5, }; // Flags for A_Fade* From 2c7a3f2ebaa542364a90ed0ad7836e0cbe10a790 Mon Sep 17 00:00:00 2001 From: MajorCooke Date: Sun, 21 Dec 2014 10:38:51 -0600 Subject: [PATCH 4/4] - Optimized DoDamage and DoKill. - Do a filter and species check first to save time. - Added DMSS/KILS/RMVF_EITHER, which means if the actor is of type or species, it counts. - A_DamageTarget(20,"Normal",DMSS_EITHER,"DoomImp","CyberdemonSpecies") - This affects actor DoomImp, and anything that's of species CyberdemonSpecies. - Added a little more documentation via comments. --- src/thingdef/thingdef_codeptr.cpp | 102 ++++++++++++++++------------- wadsrc/static/actors/constants.txt | 50 ++++++++------ 2 files changed, 85 insertions(+), 67 deletions(-) diff --git a/src/thingdef/thingdef_codeptr.cpp b/src/thingdef/thingdef_codeptr.cpp index e61f33ea4..1edfc4f32 100644 --- a/src/thingdef/thingdef_codeptr.cpp +++ b/src/thingdef/thingdef_codeptr.cpp @@ -5039,44 +5039,51 @@ static bool DoCheckFilter(AActor *mo, const PClass *filter, bool exclude) // // Common A_Damage handler // -// A_Damage* (int amount, str damagetype, int flags) +// A_Damage* (int amount, str damagetype, int flags, str filter, str species) // Damages the specified actor by the specified amount. Negative values heal. +// Flags: See below. +// Filter: Specified actor is the only type allowed to be affected. +// Species: Specified species is the only type allowed to be affected. +// +// Examples: +// A_Damage(20,"Normal",DMSS_FOILINVUL,0,"DemonicSpecies") <--Only actors +// with a species "DemonicSpecies" will be affected. Use 0 to not filter by actor. // //=========================================================================== enum DMSS { - DMSS_FOILINVUL = 1, - DMSS_AFFECTARMOR = 2, - DMSS_KILL = 4, - DMSS_NOFACTOR = 8, - DMSS_FOILBUDDHA = 16, - DMSS_NOPROTECT = 32, - DMSS_EXFILTER = 64, - DMSS_EXSPECIES = 128, + DMSS_FOILINVUL = 1, //Foil invulnerability + DMSS_AFFECTARMOR = 2, //Make it affect armor + DMSS_KILL = 4, //Damages them for their current health + DMSS_NOFACTOR = 8, //Ignore DamageFactors + DMSS_FOILBUDDHA = 16, //Can kill actors with Buddha flag, except the player. + DMSS_NOPROTECT = 32, //Ignores PowerProtection entirely + DMSS_EXFILTER = 64, //Changes filter into a blacklisted class instead of whitelisted. + DMSS_EXSPECIES = 128, // ^ but with species instead. + DMSS_EITHER = 256, //Allow either type or species to be affected. }; static void DoDamage(AActor *dmgtarget, AActor *self, int amount, FName DamageType, int flags, const PClass *filter, FName species) { - int dmgFlags = 0; - if (flags & DMSS_FOILINVUL) - dmgFlags += DMG_FOILINVUL; - if (flags & DMSS_FOILBUDDHA) - dmgFlags += DMG_FOILBUDDHA; - if ((flags & DMSS_KILL) || (flags & DMSS_NOFACTOR)) //Kill implies NoFactor - dmgFlags += DMG_NO_FACTOR; - if (!(flags & DMSS_AFFECTARMOR) || (flags & DMSS_KILL)) //Kill overrides AffectArmor - dmgFlags += DMG_NO_ARMOR; - if (flags & DMSS_KILL) //Kill adds the value of the damage done to it. Allows for more controlled extreme death types. - amount += dmgtarget->health; - if (flags & DMSS_NOPROTECT) //Ignore PowerProtection. - dmgFlags += DMG_NO_PROTECT; - bool filterpass = DoCheckFilter(dmgtarget, filter, (flags & DMSS_EXFILTER) ? true : false), speciespass = DoCheckSpecies(dmgtarget, species, (flags & DMSS_EXSPECIES) ? true : false); - - if (filterpass && speciespass) + if ((flags & DMSS_EITHER) ? (filterpass || speciespass) : (filterpass && speciespass)) { + int dmgFlags = 0; + if (flags & DMSS_FOILINVUL) + dmgFlags += DMG_FOILINVUL; + if (flags & DMSS_FOILBUDDHA) + dmgFlags += DMG_FOILBUDDHA; + if ((flags & DMSS_KILL) || (flags & DMSS_NOFACTOR)) //Kill implies NoFactor + dmgFlags += DMG_NO_FACTOR; + if (!(flags & DMSS_AFFECTARMOR) || (flags & DMSS_KILL)) //Kill overrides AffectArmor + dmgFlags += DMG_NO_ARMOR; + if (flags & DMSS_KILL) //Kill adds the value of the damage done to it. Allows for more controlled extreme death types. + amount += dmgtarget->health; + if (flags & DMSS_NOPROTECT) //Ignore PowerProtection. + dmgFlags += DMG_NO_PROTECT; + if (amount > 0) P_DamageMobj(dmgtarget, self, self, amount, DamageType, dmgFlags); //Should wind up passing them through just fine. @@ -5228,27 +5235,29 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSiblings) //=========================================================================== enum KILS { - KILS_FOILINVUL = 1 << 0, - KILS_KILLMISSILES = 1 << 1, - KILS_NOMONSTERS = 1 << 2, - KILS_FOILBUDDHA = 1 << 3, - KILS_EXFILTER = 1 << 4, - KILS_EXSPECIES = 1 << 5, + KILS_FOILINVUL = 1 << 0, + KILS_KILLMISSILES = 1 << 1, + KILS_NOMONSTERS = 1 << 2, + KILS_FOILBUDDHA = 1 << 3, + KILS_EXFILTER = 1 << 4, + KILS_EXSPECIES = 1 << 5, + KILS_EITHER = 1 << 6, }; static void DoKill(AActor *killtarget, AActor *self, FName damagetype, int flags, const PClass *filter, FName species) { - int dmgFlags = DMG_NO_ARMOR + DMG_NO_FACTOR; - - if (KILS_FOILINVUL) - dmgFlags += DMG_FOILINVUL; - if (KILS_FOILBUDDHA) - dmgFlags += DMG_FOILBUDDHA; - bool filterpass = DoCheckFilter(killtarget, filter, (flags & KILS_EXFILTER) ? true : false), speciespass = DoCheckSpecies(killtarget, species, (flags & KILS_EXSPECIES) ? true : false); - if (filterpass && speciespass) //Check this first. I think it'll save the engine a lot more time this way. + if ((flags & KILS_EITHER) ? (filterpass || speciespass) : (filterpass && speciespass)) //Check this first. I think it'll save the engine a lot more time this way. { + int dmgFlags = DMG_NO_ARMOR + DMG_NO_FACTOR; + + if (KILS_FOILINVUL) + dmgFlags += DMG_FOILINVUL; + if (KILS_FOILBUDDHA) + dmgFlags += DMG_FOILBUDDHA; + + if ((killtarget->flags & MF_MISSILE) && (flags & KILS_KILLMISSILES)) { //[MC] Now that missiles can set masters, lets put in a check to properly destroy projectiles. BUT FIRST! New feature~! @@ -5386,19 +5395,20 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillSiblings) enum RMVF_flags { - RMVF_MISSILES = 1 << 0, - RMVF_NOMONSTERS = 1 << 1, - RMVF_MISC = 1 << 2, - RMVF_EVERYTHING = 1 << 3, - RMVF_EXFILTER = 1 << 4, - RMVF_EXSPECIES = 1 << 5, + RMVF_MISSILES = 1 << 0, + RMVF_NOMONSTERS = 1 << 1, + RMVF_MISC = 1 << 2, + RMVF_EVERYTHING = 1 << 3, + RMVF_EXFILTER = 1 << 4, + RMVF_EXSPECIES = 1 << 5, + RMVF_EITHER = 1 << 6, }; static void DoRemove(AActor *removetarget, int flags, const PClass *filter, FName species) { bool filterpass = DoCheckFilter(removetarget, filter, (flags & RMVF_EXFILTER) ? true : false), speciespass = DoCheckSpecies(removetarget, species, (flags & RMVF_EXSPECIES) ? true : false); - if (filterpass && speciespass) + if ((flags & RMVF_EITHER) ? (filterpass || speciespass) : (filterpass && speciespass)) { if ((flags & RMVF_EVERYTHING)) { diff --git a/wadsrc/static/actors/constants.txt b/wadsrc/static/actors/constants.txt index 1d4252188..e8ba15d46 100644 --- a/wadsrc/static/actors/constants.txt +++ b/wadsrc/static/actors/constants.txt @@ -396,23 +396,30 @@ enum }; // Flags for A_Kill (Master/Target/Tracer/Children/Siblings) series - -const int KILS_FOILINVUL = 1; -const int KILS_KILLMISSILES = 2; -const int KILS_NOMONSTERS = 4; -const int KILS_FOILBUDDHA = 8; -const int KILS_EXFILTER = 16; -const int KILS_EXSPECIES = 32; +enum +{ + KILS_FOILINVUL = 0x00000001, + KILS_KILLMISSILES = 0x00000002, + KILS_NOMONSTERS = 0x00000004, + KILS_FOILBUDDHA = 0x00000008, + KILS_EXFILTER = 0x00000010, + KILS_EXSPECIES = 0x00000020, + KILS_EITHER = 0x00000040, +}; // Flags for A_Damage (Master/Target/Tracer/Children/Siblings/Self) series -const int DMSS_FOILINVUL = 1; -const int DMSS_AFFECTARMOR = 2; -const int DMSS_KILL = 4; -const int DMSS_NOFACTOR = 8; -const int DMSS_FOILBUDDHA = 16; -const int DMSS_NOPROTECT = 32; -const int DMSS_EXFILTER = 64; -const int DMSS_EXSPECIES = 128; +enum +{ + DMSS_FOILINVUL = 0x00000001, + DMSS_AFFECTARMOR = 0x00000002, + DMSS_KILL = 0x00000004, + DMSS_NOFACTOR = 0x00000008, + DMSS_FOILBUDDHA = 0x00000010, + DMSS_NOPROTECT = 0x00000020, + DMSS_EXFILTER = 0x00000040, + DMSS_EXSPECIES = 0x00000080, + DMSS_EITHER = 0x00000100, +}; // Flags for A_AlertMonsters const int AMF_TARGETEMITTER = 1; @@ -422,12 +429,13 @@ const int AMF_EMITFROMTARGET = 4; // Flags for A_Remove* enum { - RMVF_MISSILES = 1 << 0, - RMVF_NOMONSTERS = 1 << 1, - RMVF_MISC = 1 << 2, - RMVF_EVERYTHING = 1 << 3, - RMVF_EXFILTER = 1 << 4, - RMVF_EXSPECIES = 1 << 5, + RMVF_MISSILES = 0x00000001, + RMVF_NOMONSTERS = 0x00000002, + RMVF_MISC = 0x00000004, + RMVF_EVERYTHING = 0x00000008, + RMVF_EXFILTER = 0x00000010, + RMVF_EXSPECIES = 0x00000020, + RMVF_EITHER = 0x00000040, }; // Flags for A_Fade*