From bb3d2fa5350cbb3b37147be73ac45a5d9c6fd3d5 Mon Sep 17 00:00:00 2001 From: GitExl Date: Tue, 23 Sep 2014 12:10:39 +0200 Subject: [PATCH 1/8] Add CanRaiseActor ACS function. --- src/p_acs.cpp | 21 +++++++++++++++++++++ src/p_local.h | 1 + src/p_things.cpp | 34 ++++++++++++++++++++++++++++++++++ 3 files changed, 56 insertions(+) diff --git a/src/p_acs.cpp b/src/p_acs.cpp index fd41d6e51..86ab02272 100644 --- a/src/p_acs.cpp +++ b/src/p_acs.cpp @@ -4369,6 +4369,7 @@ enum EACSFunctions ACSF_GetArmorInfo, ACSF_DropInventory, ACSF_PickActor, + ACSF_CanRaiseActor, /* Zandronum's - these must be skipped when we reach 99! -100:ResetMap(0), @@ -5626,6 +5627,26 @@ doplaysound: if (funcIndex == ACSF_PlayActorSound) } break; + case ACSF_CanRaiseActor: + if (argCount >= 1) { + if (args[0] == 0) { + actor = SingleActorFromTID(args[0], activator); + if (actor != NULL) { + return P_Thing_CanRaise(actor); + } + } + + FActorIterator iterator(args[0]); + bool canraiseall = false; + while ((actor = iterator.Next())) + { + canraiseall = !P_Thing_CanRaise(actor) | canraiseall; + } + + return !canraiseall; + } + break; + default: break; } diff --git a/src/p_local.h b/src/p_local.h index 939018734..8ba1dd40b 100644 --- a/src/p_local.h +++ b/src/p_local.h @@ -171,6 +171,7 @@ int P_Thing_Damage (int tid, AActor *whofor0, int amount, FName type); void P_Thing_SetVelocity(AActor *actor, fixed_t vx, fixed_t vy, fixed_t vz, bool add, bool setbob); void P_RemoveThing(AActor * actor); bool P_Thing_Raise(AActor *thing); +bool P_Thing_CanRaise(AActor *thing); const PClass *P_GetSpawnableType(int spawnnum); // diff --git a/src/p_things.cpp b/src/p_things.cpp index e62c65ae7..2a93ee31e 100644 --- a/src/p_things.cpp +++ b/src/p_things.cpp @@ -445,6 +445,40 @@ bool P_Thing_Raise(AActor *thing) return true; } +bool P_Thing_CanRaise(AActor *thing) +{ + FState * RaiseState = thing->GetRaiseState(); + if (RaiseState == NULL) + { + return false; + } + + AActor *info = thing->GetDefault(); + + // Check against real height and radius + int oldflags = thing->flags; + fixed_t oldheight = thing->height; + fixed_t oldradius = thing->radius; + + thing->flags |= MF_SOLID; + thing->height = info->height; + thing->radius = info->radius; + + bool check = P_CheckPosition (thing, thing->x, thing->y); + + // Restore checked properties + thing->flags = oldflags; + thing->radius = oldradius; + thing->height = oldheight; + + if (!check) + { + return false; + } + + return true; +} + void P_Thing_SetVelocity(AActor *actor, fixed_t vx, fixed_t vy, fixed_t vz, bool add, bool setbob) { if (actor != NULL) From a2f7b86a0f460c88821ddfb2463d2c9de252cbd2 Mon Sep 17 00:00:00 2001 From: fdari Date: Sun, 28 Sep 2014 11:52:37 +0200 Subject: [PATCH 2/8] IsPointerEqual (ACS and Decorate) Decorate: IsPointerEqual(int aaptr_selector1, int aaptr_selector2) ACS: IsPointerEqual(int aaptr_selector1, int aaptr_selector2, int tid1 = 0, int tid2 = 0) Compare the pointers values returned by two pointer select operations. Returns true if they both resolve to the same value. Null values can be explicitly tested using IsPointerEqual(AAPTR_NULL, ...) ACS: IsPointerEqual(int aaptr1, int aaptr2, int tid1 = 0, int tid2 = 0) This function lets you compare pointers from other actors than the activator, using tids. Tid1 determines the actor used to resolve aaptr1, Tid2 does the same for aaptr2. If tid1 and tid2 are equal, the same actor will be used for resolving both pointers (that could always happen randomly; this way you know it will happen). --- src/namedef.h | 1 + src/p_acs.cpp | 17 +++++++++++++++ src/thingdef/thingdef_function.cpp | 35 +++++++++++++++++++++++++++++- 3 files changed, 52 insertions(+), 1 deletion(-) diff --git a/src/namedef.h b/src/namedef.h index 1e7fbd0d3..5c65ab655 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -299,6 +299,7 @@ xx(ACS_NamedExecuteWithResult) xx(CallACS) xx(Sqrt) xx(CheckClass) +xx(IsPointerEqual) // Various actor names which are used internally xx(MapSpot) diff --git a/src/p_acs.cpp b/src/p_acs.cpp index 983728c8d..9fa5079ff 100644 --- a/src/p_acs.cpp +++ b/src/p_acs.cpp @@ -4373,6 +4373,7 @@ enum EACSFunctions ACSF_GetArmorInfo, ACSF_DropInventory, ACSF_PickActor, + ACSF_IsPointerEqual, /* Zandronum's - these must be skipped when we reach 99! -100:ResetMap(0), @@ -5630,6 +5631,22 @@ doplaysound: if (funcIndex == ACSF_PlayActorSound) } break; + case ACSF_IsPointerEqual: + { + int tid1 = 0, tid2 = 0; + switch (argCount) + { + case 4: tid2 = args[3]; + case 3: tid1 = args[2]; + } + + actor = SingleActorFromTID(tid1, activator); + AActor * actor2 = tid2 == tid1 ? actor : SingleActorFromTID(tid2, activator); + + return COPY_AAPTR(actor, args[0]) == COPY_AAPTR(actor2, args[1]); + } + break; + default: break; } diff --git a/src/thingdef/thingdef_function.cpp b/src/thingdef/thingdef_function.cpp index 9bf80dcaa..fcc936017 100644 --- a/src/thingdef/thingdef_function.cpp +++ b/src/thingdef/thingdef_function.cpp @@ -260,4 +260,37 @@ class FxGlobalFunctionCall_CheckClass : public FxGlobalFunctionCall } }; -GLOBALFUNCTION_ADDER(CheckClass); \ No newline at end of file +GLOBALFUNCTION_ADDER(CheckClass); + +//========================================================================== +// +// Function: ispointerequal +// +//========================================================================== + +class FxGlobalFunctionCall_IsPointerEqual : public FxGlobalFunctionCall +{ + public: + GLOBALFUNCTION_DEFINE(IsPointerEqual); + + FxExpression *Resolve(FCompileContext& ctx) + { + CHECKRESOLVED(); + + if (!ResolveArgs(ctx, 2, 2, true)) + return NULL; + + ValueType = VAL_Int; + return this; + } + + ExpVal EvalExpression(AActor *self) + { + ExpVal ret; + ret.Type = VAL_Int; + ret.Int = COPY_AAPTR(self, (*ArgList)[0]->EvalExpression(self).GetInt()) == COPY_AAPTR(self, (*ArgList)[1]->EvalExpression(self).GetInt()); + return ret; + } +}; + +GLOBALFUNCTION_ADDER(IsPointerEqual); \ No newline at end of file From c4f0f95ec8bc0320f0d50be2b55bdc55bc016843 Mon Sep 17 00:00:00 2001 From: fdari Date: Sun, 28 Sep 2014 15:06:52 +0200 Subject: [PATCH 3/8] Get linetarget (aim target) from any actor (not just player): AAPTR_LINETARGET --- src/actorptrselect.cpp | 7 +++++++ src/actorptrselect.h | 3 ++- wadsrc/static/actors/constants.txt | 31 +++++++++++++++--------------- 3 files changed, 25 insertions(+), 16 deletions(-) diff --git a/src/actorptrselect.cpp b/src/actorptrselect.cpp index f1f50eeb5..774067550 100644 --- a/src/actorptrselect.cpp +++ b/src/actorptrselect.cpp @@ -56,6 +56,13 @@ AActor *COPY_AAPTR(AActor *origin, int selector) case AAPTR_TRACER: return origin->tracer; case AAPTR_FRIENDPLAYER: return origin->FriendPlayer ? AAPTR_RESOLVE_PLAYERNUM(origin->FriendPlayer - 1) : NULL; + + case AAPTR_GET_LINETARGET: + { + AActor *gettarget = NULL; + P_BulletSlope(origin, &gettarget); + return gettarget; + } } } diff --git a/src/actorptrselect.h b/src/actorptrselect.h index 46e1aa54d..bfc88fb3c 100644 --- a/src/actorptrselect.h +++ b/src/actorptrselect.h @@ -36,12 +36,13 @@ enum AAPTR AAPTR_PLAYER8 = 0x2000, AAPTR_FRIENDPLAYER = 0x4000, + AAPTR_GET_LINETARGET = 0x8000, AAPTR_PLAYER_SELECTORS = AAPTR_PLAYER_GETTARGET|AAPTR_PLAYER_GETCONVERSATION, AAPTR_GENERAL_SELECTORS = - AAPTR_TARGET|AAPTR_MASTER|AAPTR_TRACER|AAPTR_FRIENDPLAYER, + AAPTR_TARGET|AAPTR_MASTER|AAPTR_TRACER|AAPTR_FRIENDPLAYER|AAPTR_GET_LINETARGET, AAPTR_STATIC_SELECTORS = AAPTR_PLAYER1|AAPTR_PLAYER2|AAPTR_PLAYER3|AAPTR_PLAYER4| diff --git a/wadsrc/static/actors/constants.txt b/wadsrc/static/actors/constants.txt index 3419561f8..428f92d14 100644 --- a/wadsrc/static/actors/constants.txt +++ b/wadsrc/static/actors/constants.txt @@ -279,24 +279,25 @@ Const Int BLOCKF_USE = 128; // Pointer constants, bitfield-enabled Const Int AAPTR_DEFAULT = 0; -Const Int AAPTR_NULL = 1; -Const Int AAPTR_TARGET = 2; -Const Int AAPTR_MASTER = 4; -Const Int AAPTR_TRACER = 8; +Const Int AAPTR_NULL = 0x1; +Const Int AAPTR_TARGET = 0x2; +Const Int AAPTR_MASTER = 0x4; +Const Int AAPTR_TRACER = 0x8; -Const Int AAPTR_PLAYER_GETTARGET = 16; -Const Int AAPTR_PLAYER_GETCONVERSATION = 32; +Const Int AAPTR_PLAYER_GETTARGET = 0x10; +Const Int AAPTR_PLAYER_GETCONVERSATION = 0x20; -Const Int AAPTR_PLAYER1 = 64; -Const Int AAPTR_PLAYER2 = 128; -Const Int AAPTR_PLAYER3 = 256; -Const Int AAPTR_PLAYER4 = 512; -Const Int AAPTR_PLAYER5 = 1024; -Const Int AAPTR_PLAYER6 = 2048; -Const Int AAPTR_PLAYER7 = 4096; -Const Int AAPTR_PLAYER8 = 8192; +Const Int AAPTR_PLAYER1 = 0x40; +Const Int AAPTR_PLAYER2 = 0x80; +Const Int AAPTR_PLAYER3 = 0x100; +Const Int AAPTR_PLAYER4 = 0x200; +Const Int AAPTR_PLAYER5 = 0x400; +Const Int AAPTR_PLAYER6 = 0x800; +Const Int AAPTR_PLAYER7 = 0x1000; +Const Int AAPTR_PLAYER8 = 0x2000; -Const Int AAPTR_FRIENDPLAYER = 16384; +Const Int AAPTR_FRIENDPLAYER = 0x4000; +Const Int AAPTR_LINETARGET = 0x8000; // Pointer operation flags From 43b86288c76e50c1eac79257714b5e3243b55be1 Mon Sep 17 00:00:00 2001 From: MajorCooke Date: Sun, 28 Sep 2014 08:15:00 -0500 Subject: [PATCH 4/8] - Added A_Remove(int pointer, int flags). - RMVF_MISSILES removes missiles. - RMVF_NOMONSTERS ignores monsters. - RMVF_MISC includes non-monsters and missiles. - RMVF_EVERYTHING disregards all checks and remove it. These flags now apply to the following in addition to the new function: -A_RemoveTarget -A_RemoveMaster -A_RemoveTracer -A_RemoveChildren -A_RemoveSiblings --- src/thingdef/thingdef_codeptr.cpp | 181 +++++++++++++++++++---------- wadsrc/static/actors/actor.txt | 11 +- wadsrc/static/actors/constants.txt | 9 ++ 3 files changed, 133 insertions(+), 68 deletions(-) diff --git a/src/thingdef/thingdef_codeptr.cpp b/src/thingdef/thingdef_codeptr.cpp index 4266c01c7..13b5a0cb3 100644 --- a/src/thingdef/thingdef_codeptr.cpp +++ b/src/thingdef/thingdef_codeptr.cpp @@ -3671,65 +3671,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckFlag) } } - -//=========================================================================== -// -// A_RemoveMaster -// -//=========================================================================== -DEFINE_ACTION_FUNCTION(AActor, A_RemoveMaster) -{ - if (self->master != NULL) - { - P_RemoveThing(self->master); - } -} - -//=========================================================================== -// -// A_RemoveChildren -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveChildren) -{ - TThinkerIterator it; - AActor *mo; - ACTION_PARAM_START(1); - ACTION_PARAM_BOOL(removeall,0); - - while ((mo = it.Next()) != NULL) - { - if (mo->master == self && (mo->health <= 0 || removeall)) - { - P_RemoveThing(mo); - } - } -} - -//=========================================================================== -// -// A_RemoveSiblings -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) -{ - TThinkerIterator it; - AActor *mo; - ACTION_PARAM_START(1); - ACTION_PARAM_BOOL(removeall,0); - - if (self->master != NULL) - { - while ((mo = it.Next()) != NULL) - { - if (mo->master == self->master && mo != self && (mo->health <= 0 || removeall)) - { - P_RemoveThing(mo); - } - } - } -} - //=========================================================================== // // A_RaiseMaster @@ -5063,7 +5004,6 @@ static void DoKill(AActor *killtarget, AActor *self, FName damagetype, int flags } - //=========================================================================== // // A_KillTarget(damagetype, int flags) @@ -5149,6 +5089,39 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillSiblings) } } +//=========================================================================== +// +// DoRemove +// +//=========================================================================== + +enum RMVF_flags +{ + RMVF_MISSILES = 1 << 0, + RMVF_NOMONSTERS = 1 << 1, + RMVF_MISC = 1 << 2, + RMVF_EVERYTHING = 1 << 3, +}; + +static void DoRemove(AActor *removetarget, int flags) +{ + 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); + } +} //=========================================================================== // @@ -5157,7 +5130,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillSiblings) //=========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_RemoveTarget) { - if (self->target != NULL) + if ((self->target != NULL) && (self->tracer->flags3 & MF3_ISMONSTER)) { P_RemoveThing(self->target); } @@ -5170,8 +5143,90 @@ DEFINE_ACTION_FUNCTION(AActor, A_RemoveTarget) //=========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_RemoveTracer) { - if (self->tracer != NULL) + if ((self->tracer != NULL) && (self->tracer->flags3 & MF3_ISMONSTER)) { P_RemoveThing(self->tracer); } -} \ No newline at end of file +} + +//=========================================================================== +// +// A_RemoveMaster +// +//=========================================================================== +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveMaster) +{ + ACTION_PARAM_START(1); + ACTION_PARAM_INT(flags, 0); + if (self->master != NULL) + { + DoRemove(self->master, flags); + } +} + +//=========================================================================== +// +// A_RemoveChildren +// +//=========================================================================== +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveChildren) +{ + TThinkerIterator it; + AActor *mo; + ACTION_PARAM_START(2); + ACTION_PARAM_BOOL(removeall, 0); + ACTION_PARAM_INT(flags, 1); + + while ((mo = it.Next()) != NULL) + { + if (mo->master == self && (mo->health <= 0 || removeall)) + { + DoRemove(mo, flags); + } + } +} + +//=========================================================================== +// +// A_RemoveSiblings +// +//=========================================================================== +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) +{ + TThinkerIterator it; + AActor *mo; + ACTION_PARAM_START(2); + ACTION_PARAM_BOOL(removeall, 0); + ACTION_PARAM_INT(flags, 1); + + if (self->master != NULL) + { + while ((mo = it.Next()) != NULL) + { + if (mo->master == self->master && mo != self && (mo->health <= 0 || removeall)) + { + DoRemove(mo, flags); + } + } + } +} + +//=========================================================================== +// +// A_Remove +// +//=========================================================================== +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Remove) +{ + ACTION_PARAM_START(2); + ACTION_PARAM_INT(removee, 0); + ACTION_PARAM_INT(flags, 1); + + AActor *reference = COPY_AAPTR(self, removee); + + if (reference != NULL) + { + DoRemove(reference, flags); + } +} + diff --git a/wadsrc/static/actors/actor.txt b/wadsrc/static/actors/actor.txt index d404f23a2..280321ad0 100644 --- a/wadsrc/static/actors/actor.txt +++ b/wadsrc/static/actors/actor.txt @@ -234,9 +234,9 @@ 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(); - action native A_RemoveChildren(bool removeall = false); - action native A_RemoveSiblings(bool removeall = false); + 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); @@ -309,8 +309,9 @@ ACTOR Actor native //: Thinker 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(); - action native A_RemoveTracer(); + 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_CheckSightOrRange(float distance, state label); action native A_CheckRange(float distance, state label); diff --git a/wadsrc/static/actors/constants.txt b/wadsrc/static/actors/constants.txt index 3419561f8..41d69a157 100644 --- a/wadsrc/static/actors/constants.txt +++ b/wadsrc/static/actors/constants.txt @@ -380,6 +380,15 @@ const int AMF_TARGETEMITTER = 1; const int AMF_TARGETNONPLAYER = 2; 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 +}; + // This is only here to provide one global variable for testing. native int testglobalvar; From 96c6e7d9bfe5b466c85e01e6bee65cf62dad22c2 Mon Sep 17 00:00:00 2001 From: MajorCooke Date: Sun, 28 Sep 2014 08:20:27 -0500 Subject: [PATCH 5/8] Minor fix; didn't mean to include that flag check. --- src/thingdef/thingdef_codeptr.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/thingdef/thingdef_codeptr.cpp b/src/thingdef/thingdef_codeptr.cpp index 13b5a0cb3..e724a1ba2 100644 --- a/src/thingdef/thingdef_codeptr.cpp +++ b/src/thingdef/thingdef_codeptr.cpp @@ -5130,7 +5130,7 @@ static void DoRemove(AActor *removetarget, int flags) //=========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_RemoveTarget) { - if ((self->target != NULL) && (self->tracer->flags3 & MF3_ISMONSTER)) + if ((self->target != NULL)) { P_RemoveThing(self->target); } @@ -5143,7 +5143,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RemoveTarget) //=========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_RemoveTracer) { - if ((self->tracer != NULL) && (self->tracer->flags3 & MF3_ISMONSTER)) + if ((self->tracer != NULL)) { P_RemoveThing(self->tracer); } From 770547e6618588a47c1c5d4b65bd3603cd59873b Mon Sep 17 00:00:00 2001 From: Teemu Piippo Date: Sun, 28 Sep 2014 17:17:19 +0300 Subject: [PATCH 6/8] - added udmf key midtex3dimpassible which causes the midtex to behave like a finite-height impassible line; practically this means the mid texture lets projectiles pass through it. --- specs/udmf_zdoom.txt | 51 +++++++++++++++++++++++--------------------- src/doomdata.h | 1 + src/namedef.h | 3 ++- src/p_3dmidtex.cpp | 7 ++++++ src/p_udmf.cpp | 11 +++++++++- 5 files changed, 47 insertions(+), 26 deletions(-) diff --git a/specs/udmf_zdoom.txt b/specs/udmf_zdoom.txt index 1128b2e55..cbb5b902c 100644 --- a/specs/udmf_zdoom.txt +++ b/specs/udmf_zdoom.txt @@ -92,30 +92,33 @@ Note: All fields default to false unless mentioned otherwise. linedef { - alpha = ; // Translucency of this line, default is 1.0 - renderstyle = ; // Render style, can be "translucent" or "add", - // default is "translucent". - playeruseback = ; // New SPAC flag, true = player can use from back side. - anycross = ; // New SPAC flag, true = any non-projectile - // crossing will trigger this line - monsteractivate = ; // Monsters can trigger this line. - // For compatibility only because this flag's - // semantics can not be fully reproduced with - // explicit trigger flags. - blockplayers = ; // Line blocks players' movement. - blockeverything = ; // Line blocks everything. - firstsideonly = ; // Line can only be triggered from the front side. - zoneboundary = ; // Line is a boundary for sound reverb zones. - clipmidtex = ; // Line's mid textures are clipped to floor and ceiling. - wrapmidtex = ; // Line's mid textures are wrapped. - midtex3d = ; // Actors can walk on mid texture. - checkswitchrange = ;// Switches can only be activated when vertically reachable. - blockprojectiles = ;// Line blocks all projectiles - blockuse = ; // Line blocks all use actions - blocksight = ; // Line blocks monster line of sight - blockhitscan = ; // Line blocks hitscan attacks - locknumber = ; // Line special is locked - arg0str = ; // Alternate string-based version of arg0 + alpha = ; // Translucency of this line, default is 1.0 + renderstyle = ; // Render style, can be "translucent" or "add", + // default is "translucent". + playeruseback = ; // New SPAC flag, true = player can use from back side. + anycross = ; // New SPAC flag, true = any non-projectile + // crossing will trigger this line + monsteractivate = ; // Monsters can trigger this line. + // For compatibility only because this flag's + // semantics can not be fully reproduced with + // explicit trigger flags. + blockplayers = ; // Line blocks players' movement. + blockeverything = ; // Line blocks everything. + firstsideonly = ; // Line can only be triggered from the front side. + zoneboundary = ; // Line is a boundary for sound reverb zones. + clipmidtex = ; // Line's mid textures are clipped to floor and ceiling. + wrapmidtex = ; // Line's mid textures are wrapped. + midtex3d = ; // Actors can walk on mid texture. + midtex3dimpassible = ;// Used in conjuction with midtex3d - causes the mid + // texture to behave like an impassible line (projectiles + // pass through it). + checkswitchrange = ; // Switches can only be activated when vertically reachable. + blockprojectiles = ; // Line blocks all projectiles + blockuse = ; // Line blocks all use actions + blocksight = ; // Line blocks monster line of sight + blockhitscan = ; // Line blocks hitscan attacks + locknumber = ; // Line special is locked + arg0str = ; // Alternate string-based version of arg0 transparent = ; // true = line is a Strife transparent line (alpha 0.25) diff --git a/src/doomdata.h b/src/doomdata.h index 215c2a263..f190be37d 100644 --- a/src/doomdata.h +++ b/src/doomdata.h @@ -162,6 +162,7 @@ enum ELineFlags ML_BLOCKUSE = 0x02000000, // blocks all use actions through this line ML_BLOCKSIGHT = 0x04000000, // blocks monster line of sight ML_BLOCKHITSCAN = 0x08000000, // blocks hitscan attacks + ML_3DMIDTEX_IMPASS = 0x10000000, // [TP] if 3D midtex, behaves like a height-restricted ML_BLOCKING }; diff --git a/src/namedef.h b/src/namedef.h index 1e7fbd0d3..4706fa500 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -419,6 +419,7 @@ xx(Passuse) xx(Repeatspecial) xx(Conversation) xx(Locknumber) +xx(Midtex3dimpassible) xx(Playercross) xx(Playeruse) @@ -597,4 +598,4 @@ xx(NeverSwitchOnPickup) xx(MoveBob) xx(StillBob) xx(PlayerClass) -xx(Wi_NoAutostartMap) \ No newline at end of file +xx(Wi_NoAutostartMap) diff --git a/src/p_3dmidtex.cpp b/src/p_3dmidtex.cpp index ccb6f0359..ac6d7aca7 100644 --- a/src/p_3dmidtex.cpp +++ b/src/p_3dmidtex.cpp @@ -258,6 +258,13 @@ bool P_GetMidTexturePosition(const line_t *line, int sideno, fixed_t *ptextop, f bool P_LineOpening_3dMidtex(AActor *thing, const line_t *linedef, FLineOpening &open, bool restrict) { + // [TP] Impassible-like 3dmidtextures do not block missiles + if ((linedef->flags & ML_3DMIDTEX_IMPASS) + && (thing->flags & MF_MISSILE || thing->BounceFlags & BOUNCE_MBF)) + { + return false; + } + fixed_t tt, tb; open.abovemidtex = false; diff --git a/src/p_udmf.cpp b/src/p_udmf.cpp index 7588199b4..473cdcd81 100644 --- a/src/p_udmf.cpp +++ b/src/p_udmf.cpp @@ -1030,11 +1030,16 @@ public: Flag(ld->flags, ML_BLOCKHITSCAN, key); continue; - // [Dusk] lock number + // [TP] Locks the special with a key case NAME_Locknumber: ld->locknumber = CheckInt(key); continue; + // [TP] Causes a 3d midtex to behave like an impassible line + case NAME_Midtex3dimpassible: + Flag(ld->flags, ML_3DMIDTEX_IMPASS, key); + continue; + default: break; } @@ -1081,6 +1086,10 @@ public: { ld->args[1] = -FName(arg1str); } + if ((ld->flags & ML_3DMIDTEX_IMPASS) && !(ld->flags & ML_3DMIDTEX)) // [TP] + { + Printf ("Line %d has midtex3dimpassible without midtex3d.\n", index); + } } //=========================================================================== From 3050ea9a6d3a85f89bcb27c5254e26cf0304a3b7 Mon Sep 17 00:00:00 2001 From: MajorCooke Date: Thu, 2 Oct 2014 11:27:22 -0500 Subject: [PATCH 7/8] - Fixed: A_RemoveTracer/Target didn't take flags into account. --- src/thingdef/thingdef_codeptr.cpp | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/src/thingdef/thingdef_codeptr.cpp b/src/thingdef/thingdef_codeptr.cpp index e724a1ba2..e3dbbfbb7 100644 --- a/src/thingdef/thingdef_codeptr.cpp +++ b/src/thingdef/thingdef_codeptr.cpp @@ -5128,11 +5128,13 @@ static void DoRemove(AActor *removetarget, int flags) // A_RemoveTarget // //=========================================================================== -DEFINE_ACTION_FUNCTION(AActor, A_RemoveTarget) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTarget) { - if ((self->target != NULL)) + ACTION_PARAM_START(1); + ACTION_PARAM_INT(flags, 0); + if (self->master != NULL) { - P_RemoveThing(self->target); + DoRemove(self->target, flags); } } @@ -5141,11 +5143,13 @@ DEFINE_ACTION_FUNCTION(AActor, A_RemoveTarget) // A_RemoveTracer // //=========================================================================== -DEFINE_ACTION_FUNCTION(AActor, A_RemoveTracer) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTracer) { - if ((self->tracer != NULL)) + ACTION_PARAM_START(1); + ACTION_PARAM_INT(flags, 0); + if (self->master != NULL) { - P_RemoveThing(self->tracer); + DoRemove(self->tracer, flags); } } From 5030832df0141a7598f5a6d4363f3febf3711829 Mon Sep 17 00:00:00 2001 From: MajorCooke Date: Thu, 2 Oct 2014 11:48:07 -0500 Subject: [PATCH 8/8] - Added DMSS_NOFACTOR for all A_Damage functions. --- src/thingdef/thingdef_codeptr.cpp | 35 +++++++++++++++++++++++------- wadsrc/static/actors/constants.txt | 1 + 2 files changed, 28 insertions(+), 8 deletions(-) diff --git a/src/thingdef/thingdef_codeptr.cpp b/src/thingdef/thingdef_codeptr.cpp index e724a1ba2..65888d0d5 100644 --- a/src/thingdef/thingdef_codeptr.cpp +++ b/src/thingdef/thingdef_codeptr.cpp @@ -4830,6 +4830,7 @@ enum DMSS DMSS_FOILINVUL = 1, DMSS_AFFECTARMOR = 2, DMSS_KILL = 4, + DMSS_NOFACTOR = 8, }; static void DoDamage(AActor *dmgtarget, AActor *self, int amount, FName DamageType, int flags) @@ -4844,12 +4845,26 @@ static void DoDamage(AActor *dmgtarget, AActor *self, int amount, FName DamageTy } if (flags & DMSS_AFFECTARMOR) { - P_DamageMobj(dmgtarget, self, self, amount, DamageType, DMG_FOILINVUL); + if (flags & DMSS_NOFACTOR) + { + P_DamageMobj(dmgtarget, self, self, amount, DamageType, DMG_FOILINVUL | DMG_NO_FACTOR); + } + else + { + P_DamageMobj(dmgtarget, self, self, amount, DamageType, DMG_FOILINVUL); + } } else { + if (flags & DMSS_NOFACTOR) + { + P_DamageMobj(dmgtarget, self, self, amount, DamageType, DMG_FOILINVUL | DMG_NO_ARMOR | DMG_NO_FACTOR); + } //[MC] DMG_FOILINVUL is needed for making the damage occur on the actor. - P_DamageMobj(dmgtarget, self, self, amount, DamageType, DMG_FOILINVUL | DMG_NO_ARMOR); + else + { + P_DamageMobj(dmgtarget, self, self, amount, DamageType, DMG_FOILINVUL | DMG_NO_ARMOR); + } } } } @@ -5128,11 +5143,13 @@ static void DoRemove(AActor *removetarget, int flags) // A_RemoveTarget // //=========================================================================== -DEFINE_ACTION_FUNCTION(AActor, A_RemoveTarget) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTarget) { - if ((self->target != NULL)) + ACTION_PARAM_START(1); + ACTION_PARAM_INT(flags, 0); + if (self->master != NULL) { - P_RemoveThing(self->target); + DoRemove(self->target, flags); } } @@ -5141,11 +5158,13 @@ DEFINE_ACTION_FUNCTION(AActor, A_RemoveTarget) // A_RemoveTracer // //=========================================================================== -DEFINE_ACTION_FUNCTION(AActor, A_RemoveTracer) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTracer) { - if ((self->tracer != NULL)) + ACTION_PARAM_START(1); + ACTION_PARAM_INT(flags, 0); + if (self->master != NULL) { - P_RemoveThing(self->tracer); + DoRemove(self->tracer, flags); } } diff --git a/wadsrc/static/actors/constants.txt b/wadsrc/static/actors/constants.txt index 1fe8e75cb..57de8e6ad 100644 --- a/wadsrc/static/actors/constants.txt +++ b/wadsrc/static/actors/constants.txt @@ -375,6 +375,7 @@ const int KILS_NOMONSTERS = 4; const int DMSS_FOILINVUL = 1; const int DMSS_AFFECTARMOR = 2; const int DMSS_KILL = 4; +const int DMSS_NOFACTOR = 8; // Flags for A_AlertMonsters const int AMF_TARGETEMITTER = 1;