From 162591efdb6b129bf67fe451a9fb4995414648f2 Mon Sep 17 00:00:00 2001 From: AJ Martinez Date: Fri, 29 Mar 2024 18:11:05 -0700 Subject: [PATCH] Sealed Star Emeralds retarget when their carrier dies --- src/objects/emerald.c | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/src/objects/emerald.c b/src/objects/emerald.c index c42578e7c..bb482965d 100644 --- a/src/objects/emerald.c +++ b/src/objects/emerald.c @@ -17,6 +17,7 @@ #include "../r_main.h" #include "../s_sound.h" #include "../tables.h" +#include "../g_game.h" #define emerald_type(o) ((o)->extravalue1) #define emerald_anim_start(o) ((o)->movedir) @@ -126,6 +127,33 @@ static void Obj_EmeraldOrbitPlayer(mobj_t *emerald) fixed_t x = FixedMul(r, FCOS(emerald->angle)); fixed_t y = FixedMul(r, FSIN(emerald->angle)); + // Multiplayer Sealed Stars can become unwinnable if someone deathpits with the emerald. Find a player to retarget! + if ((gametyperules & GTR_CATCHER) && emerald_orbit(emerald)->player && (emerald_orbit(emerald)->player->pflags & PF_NOCONTEST)) + { + player_t *bestplayer = emerald_orbit(emerald)->player; + + for (int i = 0; i < MAXPLAYERS; i++) + { + if (!playeringame[i]) + continue; + if (players[i].spectator) + continue; + if (players[i].pflags & PF_NOCONTEST) + continue; + if (!(players[i].mo && !P_MobjWasRemoved(players[i].mo))) + continue; + if ((bestplayer->pflags & PF_NOCONTEST) || (players[i].distancetofinish < bestplayer->distancetofinish)) + bestplayer = &players[i]; + } + + if (!(bestplayer->pflags & PF_NOCONTEST)) + { + P_MoveOrigin(emerald, bestplayer->mo->x, bestplayer->mo->y, bestplayer->mo->z); + Obj_BeginEmeraldOrbit(emerald, bestplayer->mo, 100 * mapobjectscale, 64, 0); + return; + } + } + P_MoveOrigin( emerald, emerald_orbit(emerald)->x + x,