Skip to content
GitLab
  • Menu
Projects Groups Snippets
  • /
  • Help
    • Help
    • Support
    • Community forum
    • Submit feedback
    • Contribute to GitLab
  • Sign in / Register
  • EDuke32 EDuke32
  • Project information
    • Project information
    • Activity
    • Labels
    • Members
  • Repository
    • Repository
    • Files
    • Commits
    • Branches
    • Tags
    • Contributors
    • Graph
    • Compare
  • Issues 98
    • Issues 98
    • List
    • Boards
    • Service Desk
    • Milestones
  • Merge requests 11
    • Merge requests 11
  • Deployments
    • Deployments
    • Releases
  • Analytics
    • Analytics
    • Value stream
    • Repository
  • Activity
  • Graph
  • Create a new issue
  • Commits
  • Issue Boards
Collapse sidebar
  • Richard Gobeille
  • EDuke32EDuke32
  • Issues
  • #219
Closed
Open
Created Nov 26, 2021 by Dino Bollinger@dibollingerDeveloper

Duke3D: Strange conditional branch in A_IncurDamage()

So I was looking at the A_IncurDamage() to check hardcoded behavior with RADIUSEXPLOSION, and in the process I discovered this code that doesn't quite seem to make sense:

         switch (tileGetMapping(pActor->htpicnum))
         {
             case RADIUSEXPLOSION__:
             case SEENINE__:
 #ifndef EDUKE32_STANDALONE
             case RPG__:
             case HYDRENT__:
             case HEAVYHBOMB__:
             case OOZFILTER__:
             case EXPLODINGBARREL__:
 #endif
                 P_Nudge(playerNum, spriteNum, 2);
                 break;

             default:
                 P_Nudge(playerNum, spriteNum, (A_CheckSpriteFlags(pActor->htowner, SFLAG_PROJECTILE) &&
                                        (SpriteProjectile[pActor->htowner].workslike & PROJECTILE_RPG))
                                       ? 2
                                       : 1);
                 break;
         }

Hardcoded explosions move the player with a force of 2. If the projectile is not a hardcoded explosion, the game checks whether the owner of the projectile that hit the player, i.e. the actor that fired the projectile is also an RPG projectile, and if so, applies a force of 2. This seems odd, and is almost never actually fulfilled, unless somehow a custom RPG projectile manages to fire another projectile at the player.

I believe this was probably meant to be a check for the spriteNum of the projectile that hit the player instead -- but this number is not available here. The following diff would change this, such that we use the htpicnum to determine the workslike flag:

diff --git a/source/duke3d/src/actors.cpp b/source/duke3d/src/actors.cpp
index d23acae1e..88dfb59d0 100644
--- a/source/duke3d/src/actors.cpp
+++ b/source/duke3d/src/actors.cpp
@@ -1301,8 +1301,8 @@ int A_IncurDamage(int const spriteNum)
                 break;

             default:
-                P_Nudge(playerNum, spriteNum, (A_CheckSpriteFlags(pActor->htowner, SFLAG_PROJECTILE) &&
-                                       (SpriteProjectile[pActor->htowner].workslike & PROJECTILE_RPG))
+                P_Nudge(playerNum, spriteNum, ((g_tile[pActor->htpicnum].flags & SFLAG_PROJECTILE) &&
+                                    (g_tile[pActor->htpicnum].proj->workslike & PROJECTILE_RPG))
                                       ? 2
                                       : 1);        

However, I'm not sure whether this patch should actually be applied, because it would double the pushback force the player receives from all custom projectiles. This might significantly affect existing mods.

Edited Dec 02, 2021 by Dino Bollinger
Assignee
Assign to
Time tracking