From 01b2f9d5b0cd12fe13b74b5ce7e32fddd04a4c70 Mon Sep 17 00:00:00 2001 From: JugadorXEI Date: Sun, 21 Sep 2025 18:27:32 +0200 Subject: [PATCH 1/3] Add workaround for gremlin'd wall collisions --- src/p_test.cpp | 34 +++++++++++++++++++++++++++++++--- 1 file changed, 31 insertions(+), 3 deletions(-) diff --git a/src/p_test.cpp b/src/p_test.cpp index 0fba3e4cb..fb1959610 100644 --- a/src/p_test.cpp +++ b/src/p_test.cpp @@ -15,6 +15,8 @@ #include "p_sweep.hpp" #include "p_local.h" +#include "g_demo.h" +#include "r_main.h" consvar_t cv_showgremlins = CVAR_INIT ("showgremlins", "Off", 0, CV_OnOff, NULL); @@ -62,13 +64,39 @@ line_t* P_SweepTestLines(fixed_t ax, fixed_t ay, fixed_t bx, fixed_t by, fixed_t } } - g_lines.clear(); - if (!collision) { - return nullptr; + line_t *line = nullptr; + + if (!g_lines.empty() && !G_CompatLevel(0x000E)) + { + // FIXME: This condition is a failsafe! + // SlopeAABBvsLine::vs_slope can sometimes report + // no collision despite P_CheckPosition saying otherwise. + // (Generally related to infinitesimal numbers or overflows.) + // When it reports no collision, that means no line and + // no normals to base the collision off of. + // Here we provide the last line checked and normals based on + // the line and the player's momentum angle. + // But the proper fix would be to make vs_slope work!! + + line = g_lines.back(); + + angle_t lineangle = line->angle; + angle_t mobjangle = R_PointToAngle2(ax, ay, bx, by); + angle_t diff = lineangle - mobjangle; + + lineangle += diff > ANGLE_180 ? -ANGLE_90 : ANGLE_90; + + return_normal->x = FINECOSINE((lineangle >> ANGLETOFINESHIFT) & FINEMASK); + return_normal->y = FINESINE((lineangle >> ANGLETOFINESHIFT) & FINEMASK); + } + + g_lines.clear(); + return line; } + g_lines.clear(); return_normal->x = Fixed {collision->normal.x}; return_normal->y = Fixed {collision->normal.y}; From eb4d4717e5199fef7ab05102d60f375e6a8707a0 Mon Sep 17 00:00:00 2001 From: JugadorXEI Date: Sun, 21 Sep 2025 18:35:50 +0200 Subject: [PATCH 2/3] Move cv_showgremlins code to P_SweepTestLines so it can still fire --- src/p_map.c | 21 ++++----------------- src/p_test.cpp | 28 ++++++++++++++++++++++++++++ 2 files changed, 32 insertions(+), 17 deletions(-) diff --git a/src/p_map.c b/src/p_map.c index 6103b3c2d..0317b34c3 100644 --- a/src/p_map.c +++ b/src/p_map.c @@ -3496,25 +3496,12 @@ static void P_BouncePlayerMove(mobj_t *mo, TryMoveResult_t *result) slidemo = mo; bestslideline = result->line; - if (bestslideline == NULL && cv_showgremlins.value) + /*if (mo->health <= 0) { - // debug - mobj_t*x = P_SpawnMobj(mo->x, mo->y, mo->z, MT_THOK); - x->frame = FF_FULLBRIGHT | FF_ADD; - x->renderflags = RF_ALWAYSONTOP; - x->color = SKINCOLOR_RED; - - CONS_Printf( - "GREMLIN: leveltime=%u x=%f y=%f z=%f angle=%f\n", - leveltime, - FixedToFloat(mo->x), - FixedToFloat(mo->y), - FixedToFloat(mo->z), - AngleToFloat(R_PointToAngle2(0, 0, oldmomx, oldmomy)) - ); + tmxmove = mo->momx; + tmymove = mo->momy; } - - if (mo->eflags & MFE_JUSTBOUNCEDWALL) // Stronger push-out + else */if (mo->eflags & MFE_JUSTBOUNCEDWALL) // Stronger push-out { tmxmove = mmomx; tmymove = mmomy; diff --git a/src/p_test.cpp b/src/p_test.cpp index fb1959610..9930a4434 100644 --- a/src/p_test.cpp +++ b/src/p_test.cpp @@ -34,6 +34,8 @@ void P_TestLine(line_t* ld) line_t* P_SweepTestLines(fixed_t ax, fixed_t ay, fixed_t bx, fixed_t by, fixed_t r, vector2_t* return_normal) { + extern consvar_t cv_showgremlins; + using namespace srb2::math; using namespace srb2::sweep; @@ -90,6 +92,32 @@ line_t* P_SweepTestLines(fixed_t ax, fixed_t ay, fixed_t bx, fixed_t by, fixed_t return_normal->x = FINECOSINE((lineangle >> ANGLETOFINESHIFT) & FINEMASK); return_normal->y = FINESINE((lineangle >> ANGLETOFINESHIFT) & FINEMASK); + + // Moving the gremlin debug here so that it + // still fires even when the workaround is used. + if (cv_showgremlins.value) + { + mobj_t *mo = g_tm.thing; + + if (mo) + { + mobj_t *x = P_SpawnMobj(mo->x, mo->y, mo->z, MT_THOK); + x->frame = FF_FULLBRIGHT | FF_ADD; + x->renderflags = RF_ALWAYSONTOP; + x->color = SKINCOLOR_RED; + + CONS_Printf( + "GREMLIN: leveltime=%u x=%f y=%f z=%f momx=%f momy=%f momz=%f\n", + leveltime, + FixedToFloat(mo->x), + FixedToFloat(mo->y), + FixedToFloat(mo->z), + FixedToFloat(mo->momx), + FixedToFloat(mo->momy), + FixedToFloat(mo->momz) + ); + } + } } g_lines.clear(); From b769bcd295fc184a22a6b8daa7d8778593841864 Mon Sep 17 00:00:00 2001 From: NepDisk Date: Sun, 21 Sep 2025 15:20:41 -0400 Subject: [PATCH 3/3] Adjust for our needs --- src/p_map.c | 3 ++- src/p_test.cpp | 4 +--- 2 files changed, 3 insertions(+), 4 deletions(-) diff --git a/src/p_map.c b/src/p_map.c index 0317b34c3..22f893c0f 100644 --- a/src/p_map.c +++ b/src/p_map.c @@ -3501,7 +3501,8 @@ static void P_BouncePlayerMove(mobj_t *mo, TryMoveResult_t *result) tmxmove = mo->momx; tmymove = mo->momy; } - else */if (mo->eflags & MFE_JUSTBOUNCEDWALL) // Stronger push-out + else if*/ + if (mo->eflags & MFE_JUSTBOUNCEDWALL) // Stronger push-out { tmxmove = mmomx; tmymove = mmomy; diff --git a/src/p_test.cpp b/src/p_test.cpp index 9930a4434..2ffb53cbd 100644 --- a/src/p_test.cpp +++ b/src/p_test.cpp @@ -34,8 +34,6 @@ void P_TestLine(line_t* ld) line_t* P_SweepTestLines(fixed_t ax, fixed_t ay, fixed_t bx, fixed_t by, fixed_t r, vector2_t* return_normal) { - extern consvar_t cv_showgremlins; - using namespace srb2::math; using namespace srb2::sweep; @@ -70,7 +68,7 @@ line_t* P_SweepTestLines(fixed_t ax, fixed_t ay, fixed_t bx, fixed_t by, fixed_t { line_t *line = nullptr; - if (!g_lines.empty() && !G_CompatLevel(0x000E)) + if (!g_lines.empty()) { // FIXME: This condition is a failsafe! // SlopeAABBvsLine::vs_slope can sometimes report