From 63fe657c7d80cba4893441131200a308c90747a8 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 5 Oct 2024 05:25:25 +0200 Subject: [PATCH 001/143] Do not set hu_stopped on interpolated frame --- src/d_clisrv.c | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index f9110bb2d..1c24606f3 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -6405,19 +6405,21 @@ boolean TryRunTics(tic_t realtics) } #endif - if (neededtic > gametic) + ticking = neededtic > gametic; + + if (ticking) { - hu_stopped = false; + if (realtics) + hu_stopped = false; } if (player_joining) { - hu_stopped = true; + if (realtics) + hu_stopped = true; return false; } - ticking = neededtic > gametic; - if (ticking) { // run the count * tics @@ -6448,7 +6450,8 @@ boolean TryRunTics(tic_t realtics) } else { - hu_stopped = true; + if (realtics) + hu_stopped = true; } return ticking; -- 2.54.0 From f9e1cdb9403cad483a98b0599a97b76918b332e1 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 5 Oct 2024 06:08:23 +0200 Subject: [PATCH 002/143] P_Ticker: update view interpolation at the start of a tic --- src/p_setup.c | 1 - src/p_tick.c | 16 +++++++++++++--- src/p_user.c | 1 - 3 files changed, 13 insertions(+), 5 deletions(-) diff --git a/src/p_setup.c b/src/p_setup.c index 17d050dc4..c9e05f9ec 100644 --- a/src/p_setup.c +++ b/src/p_setup.c @@ -3011,7 +3011,6 @@ boolean P_SetupLevel(boolean skipprecip, boolean reloadinggamestate) if (rendermode != render_none && !reloadinggamestate) { - R_ResetViewInterpolation(0); R_ResetViewInterpolation(0); R_UpdateMobjInterpolators(); } diff --git a/src/p_tick.c b/src/p_tick.c index 7405792d0..19f18f725 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -434,10 +434,21 @@ void P_Ticker(boolean run) { INT32 i; - //Increment jointime even if paused. + // Increment jointime and quittime even if paused for (i = 0; i < MAXPLAYERS; i++) + { if (playeringame[i]) - ++players[i].jointime; + { + players[i].jointime++; + } + } + + if (run) + { + // Update old view state BEFORE ticking so resetting + // the old interpolation state from game logic works. + R_UpdateViewInterpolation(); + } if (objectplacing) { @@ -672,7 +683,6 @@ void P_Ticker(boolean run) if (run) { R_UpdateLevelInterpolators(); - R_UpdateViewInterpolation(); // Hack: ensure newview is assigned every tic. // Ensures view interpolation is T-1 to T in poor network conditions diff --git a/src/p_user.c b/src/p_user.c index a9b1b6b72..31297c132 100644 --- a/src/p_user.c +++ b/src/p_user.c @@ -4002,7 +4002,6 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall { P_MoveChaseCamera(player, thiscam, false); R_ResetViewInterpolation(num + 1); - R_ResetViewInterpolation(num + 1); } return (x == thiscam->x && y == thiscam->y && z == thiscam->z && angle == thiscam->aiming); -- 2.54.0 From afd7b850053e33665624aea156437482cc59c1ce Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 6 Oct 2024 12:49:29 +0200 Subject: [PATCH 003/143] R_ResetViewInterpolation: wait an extra tic if R_UpdateViewInterpolation has not run yet, do not add extra time for subsequent calls --- src/r_fps.c | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/src/r_fps.c b/src/r_fps.c index 9ccba8a7b..7dcdcf9a9 100644 --- a/src/r_fps.c +++ b/src/r_fps.c @@ -23,6 +23,7 @@ #include "r_state.h" #include "z_zone.h" #include "console.h" // con_startup_loadprogress +#include "i_time.h" #ifdef HWRENDER #include "hardware/hw_main.h" // for cv_grshearing @@ -79,6 +80,7 @@ static viewvars_t skyview_old[MAXSPLITSCREENPLAYERS]; static viewvars_t skyview_new[MAXSPLITSCREENPLAYERS]; static viewvars_t *oldview = &pview_old[0]; +static tic_t last_view_update; static int oldview_invalid[MAXSPLITSCREENPLAYERS] = {0, 0, 0, 0}; viewvars_t *newview = &pview_new[0]; @@ -207,21 +209,27 @@ void R_UpdateViewInterpolation(void) if (oldview_invalid[i]) oldview_invalid[i]--; } + + last_view_update = I_GetTime(); } void R_ResetViewInterpolation(UINT8 p) { + // Wait an extra tic if the interpolation state hasn't + // updated yet. + int t = last_view_update == I_GetTime() ? 1 : 2; + if (p == 0) { UINT8 i; for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) { - oldview_invalid[i]++; + oldview_invalid[i] = t; } } else { - oldview_invalid[p - 1]++; + oldview_invalid[p - 1] = t; } } -- 2.54.0 From ccd691548e5795aaf5f5c505491c77297c45dfd0 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 6 Oct 2024 12:53:24 +0200 Subject: [PATCH 004/143] more R_ResetViewInterpolation stuff --- src/p_spec.c | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/src/p_spec.c b/src/p_spec.c index c0ad9ea7f..9a06be92a 100644 --- a/src/p_spec.c +++ b/src/p_spec.c @@ -2097,7 +2097,6 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) camera[i].reset = true; camera[i].subsector = R_PointInSubsector(camera[i].x, camera[i].y); R_RelativeTeleportViewInterpolation(i, x, y, z, 0); - R_ResetViewInterpolation(i + 1); // reset view interp as well break; } } @@ -2485,6 +2484,7 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) case 422: // Cut away to another view { mobj_t *altview; + INT32 i; if (!mo || !mo->player) // only players have views return; @@ -2496,6 +2496,17 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) if (!altview) return; + if (gamestate == GS_LEVEL) + { + for (i = 0; i <= splitscreen; i++) + { + if (displayplayers[i] == (mo->player - players)) + { + R_ResetViewInterpolation(i + 1); + } + } + } + P_SetTarget(&mo->player->awayviewmobj, altview); mo->player->awayviewtics = P_AproxDistance(line->dx, line->dy)>>FRACBITS; -- 2.54.0 From 112c9398e7d51c63489d658935d9d5d8dbcb46b7 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 6 Oct 2024 12:56:19 +0200 Subject: [PATCH 005/143] add missing break --- src/p_telept.c | 1 + 1 file changed, 1 insertion(+) diff --git a/src/p_telept.c b/src/p_telept.c index a7cef7b1d..ceed7dc93 100644 --- a/src/p_telept.c +++ b/src/p_telept.c @@ -166,6 +166,7 @@ boolean P_Teleport(mobj_t *thing, fixed_t x, fixed_t y, fixed_t z, angle_t angle P_ResetCamera(thing->player, &camera[i]); R_ResetViewInterpolation(i + 1); + break; } // don't run in place after a teleport -- 2.54.0 From a754e9c08a79d04d0b4411860478d87c48d71283 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 6 Oct 2024 13:00:07 +0200 Subject: [PATCH 006/143] HACK: reset interp values in case 412 teleporter without using P_Setorigin since that function does some wonky stuff and idk if that would be synch safe --- src/p_spec.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/p_spec.c b/src/p_spec.c index 9a06be92a..96d7ef9b8 100644 --- a/src/p_spec.c +++ b/src/p_spec.c @@ -2079,6 +2079,9 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) mo->y += y; mo->z += z; P_SetThingPosition(mo); + mo->old_x = mo->x; + mo->old_y = mo->y; + mo->old_z = mo->z; if (mo->player) { -- 2.54.0 From 8e799ddd74b813ab259f336dcb885a56da7bd158 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 6 Oct 2024 13:04:43 +0200 Subject: [PATCH 007/143] fix a interp bug where the jitter on tally increase would be for only one rendered frame, not one full tic. --- src/y_inter.c | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/src/y_inter.c b/src/y_inter.c index b62566e0a..bbfccf959 100644 --- a/src/y_inter.c +++ b/src/y_inter.c @@ -463,14 +463,12 @@ void Y_IntermissionDrawer(void) for (i = 0; i < data.match.numplayers; i++) { - boolean dojitter = data.match.jitter[data.match.num[i]]; - data.match.jitter[data.match.num[i]] = 0; - if (data.match.num[i] != MAXPLAYERS && playeringame[data.match.num[i]] && !players[data.match.num[i]].spectator) { char strtime[MAXPLAYERNAME+1]; - if (dojitter) + // Apply the jitter offset (later reversed) + if (data.match.jitter[data.match.num[i]] > 0) y--; V_DrawCenteredString(x+6, y, 0, va("%d", data.match.pos[i])); @@ -559,7 +557,7 @@ void Y_IntermissionDrawer(void) } } - if (dojitter) + if (data.match.jitter[data.match.num[i]] > 0) y++; } else @@ -666,8 +664,16 @@ void Y_Ticker(void) return; } - if (intertic < TICRATE || intertic & 1 || endtic != -1) + if (intertic < TICRATE || endtic != -1) + { return; + } + + if (data.match.rankingsmode && intertic & 1) + { + memset(data.match.jitter, 0, sizeof (data.match.jitter)); + return; + } if (intertype == int_race || intertype == int_match) { -- 2.54.0 From 595648a2b30b227c12c43f10c9a62dbbf585312e Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 6 Oct 2024 13:12:27 +0200 Subject: [PATCH 008/143] Interpolate view, even when paused https://github.com/KartKrewDev/RingRacers/commit/3320faec8cebecb124882d38c7ec0ad37b79340a#diff-607b68058edc6124b3061267d902aabeddb6ba338c6483df0af8b1a7cf796a01R43 --- src/d_main.c | 3 +++ src/r_main.c | 5 +++-- src/r_main.h | 2 ++ 3 files changed, 8 insertions(+), 2 deletions(-) diff --git a/src/d_main.c b/src/d_main.c index 9ca370c2a..28c1dd594 100644 --- a/src/d_main.c +++ b/src/d_main.c @@ -825,11 +825,14 @@ void D_SRB2Loop(void) { rendertimefrac = FRACUNIT; } + + rendertimefrac_unpaused = g_time.timefrac; } else { renderdeltatics = realtics * FRACUNIT; rendertimefrac = FRACUNIT; + rendertimefrac_unpaused = FRACUNIT; } if ((interp || doDisplay) && !frameskip) diff --git a/src/r_main.c b/src/r_main.c index c85ef09f2..e0cc44ea9 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -75,6 +75,7 @@ line_t *portalclipline; INT32 portalclipstart, portalclipend; fixed_t rendertimefrac; +fixed_t rendertimefrac_unpaused; fixed_t renderdeltatics; boolean renderisnewtic; @@ -1353,7 +1354,7 @@ void R_SkyboxFrame(player_t *player) // newview->sin = FINESINE(viewangle>>ANGLETOFINESHIFT); // newview->cos = FINECOSINE(viewangle>>ANGLETOFINESHIFT); - R_InterpolateView(R_UsingFrameInterpolation() ? rendertimefrac : FRACUNIT, false); + R_InterpolateView(R_UsingFrameInterpolation() ? rendertimefrac_unpaused : FRACUNIT, false); } void R_SetupFrame(player_t *player, boolean skybox) @@ -1480,7 +1481,7 @@ void R_SetupFrame(player_t *player, boolean skybox) newview->player = player; - R_InterpolateView(R_UsingFrameInterpolation() ? rendertimefrac : FRACUNIT, false); + R_InterpolateView(R_UsingFrameInterpolation() ? rendertimefrac_unpaused : FRACUNIT, false); } #define ANGLED_PORTALS diff --git a/src/r_main.h b/src/r_main.h index 8766ea65c..e6ae49103 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -33,6 +33,8 @@ extern size_t validcount, linecount, loopcount, framecount; // The fraction of a tic being drawn (for interpolation between two tics) extern fixed_t rendertimefrac; +// Same as rendertimefrac but not suspended when the game is paused +extern fixed_t rendertimefrac_unpaused; // Evaluated delta tics for this frame (how many tics since the last frame) extern fixed_t renderdeltatics; // The current render is a new logical tic -- 2.54.0 From 90d64c4e1590cc86613938af9e90d40ebf026427 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 6 Oct 2024 13:32:46 +0200 Subject: [PATCH 009/143] fix main menu interpolation apparently in main menu, opening the menu pauses the game so rendertimefrac was FRACUNIT and didnt interpolate --- src/f_finale.c | 10 +++++----- src/r_main.c | 5 +++++ src/r_main.h | 2 ++ 3 files changed, 12 insertions(+), 5 deletions(-) diff --git a/src/f_finale.c b/src/f_finale.c index 7f86303c0..18eab51eb 100644 --- a/src/f_finale.c +++ b/src/f_finale.c @@ -170,8 +170,8 @@ static void F_SkyScroll(INT32 scrollspeed) w = (vid.width / vid.dupx)<width)*16))<width)<width)*16))<width)*16))<width)<width)*16))<= 20) V_DrawSmallScaledPatch(84, 87, 0, ttkart); else if (finalecount >= 10) - V_DrawSciencePatch((84< Date: Sun, 6 Oct 2024 14:30:21 +0200 Subject: [PATCH 010/143] only do this in replays otherwise shit will jitter during netlag --- src/r_main.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/r_main.c b/src/r_main.c index f61753a19..90b4bbd55 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -1359,7 +1359,7 @@ void R_SkyboxFrame(player_t *player) // newview->sin = FINESINE(viewangle>>ANGLETOFINESHIFT); // newview->cos = FINECOSINE(viewangle>>ANGLETOFINESHIFT); - R_InterpolateView(R_UsingFrameInterpolation() ? rendertimefrac_unpaused : FRACUNIT, false); + R_InterpolateView(R_UsingFrameInterpolation() ? demo.playback ? rendertimefrac_unpaused : rendertimefrac : FRACUNIT, false); } void R_SetupFrame(player_t *player, boolean skybox) @@ -1486,7 +1486,7 @@ void R_SetupFrame(player_t *player, boolean skybox) newview->player = player; - R_InterpolateView(R_UsingFrameInterpolation() ? rendertimefrac_unpaused : FRACUNIT, false); + R_InterpolateView(R_UsingFrameInterpolation() ? demo.playback ? rendertimefrac_unpaused : rendertimefrac : FRACUNIT, false); } #define ANGLED_PORTALS -- 2.54.0 From b2cac971068ebee6049038a57208f9cfcfc81e95 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 6 Oct 2024 14:52:35 +0200 Subject: [PATCH 011/143] fix this --- src/p_spec.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/p_spec.c b/src/p_spec.c index 96d7ef9b8..af3687bfb 100644 --- a/src/p_spec.c +++ b/src/p_spec.c @@ -2499,6 +2499,9 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) if (!altview) return; + P_SetTarget(&mo->player->awayviewmobj, altview); + mo->player->awayviewtics = P_AproxDistance(line->dx, line->dy)>>FRACBITS; + if (gamestate == GS_LEVEL) { for (i = 0; i <= splitscreen; i++) @@ -2510,9 +2513,6 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) } } - P_SetTarget(&mo->player->awayviewmobj, altview); - mo->player->awayviewtics = P_AproxDistance(line->dx, line->dy)>>FRACBITS; - if (line->flags & ML_NOCLIMB) // lets you specify a vertical angle { INT32 aim; -- 2.54.0 From ef763487a5f3c187e0aefb3cc7a6dbb99aac8235 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 6 Oct 2024 18:35:26 +0200 Subject: [PATCH 012/143] this doesent make much sense tbh --- src/d_main.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/d_main.c b/src/d_main.c index 471d29fa2..8be5bd2c2 100644 --- a/src/d_main.c +++ b/src/d_main.c @@ -818,7 +818,7 @@ void D_SRB2Loop(void) { renderdeltatics = FLOAT_TO_FIXED(deltatics); - if (!(paused || P_AutoPause()) && deltatics < 1.0 && !hu_stopped) + if (!(paused || P_AutoPause()) && !hu_stopped) { rendertimefrac = g_time.timefrac; } -- 2.54.0 From 7c78cf067c341f0ff5636a32f10c42731cc92840 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 3 Nov 2024 15:33:26 +0100 Subject: [PATCH 013/143] forgor ifdef here --- src/m_menu.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/m_menu.c b/src/m_menu.c index 4e215a9a9..89009dbfa 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -3473,7 +3473,9 @@ void SaturnHud_menu_Onchange(void) #ifdef HWRENDER void M_UpdateOGLMenu(void) { +#ifdef USE_FBO_OGL OP_ExpOptionsMenu[op_exp_fbo].status = (!supportFBO || cv_glscreentextures.value != 2) ? IT_GRAYEDOUT : IT_STRING | IT_CVAR; +#endif OP_ExpOptionsMenu[op_exp_paldepth].status = (!HWR_ShouldUsePaletteRendering()) ? IT_GRAYEDOUT : IT_STRING | IT_CVAR; OP_OpenGLOptionsMenu[op_gl_falbckmdls].status = (!cv_glmdls.value) ? IT_GRAYEDOUT : IT_STRING | IT_CVAR; -- 2.54.0 From f4703be2ca4d868563cd3a7ebcf535ee89d8854f Mon Sep 17 00:00:00 2001 From: Indev Date: Fri, 8 Nov 2024 11:47:58 +0300 Subject: [PATCH 014/143] Fix r_portal.c and r_portal.h missing from src/CMakeLists.txt --- src/CMakeLists.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 7d84323bc..8fde277c7 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -134,6 +134,7 @@ set(SRB2_CORE_RENDER_SOURCES r_sky.c r_splats.c r_things.c + r_portal.c r_bsp.h r_data.h @@ -149,6 +150,7 @@ set(SRB2_CORE_RENDER_SOURCES r_splats.h r_state.h r_things.h + r_portal.h ) set(SRB2_CORE_GAME_SOURCES @@ -488,7 +490,7 @@ if(${SRB2_CONFIG_HWRENDER}) ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_drv.h ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_glob.h ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_main.h - ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_portal.c + ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_portal.h ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_md2.h ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_md2load.h ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_md3load.h -- 2.54.0 From fc469d6433c2595a669f9c871e5d63102973f199 Mon Sep 17 00:00:00 2001 From: Indev Date: Sun, 10 Nov 2024 03:18:01 +0300 Subject: [PATCH 015/143] Fix spectating other players setting wrong angle when returning back to local player --- src/g_game.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/g_game.c b/src/g_game.c index 1cf6f2ddb..3a30570e6 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -1493,7 +1493,7 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) if ((cmd->forwardmove || cmd->sidemove || cmd->buttons) && displayplayers[0] != consoleplayer && ssplayer == 1) { - displayplayers[0] = consoleplayer; + G_ResetView(1, consoleplayer, false); // i dont like this lmao if (cv_director.value) CV_SetValue(&cv_director, 0); @@ -2007,7 +2007,7 @@ static void G_FixCamera(UINT8 view) // The order of displayplayers can change, which would // invalidate localangle. - localangle[view - 1] = player->cmd.angleturn; + localangle[view - 1] = player->mo->angle; // Players *always* have mobjs, right? P_ResetCamera(player, &camera[view - 1]); -- 2.54.0 From 38abb4c9e429b6bc385df2b646719edf10265beb Mon Sep 17 00:00:00 2001 From: Indev Date: Sun, 10 Nov 2024 03:26:15 +0300 Subject: [PATCH 016/143] That didn't work in spectator camera, oops --- src/g_game.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/g_game.c b/src/g_game.c index 3a30570e6..8fbb418ca 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -366,6 +366,8 @@ void SendWeaponPref2(void); void SendWeaponPref3(void); void SendWeaponPref4(void); +static void G_FixCamera(UINT8 view); + //static CV_PossibleValue_t crosshair_cons_t[] = {{0, "Off"}, {1, "Cross"}, {2, "Angle"}, {3, "Point"}, {0, NULL}}; static CV_PossibleValue_t joyaxis_cons_t[] = {{0, "None"}, {1, "Left X"}, {2, "Left Y"}, {-1, "Left X-"}, {-2, "Left Y-"}, @@ -1493,7 +1495,8 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) if ((cmd->forwardmove || cmd->sidemove || cmd->buttons) && displayplayers[0] != consoleplayer && ssplayer == 1) { - G_ResetView(1, consoleplayer, false); + displayplayers[0] = consoleplayer; + G_FixCamera(1); // i dont like this lmao if (cv_director.value) CV_SetValue(&cv_director, 0); -- 2.54.0 From 6816c6dd19a5d29a6fec449d79588484316177f7 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 12 Nov 2024 15:43:46 +0100 Subject: [PATCH 017/143] add some paranthesis here --- src/r_fps.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/r_fps.c b/src/r_fps.c index 660dc7d7a..0f86160a6 100644 --- a/src/r_fps.c +++ b/src/r_fps.c @@ -217,7 +217,7 @@ void R_ResetViewInterpolation(UINT8 p) { // Wait an extra tic if the interpolation state hasn't // updated yet. - int t = last_view_update == I_GetTime() ? 1 : 2; + int t = ((last_view_update == I_GetTime()) ? 1 : 2); if (p == 0) { -- 2.54.0 From e2c8a773bec4d874ee12273ba1a2dd6c3bf1a985 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 12 Nov 2024 16:22:51 +0100 Subject: [PATCH 018/143] prevent some palrender startup crashes thx srb2 apparently this can be null during init so add some extra safety --- src/hardware/hw_main.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index b02730814..8c10f1eec 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -329,7 +329,7 @@ static void HWR_SetShaderState(void) boolean HWR_ShouldUsePaletteRendering(void) { - return (cv_glpaletterendering.value && HWR_UseShader()); + return (cv_glpaletterendering.value && (pLocalPalette != NULL) && HWR_UseShader()); } boolean HWR_PalRenderFlashpal(void) -- 2.54.0 From ebfd7f3e4eec42c84ec5e91fb14aa064a2d7baef Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 15 Nov 2024 21:55:50 +0100 Subject: [PATCH 019/143] try make this look less like crap lol --- src/p_mobj.c | 14 ++++---------- 1 file changed, 4 insertions(+), 10 deletions(-) diff --git a/src/p_mobj.c b/src/p_mobj.c index ad296c576..9da7b0235 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -10568,7 +10568,8 @@ void P_SpawnPlayer(INT32 playernum) } // spawn as spectator determination - if (multiplayer && demo.playback); // Don't mess with spectator values since the demo setup handles them already. + if (multiplayer && demo.playback) + ; // Don't mess with spectator values since the demo setup handles them already. else if (!G_GametypeHasSpectators()) p->spectator = false; else if (netgame && p->jointime <= 1 && pcount) @@ -10635,15 +10636,8 @@ void P_SpawnPlayer(INT32 playernum) // (usefulness: when body mobj is detached from player (who respawns), // the dead body mobj retains the skin through the 'spritedef' override). mobj->skin = &skins[p->skin]; - if (p->localskin > 0) - { - if (p->skinlocal) - mobj->localskin = &localskins[p->localskin - 1]; - else - mobj->localskin = & skins[p->localskin - 1]; - } - else - mobj->localskin = 0; + + mobj->localskin = ((p->localskin > 0) ? (p->skinlocal ? &localskins[p->localskin - 1] : &skins[p->localskin - 1]) : 0); mobj->skinlocal = p->skinlocal; mobj->health = p->health; -- 2.54.0 From 3361ebe3c54508fbd3fcdf135b39d620bbe5edea Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 17 Nov 2024 13:02:57 +0100 Subject: [PATCH 020/143] make menucaps stuff global macro and also apply to downloader text --- src/d_clisrv.c | 40 +++++++++++++++++----------------- src/m_menu.c | 58 +++++++++++++++++++++----------------------------- src/v_video.h | 3 +++ 3 files changed, 47 insertions(+), 54 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 2a7b9f761..41d5482eb 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -1228,7 +1228,7 @@ static inline void CL_DrawConnectionStatus(void) //Draw bottom box M_DrawTextBox(BASEVIDWIDTH/2-128-8, BASEVIDHEIGHT-24-8, 32, 1); - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-24, V_YELLOWMAP, "Press ESC to abort"); + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-24, V_YELLOWMAP|MENUCAPS, "Press ESC to abort"); for (i = 0; i < 16; ++i) V_DrawFill((BASEVIDWIDTH/2-128) + (i * 16), BASEVIDHEIGHT-24, 16, 8, palstart + ((animtime - i) & 15)); @@ -1275,7 +1275,7 @@ static inline void CL_DrawConnectionStatus(void) cltext = M_GetText("Connecting to server..."); break; } - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-32, V_YELLOWMAP, cltext); + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-32, V_YELLOWMAP|MENUCAPS, cltext); } else { @@ -1285,7 +1285,7 @@ static inline void CL_DrawConnectionStatus(void) INT32 checkednum = 0; INT32 i; - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-24, V_YELLOWMAP, "Press ESC to abort"); + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-24, V_YELLOWMAP|MENUCAPS, "Press ESC to abort"); //ima just count files here for (i = 0; i < fileneedednum; i++) @@ -1293,12 +1293,12 @@ static inline void CL_DrawConnectionStatus(void) checkednum++; // Loading progress - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-32, V_YELLOWMAP, "Checking server addons..."); + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-32, V_YELLOWMAP|MENUCAPS, "Checking server addons..."); totalfileslength = (INT32)((checkednum/(double)(fileneedednum)) * 256); M_DrawTextBox(BASEVIDWIDTH/2-128-8, BASEVIDHEIGHT-24-8, 32, 1); V_DrawFill(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, 256, 8, 175); V_DrawFill(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, totalfileslength, 8, 160); - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE, + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE|MENUCAPS, va(" %2u/%2u Files",checkednum,fileneedednum)); } else if (cl_mode == CL_LOADFILES) @@ -1307,7 +1307,7 @@ static inline void CL_DrawConnectionStatus(void) INT32 loadcompletednum = 0; INT32 i; - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-24, V_YELLOWMAP, "Press ESC to abort"); + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-24, V_YELLOWMAP|MENUCAPS, "Press ESC to abort"); //ima just count files here for (i = 0; i < fileneedednum; i++) @@ -1315,12 +1315,12 @@ static inline void CL_DrawConnectionStatus(void) loadcompletednum++; // Loading progress - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-32, V_YELLOWMAP, "Loading server addons..."); + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-32, V_YELLOWMAP|MENUCAPS, "Loading server addons..."); totalfileslength = (INT32)((loadcompletednum/(double)(fileneedednum)) * 256); M_DrawTextBox(BASEVIDWIDTH/2-128-8, BASEVIDHEIGHT-24-8, 32, 1); V_DrawFill(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, 256, 8, 175); V_DrawFill(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, totalfileslength, 8, 160); - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE, + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE|MENUCAPS, va(" %2u/%2u Files",loadcompletednum,fileneedednum)); } else if (lastfilenum != -1) @@ -1334,7 +1334,7 @@ static inline void CL_DrawConnectionStatus(void) // Draw the bottom box. M_DrawTextBox(BASEVIDWIDTH/2-128-8, BASEVIDHEIGHT-58-8, 32, 1); - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-58-14, V_YELLOWMAP, "Press ESC to abort"); + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-58-14, V_YELLOWMAP|MENUCAPS, "Press ESC to abort"); Net_GetNetStat(); dldlength = (INT32)((file->currentsize/(double)file->totalsize) * 256); @@ -1359,17 +1359,17 @@ static inline void CL_DrawConnectionStatus(void) strncpy(tempname, filename, sizeof(tempname)-1); } #ifdef HAVE_CURL - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-58-30, 0, + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-58-30, MENUCAPS, va(M_GetText("%s downloading"), ((cl_mode == CL_DOWNLOADHTTPFILES) ? "\x82""HTTP" : "\x85""Direct"))); #else - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-58-30, 0, + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-58-30, MENUCAPS, va(M_GetText("%s downloading"),("\x85""Direct"))); #endif - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-58-22, V_YELLOWMAP, + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-58-22, V_YELLOWMAP|MENUCAPS, va(M_GetText("\"%s\""), tempname)); - V_DrawString(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-58, V_20TRANS|V_MONOSPACE, + V_DrawString(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-58, V_20TRANS|V_MONOSPACE|MENUCAPS, va(" %4uK/%4uK",fileneeded[lastfilenum].currentsize>>10,file->totalsize>>10)); - V_DrawRightAlignedString(BASEVIDWIDTH/2+128, BASEVIDHEIGHT-58, V_20TRANS|V_MONOSPACE, + V_DrawRightAlignedString(BASEVIDWIDTH/2+128, BASEVIDHEIGHT-58, V_20TRANS|V_MONOSPACE|MENUCAPS, va("%3.1fK/s ", ((double)getbps)/1024)); // Download progress @@ -1379,20 +1379,20 @@ static inline void CL_DrawConnectionStatus(void) else totaldldsize = downloadcompletedsize; - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-14, V_YELLOWMAP, "Overall Download Progress"); + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-14, V_YELLOWMAP|MENUCAPS, "Overall Download Progress"); totalfileslength = (INT32)((totaldldsize/(double)totalfilesrequestedsize) * 256); M_DrawTextBox(BASEVIDWIDTH/2-128-8, BASEVIDHEIGHT-24-8, 32, 1); V_DrawFill(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, 256, 8, 175); V_DrawFill(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, totalfileslength, 8, 160); if (totalfilesrequestedsize>>20 >= 10) //display in MB if over 10MB - V_DrawString(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE, + V_DrawString(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE|MENUCAPS, va(" %4uM/%4uM",totaldldsize>>20,totalfilesrequestedsize>>20)); else - V_DrawString(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE, + V_DrawString(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE|MENUCAPS, va(" %4uK/%4uK",totaldldsize>>10,totalfilesrequestedsize>>10)); - V_DrawRightAlignedString(BASEVIDWIDTH/2+128, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE, + V_DrawRightAlignedString(BASEVIDWIDTH/2+128, BASEVIDHEIGHT-24, V_20TRANS|V_MONOSPACE|MENUCAPS, va("%2u/%2u Files ",downloadcompletednum,totalfilesrequestednum)); } else @@ -1403,12 +1403,12 @@ static inline void CL_DrawConnectionStatus(void) //Draw bottom box M_DrawTextBox(BASEVIDWIDTH/2-128-8, BASEVIDHEIGHT-24-8, 32, 1); - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-24, V_YELLOWMAP, "Press ESC to abort"); + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-24, V_YELLOWMAP|MENUCAPS, "Press ESC to abort"); for (i = 0; i < 16; ++i) V_DrawFill((BASEVIDWIDTH/2-128) + (i * 16), BASEVIDHEIGHT-24, 16, 8, palstart + ((animtime - i) & 15)); - V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-32, V_YELLOWMAP, + V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT-24-32, V_YELLOWMAP|MENUCAPS, M_GetText("Waiting to download files...")); } } diff --git a/src/m_menu.c b/src/m_menu.c index 89009dbfa..32322b860 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -5153,8 +5153,6 @@ static void M_DrawGenericMenu(void) { INT32 x, y, w, i, cursory = 0; - INT32 lowercase = !cv_menucaps.value ? V_ALLOWLOWERCASE : 0; - // DRAW MENU x = currentMenu->x; y = currentMenu->y; @@ -5200,9 +5198,9 @@ static void M_DrawGenericMenu(void) cursory = y; if ((currentMenu->menuitems[i].status & IT_DISPLAY)==IT_STRING) - V_DrawString(x, y, lowercase, currentMenu->menuitems[i].text); + V_DrawString(x, y, MENUCAPS, currentMenu->menuitems[i].text); else - V_DrawString(x, y, lowercase|highlightflags, currentMenu->menuitems[i].text); + V_DrawString(x, y, MENUCAPS|highlightflags, currentMenu->menuitems[i].text); // Cvar specific handling switch (currentMenu->menuitems[i].status & IT_TYPE) @@ -5229,7 +5227,7 @@ static void M_DrawGenericMenu(void) default: w = V_StringWidth(cv->string, 0); V_DrawString(BASEVIDWIDTH - x - w, y, - ((cv->flags & CV_CHEAT) && !CV_IsSetToDefault(cv) ? warningflags : highlightflags)|lowercase, cv->string); + ((cv->flags & CV_CHEAT) && !CV_IsSetToDefault(cv) ? warningflags : highlightflags)|MENUCAPS, cv->string); if (i == itemOn) { V_DrawCharacter(BASEVIDWIDTH - x - 10 - w - (skullAnimCounter/5), y, @@ -5244,7 +5242,7 @@ static void M_DrawGenericMenu(void) y += STRINGHEIGHT; break; case IT_STRING2: - V_DrawString(((BASEVIDWIDTH - V_StringWidth(currentMenu->menuitems[i].text, 0))>>1), y, lowercase, currentMenu->menuitems[i].text); + V_DrawString(((BASEVIDWIDTH - V_StringWidth(currentMenu->menuitems[i].text, 0))>>1), y, MENUCAPS, currentMenu->menuitems[i].text); /* FALLTHRU */ case IT_DYLITLSPACE: y += SMALLLINEHEIGHT; @@ -5260,21 +5258,21 @@ static void M_DrawGenericMenu(void) y = currentMenu->y+currentMenu->menuitems[i].alphaKey; /* FALLTHRU */ case IT_TRANSTEXT2: - V_DrawString(x, y, V_TRANSLUCENT|lowercase, currentMenu->menuitems[i].text); + V_DrawString(x, y, V_TRANSLUCENT|MENUCAPS, currentMenu->menuitems[i].text); y += SMALLLINEHEIGHT; break; case IT_QUESTIONMARKS: if (currentMenu->menuitems[i].alphaKey) y = currentMenu->y+currentMenu->menuitems[i].alphaKey; - V_DrawString(x, y, V_TRANSLUCENT|V_OLDSPACING|lowercase, M_CreateSecretMenuOption(currentMenu->menuitems[i].text)); + V_DrawString(x, y, V_TRANSLUCENT|V_OLDSPACING|MENUCAPS, M_CreateSecretMenuOption(currentMenu->menuitems[i].text)); y += SMALLLINEHEIGHT; break; case IT_HEADERTEXT: // draws 16 pixels to the left, in yellow text if (currentMenu->menuitems[i].alphaKey) y = currentMenu->y+currentMenu->menuitems[i].alphaKey; - V_DrawString(x-16, y, highlightflags|lowercase, currentMenu->menuitems[i].text); + V_DrawString(x-16, y, highlightflags|MENUCAPS, currentMenu->menuitems[i].text); y += SMALLLINEHEIGHT; break; } @@ -5291,7 +5289,7 @@ static void M_DrawGenericMenu(void) { V_DrawScaledPatch(currentMenu->x - 24, cursory, 0, W_CachePatchName("M_CURSOR", PU_CACHE)); - V_DrawString(currentMenu->x, cursory, lowercase|highlightflags, currentMenu->menuitems[itemOn].text); + V_DrawString(currentMenu->x, cursory, MENUCAPS|highlightflags, currentMenu->menuitems[itemOn].text); } // dumb hack @@ -5369,8 +5367,6 @@ static void M_DrawGenericScrollMenu(void) // draw title (or big pic) M_DrawMenuTitle(); - INT32 lowercase = !cv_menucaps.value ? V_ALLOWLOWERCASE : 0; - for (; i < max; i++) { y = currentMenu->menuitems[i].alphaKey*2 + tempcentery; @@ -5387,9 +5383,9 @@ static void M_DrawGenericScrollMenu(void) case IT_STRING: case IT_WHITESTRING: if (i != itemOn && (currentMenu->menuitems[i].status & IT_DISPLAY)==IT_STRING) - V_DrawString(x, y, lowercase, currentMenu->menuitems[i].text); + V_DrawString(x, y, MENUCAPS, currentMenu->menuitems[i].text); else - V_DrawString(x, y, lowercase|highlightflags, currentMenu->menuitems[i].text); + V_DrawString(x, y, MENUCAPS|highlightflags, currentMenu->menuitems[i].text); // Cvar specific handling switch (currentMenu->menuitems[i].status & IT_TYPE) @@ -5411,12 +5407,12 @@ static void M_DrawGenericScrollMenu(void) if (itemOn == i) M_DrawTextInput(x + 8, y + 12, &menuinput, 0); else - V_DrawString(x + 8, y + 12, lowercase, cv->string); + V_DrawString(x + 8, y + 12, MENUCAPS, cv->string); break; default: V_DrawRightAlignedString(BASEVIDWIDTH - x, y, - ((cv->flags & CV_CHEAT) && !CV_IsSetToDefault(cv) ? V_REDMAP : highlightflags)|lowercase, cv->string); + ((cv->flags & CV_CHEAT) && !CV_IsSetToDefault(cv) ? V_REDMAP : highlightflags)|MENUCAPS, cv->string); if (i == itemOn) { V_DrawCharacter(BASEVIDWIDTH - x - 10 - V_StringWidth(cv->string, 0) - (skullAnimCounter/5), y, @@ -5430,13 +5426,13 @@ static void M_DrawGenericScrollMenu(void) } break; case IT_TRANSTEXT: - V_DrawString(x, y, V_TRANSLUCENT|lowercase, currentMenu->menuitems[i].text); + V_DrawString(x, y, V_TRANSLUCENT|MENUCAPS, currentMenu->menuitems[i].text); break; case IT_QUESTIONMARKS: - V_DrawString(x, y, lowercase|V_TRANSLUCENT|V_OLDSPACING, M_CreateSecretMenuOption(currentMenu->menuitems[i].text)); + V_DrawString(x, y, MENUCAPS|V_TRANSLUCENT|V_OLDSPACING, M_CreateSecretMenuOption(currentMenu->menuitems[i].text)); break; case IT_HEADERTEXT: - V_DrawString(x-16, y, highlightflags|lowercase, currentMenu->menuitems[i].text); + V_DrawString(x-16, y, highlightflags|MENUCAPS, currentMenu->menuitems[i].text); break; } } @@ -5491,8 +5487,6 @@ static void M_DrawCenteredMenu(void) // draw title (or big pic) M_DrawMenuTitle(); - INT32 lowercase = !cv_menucaps.value ? V_ALLOWLOWERCASE : 0; - for (i = 0; i < currentMenu->numitems; i++) { if (i == itemOn) @@ -5531,9 +5525,9 @@ static void M_DrawCenteredMenu(void) cursory = y; if ((currentMenu->menuitems[i].status & IT_DISPLAY)==IT_STRING) - V_DrawCenteredString(x, y, lowercase, currentMenu->menuitems[i].text); + V_DrawCenteredString(x, y, MENUCAPS, currentMenu->menuitems[i].text); else - V_DrawCenteredString(x, y, highlightflags|lowercase, currentMenu->menuitems[i].text); + V_DrawCenteredString(x, y, highlightflags|MENUCAPS, currentMenu->menuitems[i].text); // Cvar specific handling switch(currentMenu->menuitems[i].status & IT_TYPE) @@ -5558,7 +5552,7 @@ static void M_DrawCenteredMenu(void) break; default: V_DrawString(BASEVIDWIDTH - x - V_StringWidth(cv->string, 0), y, - ((cv->flags & CV_CHEAT) && !CV_IsSetToDefault(cv) ? warningflags : highlightflags)|lowercase, cv->string); + ((cv->flags & CV_CHEAT) && !CV_IsSetToDefault(cv) ? warningflags : highlightflags)|MENUCAPS, cv->string); break; } break; @@ -5566,7 +5560,7 @@ static void M_DrawCenteredMenu(void) y += STRINGHEIGHT; break; case IT_STRING2: - V_DrawCenteredString(x, y, lowercase, currentMenu->menuitems[i].text); + V_DrawCenteredString(x, y, MENUCAPS, currentMenu->menuitems[i].text); /* FALLTHRU */ case IT_DYLITLSPACE: y += SMALLLINEHEIGHT; @@ -5575,7 +5569,7 @@ static void M_DrawCenteredMenu(void) if (currentMenu->menuitems[i].alphaKey) y = currentMenu->y+currentMenu->menuitems[i].alphaKey; - V_DrawCenteredString(x, y, V_TRANSLUCENT|V_OLDSPACING|lowercase, M_CreateSecretMenuOption(currentMenu->menuitems[i].text)); + V_DrawCenteredString(x, y, V_TRANSLUCENT|V_OLDSPACING|MENUCAPS, M_CreateSecretMenuOption(currentMenu->menuitems[i].text)); y += SMALLLINEHEIGHT; break; case IT_GRAYPATCH: @@ -5598,7 +5592,7 @@ static void M_DrawCenteredMenu(void) { V_DrawScaledPatch(x - V_StringWidth(currentMenu->menuitems[itemOn].text, 0)/2 - 24, cursory, 0, W_CachePatchName("M_CURSOR", PU_CACHE)); - V_DrawCenteredString(x, cursory, highlightflags|lowercase, currentMenu->menuitems[itemOn].text); + V_DrawCenteredString(x, cursory, highlightflags|MENUCAPS, currentMenu->menuitems[itemOn].text); } } @@ -10274,18 +10268,16 @@ static void M_DrawMPMainMenu(void) // use generic drawer for cursor, items and title M_DrawGenericMenu(); - INT32 lowercase = !cv_menucaps.value ? V_ALLOWLOWERCASE : 0; - #ifndef NONET #if MAXPLAYERS != 16 Update the maxplayers label... #endif V_DrawRightAlignedString(BASEVIDWIDTH-x, y+MP_MainMenu[4].alphaKey, - ((itemOn == 4) ? highlightflags : 0)|lowercase, "(2-16 Players)"); + ((itemOn == 4) ? highlightflags : 0)|MENUCAPS, "(2-16 Players)"); #endif V_DrawRightAlignedString(BASEVIDWIDTH-x, y+MP_MainMenu[5].alphaKey, - ((itemOn == 5) ? highlightflags : 0)|lowercase, + ((itemOn == 5) ? highlightflags : 0)|MENUCAPS, "(2-4 players)" ); @@ -12632,10 +12624,8 @@ static void M_DrawVideoMenu(void) { M_DrawGenericMenu(); - INT32 lowercase = !cv_menucaps.value ? V_ALLOWLOWERCASE : 0; - V_DrawRightAlignedString(BASEVIDWIDTH - currentMenu->x, currentMenu->y + OP_VideoOptionsMenu[0].alphaKey, - (SCR_IsAspectCorrect(vid.width, vid.height) ? recommendedflags : highlightflags)|lowercase, + (SCR_IsAspectCorrect(vid.width, vid.height) ? recommendedflags : highlightflags)|MENUCAPS, va("%dx%d", vid.width, vid.height)); } diff --git a/src/v_video.h b/src/v_video.h index a06760215..dfab7dfde 100644 --- a/src/v_video.h +++ b/src/v_video.h @@ -182,6 +182,9 @@ void V_DrawFadeScreen(UINT16 color, UINT8 strength); void V_DrawFadeConsBack(INT32 plines); +// allow menu text to be displayed in lowercase +#define MENUCAPS (!cv_menucaps.value ? V_ALLOWLOWERCASE : 0) + // draw a single character void V_DrawCharacter(INT32 x, INT32 y, INT32 c, boolean lowercaseallowed); // draw a single character, but for the chat -- 2.54.0 From 35859692856ac39fa03abf6a804aa172d478d6fd Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 17 Nov 2024 13:30:20 +0100 Subject: [PATCH 021/143] why is that declared here?? --- src/p_setup.c | 4 ++++ src/p_setup.h | 5 +++++ src/r_splats.h | 3 --- 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/src/p_setup.c b/src/p_setup.c index ce1dd6efb..dd1042be3 100644 --- a/src/p_setup.c +++ b/src/p_setup.c @@ -460,7 +460,11 @@ FUNCINLINE static ATTRINLINE void P_LoadRawVertexes(UINT8 *data) * \param seg Seg to compute length for. * \return Length in fracunits. */ +#if defined (WALLSPLATS) || defined (FLOORSPLATS) fixed_t P_SegLength(seg_t *seg) +#else +static inline fixed_t P_SegLength(seg_t *seg) +#endif { INT64 dx = (seg->v2->x - seg->v1->x)>>1; INT64 dy = (seg->v2->y - seg->v1->y)>>1; diff --git a/src/p_setup.h b/src/p_setup.h index c6a18915a..7f90564e0 100644 --- a/src/p_setup.h +++ b/src/p_setup.h @@ -88,6 +88,11 @@ SINT8 P_PartialAddGetStage(void); boolean P_RunSOC(const char *socfilename); void P_WriteThings(lumpnum_t lump); + +#if defined (WALLSPLATS) || defined (FLOORSPLATS) +fixed_t P_SegLength(seg_t *seg); +#endif + void P_UpdateSegLightOffset(seg_t *li); size_t P_PrecacheLevelFlats(void); void P_AllocMapHeader(INT16 i); diff --git a/src/r_splats.h b/src/r_splats.h index 387b29582..b76ab90b4 100644 --- a/src/r_splats.h +++ b/src/r_splats.h @@ -59,9 +59,6 @@ typedef struct floorsplat_s struct floorsplat_s *nextvis; } floorsplat_t; -// p_setup.c -fixed_t P_SegLength(seg_t *seg); - // call at P_SetupLevel() void R_ClearLevelSplats(void); -- 2.54.0 From 7dfc63830522ed6c4f6de092505e3dc75783e278 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 17 Nov 2024 14:41:41 +0100 Subject: [PATCH 022/143] make replay/time attack menu support lowercase if toggled, also levelselect addon names too --- src/m_menu.c | 34 ++++++++++++++++------------------ 1 file changed, 16 insertions(+), 18 deletions(-) diff --git a/src/m_menu.c b/src/m_menu.c index 32322b860..86c64eccb 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -7098,11 +7098,11 @@ static void DrawReplayHutReplayInfo(void) switch (demolist[dir_on[menudepthleft]].type) { case MD_NOTLOADED: - V_DrawCenteredString(160, 40, V_SNAPTOTOP, "Loading replay information..."); + V_DrawCenteredString(160, 40, V_SNAPTOTOP|MENUCAPS, "Loading replay information..."); break; case MD_INVALID: - V_DrawCenteredString(160, 40, V_SNAPTOTOP|warningflags, "This replay cannot be played."); + V_DrawCenteredString(160, 40, V_SNAPTOTOP|warningflags|MENUCAPS, "This replay cannot be played."); break; case MD_SUBDIR: @@ -7144,7 +7144,7 @@ static void DrawReplayHutReplayInfo(void) if (mapheaderinfo[demolist[dir_on[menudepthleft]].map-1]) { char *title = G_BuildMapTitle(demolist[dir_on[menudepthleft]].map); - V_DrawString(x, y, V_SNAPTOTOP, title); + V_DrawString(x, y, V_SNAPTOTOP|MENUCAPS, title); Z_Free(title); } else @@ -7161,26 +7161,24 @@ static void DrawReplayHutReplayInfo(void) { // No standings were loaded! V_DrawString(x, y+39, V_SNAPTOTOP|V_ALLOWLOWERCASE|V_TRANSLUCENT, "No standings available."); - - break; } - V_DrawThinString(x, y+29, V_SNAPTOTOP|highlightflags, "WINNER"); + V_DrawThinString(x, y+29, V_SNAPTOTOP|highlightflags|MENUCAPS, "Winner"); V_DrawString(x+38, y+30, V_SNAPTOTOP|V_ALLOWLOWERCASE, demolist[dir_on[menudepthleft]].standings[0].name); if (demolist[dir_on[menudepthleft]].gametype == GT_RACE) { - V_DrawThinString(x, y+39, V_SNAPTOTOP|highlightflags, "TIME"); + V_DrawThinString(x, y+39, V_SNAPTOTOP|highlightflags|MENUCAPS, "Time"); } else { - V_DrawThinString(x, y+39, V_SNAPTOTOP|highlightflags, "SCORE"); + V_DrawThinString(x, y+39, V_SNAPTOTOP|highlightflags|MENUCAPS, "Score"); } if (demolist[dir_on[menudepthleft]].standings[0].timeorscore == (UINT32_MAX-1)) { - V_DrawThinString(x+32, y+40-1, V_SNAPTOTOP, "NO CONTEST"); + V_DrawThinString(x+32, y+40-1, V_SNAPTOTOP|MENUCAPS, "No Contest"); } else if (demolist[dir_on[menudepthleft]].gametype == GT_RACE) { @@ -8950,7 +8948,7 @@ void M_DrawTimeAttackMenu(void) if (i == itemOn) cursory = y; - V_DrawString(x, y, (dispstatus == IT_WHITESTRING) ? highlightflags : 0 , currentMenu->menuitems[i].text); + V_DrawString(x, y, ((dispstatus == IT_WHITESTRING) ? highlightflags : 0)|MENUCAPS, currentMenu->menuitems[i].text); // Cvar specific handling if ((currentMenu->menuitems[i].status & IT_TYPE) == IT_CVAR) @@ -8975,7 +8973,7 @@ void M_DrawTimeAttackMenu(void) soffset = 0; // Should see nothing but strings - V_DrawString(BASEVIDWIDTH - x - soffset - strw, y, highlightflags, str); + V_DrawString(BASEVIDWIDTH - x - soffset - strw, y, highlightflags|MENUCAPS, str); if (i == itemOn) { @@ -9005,7 +9003,7 @@ void M_DrawTimeAttackMenu(void) // DRAW THE SKULL CURSOR V_DrawScaledPatch(x - 24, cursory, 0, W_CachePatchName("M_CURSOR", PU_CACHE)); - V_DrawString(x, cursory, highlightflags, currentMenu->menuitems[itemOn].text); + V_DrawString(x, cursory, highlightflags|MENUCAPS, currentMenu->menuitems[itemOn].text); // Level record list if (cv_nextmap.value) @@ -9020,10 +9018,10 @@ void M_DrawTimeAttackMenu(void) V_DrawFill((BASEVIDWIDTH - dupadjust)>>1, 78, dupadjust, 36, 239); - V_DrawRightAlignedString(149, 80, highlightflags, "BEST LAP:"); + V_DrawRightAlignedString(149, 80, highlightflags|MENUCAPS, "Best Lap:"); K_drawKartTimestamp(lap, 19, 86, 0, 2); - V_DrawRightAlignedString(292, 80, highlightflags, "BEST TIME:"); + V_DrawRightAlignedString(292, 80, highlightflags|MENUCAPS, "Best Time:"); K_drawKartTimestamp(time, 162, 86, cv_nextmap.value, 1); } @@ -9035,7 +9033,7 @@ void M_DrawTimeAttackMenu(void) for (i = 0; i < 4; ++i) { y = currentMenu->y+SP_TimeAttackMenu[i].alphaKey; - V_DrawString(x, y, V_TRANSLUCENT, SP_TimeAttackMenu[i].text); + V_DrawString(x, y, V_TRANSLUCENT|MENUCAPS, SP_TimeAttackMenu[i].text); ncv = (consvar_t *)SP_TimeAttackMenu[i].itemaction; if (SP_TimeAttackMenu[i].status & IT_CV_STRING) { @@ -9052,7 +9050,7 @@ void M_DrawTimeAttackMenu(void) soffset = 0; // Should see nothing but strings - V_DrawString(BASEVIDWIDTH - x - soffset - strw, y, highlightflags|V_TRANSLUCENT, str); + V_DrawString(BASEVIDWIDTH - x - soffset - strw, y, highlightflags|V_TRANSLUCENT|MENUCAPS, str); } } } @@ -10082,10 +10080,10 @@ static void M_DrawLevelSelectOnly(boolean leftfade, boolean rightfade) len = strlen(addonname); #define charsonside 14 if (len > charlimit) - V_DrawThinString(x+w+5, y+i-8, V_TRANSLUCENT, va("%.*s...%s", charsonside, addonname, addonname+((len-charlimit) + charsonside))); // variable reuse... + V_DrawThinString(x+w+5, y+i-8, V_TRANSLUCENT|MENUCAPS, va("%.*s...%s", charsonside, addonname, addonname+((len-charlimit) + charsonside))); // variable reuse... #undef charsonside else - V_DrawThinString(x+w+5, y+i-8, V_TRANSLUCENT, addonname); // variable reuse... + V_DrawThinString(x+w+5, y+i-8, V_TRANSLUCENT|MENUCAPS, addonname); // variable reuse... } if (!cv_kartencore.value || gamestate == GS_TIMEATTACK || cv_newgametype.value != GT_RACE) -- 2.54.0 From c9a3dfcac94d9f993ced1bced53dbf6559436fe6 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 17 Nov 2024 21:41:25 +0100 Subject: [PATCH 023/143] reset pingtable in SV_ResetServer and use some memsets cause they look cooler also use ClearAdminPlayers simply to make this consistent with the other stuff that resets adminplayers --- src/d_clisrv.c | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 41d5482eb..81518e4d7 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -4275,14 +4275,20 @@ void SV_ResetServer(void) for (i = 0; i < MAXPLAYERS; i++) { LUA_InvalidatePlayer(&players[i]); - playeringame[i] = false; - playernode[i] = UINT8_MAX; sprintf(player_names[i], "Player %d", i + 1); - adminplayers[i] = -1; // Populate the entire adminplayers array with -1. } + memset(playeringame, false, sizeof playeringame); + memset(playernode, UINT8_MAX, sizeof playernode); + + ClearAdminPlayers(); // Populate the entire adminplayers array with -1. + memset(player_name_changes, 0, sizeof player_name_changes); + pingmeasurecount = 1; + memset(realpingtable, 0, sizeof realpingtable); + memset(playerpingtable, 0, sizeof playerpingtable); + mynode = 0; cl_packetmissed = false; #ifdef SATURNSYNCH @@ -4551,7 +4557,9 @@ static boolean SV_AddWaitingPlayers(void) buf[0] = (UINT8)node; buf[1] = newplayernum; if (playerpernode[node] < 1) + { nodetoplayer[node] = newplayernum; + } else if (playerpernode[node] < 2) { nodetoplayer2[node] = newplayernum; -- 2.54.0 From 0c2ccc56cdd8b2f5aae035a42a773b2149270dd3 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 14 Nov 2024 07:37:40 +0100 Subject: [PATCH 024/143] inline _GetZAt stuff those are very small but frequently used, so cant hurt --- src/p_slopes.c | 108 ++++++++++++++++--------------------------------- src/p_slopes.h | 45 +++++++++++++++++---- 2 files changed, 71 insertions(+), 82 deletions(-) diff --git a/src/p_slopes.c b/src/p_slopes.c index 6270821b1..0ba37a816 100644 --- a/src/p_slopes.c +++ b/src/p_slopes.c @@ -364,11 +364,11 @@ void P_SpawnSlope_Line(int linenum) // In P_SpawnSlopeLine the origin is the centerpoint of the sourcelinedef fslope = line->frontsector->f_slope = - P_MakeSlope(&point, &direction, dz, flags); + P_MakeSlope(&point, &direction, dz, flags); - // Set up some shit - fslope->extent = extent; - fslope->refpos = 1; + // Set up some shit + fslope->extent = extent; + fslope->refpos = 1; // Now remember that f_slope IS a vector // fslope->o = origin 3D point 1 of the vector @@ -425,11 +425,11 @@ void P_SpawnSlope_Line(int linenum) dz = FixedDiv(origin.z - point.z, extent); cslope = line->frontsector->c_slope = - P_MakeSlope(&point, &direction, dz, flags); + P_MakeSlope(&point, &direction, dz, flags); - // Set up some shit - cslope->extent = extent; - cslope->refpos = 2; + // Set up some shit + cslope->extent = extent; + cslope->refpos = 2; // Sync the linedata of the line that started this slope // TODO: Anything special for control sector based slopes later? @@ -494,11 +494,11 @@ void P_SpawnSlope_Line(int linenum) dz = FixedDiv(origin.z - point.z, extent); fslope = line->backsector->f_slope = - P_MakeSlope(&point, &direction, dz, flags); + P_MakeSlope(&point, &direction, dz, flags); - // Set up some shit - fslope->extent = extent; - fslope->refpos = 3; + // Set up some shit + fslope->extent = extent; + fslope->refpos = 3; // Sync the linedata of the line that started this slope // TODO: Anything special for control sector based slopes later? @@ -531,6 +531,7 @@ void P_SpawnSlope_Line(int linenum) P_CalculateSlopeNormal(fslope); } + if (backceil) { fixed_t highest, lowest; @@ -540,11 +541,11 @@ void P_SpawnSlope_Line(int linenum) dz = FixedDiv(origin.z - point.z, extent); cslope = line->backsector->c_slope = - P_MakeSlope(&point, &direction, dz, flags); + P_MakeSlope(&point, &direction, dz, flags); - // Set up some shit - cslope->extent = extent; - cslope->refpos = 4; + // Set up some shit + cslope->extent = extent; + cslope->refpos = 4; // Sync the linedata of the line that started this slope // TODO: Anything special for control sector based slopes later? @@ -604,7 +605,8 @@ static pslope_t *P_NewVertexSlope(INT16 tag1, INT16 tag2, INT16 tag3, UINT8 flag memset(ret->vertices, 0, 3*sizeof(mapthing_t)); // And... look for the vertices in question. - for (i = 0; i < nummapthings; i++, mt++) { + for (i = 0; i < nummapthings; i++, mt++) + { if (mt->type != 750) // Haha, I'm hijacking the old Chaos Spawn thingtype for something! continue; @@ -617,7 +619,8 @@ static pslope_t *P_NewVertexSlope(INT16 tag1, INT16 tag2, INT16 tag3, UINT8 flag } // Now set heights for each vertex, because they haven't been set yet - for (i = 0; i < 3; i++) { + for (i = 0; i < 3; i++) + { mt = ret->vertices[i]; if (!mt) // If a vertex wasn't found, it's game over. There's nothing you can do to recover (except maybe try and kill the slope instead - TODO?) I_Error("P_NewVertexSlope: Slope vertex %s (for linedef tag %d) not found!", sizeu1(i), tag1); @@ -649,23 +652,23 @@ static pslope_t *P_NewVertexSlope(INT16 tag1, INT16 tag2, INT16 tag3, UINT8 flag // void P_CopySectorSlope(line_t *line) { - sector_t *fsec = line->frontsector; - int i, special = line->special; + sector_t *fsec = line->frontsector; + int i, special = line->special; - // Check for copy linedefs - for(i = -1; (i = P_FindSectorFromLineTag(line, i)) >= 0;) - { - sector_t *srcsec = sectors + i; + // Check for copy linedefs + for(i = -1; (i = P_FindSectorFromLineTag(line, i)) >= 0;) + { + sector_t *srcsec = sectors + i; - if((special - 719) & 1 && !fsec->f_slope && srcsec->f_slope) - fsec->f_slope = srcsec->f_slope; //P_CopySlope(srcsec->f_slope); - if((special - 719) & 2 && !fsec->c_slope && srcsec->c_slope) - fsec->c_slope = srcsec->c_slope; //P_CopySlope(srcsec->c_slope); - } + if((special - 719) & 1 && !fsec->f_slope && srcsec->f_slope) + fsec->f_slope = srcsec->f_slope; //P_CopySlope(srcsec->f_slope); + if((special - 719) & 2 && !fsec->c_slope && srcsec->c_slope) + fsec->c_slope = srcsec->c_slope; //P_CopySlope(srcsec->c_slope); + } - fsec->hasslope = true; + fsec->hasslope = true; - line->special = 0; // Linedef was use to set slopes, it finished its job, so now make it a normal linedef + line->special = 0; // Linedef was use to set slopes, it finished its job, so now make it a normal linedef } // @@ -790,49 +793,6 @@ void P_ResetDynamicSlopes(void) // Various utilities related to slopes // -// -// P_GetZAt -// -// Returns the height of the sloped plane at (x, y) as a fixed_t -// -fixed_t P_GetZAt(pslope_t *slope, fixed_t x, fixed_t y) -{ - fixed_t dist = FixedMul(x - slope->o.x, slope->d.x) + - FixedMul(y - slope->o.y, slope->d.y); - - return slope->o.z + FixedMul(dist, slope->zdelta); -} - -// Returns the height of the sector floor at (x, y) -fixed_t P_GetSectorFloorZAt(const sector_t *sector, fixed_t x, fixed_t y) -{ - return sector->f_slope ? P_GetZAt(sector->f_slope, x, y) : sector->floorheight; -} - -// Returns the height of the sector ceiling at (x, y) -fixed_t P_GetSectorCeilingZAt(const sector_t *sector, fixed_t x, fixed_t y) -{ - return sector->c_slope ? P_GetZAt(sector->c_slope, x, y) : sector->ceilingheight; -} - -// Returns the height of the FOF top at (x, y) -fixed_t P_GetFFloorTopZAt(const ffloor_t *ffloor, fixed_t x, fixed_t y) -{ - return *ffloor->t_slope ? P_GetZAt(*ffloor->t_slope, x, y) : *ffloor->topheight; -} - -// Returns the height of the FOF bottom at (x, y) -fixed_t P_GetFFloorBottomZAt(const ffloor_t *ffloor, fixed_t x, fixed_t y) -{ - return *ffloor->b_slope ? P_GetZAt(*ffloor->b_slope, x, y) : *ffloor->bottomheight; -} - -// Returns the height of the light list at (x, y) -fixed_t P_GetLightZAt(const lightlist_t *light, fixed_t x, fixed_t y) -{ - return light->slope ? P_GetZAt(light->slope, x, y) : light->height; -} - // // P_QuantizeMomentumToSlope // diff --git a/src/p_slopes.h b/src/p_slopes.h index 57683d6e1..82dd90738 100644 --- a/src/p_slopes.h +++ b/src/p_slopes.h @@ -13,9 +13,12 @@ #ifndef P_SLOPES_H__ #define P_SLOPES_H__ +#include "doomtype.h" + void P_CalculateSlopeNormal(pslope_t *slope); void P_ResetDynamicSlopes(void); void P_RunDynamicSlopes(void); + // P_SpawnSlope_Line // Creates one or more slopes based on the given line type and front/back // sectors. @@ -30,19 +33,45 @@ void P_CopySectorSlope(line_t *line); pslope_t *P_SlopeById(UINT16 id); +// +// P_GetZAt +// + // Returns the height of the sloped plane at (x, y) as a fixed_t -fixed_t P_GetZAt(pslope_t *slope, fixed_t x, fixed_t y); +FUNCINLINE static ATTRINLINE fixed_t P_GetZAt(pslope_t *z_slope, fixed_t x, fixed_t y) +{ + return z_slope->o.z + FixedMul((FixedMul(x - z_slope->o.x, z_slope->d.x) + FixedMul(y - z_slope->o.y, z_slope->d.y)), z_slope->zdelta); +} -// Returns the height of the sector at (x, y) -fixed_t P_GetSectorFloorZAt (const sector_t *sector, fixed_t x, fixed_t y); -fixed_t P_GetSectorCeilingZAt(const sector_t *sector, fixed_t x, fixed_t y); +// Returns the height of the sector floor at (x, y) +FUNCINLINE static ATTRINLINE fixed_t P_GetSectorFloorZAt(const sector_t *z_sector, fixed_t x, fixed_t y) +{ + return z_sector->f_slope ? P_GetZAt(z_sector->f_slope, x, y) : z_sector->floorheight; +} -// Returns the height of the FOF at (x, y) -fixed_t P_GetFFloorTopZAt (const ffloor_t *ffloor, fixed_t x, fixed_t y); -fixed_t P_GetFFloorBottomZAt(const ffloor_t *ffloor, fixed_t x, fixed_t y); +// Returns the height of the sector ceiling at (x, y) +FUNCINLINE static ATTRINLINE fixed_t P_GetSectorCeilingZAt(const sector_t *z_sector, fixed_t x, fixed_t y) +{ + return z_sector->c_slope ? P_GetZAt(z_sector->c_slope, x, y) : z_sector->ceilingheight; +} + +// Returns the height of the FOF top at (x, y) +FUNCINLINE static ATTRINLINE fixed_t P_GetFFloorTopZAt(const ffloor_t *z_ffloor, fixed_t x, fixed_t y) +{ + return *z_ffloor->t_slope ? P_GetZAt(*z_ffloor->t_slope, x, y) : *z_ffloor->topheight; +} + +// Returns the height of the FOF bottom at (x, y) +FUNCINLINE static ATTRINLINE fixed_t P_GetFFloorBottomZAt(const ffloor_t *z_ffloor, fixed_t x, fixed_t y) +{ + return *z_ffloor->b_slope ? P_GetZAt(*z_ffloor->b_slope, x, y) : *z_ffloor->bottomheight; +} // Returns the height of the light list at (x, y) -fixed_t P_GetLightZAt(const lightlist_t *light, fixed_t x, fixed_t y); +FUNCINLINE static ATTRINLINE fixed_t P_GetLightZAt(const lightlist_t *z_light, fixed_t x, fixed_t y) +{ + return z_light->slope ? P_GetZAt(z_light->slope, x, y) : z_light->height; +} // Lots of physics-based bullshit void P_QuantizeMomentumToSlope(vector3_t *momentum, pslope_t *slope); -- 2.54.0 From 7b26ecb5f559469da045ce39097db9d407030106 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 19 Nov 2024 20:18:16 +0100 Subject: [PATCH 025/143] fixed float to integer conversion problems from dsda doom should hopefully make this behave the same everywhere --- src/hardware/hw_clip.c | 4 ++-- src/m_fixed.h | 29 +++++++++++++++++++++++++++++ 2 files changed, 31 insertions(+), 2 deletions(-) diff --git a/src/hardware/hw_clip.c b/src/hardware/hw_clip.c index 2c6e1d52e..12d870ea4 100644 --- a/src/hardware/hw_clip.c +++ b/src/hardware/hw_clip.c @@ -337,7 +337,7 @@ angle_t gld_FrustumAngle(angle_t tiltangle) floatangle = 2.0f + (45.0f + (tilt / 1.9f)) * clipfov / 90.0f; if (floatangle >= 180.0) return 0xffffffff; - a1 = (angle_t)(ANG1 * (int)floatangle); + a1 = (angle_t)xs_CRoundToInt(ANG1 * floatangle); return a1; } @@ -458,4 +458,4 @@ boolean gld_SphereInFrustum(float x, float y, float z, float radius) } return true; } -#endif \ No newline at end of file +#endif diff --git a/src/m_fixed.h b/src/m_fixed.h index d67777162..3f1acd7ae 100644 --- a/src/m_fixed.h +++ b/src/m_fixed.h @@ -247,6 +247,35 @@ FUNCMATH FUNCINLINE static ATTRINLINE fixed_t FixedRound(fixed_t x) return INT32_MAX; } +/** \brief The xs_CRoundToInt function + + \param val double number + + \return Round toward nearest, but ties round toward even +*/ +#if defined(SRB2_BIG_ENDIAN) + #define _xs_iexp_ 0 + #define _xs_iman_ 1 +#else + #define _xs_iexp_ 1 //intel is little endian + #define _xs_iman_ 0 +#endif //BigEndian_ + +typedef double real64; + +typedef union _xs_doubleints +{ + real64 val; + unsigned ival[2]; +} _xs_doubleints; + +FUNCMATH FUNCINLINE static ATTRINLINE int xs_CRoundToInt(real64 val) +{ + _xs_doubleints uval; + uval.val = val + 6755399441055744.0; + return uval.ival[_xs_iman_]; +} + typedef struct { fixed_t x; -- 2.54.0 From 809ae20558529092694544bc615628d32f8a24cf Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 23 Oct 2024 02:37:08 +0200 Subject: [PATCH 026/143] use highly optmized (but slightly inaccurate) version of R_PointOnSide for rendering --- src/hardware/hw_main.c | 2 +- src/r_bsp.c | 3 ++- src/r_main.h | 6 ++++++ 3 files changed, 9 insertions(+), 2 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 8c10f1eec..cfb9636d6 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -3103,7 +3103,7 @@ static void HWR_RenderBSPNode(INT32 bspnum) bsp = &nodes[bspnum]; // Decide which side the view point is on. - side = R_PointOnSide(viewx, viewy, bsp); + side = R_PointOnSideRender(viewx, viewy, bsp); // Recursively divide front space. if (HWR_PortalCheckBBox(bsp->bbox[side])) diff --git a/src/r_bsp.c b/src/r_bsp.c index 500a58035..a6530ce21 100644 --- a/src/r_bsp.c +++ b/src/r_bsp.c @@ -1320,7 +1320,8 @@ void R_RenderBSPNode(INT32 bspnum) bsp = &nodes[bspnum]; // Decide which side the view point is on. - side = R_PointOnSide(viewx, viewy, bsp); + side = R_PointOnSideRender(viewx, viewy, bsp); + // Recursively divide front space. R_RenderBSPNode(bsp->children[side]); diff --git a/src/r_main.h b/src/r_main.h index cfca7e1a4..6b7c88de3 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -74,6 +74,12 @@ extern lighttable_t *zlight[LIGHTLEVELS][MAXLIGHTZ]; // Utility functions. INT32 R_PointOnSide(fixed_t x, fixed_t y, const node_t *node); +FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSideRender(fixed_t x, fixed_t y, const node_t *node) +{ + // use cross product to determine side quickly + return (INT64)(y - node->y) * node->dx - (INT64)(x - node->x) * node->dy > 0; +} + FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSegSide(fixed_t x, fixed_t y, const seg_t *line) { fixed_t lx = line->v1->x; -- 2.54.0 From e66d215dd309fb6c9892c80ee90035efb485d97c Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 20 Nov 2024 20:36:22 +0100 Subject: [PATCH 027/143] Fix integer overflows on very large numbers --- src/r_main.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/r_main.h b/src/r_main.h index 6b7c88de3..f173307b7 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -77,7 +77,7 @@ INT32 R_PointOnSide(fixed_t x, fixed_t y, const node_t *node); FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSideRender(fixed_t x, fixed_t y, const node_t *node) { // use cross product to determine side quickly - return (INT64)(y - node->y) * node->dx - (INT64)(x - node->x) * node->dy > 0; + return ((INT64)y - node->y) * node->dx - ((INT64)x - node->x) * node->dy > 0; } FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSegSide(fixed_t x, fixed_t y, const seg_t *line) @@ -88,7 +88,7 @@ FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSegSide(fixed_t x, fixed_t fixed_t ldy = line->v2->y - ly; // use cross product to determine side quickly - return (INT64)(y - ly) * ldx - (INT64)(x - lx) * ldy > 0; + return ((INT64)y - ly) * ldx - ((INT64)x - lx) * ldy > 0; } angle_t R_PointToAngle(fixed_t x, fixed_t y); -- 2.54.0 From a14c2f59b80eb404a5369b0a9419077b812afa74 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 20 Nov 2024 21:25:18 +0100 Subject: [PATCH 028/143] rename to R_PointOnSideFast --- src/hardware/hw_main.c | 2 +- src/r_bsp.c | 2 +- src/r_main.h | 4 +++- 3 files changed, 5 insertions(+), 3 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index cfb9636d6..45660af0b 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -3103,7 +3103,7 @@ static void HWR_RenderBSPNode(INT32 bspnum) bsp = &nodes[bspnum]; // Decide which side the view point is on. - side = R_PointOnSideRender(viewx, viewy, bsp); + side = R_PointOnSideFast(viewx, viewy, bsp); // Recursively divide front space. if (HWR_PortalCheckBBox(bsp->bbox[side])) diff --git a/src/r_bsp.c b/src/r_bsp.c index a6530ce21..a8e5b8551 100644 --- a/src/r_bsp.c +++ b/src/r_bsp.c @@ -1320,7 +1320,7 @@ void R_RenderBSPNode(INT32 bspnum) bsp = &nodes[bspnum]; // Decide which side the view point is on. - side = R_PointOnSideRender(viewx, viewy, bsp); + side = R_PointOnSideFast(viewx, viewy, bsp); // Recursively divide front space. R_RenderBSPNode(bsp->children[side]); diff --git a/src/r_main.h b/src/r_main.h index f173307b7..d27530f41 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -74,7 +74,9 @@ extern lighttable_t *zlight[LIGHTLEVELS][MAXLIGHTZ]; // Utility functions. INT32 R_PointOnSide(fixed_t x, fixed_t y, const node_t *node); -FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSideRender(fixed_t x, fixed_t y, const node_t *node) +// This is not as accurate +// SHOULD NOT BE USED FOR ANYTHING GAMEPLAY RELATED!! +FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSideFast(fixed_t x, fixed_t y, const node_t *node) { // use cross product to determine side quickly return ((INT64)y - node->y) * node->dx - ((INT64)x - node->x) * node->dy > 0; -- 2.54.0 From bec632800de6dbca9476f7c193c906f746a5a5d6 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 20 Nov 2024 21:26:18 +0100 Subject: [PATCH 029/143] use it for R_IsPointInSubsector this is fine since R_IsPointInSubsector is only used for precip spawn unless you disable noclipcam lol --- src/r_main.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/r_main.c b/src/r_main.c index 1c45d4112..c47095078 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -1076,7 +1076,8 @@ subsector_t *R_IsPointInSubsector(fixed_t x, fixed_t y) while (!(nodenum & NF_SUBSECTOR)) { node = &nodes[nodenum]; - side = R_PointOnSide(x, y, node); + //side = R_PointOnSide(x, y, node); + side = R_PointOnSideFast(x, y, node); // this is fine since R_IsPointInSubsector is only used for precip spawn unless you disable noclipcam lol nodenum = node->children[side]; } -- 2.54.0 From f499b1111393846ea11b9b01ed94a82e1caa491e Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 20 Nov 2024 21:27:29 +0100 Subject: [PATCH 030/143] add R_PointInSubsectorFast for non critical gameplay stuff like sounds and camera and some parts of rendering --- src/d_clisrv.c | 2 +- src/hardware/hw_main.c | 2 +- src/hardware/hw_portal.c | 2 +- src/p_mobj.c | 4 ++-- src/p_setup.c | 4 ++-- src/p_user.c | 4 ++-- src/r_fps.c | 2 +- src/r_main.h | 13 ++++++++++++- src/s_sound.c | 4 ++-- 9 files changed, 24 insertions(+), 13 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 6efeffc6f..f8f47f4ae 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -2013,7 +2013,7 @@ static void CL_ReloadReceivedSavegame(void) for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) { - camera[i].subsector = R_PointInSubsector(camera[i].x, camera[i].y); + camera[i].subsector = R_PointInSubsectorFast(camera[i].x, camera[i].y); } cl_redownloadinggamestate = false; diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 45660af0b..a0059f184 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -3177,7 +3177,7 @@ static gl_vissprite_t *HWR_NewVisSprite(void) // Finds a floor through which light does not pass. static fixed_t HWR_OpaqueFloorAtPos(fixed_t x, fixed_t y, fixed_t z, fixed_t height) { - const sector_t *sec = R_PointInSubsector(x, y)->sector; + const sector_t *sec = R_PointInSubsectorFast(x, y)->sector; fixed_t floorz = sec->floorheight; if (sec->ffloors) diff --git a/src/hardware/hw_portal.c b/src/hardware/hw_portal.c index 96a1b300a..fb4d88cb3 100644 --- a/src/hardware/hw_portal.c +++ b/src/hardware/hw_portal.c @@ -132,7 +132,7 @@ void HWR_PortalFrame(gl_portal_t* portal) { portalclipline = NULL; portalcullsector = NULL; - viewsector = R_PointInSubsector(viewx, viewy)->sector; + viewsector = R_PointInSubsectorFast(viewx, viewy)->sector; } } diff --git a/src/p_mobj.c b/src/p_mobj.c index 9da7b0235..75746118e 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -3318,7 +3318,7 @@ boolean P_CameraThinker(player_t *player, camera_t *thiscam, boolean resetcalled P_CheckCameraPosition(thiscam->x, thiscam->y, thiscam); - thiscam->subsector = R_PointInSubsector(thiscam->x, thiscam->y); + thiscam->subsector = R_PointInSubsectorFast(thiscam->x, thiscam->y); thiscam->floorz = tmfloorz; thiscam->ceilingz = tmceilingz; @@ -10368,7 +10368,7 @@ void P_PrecipitationEffects(void) for (y = yl; y <= yh; y += RADIUSSTEP) for (x = xl; x <= xh; x += RADIUSSTEP) { - if (R_PointInSubsector((fixed_t)x, (fixed_t)y)->sector->ceilingpic != skyflatnum) // Found the outdoors! + if (R_PointInSubsectorFast((fixed_t)x, (fixed_t)y)->sector->ceilingpic != skyflatnum) // Found the outdoors! continue; newdist = S_CalculateSoundDistance(players[displayplayers[0]].mo->x, players[displayplayers[0]].mo->y, 0, (fixed_t)x, (fixed_t)y, 0); diff --git a/src/p_setup.c b/src/p_setup.c index 93207a3c1..e304aa7f3 100644 --- a/src/p_setup.c +++ b/src/p_setup.c @@ -2430,7 +2430,7 @@ static void P_SetupCamera(UINT8 pnum, camera_t *cam) cam->y = players[pnum].mo->y; cam->z = players[pnum].mo->z; cam->angle = players[pnum].mo->angle; - cam->subsector = R_PointInSubsector(cam->x, cam->y); // make sure camera has a subsector set -- Monster Iestyn (12/11/18) + cam->subsector = R_PointInSubsectorFast(cam->x, cam->y); // make sure camera has a subsector set -- Monster Iestyn (12/11/18) } else { @@ -2455,7 +2455,7 @@ static void P_SetupCamera(UINT8 pnum, camera_t *cam) cam->y = thing->y; cam->z = thing->z; cam->angle = FixedAngle((fixed_t)thing->angle << FRACBITS); - cam->subsector = R_PointInSubsector(cam->x, cam->y); // make sure camera has a subsector set -- Monster Iestyn (12/11/18) + cam->subsector = R_PointInSubsectorFast(cam->x, cam->y); // make sure camera has a subsector set -- Monster Iestyn (12/11/18) } } diff --git a/src/p_user.c b/src/p_user.c index 4041c17d6..2c061e7ce 100644 --- a/src/p_user.c +++ b/src/p_user.c @@ -3357,7 +3357,7 @@ void P_DemoCameraMovement(camera_t *cam) democam.soundmobj = awayviewmobj_hack; // update subsector to avoid crashes; - cam->subsector = R_PointInSubsector(cam->x, cam->y); + cam->subsector = R_PointInSubsectorFast(cam->x, cam->y); } void P_ResetCamera(player_t *player, camera_t *thiscam) @@ -3398,7 +3398,7 @@ void P_ResetCamera(player_t *player, camera_t *thiscam) } thiscam->relativex = 0; - thiscam->subsector = R_PointInSubsector(thiscam->x,thiscam->y); + thiscam->subsector = R_PointInSubsectorFast(thiscam->x,thiscam->y); thiscam->radius = 20*FRACUNIT; thiscam->height = 16*FRACUNIT; diff --git a/src/r_fps.c b/src/r_fps.c index 0f86160a6..15c3f2259 100644 --- a/src/r_fps.c +++ b/src/r_fps.c @@ -193,7 +193,7 @@ void R_InterpolateView(fixed_t frac, boolean forceinvalid) viewcos = FINECOSINE(viewangle>>ANGLETOFINESHIFT); viewplayer = newview->player; - viewsector = R_PointInSubsector(viewx, viewy)->sector; + viewsector = R_PointInSubsectorFast(viewx, viewy)->sector; R_SetupFreelook(); } diff --git a/src/r_main.h b/src/r_main.h index d27530f41..6d4546f39 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -102,10 +102,21 @@ fixed_t R_ScaleFromGlobalAngle(angle_t visangle); subsector_t *R_PointInSubsector(fixed_t x, fixed_t y); subsector_t *R_IsPointInSubsector(fixed_t x, fixed_t y); +// uses R_PointOnSideFast +// SHOULD NOT BE USED FOR ANYTHING GAMEPLAY RELATED!! +FUNCINLINE static ATTRINLINE subsector_t *R_PointInSubsectorFast(fixed_t x, fixed_t y) +{ + size_t nodenum = numnodes-1; + + while (!(nodenum & NF_SUBSECTOR)) + nodenum = nodes[nodenum].children[R_PointOnSideFast(x, y, nodes+nodenum)]; + + return &subsectors[nodenum & ~NF_SUBSECTOR]; +} + #define R_PointToDist(x, y) R_PointToDist2(viewx, viewy, x, y) #define R_PointToDist2(px2, py2, px1, py1) FixedHypot((px1) - (px2), (py1) - (py2)) - boolean R_DoCulling(line_t *cullheight, line_t *viewcullheight, fixed_t vz, fixed_t bottomh, fixed_t toph); void R_GetRenderBlockMapDimensions(fixed_t drawdist, INT32 *xl, INT32 *xh, INT32 *yl, INT32 *yh); diff --git a/src/s_sound.c b/src/s_sound.c index 868bccc77..d54ee2884 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -1046,7 +1046,7 @@ boolean S_AdjustSoundParams(const mobj_t *listener, const mobj_t *source, INT32 INT64 x, y, yl, yh, xl, xh; fixed_t newdist; - if (R_PointInSubsector(listensource.x, listensource.y)->sector->ceilingpic == skyflatnum) + if (R_PointInSubsectorFast(listensource.x, listensource.y)->sector->ceilingpic == skyflatnum) approx_dist = 0; else { @@ -1059,7 +1059,7 @@ boolean S_AdjustSoundParams(const mobj_t *listener, const mobj_t *source, INT32 for (y = yl; y <= yh; y += FRACUNIT*64) for (x = xl; x <= xh; x += FRACUNIT*64) { - if (R_PointInSubsector(x, y)->sector->ceilingpic == skyflatnum) + if (R_PointInSubsectorFast(x, y)->sector->ceilingpic == skyflatnum) { // Found the outdoors! newdist = S_CalculateSoundDistance(listensource.x, listensource.y, 0, x, y, 0); -- 2.54.0 From 8a15b5e64039aaba7bdb4a7d2fe17db54ecaed24 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 20 Nov 2024 23:44:35 +0100 Subject: [PATCH 031/143] last attempt at fixing those things --- src/hardware/hw_defs.h | 1 - src/hardware/hw_main.c | 11 +---------- src/hardware/hw_shaders.c | 4 ---- src/hardware/hw_shaders.h | 4 ---- 4 files changed, 1 insertion(+), 19 deletions(-) diff --git a/src/hardware/hw_defs.h b/src/hardware/hw_defs.h index 85261c859..5d23099cb 100644 --- a/src/hardware/hw_defs.h +++ b/src/hardware/hw_defs.h @@ -171,7 +171,6 @@ enum { SHADER_NONE = -1, SHADER_FLOOR = 0, - SHADER_SHADOW, SHADER_WALL, SHADER_SPRITE, SHADER_MODEL, diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 8c10f1eec..d0f3d17b7 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -3218,8 +3218,6 @@ static void HWR_DrawSpriteShadow(gl_vissprite_t *spr, GLPatch_t *gpatch) pslope_t *floorslope; fixed_t slopez; float offset = 0; - - INT32 shader = SHADER_NONE; // technically this_scale gets multiplied and added to sprite y/x scale, but this thing needs it for some crap so ill just throw it in here again const boolean hires = (spr->mobj && spr->mobj->skin && ((skin_t *)( (spr->mobj->localskin) ? spr->mobj->localskin : spr->mobj->skin ))->flags & SF_HIRES); @@ -3376,14 +3374,7 @@ static void HWR_DrawSpriteShadow(gl_vissprite_t *spr, GLPatch_t *gpatch) if (sSurf.PolyColor.s.alpha > floorheight/4) { sSurf.PolyColor.s.alpha = (UINT8)(sSurf.PolyColor.s.alpha - floorheight/4); - - if (HWR_UseShader()) - { - shader = SHADER_SHADOW; - blendmode |= PF_ColorMapped; - } - - HWR_ProcessPolygon(&sSurf, swallVerts, 4, blendmode|PF_Translucent|PF_Modulated, shader, false); + HWR_ProcessPolygon(&sSurf, swallVerts, 4, blendmode|PF_Translucent|PF_Modulated, SHADER_NONE, false); } } diff --git a/src/hardware/hw_shaders.c b/src/hardware/hw_shaders.c index 3046b902e..d73efaa37 100644 --- a/src/hardware/hw_shaders.c +++ b/src/hardware/hw_shaders.c @@ -29,9 +29,6 @@ static struct { // Floor shader {GLSL_DEFAULT_VERTEX_SHADER, GLSL_FLOOR_FRAGMENT_SHADER}, - // Shadow shader - {GLSL_DEFAULT_VERTEX_SHADER, GLSL_SHADOW_FRAGMENT_SHADER}, - // Wall shader {GLSL_DEFAULT_VERTEX_SHADER, GLSL_WALL_FRAGMENT_SHADER}, @@ -432,7 +429,6 @@ static inline UINT16 HWR_FindShaderDefs(UINT16 wadnum) customshaderxlat_t shaderxlat[] = { {"Flat", SHADER_FLOOR}, - {"Shadow", SHADER_SHADOW}, {"WallTexture", SHADER_WALL}, {"Sprite", SHADER_SPRITE}, {"Model", SHADER_MODEL}, diff --git a/src/hardware/hw_shaders.h b/src/hardware/hw_shaders.h index 77a93eb2e..b540d4ac3 100644 --- a/src/hardware/hw_shaders.h +++ b/src/hardware/hw_shaders.h @@ -211,10 +211,6 @@ GLSL_WALL_FUDGES \ GLSL_SOFTWARE_FRAGMENT_SHADER -#define GLSL_SHADOW_FRAGMENT_SHADER \ - GLSL_FLOOR_FUDGES \ - GLSL_SOFTWARE_FRAGMENT_SHADER_NOPAL - // // Water surface shader // -- 2.54.0 From e2222f66a9848de1035a16d3f174b3143deb9925 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 02:10:57 +0100 Subject: [PATCH 032/143] those should be SHORT i think? --- src/r_patch.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/r_patch.c b/src/r_patch.c index c9ff704a7..37e7a2321 100644 --- a/src/r_patch.c +++ b/src/r_patch.c @@ -842,8 +842,8 @@ patch_t *Patch_GetRotatedSprite(spriteframe_t *sprite, size_t frame, size_t spri } else { - xpivot = patch->leftoffset; - ypivot = patch->height / 2; + xpivot = SHORT(patch->leftoffset); + ypivot = SHORT(patch->height) / 2; } RotatedPatch_DoRotation(rotsprite, patch, rotationangle, xpivot, ypivot, flip); @@ -902,9 +902,9 @@ void RotatedPatch_DoRotation(rotsprite_t *rotsprite, patch_t *patch, INT32 angle size_t size; INT32 bflip = (flip != 0x00); - INT32 width = patch->width; - INT32 height = patch->height; - INT32 leftoffset = patch->leftoffset; + INT32 width = SHORT(patch->width); + INT32 height = SHORT(patch->height); + INT32 leftoffset = SHORT(patch->leftoffset); INT32 newwidth, newheight; fixed_t ca = rollcosang[angle]; @@ -975,7 +975,7 @@ void RotatedPatch_DoRotation(rotsprite_t *rotsprite, patch_t *patch, INT32 angle } ox = (newwidth / 2) + (leftoffset - xpivot); - oy = (newheight / 2) + (patch->topoffset - ypivot); + oy = (newheight / 2) + (SHORT(patch->topoffset) - ypivot); width = (maxx - minx); height = (maxy - miny); -- 2.54.0 From 1659c2e75332ca4e135ada40a3daad28c3c60e79 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 02:11:40 +0100 Subject: [PATCH 033/143] try to make shadows not so offset on slopes with rotation enabled lmaos --- src/hardware/hw_main.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index d0f3d17b7..e96c9e36a 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4590,6 +4590,14 @@ static void HWR_ProjectSprite(mobj_t *thing) else rollsum = rollangle; + // this is kinda dumb lkmao, but try to mitigate shadows being weirdly offset on slopes + if (thing->type == MT_SHADOW) + { + sprinfo->available = true; // < lmao + sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].x = spr_offset>>FRACBITS; + sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].y = -8; // noones gonna replace shadow sprite anyways, right? that random value ftw, otherwise this clips into the ground Zzz... + } + rollangle = R_GetRollAngle(rollsum); rotsprite = Patch_GetRotatedSprite(sprframe, (thing->frame & FF_FRAMEMASK), rot, flip, false, sprinfo, rollangle); -- 2.54.0 From e1cb858d9ab8d8b3404aa3b78c0fe873b21465d4 Mon Sep 17 00:00:00 2001 From: Indev Date: Thu, 21 Nov 2024 22:02:25 +0300 Subject: [PATCH 034/143] Players that get 'NO CONTEST' can save replays too now --- src/p_user.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/p_user.c b/src/p_user.c index 4041c17d6..f8e4de294 100644 --- a/src/p_user.c +++ b/src/p_user.c @@ -4213,6 +4213,8 @@ void P_DoTimeOver(player_t *player) player->pflags |= PF_TIMEOVER; + demo.savebutton = leveltime; + if (P_IsLocalPlayer(player) && !demo.playback) legitimateexit = true; // SRB2kart: losing a race is still seeing it through to the end :p -- 2.54.0 From 549112822aea5d9609c090387fc61d7327d32d04 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 20:33:06 +0100 Subject: [PATCH 035/143] port srb2 hooklib refactor (WIP) lol lmao --- src/b_bot.c | 4 +- src/d_clisrv.c | 8 +- src/d_netcmd.c | 2 +- src/doomtype.h | 24 + src/g_game.c | 10 +- src/hu_stuff.c | 2 +- src/k_kart.c | 4 +- src/lua_hook.h | 189 ++-- src/lua_hooklib.c | 2422 ++++++++++++++++----------------------------- src/lua_script.c | 4 +- src/lua_script.h | 2 +- src/p_enemy.c | 2 +- src/p_inter.c | 16 +- src/p_map.c | 4 +- src/p_mobj.c | 16 +- src/p_setup.c | 4 +- src/p_spec.c | 4 +- src/p_tick.c | 12 +- src/p_user.c | 10 +- src/r_patch.c | 1 + src/s_sound.c | 11 +- src/s_sound.h | 10 + src/y_inter.c | 5 +- 23 files changed, 1069 insertions(+), 1697 deletions(-) diff --git a/src/b_bot.c b/src/b_bot.c index edaf477ad..53f93374e 100644 --- a/src/b_bot.c +++ b/src/b_bot.c @@ -36,7 +36,7 @@ static inline void B_BuildTailsTiccmd(mobj_t *sonic, mobj_t *tails, ticcmd_t *cm return; // Lua can handle it! - if (LUAh_BotAI(sonic, tails, cmd)) + if (LUA_HookBotAI(sonic, tails, cmd)) return; if (tails->player->pflags & (PF_MACESPIN|PF_ITEMHANG)) @@ -122,7 +122,7 @@ void B_BuildTiccmd(player_t *player, ticcmd_t *cmd) //CV_SetValue(&cv_analog2, false); // Let Lua scripts build ticcmds - if (LUAh_BotTiccmd(player, cmd)) + if (LUA_HookTiccmd(player, cmd, HOOK(BotTiccmd))) return; // We don't have any main character AI, sorry. D: diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 6efeffc6f..5b1997e90 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -3297,7 +3297,7 @@ void CL_RemovePlayer(INT32 playernum, INT32 reason) } } - LUAh_PlayerQuit(&players[playernum], reason); // Lua hook for player quitting + LUA_HookPlayerQuit(&players[playernum], reason); // Lua hook for player quitting // Reset player data CL_ClearPlayer(playernum); @@ -4472,10 +4472,10 @@ static void Got_AddPlayer(UINT8 **p, INT32 playernum) D_AddPostloadFiles(); - LUAh_PlayerJoin(newplayernum); + LUA_HookInt(newplayernum, HOOK(PlayerJoin)); - if (newplayernum == consoleplayer) - LUAh_ServerJoin(); + //if (newplayernum == consoleplayer) + //LUA_ServerJoin(); #ifdef HAVE_DISCORDRPC DRPC_UpdatePresence(); diff --git a/src/d_netcmd.c b/src/d_netcmd.c index 281fb8856..2968b4a65 100644 --- a/src/d_netcmd.c +++ b/src/d_netcmd.c @@ -3114,7 +3114,7 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum) SetPlayerSkinByNum(0, cv_chooseskin.value-1); //mapnumber = M_MapNumber(mapname[3], mapname[4]); - //LUAh_MapChange(mapnumber); + //LUA_HookInt(mapnumber, HOOK(MapChange)); demo.savemode = (cv_recordmultiplayerdemos.value == 2) ? DSM_WILLAUTOSAVE : DSM_NOTSAVING; demo.savebutton = 0; diff --git a/src/doomtype.h b/src/doomtype.h index d7ad320c8..429eba77e 100644 --- a/src/doomtype.h +++ b/src/doomtype.h @@ -365,6 +365,30 @@ typedef UINT32 tic_t; #define UINT2RGBA(a) (UINT32)((a&0xff)<<24)|((a&0xff00)<<8)|((a&0xff0000)>>8)|(((UINT32)a&0xff000000)>>24) #endif +#define TOSTR(x) #x + +typedef UINT8 bitarray_t; + +#define BIT_ARRAY_SIZE(n) (((n) + 7) >> 3) + +static inline int +in_bit_array (const bitarray_t * const array, const int value) +{ + return (array[value >> 3] & (1<<(value & 7))); +} + +static inline void +set_bit_array (bitarray_t * const array, const int value) +{ + array[value >> 3] |= (1<<(value & 7)); +} + +static inline void +unset_bit_array (bitarray_t * const array, const int value) +{ + array[value >> 3] &= ~(1<<(value & 7)); +} + typedef UINT64 precise_t; #endif //__DOOMTYPE__ diff --git a/src/g_game.c b/src/g_game.c index f807b724c..76ea49c17 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -1489,7 +1489,7 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) -Making a Mario Kart 8 Deluxe tier baby mode that steers you away from walls and whatnot. You know what, do what you want! */ if (gamestate == GS_LEVEL) - LUAh_PlayerCmd(player, cmd); + LUA_HookTiccmd(player, cmd, HOOK(PlayerCmd)); //Reset away view if a command is given. if ((cmd->forwardmove || cmd->sidemove || cmd->buttons) @@ -2727,7 +2727,7 @@ void G_SpawnPlayer(INT32 playernum, boolean starpost) if (starpost) //Don't even bother with looking for a place to spawn. { P_MovePlayerToStarpost(playernum); - LUAh_PlayerSpawn(&players[playernum]); // Lua hook for player spawning :) + LUA_HookPlayer(&players[playernum], HOOK(PlayerSpawn)); // Lua hook for player spawning :) return; } @@ -2783,7 +2783,7 @@ void G_SpawnPlayer(INT32 playernum, boolean starpost) } P_MovePlayerToSpawn(playernum, spawnpoint); - LUAh_PlayerSpawn(&players[playernum]); // Lua hook for player spawning :) + LUA_HookPlayer(&players[playernum], HOOK(PlayerSpawn)); // Lua hook for player spawning :) } mapthing_t *G_FindCTFStart(INT32 playernum) @@ -4384,7 +4384,7 @@ void G_InitNew(UINT8 pencoremode, const char *mapname, boolean resetplayer, bool F_StartCustomCutscene(mapheaderinfo[gamemap-1]->precutscenenum-1, true, resetplayer); else { - LUAh_MapChange(gamemap); + LUA_HookInt(gamemap, HOOK(MapChange)); S_CheckMap(); G_DoLoadLevel(resetplayer); } @@ -7505,7 +7505,7 @@ void G_DoPlayDemo(char *defdemoname) // didn't start recording right away. demo.deferstart = false; - //LUAh_MapChange(gamemap); + //LUA_HookInt(gamemap, HOOK(MapChange)); displayplayers[0] = consoleplayer = 0; memset(playeringame,0,sizeof(playeringame)); diff --git a/src/hu_stuff.c b/src/hu_stuff.c index e68888c84..8a999b83f 100644 --- a/src/hu_stuff.c +++ b/src/hu_stuff.c @@ -1003,7 +1003,7 @@ static void Got_Saycmd(UINT8 **p, INT32 playernum) // run the lua hook even if we were supposed to eat the msg, netgame consistency goes first. - if (LUAh_PlayerMsg(playernum, target, flags, msg, spam_eatmsg)) + if (LUA_HookPlayerMsg(playernum, target, flags, msg, spam_eatmsg)) return; if (spam_eatmsg) diff --git a/src/k_kart.c b/src/k_kart.c index c27ffec4c..14f9cc580 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -497,10 +497,9 @@ UINT8 colortranslations[MAXTRANSLATIONS][16] = { */ void K_RainbowColormap(UINT8 *dest_colormap, UINT8 skincolor) { - INT32 i; + INT32 i, j; RGBA_t color; UINT8 brightness; - INT32 j; UINT8 colorbrightnesses[16]; UINT16 brightdif; INT32 temp; @@ -523,6 +522,7 @@ void K_RainbowColormap(UINT8 *dest_colormap, UINT8 skincolor) color = V_GetColor(i); SETBRIGHTNESS(brightness, color.s.red, color.s.green, color.s.blue); brightdif = 256; + for (j = 0; j < 16; j++) { temp = abs((INT16)brightness - (INT16)colorbrightnesses[j]); diff --git a/src/lua_hook.h b/src/lua_hook.h index 921336cd2..a54a09f00 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -13,91 +13,112 @@ #include "r_defs.h" #include "d_player.h" -enum hook { - hook_NetVars=0, - hook_MapChange, - hook_MapLoad, - hook_PlayerJoin, - hook_PreThinkFrame, - hook_ThinkFrame, - hook_PostThinkFrame, - hook_MobjSpawn, - hook_MobjCollide, - hook_MobjMoveCollide, - hook_TouchSpecial, - hook_MobjFuse, - hook_MobjThinker, - hook_BossThinker, - hook_ShouldDamage, - hook_MobjDamage, - hook_MobjDeath, - hook_BossDeath, - hook_MobjRemoved, - hook_JumpSpecial, - hook_AbilitySpecial, - hook_SpinSpecial, - hook_JumpSpinSpecial, - hook_BotTiccmd, - hook_BotAI, - hook_LinedefExecute, - hook_PlayerMsg, - hook_HurtMsg, - hook_PlayerSpawn, - hook_PlayerQuit, - hook_PlayerThink, - hook_MusicChange, - hook_ShouldSpin, //SRB2KART - hook_ShouldExplode, //SRB2KART - hook_ShouldSquish, //SRB2KART - hook_PlayerSpin, //SRB2KART - hook_PlayerExplode, //SRB2KART - hook_PlayerSquish, //SRB2KART - hook_PlayerCmd, //SRB2KART - hook_IntermissionThinker, //SRB2KART - hook_VoteThinker, //SRB2KART - hook_ServerJoin, // SRB2KART - Saturn 32p +/* + * Do you know what an 'X Macro' is? Such a macro is called over each element of + * a list and expands the input. I use it for the hook lists because both an enum + * and array of hook names need to be kept in order. The X Macro handles this + * automatically. + */ + +#define MOBJ_HOOK_LIST(X) \ +X (MobjSpawn),/* P_SpawnMobj */\ +X (MobjCollide),/* PIT_CheckThing */\ +X (MobjMoveCollide),/* tritto */\ +X (TouchSpecial),/* P_TouchSpecialThing */\ +X (MobjFuse),/* when mobj->fuse runs out */\ +X (MobjThinker),/* P_MobjThinker, P_SceneryThinker */\ +X (BossThinker),/* P_GenericBossThinker */\ +X (ShouldDamage),/* P_DamageMobj (Should mobj take damage?) */\ +X (MobjDamage),/* P_DamageMobj (Mobj actually takes damage!) */\ +X (MobjDeath),/* P_KillMobj */\ +X (BossDeath),/* A_BossDeath */\ +X (MobjRemoved),/* P_RemoveMobj */\ + +#define HOOK_LIST(X) \ +X (NetVars),/* add to archive table (netsave) */\ +X (MapChange),/* (before map load) */\ +X (MapLoad),\ +X (PlayerJoin),/* Got_AddPlayer */\ +X (PreThinkFrame)/* frame (before mobj and player thinkers) */,\ +X (ThinkFrame),/* frame (after mobj and player thinkers) */\ +X (PostThinkFrame),/* frame (at end of tick, ie after overlays, precipitation, specials) */\ +X (JumpSpecial),/* P_DoJumpStuff (Any-jumping) */\ +X (AbilitySpecial),/* P_DoJumpStuff (Double-jumping) */\ +X (SpinSpecial),/* P_DoSpinAbility (Spin button effect) */\ +X (JumpSpinSpecial),/* P_DoJumpStuff (Spin button effect (mid-air)) */\ +X (BotTiccmd),/* B_BuildTiccmd */\ +X (PlayerMsg),/* chat messages */\ +X (HurtMsg),/* imhurttin */\ +X (PlayerSpawn),/* G_SpawnPlayer */\ +X (PlayerQuit),\ +X (IntermissionThinker),/* Y_Ticker */\ +X (PlayerThink),/* P_PlayerThink */\ +X (GameQuit),\ +X (PlayerCmd),/* building the player's ticcmd struct (Ported from SRB2Kart) */\ +X (MusicChange),\ +X (ShouldSpin),/*SRB2KART*/\ +X (ShouldExplode),/*SRB2KART*/\ +X (ShouldSquish),/*SRB2KART*/\ +X (PlayerSpin),/*SRB2KART*/\ +X (PlayerExplode),/*SRB2KART*/\ +X (PlayerSquish),/*SRB2KART*/\ +X (VoteThinker),/*SRB2KART*/\ +X (ServerJoin),/* SRB2KART - Saturn 32p*/\ + +#define STRING_HOOK_LIST(X) \ +X (BotAI),/* B_BuildTailsTiccmd by skin name */\ +X (LinedefExecute),\ + +/* + * I chose to access the hook enums through a macro as well. This could provide + * a hint to lookup the macro's definition instead of the enum's definition. + * (Since each enumeration is not defined in the source code, but by the list + * macros above, it is not greppable.) The name passed to the macro can also be + * grepped and found in the lists above. + */ + +#define MOBJ_HOOK(name) mobjhook_ ## name +#define HOOK(name) hook_ ## name +#define STRING_HOOK(name) stringhook_ ## name + +enum { MOBJ_HOOK_LIST (MOBJ_HOOK) MOBJ_HOOK(MAX) }; +enum { HOOK_LIST (HOOK) HOOK(MAX) }; +enum { STRING_HOOK_LIST (STRING_HOOK) STRING_HOOK(MAX) }; + +/* dead simple, LUA_HOOK(GameQuit) */ +#define LUA_HOOK(type) LUA_HookVoid(HOOK(type)) - hook_MAX // last hook -}; -extern const char *const hookNames[]; extern boolean hook_cmd_running; // This is used by PlayerCmd and lua_playerlib to prevent anything from being wirtten to player while we run PlayerCmd. extern int hook_defrosting; -void LUAh_MapChange(INT16 mapnumber); // Hook for map change (before load) -void LUAh_MapLoad(void); // Hook for map load -void LUAh_PlayerJoin(int playernum); // Hook for Got_AddPlayer -void LUAh_PreThinkFrame(void); // Hook for frame (before mobj and player thinkers) -void LUAh_ThinkFrame(void); // Hook for frame (after mobj and player thinkers) -void LUAh_PostThinkFrame(void); // Hook for frame (at end of tick, ie after overlays, precipitation, specials) -boolean LUAh_MobjHook(mobj_t *mo, enum hook which); -boolean LUAh_PlayerHook(player_t *plr, enum hook which); -#define LUAh_MobjSpawn(mo) LUAh_MobjHook(mo, hook_MobjSpawn) // Hook for P_SpawnMobj by mobj type -UINT8 LUAh_MobjCollideHook(mobj_t *thing1, mobj_t *thing2, enum hook which); -#define LUAh_MobjCollide(thing1, thing2) LUAh_MobjCollideHook(thing1, thing2, hook_MobjCollide) // Hook for PIT_CheckThing by (thing) mobj type -#define LUAh_MobjMoveCollide(thing1, thing2) LUAh_MobjCollideHook(thing1, thing2, hook_MobjMoveCollide) // Hook for PIT_CheckThing by (tmthing) mobj type -boolean LUAh_TouchSpecial(mobj_t *special, mobj_t *toucher); // Hook for P_TouchSpecialThing by mobj type -#define LUAh_MobjFuse(mo) LUAh_MobjHook(mo, hook_MobjFuse) // Hook for mobj->fuse == 0 by mobj type -boolean LUAh_MobjThinker(mobj_t *mo); // Hook for P_MobjThinker or P_SceneryThinker by mobj type -#define LUAh_BossThinker(mo) LUAh_MobjHook(mo, hook_BossThinker) // Hook for P_GenericBossThinker by mobj type -UINT8 LUAh_ShouldDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage); // Hook for P_DamageMobj by mobj type (Should mobj take damage?) -boolean LUAh_MobjDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage); // Hook for P_DamageMobj by mobj type (Mobj actually takes damage!) -boolean LUAh_MobjDeath(mobj_t *target, mobj_t *inflictor, mobj_t *source); // Hook for P_KillMobj by mobj type -#define LUAh_BossDeath(mo) LUAh_MobjHook(mo, hook_BossDeath) // Hook for A_BossDeath by mobj type -#define LUAh_MobjRemoved(mo) LUAh_MobjHook(mo, hook_MobjRemoved) // Hook for P_RemoveMobj by mobj type -#define LUAh_JumpSpecial(player) LUAh_PlayerHook(player, hook_JumpSpecial) // Hook for P_DoJumpStuff (Any-jumping) -#define LUAh_AbilitySpecial(player) LUAh_PlayerHook(player, hook_AbilitySpecial) // Hook for P_DoJumpStuff (Double-jumping) -#define LUAh_SpinSpecial(player) LUAh_PlayerHook(player, hook_SpinSpecial) // Hook for P_DoSpinDash (Spin button effect) -#define LUAh_JumpSpinSpecial(player) LUAh_PlayerHook(player, hook_JumpSpinSpecial) // Hook for P_DoJumpStuff (Spin button effect (mid-air)) -boolean LUAh_BotTiccmd(player_t *bot, ticcmd_t *cmd); // Hook for B_BuildTiccmd -boolean LUAh_BotAI(mobj_t *sonic, mobj_t *tails, ticcmd_t *cmd); // Hook for B_BuildTailsTiccmd by skin name -boolean LUAh_LinedefExecute(line_t *line, mobj_t *mo, sector_t *sector); // Hook for linedef executors -boolean LUAh_PlayerMsg(int source, int target, int flags, char *msg, int mute); // Hook for chat messages -boolean LUAh_HurtMsg(player_t *player, mobj_t *inflictor, mobj_t *source); // Hook for hurt messages -#define LUAh_PlayerSpawn(player) LUAh_PlayerHook(player, hook_PlayerSpawn) // Hook for G_SpawnPlayer -void LUAh_PlayerQuit(player_t *plr, int reason); // Hook for player quitting -boolean LUAh_MusicChange(const char *oldname, char *newname, UINT16 *mflags, boolean *looping, - UINT32 *position, UINT32 *prefadems, UINT32 *fadeinms); // Hook for music changes +void LUA_HookVoid(int hook); + +int LUA_HookMobj(mobj_t *, int hook); +int LUA_Hook2Mobj(mobj_t *, mobj_t *, int hook); +void LUA_HookInt(INT32 integer, int hook); +//void LUA_HookBool(boolean value, int hook); +void LUA_HookBool(int hook); +int LUA_HookPlayer(player_t *, int hook); +int LUA_HookTiccmd(player_t *, ticcmd_t *, int hook); + +void LUA_HookThinkFrame(void); +int LUA_HookTouchSpecial(mobj_t *special, mobj_t *toucher); +int LUA_HookShouldDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage); +int LUA_HookMobjDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage); +int LUA_HookMobjDeath(mobj_t *target, mobj_t *inflictor, mobj_t *source); +int LUA_HookBotAI(mobj_t *sonic, mobj_t *tails, ticcmd_t *cmd); +void LUA_HookLinedefExecute(line_t *, mobj_t *, sector_t *); +int LUA_HookPlayerMsg(int source, int target, int flags, char *msg, int mute); +int LUA_HookHurtMsg(player_t *, mobj_t *inflictor, mobj_t *source); +int LUA_HookPlayerCanDamage(player_t *, mobj_t *); +void LUA_HookPlayerQuit(player_t *, int); +int LUA_HookPlayerCmd(player_t *, ticcmd_t *); +int LUA_HookMusicChange(const char *oldname, struct MusicChange *); +int LUA_HookKey(INT32 keycode, int hooktype); // Hooks for key events + + +// No clue what to do about these UINT8 LUAh_ShouldSpin(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Should player be spun out? UINT8 LUAh_ShouldExplode(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Should player be exploded? @@ -106,11 +127,3 @@ UINT8 LUAh_ShouldSquish(player_t *player, mobj_t *inflictor, mobj_t *source); // boolean LUAh_PlayerSpin(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_SpinPlayer. Allows Lua to execute code and/or overwrite its behavior. boolean LUAh_PlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_ExplodePlayer. Allows Lua to execute code and/or overwrite its behavior. boolean LUAh_PlayerSquish(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_SquishPlayer. Allows Lua to execute code and/or overwrite its behavior. - -void LUAh_ServerJoin(void); // SRB2KART - Saturn 32p: called by client when joining a server, allows lua to load any sort of config file - -boolean LUAh_PlayerCmd(player_t *player, ticcmd_t *cmd); // Allows to write to player cmd before the game does anything with them. - -void LUAh_IntermissionThinker(void); // Hook for Y_Ticker -void LUAh_VoteThinker(void); // Hook for Y_VoteTicker -#define LUAh_PlayerThink(player) LUAh_PlayerHook(player, hook_PlayerThink) // Hook for P_PlayerThink diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 1aadea9a3..18466bc30 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -24,1663 +24,966 @@ #include "lua_hook.h" #include "lua_hud.h" // hud_running errors -static UINT8 hooksAvailable[(hook_MAX/8)+1]; +#include -const char *const hookNames[hook_MAX+1] = { - "NetVars", - "MapChange", - "MapLoad", - "PlayerJoin", - "PreThinkFrame", - "ThinkFrame", - "PostThinkFrame", - "MobjSpawn", - "MobjCollide", - "MobjMoveCollide", - "TouchSpecial", - "MobjFuse", - "MobjThinker", - "BossThinker", - "ShouldDamage", - "MobjDamage", - "MobjDeath", - "BossDeath", - "MobjRemoved", - "JumpSpecial", - "AbilitySpecial", - "SpinSpecial", - "JumpSpinSpecial", - "BotTiccmd", - "BotAI", - "LinedefExecute", - "PlayerMsg", - "HurtMsg", - "PlayerSpawn", - "PlayerQuit", - "PlayerThink", - "MusicChange", - "ShouldSpin", - "ShouldExplode", - "ShouldSquish", - "PlayerSpin", - "PlayerExplode", - "PlayerSquish", - "PlayerCmd", - "IntermissionThinker", - "VoteThinker", - "ServerJoin", - NULL +/* ========================================================================= + ABSTRACTION + ========================================================================= */ + +static const char * const mobjHookNames[] = { MOBJ_HOOK_LIST (TOSTR) NULL }; +static const char * const hookNames[] = { HOOK_LIST (TOSTR) NULL }; + +static const char * const stringHookNames[] = { + STRING_HOOK_LIST (TOSTR) NULL }; -// Hook metadata -struct hook_s +typedef struct { + int numHooks; + int *ids; +} hook_t; + +typedef struct { + int numGeneric; + int ref; +} stringhook_t; + +static hook_t hookIds[HOOK(MAX)]; +static hook_t mobjHookIds[NUMMOBJTYPES][MOBJ_HOOK(MAX)]; + +// Lua tables are used to lookup string hook ids. +static stringhook_t stringHooks[STRING_HOOK(MAX)]; + +// This will be indexed by hook id, the value of which fetches the registry. +static int * hookRefs; + +// After a hook errors once, don't print the error again. +static UINT8 * hooksErrored; + +static int errorRef; + +static boolean mobj_hook_available(int hook_type, mobjtype_t mobj_type) { - struct hook_s *next; - enum hook type; - UINT16 id; - union { - mobjtype_t mt; - char *skinname; - char *funcname; - } s; - boolean error; -}; -typedef struct hook_s* hook_p; + return + ( + mobjHookIds [MT_NULL] [hook_type].numHooks > 0 || + mobjHookIds[mobj_type][hook_type].numHooks > 0 + ); +} -// For each mobj type, a linked list to its thinker and collision hooks. -// That way, we don't have to iterate through all the hooks. -// We could do that with all other mobj hooks, but it would probably just be -// a waste of memory since they are only called occasionally. Probably... -static hook_p mobjthinkerhooks[NUMMOBJTYPES]; -static hook_p mobjcollidehooks[NUMMOBJTYPES]; +static int hook_in_list +( + const char * const name, + const char * const * const list +){ + int type; -// For each mobj type, a linked list for other mobj hooks -static hook_p mobjhooks[NUMMOBJTYPES]; + for (type = 0; list[type] != NULL; ++type) + { + if (strcmp(name, list[type]) == 0) + break; + } -// A linked list for player hooks -static hook_p playerhooks; + return type; +} -// A linked list for linedef executor hooks -static hook_p linedefexecutorhooks; +static void get_table(lua_State *L) +{ + lua_pushvalue(L, -1); + lua_rawget(L, -3); -// For other hooks, a unique linked list -hook_p roothook; + if (lua_isnil(L, -1)) + { + lua_pop(L, 1); + lua_createtable(L, 1, 0); + lua_pushvalue(L, -2); + lua_pushvalue(L, -2); + lua_rawset(L, -5); + } + + lua_remove(L, -2); +} + +static void add_hook_to_table(lua_State *L, int id, int n) +{ + lua_pushnumber(L, id); + lua_rawseti(L, -2, n); +} + +static void add_string_hook(lua_State *L, int type, int id) +{ + stringhook_t * hook = &stringHooks[type]; + + char * string = NULL; + + switch (type) + { + case STRING_HOOK(BotAI): + if (lua_isstring(L, 3)) + { // lowercase copy + string = Z_StrDup(lua_tostring(L, 3)); + strlwr(string); + } + + /*hook.s.skinname = NULL; + if (lua_isstring(L, 2)) + { // lowercase copy + const char *s = lua_tostring(L, 2); + char *p = hook.s.skinname = ZZ_Alloc(strlen(s)+1); + do { + *p = tolower(*s); + ++p; + } while(*(++s)); + *p = 0; + }*/ + break; + + case STRING_HOOK(LinedefExecute): + string = Z_StrDup(luaL_checkstring(L, 3)); + strupr(string); + + /*{ // uppercase copy + const char *s = luaL_checkstring(L, 2); + char *p = hook.s.funcname = ZZ_Alloc(strlen(s)+1); + do { + *p = toupper(*s); + ++p; + } while(*(++s)); + *p = 0; + }*/ + break; + } + + if (hook->ref > 0) + lua_getref(L, hook->ref); + else + { + lua_newtable(L); + lua_pushvalue(L, -1); + hook->ref = luaL_ref(L, LUA_REGISTRYINDEX); + } + + if (string) + { + lua_pushstring(L, string); + get_table(L); + add_hook_to_table(L, id, 1 + lua_objlen(L, -1)); + } + else + add_hook_to_table(L, id, ++hook->numGeneric); +} + +static void add_hook(hook_t *map, int id) +{ + Z_Realloc(map->ids, (map->numHooks + 1) * sizeof *map->ids, + PU_STATIC, &map->ids); + map->ids[map->numHooks++] = id; +} + +static void add_mobj_hook(lua_State *L, int hook_type, int id) +{ + mobjtype_t mobj_type = luaL_optnumber(L, 3, MT_NULL); + + luaL_argcheck(L, mobj_type < NUMMOBJTYPES, 3, "invalid mobjtype_t"); + + add_hook(&mobjHookIds[mobj_type][hook_type], id); +} // Takes hook, function, and additional arguments (mobj type to act on, etc.) static int lib_addHook(lua_State *L) { - static struct hook_s hook = {NULL, 0, 0, {0}, false}; - static UINT32 nextid; - hook_p hookp, *lastp; + static int nextid; - hook.type = luaL_checkoption(L, 1, NULL, hookNames); - lua_remove(L, 1); - - luaL_checktype(L, 1, LUA_TFUNCTION); + const char * name; + int type; if (hud_running) return luaL_error(L, "HUD rendering code should not call this function!"); - switch(hook.type) + name = luaL_checkstring(L, 1); + luaL_checktype(L, 2, LUA_TFUNCTION); + + /* this is a very special case */ + if (( type = hook_in_list(name, stringHookNames) ) < STRING_HOOK(MAX)) { - // Take a mobjtype enum which this hook is specifically for. - case hook_MobjSpawn: - case hook_MobjCollide: - case hook_MobjMoveCollide: - case hook_TouchSpecial: - case hook_MobjFuse: - case hook_MobjThinker: - case hook_BossThinker: - case hook_ShouldDamage: - case hook_MobjDamage: - case hook_MobjDeath: - case hook_BossDeath: - case hook_MobjRemoved: - case hook_HurtMsg: - hook.s.mt = MT_NULL; - if (lua_isnumber(L, 2)) - hook.s.mt = lua_tonumber(L, 2); - luaL_argcheck(L, hook.s.mt < NUMMOBJTYPES, 2, "invalid mobjtype_t"); - break; - case hook_BotAI: - hook.s.skinname = NULL; - if (lua_isstring(L, 2)) - { // lowercase copy - const char *s = lua_tostring(L, 2); - char *p = hook.s.skinname = ZZ_Alloc(strlen(s)+1); - do { - *p = tolower(*s); - ++p; - } while(*(++s)); - *p = 0; - } - break; - case hook_LinedefExecute: // Linedef executor functions - { // uppercase copy - const char *s = luaL_checkstring(L, 2); - char *p = hook.s.funcname = ZZ_Alloc(strlen(s)+1); - do { - *p = toupper(*s); - ++p; - } while(*(++s)); - *p = 0; - } - break; - case hook_ShouldSpin: - case hook_ShouldExplode: - case hook_ShouldSquish: - case hook_PlayerSpin: - case hook_PlayerExplode: - case hook_PlayerSquish: - default: - break; + add_string_hook(L, type, nextid); } - lua_settop(L, 1); // lua stack contains only the function now. - - hooksAvailable[hook.type/8] |= 1<<(hook.type%8); - - // set hook.id to the highest id + 1 - hook.id = nextid++; - - // Special cases for some hook types (see the comments above mobjthinkerhooks declaration) - switch(hook.type) + else if (( type = hook_in_list(name, mobjHookNames) ) < MOBJ_HOOK(MAX)) { - case hook_MobjThinker: - lastp = &mobjthinkerhooks[hook.s.mt]; - break; - case hook_MobjCollide: - case hook_MobjMoveCollide: - lastp = &mobjcollidehooks[hook.s.mt]; - break; - case hook_MobjSpawn: - case hook_TouchSpecial: - case hook_MobjFuse: - case hook_BossThinker: - case hook_ShouldDamage: - case hook_MobjDamage: - case hook_MobjDeath: - case hook_BossDeath: - case hook_MobjRemoved: - lastp = &mobjhooks[hook.s.mt]; - break; - case hook_JumpSpecial: - case hook_AbilitySpecial: - case hook_SpinSpecial: - case hook_JumpSpinSpecial: - case hook_PlayerSpawn: - case hook_PlayerThink: - lastp = &playerhooks; - break; - case hook_LinedefExecute: - lastp = &linedefexecutorhooks; - break; - case hook_ShouldSpin: - case hook_ShouldExplode: - case hook_ShouldSquish: - case hook_PlayerSpin: - case hook_PlayerExplode: - case hook_PlayerSquish: - case hook_ServerJoin: - default: - lastp = &roothook; - break; + add_mobj_hook(L, type, nextid); + } + else if (( type = hook_in_list(name, hookNames) ) < HOOK(MAX)) + { + add_hook(&hookIds[type], nextid); + } + else + { + return luaL_argerror(L, 1, lua_pushfstring(L, "invalid hook " LUA_QS, name)); } - // iterate the hook metadata structs - // set lastp to the last hook struct's "next" pointer. - for (hookp = *lastp; hookp; hookp = hookp->next) - lastp = &hookp->next; - // allocate a permanent memory struct to stuff hook. - hookp = ZZ_Alloc(sizeof(struct hook_s)); - memcpy(hookp, &hook, sizeof(struct hook_s)); - // tack it onto the end of the linked list. - *lastp = hookp; + if (!(nextid & 7)) + { + Z_Realloc(hooksErrored, + BIT_ARRAY_SIZE (nextid + 1) * sizeof *hooksErrored, + PU_STATIC, &hooksErrored); + hooksErrored[nextid >> 3] = 0; + } + + Z_Realloc(hookRefs, (nextid + 1) * sizeof *hookRefs, PU_STATIC, &hookRefs); // set the hook function in the registry. - lua_getfield(L, LUA_REGISTRYINDEX, "hooks"); - lua_pushvalue(L, 1); - lua_rawseti(L, -2, hook.id); + lua_pushvalue(L, 2);/* the function */ + hookRefs[nextid++] = luaL_ref(L, LUA_REGISTRYINDEX); + return 0; } int LUA_HookLib(lua_State *L) { - memset(hooksAvailable,0,sizeof(UINT8[(hook_MAX/8)+1])); - roothook = NULL; - lua_register(L, "addHook", lib_addHook); + lua_pushcfunction(L, LUA_GetErrorMessage); + errorRef = luaL_ref(L, LUA_REGISTRYINDEX); - lua_newtable(L); - lua_setfield(L, LUA_REGISTRYINDEX, "hooks"); + lua_register(L, "addHook", lib_addHook); return 0; } -boolean LUAh_MobjHook(mobj_t *mo, enum hook which) +typedef struct Hook_State Hook_State; +typedef void (*Hook_Callback)(Hook_State *); + +struct Hook_State { + INT32 status;/* return status to calling function */ + void * userdata; + int hook_type; + mobjtype_t mobj_type;/* >0 if mobj hook */ + const char * string;/* used to fetch table, ran first if set */ + int top;/* index of last argument passed to hook */ + int id;/* id to fetch ref */ + int values;/* num arguments passed to hook */ + int results;/* num values returned by hook */ + Hook_Callback results_handler;/* callback when hook successfully returns */ +}; + +enum { + EINDEX = 1,/* error handler */ + SINDEX = 2,/* string itself is pushed in case of string hook */ +}; + +static void push_error_handler(void) { - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[which/8] & (1<<(which%8)))) + lua_getref(gL, errorRef); +} + +/* repush hook string */ +static void push_string(void) +{ + lua_pushvalue(gL, SINDEX); +} + +static boolean start_hook_stack(void) +{ + lua_settop(gL, 0); + push_error_handler(); + return true; +} + +static boolean init_hook_type +( + Hook_State * hook, + int status, + int hook_type, + mobjtype_t mobj_type, + const char * string, + int nonzero +){ + hook->status = status; + + if (nonzero) + { + hook->hook_type = hook_type; + hook->mobj_type = mobj_type; + hook->string = string; + return start_hook_stack(); + } + else return false; +} - I_Assert(mo->type < NUMMOBJTYPES); +static boolean prepare_hook +( + Hook_State * hook, + int default_status, + int hook_type +){ + return init_hook_type(hook, default_status, + hook_type, 0, NULL, + hookIds[hook_type].numHooks); +} - if (!(mobjhooks[MT_NULL] || mobjhooks[mo->type])) +static boolean prepare_mobj_hook +( + Hook_State * hook, + int default_status, + int hook_type, + mobjtype_t mobj_type +){ + return init_hook_type(hook, default_status, + hook_type, mobj_type, NULL, + mobj_hook_available(hook_type, mobj_type)); +} + +static boolean prepare_string_hook +( + Hook_State * hook, + int default_status, + int hook_type, + const char * string +){ + if (init_hook_type(hook, default_status, + hook_type, 0, string, + stringHooks[hook_type].ref)) + { + lua_pushstring(gL, string); + return true; + } + else return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // Look for all generic mobj hooks - for (hookp = mobjhooks[MT_NULL]; hookp; hookp = hookp->next) - { - if (hookp->type != which) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - LUA_PushUserdata(gL, mo, META_MOBJ); - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -2); - if (lua_pcall(gL, 1, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - for (hookp = mobjhooks[mo->type]; hookp; hookp = hookp->next) - { - if (hookp->type != which) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - LUA_PushUserdata(gL, mo, META_MOBJ); - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -2); - if (lua_pcall(gL, 1, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; } -boolean LUAh_PlayerHook(player_t *plr, enum hook which) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[which/8] & (1<<(which%8)))) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = playerhooks; hookp; hookp = hookp->next) - { - if (hookp->type != which) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - LUA_PushUserdata(gL, plr, META_PLAYER); - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -2); - if (lua_pcall(gL, 1, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; +static void init_hook_call +( + Hook_State * hook, + int values, + int results, + Hook_Callback results_handler +){ + hook->top = lua_gettop(gL); + hook->values = values; + hook->results = results; + hook->results_handler = results_handler; } -// Hook for map change (before load) -void LUAh_MapChange(INT16 mapnumber) +static void get_hook(Hook_State *hook, const int *ids, int n) { - hook_p hookp; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_MapChange/8] & (1<<(hook_MapChange%8)))) - return; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - lua_pushinteger(gL, mapnumber); - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_MapChange) - continue; - - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -2); - if (lua_pcall(gL, 1, 0, 1)) { - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - } - } - - lua_settop(gL, 0); + hook->id = ids[n]; + lua_getref(gL, hookRefs[hook->id]); } -// Hook for map load -void LUAh_MapLoad(void) +static void get_hook_from_table(Hook_State *hook, int n) { - hook_p hookp; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_MapLoad/8] & (1<<(hook_MapLoad%8)))) - return; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - lua_pushinteger(gL, gamemap); - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_MapLoad) - continue; - - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -2); - if (lua_pcall(gL, 1, 0, 1)) { - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - } - } - - lua_settop(gL, 0); + lua_rawgeti(gL, -1, n); + hook->id = lua_tonumber(gL, -1); + lua_pop(gL, 1); + lua_getref(gL, hookRefs[hook->id]); } -// Hook for Got_AddPlayer -void LUAh_PlayerJoin(int playernum) +static int call_single_hook_no_copy(Hook_State *hook) { - hook_p hookp; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_PlayerJoin/8] & (1<<(hook_PlayerJoin%8)))) - return; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - lua_pushinteger(gL, playernum); - - for (hookp = roothook; hookp; hookp = hookp->next) + if (lua_pcall(gL, hook->values, hook->results, EINDEX) == 0) { - if (hookp->type != hook_PlayerJoin) - continue; - - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -2); - if (lua_pcall(gL, 1, 0, 1)) { - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - } - } - - lua_settop(gL, 0); -} - -// Hook for frame (before mobj and player thinkers) -void LUAh_PreThinkFrame(void) -{ - hook_p hookp; - int HOOKSINDEX; - // variables used by perf stats - int hook_index = 0; - precise_t time_taken = 0; - if (!gL || !(hooksAvailable[hook_PreThinkFrame/8] & (1<<(hook_PreThinkFrame%8)))) - return; - - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_PreThinkFrame) - continue; - - if (cv_perfstats.value == 4) - time_taken = I_GetPreciseTime(); - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - if (lua_pcall(gL, 0, 0, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - } - if (cv_perfstats.value == 4) + if (hook->results > 0) { - lua_Debug ar; - time_taken = I_GetPreciseTime() - time_taken; - // we need the function, let's just retrieve it again - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_getinfo(gL, ">S", &ar); - PS_SetPreThinkFrameHookInfo(hook_index, time_taken, ar.short_src); - hook_index++; + (*hook->results_handler)(hook); + lua_pop(gL, hook->results); } } + else + { + /* print the error message once */ + if (cv_debug & DBG_LUA || !in_bit_array(hooksErrored, hook->id)) + { + CONS_Alert(CONS_WARNING, "%s\n", lua_tostring(gL, -1)); + set_bit_array(hooksErrored, hook->id); + } + lua_pop(gL, 1); + } - lua_pop(gL, 2); // Pop error handler and hooks table + return 1; } -// Hook for frame (after mobj and player thinkers) -void LUAh_ThinkFrame(void) +static int call_single_hook(Hook_State *hook) { - hook_p hookp; - int HOOKSINDEX; + int i; + + for (i = -(hook->values) + 1; i <= 0; ++i) + lua_pushvalue(gL, hook->top + i); + + return call_single_hook_no_copy(hook); +} + +static int call_hook_table_for(Hook_State *hook, int n) +{ + int k; + + for (k = 1; k <= n; ++k) + { + get_hook_from_table(hook, k); + call_single_hook(hook); + } + + return n; +} + +static int call_hook_table(Hook_State *hook) +{ + return call_hook_table_for(hook, lua_objlen(gL, -1)); +} + +static int call_mapped(Hook_State *hook, const hook_t *map) +{ + int k; + + for (k = 0; k < map->numHooks; ++k) + { + get_hook(hook, map->ids, k); + call_single_hook(hook); + } + + return map->numHooks; +} + +static int call_string_hooks(Hook_State *hook) +{ + const stringhook_t *map = &stringHooks[hook->hook_type]; + + int calls = 0; + + lua_getref(gL, map->ref); + + /* call generic string hooks first */ + calls += call_hook_table_for(hook, map->numGeneric); + + push_string(); + lua_rawget(gL, -2); + calls += call_hook_table(hook); + + return calls; +} + +static int call_mobj_type_hooks(Hook_State *hook, mobjtype_t mobj_type) +{ + return call_mapped(hook, &mobjHookIds[mobj_type][hook->hook_type]); +} + +static int call_hooks +( + Hook_State * hook, + int values, + int results, + Hook_Callback results_handler +){ + int calls = 0; + + init_hook_call(hook, values, results, results_handler); + + if (hook->string) + { + calls += call_string_hooks(hook); + } + else if (hook->mobj_type > 0) + { + /* call generic mobj hooks first */ + calls += call_mobj_type_hooks(hook, MT_NULL); + calls += call_mobj_type_hooks(hook, hook->mobj_type); + + ps_lua_mobjhooks.value.i += calls; + } + else + calls += call_mapped(hook, &hookIds[hook->hook_type]); + + lua_settop(gL, 0); + + return calls; +} + +/* ========================================================================= + COMMON RESULT HANDLERS + ========================================================================= */ + +#define res_none NULL + +static void res_true(Hook_State *hook) +{ + if (lua_toboolean(gL, -1)) + hook->status = true; +} + +static void res_false(Hook_State *hook) +{ + if (!lua_isnil(gL, -1) && !lua_toboolean(gL, -1)) + hook->status = false; +} + +static void res_force(Hook_State *hook) +{ + if (!lua_isnil(gL, -1)) + { + if (lua_toboolean(gL, -1)) + hook->status = 1; // Force yes + else + hook->status = 2; // Force no + } +} + +/* ========================================================================= + GENERALISED HOOKS + ========================================================================= */ + +int LUA_HookMobj(mobj_t *mobj, int hook_type) +{ + Hook_State hook; + if (prepare_mobj_hook(&hook, false, hook_type, mobj->type)) + { + LUA_PushUserdata(gL, mobj, META_MOBJ); + call_hooks(&hook, 1, 1, res_true); + } + return hook.status; +} + +int LUA_Hook2Mobj(mobj_t *t1, mobj_t *t2, int hook_type) +{ + Hook_State hook; + if (prepare_mobj_hook(&hook, 0, hook_type, t1->type)) + { + LUA_PushUserdata(gL, t1, META_MOBJ); + LUA_PushUserdata(gL, t2, META_MOBJ); + call_hooks(&hook, 2, 1, res_force); + } + return hook.status; +} + +void LUA_HookVoid(int type) +{ + Hook_State hook; + if (prepare_hook(&hook, 0, type)) + call_hooks(&hook, 0, 0, res_none); +} + +void LUA_HookInt(INT32 number, int hook_type) +{ + Hook_State hook; + if (prepare_hook(&hook, 0, hook_type)) + { + lua_pushinteger(gL, number); + call_hooks(&hook, 1, 0, res_none); + } +} + +//void LUA_HookBool(boolean value, int hook_type) +void LUA_HookBool(int hook_type) +{ + Hook_State hook; + if (prepare_hook(&hook, 0, hook_type)) + { + //lua_pushboolean(gL, value); + call_hooks(&hook, 1, 0, res_none); + } +} + +int LUA_HookPlayer(player_t *player, int hook_type) +{ + Hook_State hook; + if (prepare_hook(&hook, false, hook_type)) + { + LUA_PushUserdata(gL, player, META_PLAYER); + call_hooks(&hook, 1, 1, res_true); + } + return hook.status; +} + +int LUA_HookTiccmd(player_t *player, ticcmd_t *cmd, int hook_type) +{ + Hook_State hook; + if (prepare_hook(&hook, false, hook_type)) + { + LUA_PushUserdata(gL, player, META_PLAYER); + LUA_PushUserdata(gL, cmd, META_TICCMD); + + if (hook_type == HOOK(PlayerCmd)) + hook_cmd_running = true; + + call_hooks(&hook, 2, 1, res_true); + + if (hook_type == HOOK(PlayerCmd)) + hook_cmd_running = false; + } + return hook.status; +} + +/* ========================================================================= + SPECIALIZED HOOKS + ========================================================================= */ + +void LUA_HookThinkFrame(void) +{ + const int type = HOOK(ThinkFrame); + // variables used by perf stats int hook_index = 0; precise_t time_taken = 0; - if (!gL || !(hooksAvailable[hook_ThinkFrame/8] & (1<<(hook_ThinkFrame%8)))) - return; + Hook_State hook; - lua_pushcfunction(gL, LUA_GetErrorMessage); + const hook_t * map = &hookIds[type]; + int k; - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) + if (prepare_hook(&hook, 0, type)) { - if (hookp->type != hook_ThinkFrame) - continue; + init_hook_call(&hook, 0, 0, res_none); - if (cv_perfstats.value == 3) - time_taken = I_GetPreciseTime(); - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - if (lua_pcall(gL, 0, 0, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - } - if (cv_perfstats.value == 3) + for (k = 0; k < map->numHooks; ++k) { - lua_Debug ar; - time_taken = I_GetPreciseTime() - time_taken; - // we need the function, let's just retrieve it again - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_getinfo(gL, ">S", &ar); - PS_SetThinkFrameHookInfo(hook_index, time_taken, ar.short_src); - hook_index++; - } - } + get_hook(&hook, map->ids, k); - lua_pop(gL, 2); // Pop error handler and hooks table -} - -// Hook for frame (at end of tick, ie after overlays, precipitation, specials) -void LUAh_PostThinkFrame(void) -{ - hook_p hookp; - int HOOKSINDEX; - // variables used by perf stats - int hook_index = 0; - precise_t time_taken = 0; - if (!gL || !(hooksAvailable[hook_PostThinkFrame/8] & (1<<(hook_PostThinkFrame%8)))) - return; - - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_PostThinkFrame) - continue; - - if (cv_perfstats.value == 5) - time_taken = I_GetPreciseTime(); - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - if (lua_pcall(gL, 0, 0, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - } - if (cv_perfstats.value == 5) - { - lua_Debug ar; - time_taken = I_GetPreciseTime() - time_taken; - // we need the function, let's just retrieve it again - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_getinfo(gL, ">S", &ar); - PS_SetPostThinkFrameHookInfo(hook_index, time_taken, ar.short_src); - hook_index++; - } - } - - lua_pop(gL, 2); // Pop error handler and hooks table -} - -// Hook for Y_Ticker -void LUAh_IntermissionThinker(void) -{ - hook_p hookp; - int HOOKSINDEX; - - if (!gL || !(hooksAvailable[hook_IntermissionThinker/8] & (1<<(hook_IntermissionThinker%8)))) - return; - - lua_pushcfunction(gL, LUA_GetErrorMessage);; - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_IntermissionThinker) - continue; - - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - if (lua_pcall(gL, 0, 0, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - } - } - - lua_pop(gL, 2); // Pop error handler and hooks table -} - -// Hook for Y_VoteTicker -void LUAh_VoteThinker(void) -{ - hook_p hookp; - int HOOKSINDEX; - - if (!gL || !(hooksAvailable[hook_VoteThinker/8] & (1<<(hook_VoteThinker%8)))) - return; - - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_VoteThinker) - continue; - - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - if (lua_pcall(gL, 0, 0, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - } - } - - lua_pop(gL, 2); // Pop error handler and hooks table -} - - -// Hook for mobj collisions -UINT8 LUAh_MobjCollideHook(mobj_t *thing1, mobj_t *thing2, enum hook which) -{ - hook_p hookp; - UINT8 shouldCollide = 0; // 0 = default, 1 = force yes, 2 = force no. - int HOOKSINDEX; - if (!gL || !(hooksAvailable[which/8] & (1<<(which%8)))) - return 0; - - I_Assert(thing1->type < NUMMOBJTYPES); - - if (!(mobjcollidehooks[MT_NULL] || mobjcollidehooks[thing1->type])) - return 0; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // Look for all generic mobj collision hooks - for (hookp = mobjcollidehooks[MT_NULL]; hookp; hookp = hookp->next) - { - if (hookp->type != which) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, thing1, META_MOBJ); - LUA_PushUserdata(gL, thing2, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -3); - lua_pushvalue(gL, -3); - if (lua_pcall(gL, 2, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (!lua_isnil(gL, -1)) - { // if nil, leave shouldCollide = 0. - if (lua_toboolean(gL, -1)) - shouldCollide = 1; // Force yes - else - shouldCollide = 2; // Force no - } - lua_pop(gL, 1); - } - - for (hookp = mobjcollidehooks[thing1->type]; hookp; hookp = hookp->next) - { - if (hookp->type != which) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, thing1, META_MOBJ); - LUA_PushUserdata(gL, thing2, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -3); - lua_pushvalue(gL, -3); - if (lua_pcall(gL, 2, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (!lua_isnil(gL, -1)) - { // if nil, leave shouldCollide = 0. - if (lua_toboolean(gL, -1)) - shouldCollide = 1; // Force yes - else - shouldCollide = 2; // Force no - } - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return shouldCollide; -} - -// Hook for mobj thinkers -boolean LUAh_MobjThinker(mobj_t *mo) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_MobjThinker/8] & (1<<(hook_MobjThinker%8)))) - return false; - - I_Assert(mo->type < NUMMOBJTYPES); - - if (!(mobjthinkerhooks[MT_NULL] || mobjthinkerhooks[mo->type])) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // Look for all generic mobj thinker hooks - for (hookp = mobjthinkerhooks[MT_NULL]; hookp; hookp = hookp->next) - { - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - LUA_PushUserdata(gL, mo, META_MOBJ); - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -2); - if (lua_pcall(gL, 1, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - for (hookp = mobjthinkerhooks[mo->type]; hookp; hookp = hookp->next) - { - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - LUA_PushUserdata(gL, mo, META_MOBJ); - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -2); - if (lua_pcall(gL, 1, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; -} - -// Hook for P_TouchSpecialThing by mobj type -boolean LUAh_TouchSpecial(mobj_t *special, mobj_t *toucher) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_TouchSpecial/8] & (1<<(hook_TouchSpecial%8)))) - return false; - - I_Assert(special->type < NUMMOBJTYPES); - - if (!(mobjhooks[MT_NULL] || mobjhooks[special->type])) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // Look for all generic touch special hooks - for (hookp = mobjhooks[MT_NULL]; hookp; hookp = hookp->next) - { - if (hookp->type != hook_TouchSpecial) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, special, META_MOBJ); - LUA_PushUserdata(gL, toucher, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -3); - lua_pushvalue(gL, -3); - if (lua_pcall(gL, 2, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - for (hookp = mobjhooks[special->type]; hookp; hookp = hookp->next) - { - if (hookp->type != hook_TouchSpecial) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, special, META_MOBJ); - LUA_PushUserdata(gL, toucher, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -3); - lua_pushvalue(gL, -3); - if (lua_pcall(gL, 2, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; -} - -// Hook for P_DamageMobj by mobj type (Should mobj take damage?) -UINT8 LUAh_ShouldDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage) -{ - hook_p hookp; - UINT8 shouldDamage = 0; // 0 = default, 1 = force yes, 2 = force no. - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_ShouldDamage/8] & (1<<(hook_ShouldDamage%8)))) - return 0; - - I_Assert(target->type < NUMMOBJTYPES); - - if (!(mobjhooks[MT_NULL] || mobjhooks[target->type])) - return 0; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // Look for all generic should damage hooks - for (hookp = mobjhooks[MT_NULL]; hookp; hookp = hookp->next) - { - if (hookp->type != hook_ShouldDamage) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, target, META_MOBJ); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - lua_pushinteger(gL, damage); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - if (lua_pcall(gL, 4, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (!lua_isnil(gL, -1)) - { - if (lua_toboolean(gL, -1)) - shouldDamage = 1; // Force yes - else - shouldDamage = 2; // Force no - } - lua_pop(gL, 1); - } - - for (hookp = mobjhooks[target->type]; hookp; hookp = hookp->next) - { - if (hookp->type != hook_ShouldDamage) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, target, META_MOBJ); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - lua_pushinteger(gL, damage); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - if (lua_pcall(gL, 4, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (!lua_isnil(gL, -1)) - { - if (lua_toboolean(gL, -1)) - shouldDamage = 1; // Force yes - else - shouldDamage = 2; // Force no - } - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return shouldDamage; -} - -// Hook for P_DamageMobj by mobj type (Mobj actually takes damage!) -boolean LUAh_MobjDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_MobjDamage/8] & (1<<(hook_MobjDamage%8)))) - return false; - - I_Assert(target->type < NUMMOBJTYPES); - - if (!(mobjhooks[MT_NULL] || mobjhooks[target->type])) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // Look for all generic mobj damage hooks - for (hookp = mobjhooks[MT_NULL]; hookp; hookp = hookp->next) - { - if (hookp->type != hook_MobjDamage) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, target, META_MOBJ); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - lua_pushinteger(gL, damage); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - if (lua_pcall(gL, 4, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - for (hookp = mobjhooks[target->type]; hookp; hookp = hookp->next) - { - if (hookp->type != hook_MobjDamage) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, target, META_MOBJ); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - lua_pushinteger(gL, damage); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - lua_pushvalue(gL, -5); - if (lua_pcall(gL, 4, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; -} - -// Hook for P_KillMobj by mobj type -boolean LUAh_MobjDeath(mobj_t *target, mobj_t *inflictor, mobj_t *source) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_MobjDeath/8] & (1<<(hook_MobjDeath%8)))) - return false; - - I_Assert(target->type < NUMMOBJTYPES); - - if (!(mobjhooks[MT_NULL] || mobjhooks[target->type])) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // Look for all generic mobj death hooks - for (hookp = mobjhooks[MT_NULL]; hookp; hookp = hookp->next) - { - if (hookp->type != hook_MobjDeath) - continue; - - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, target, META_MOBJ); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - for (hookp = mobjhooks[target->type]; hookp; hookp = hookp->next) - { - if (hookp->type != hook_MobjDeath) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, target, META_MOBJ); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; -} - -// Hook for B_BuildTiccmd -boolean LUAh_BotTiccmd(player_t *bot, ticcmd_t *cmd) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_BotTiccmd/8] & (1<<(hook_BotTiccmd%8)))) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_BotTiccmd) - continue; - - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, bot, META_PLAYER); - LUA_PushUserdata(gL, cmd, META_TICCMD); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -3); - lua_pushvalue(gL, -3); - if (lua_pcall(gL, 2, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; -} - -// Hook for G_BuildTicCmd -boolean hook_cmd_running = false; -boolean LUAh_PlayerCmd(player_t *player, ticcmd_t *cmd) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_PlayerCmd/8] & (1<<(hook_PlayerCmd%8)))) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - hook_cmd_running = true; - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_PlayerCmd) - continue; - - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, player, META_PLAYER); - LUA_PushUserdata(gL, cmd, META_TICCMD); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -3); - lua_pushvalue(gL, -3); - if (lua_pcall(gL, 2, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - hook_cmd_running = false; - lua_settop(gL, 0); - return hooked; -} - -// Hook for B_BuildTailsTiccmd by skin name -boolean LUAh_BotAI(mobj_t *sonic, mobj_t *tails, ticcmd_t *cmd) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_BotAI/8] & (1<<(hook_BotAI%8)))) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_BotAI - || (hookp->s.skinname && strcmp(hookp->s.skinname, ((skin_t*)tails->skin)->name))) - continue; - - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, sonic, META_MOBJ); - LUA_PushUserdata(gL, tails, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -3); - lua_pushvalue(gL, -3); - if (lua_pcall(gL, 2, 8, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - - // This turns forward, backward, left, right, jump, and spin into a proper ticcmd for tails. - if (lua_istable(gL, -8)) { - boolean forward=false, backward=false, left=false, right=false, strafeleft=false, straferight=false, jump=false, spin=false; -#define CHECKFIELD(field) \ - lua_getfield(gL, -8, #field);\ - if (lua_toboolean(gL, -1))\ - field = true;\ - lua_pop(gL, 1); - - CHECKFIELD(forward) - CHECKFIELD(backward) - CHECKFIELD(left) - CHECKFIELD(right) - CHECKFIELD(strafeleft) - CHECKFIELD(straferight) - CHECKFIELD(jump) - CHECKFIELD(spin) -#undef CHECKFIELD - B_KeysToTiccmd(tails, cmd, forward, backward, left, right, strafeleft, straferight, jump, spin); - } else - B_KeysToTiccmd(tails, cmd, lua_toboolean(gL, -8), lua_toboolean(gL, -7), lua_toboolean(gL, -6), lua_toboolean(gL, -5), lua_toboolean(gL, -4), lua_toboolean(gL, -3), lua_toboolean(gL, -2), lua_toboolean(gL, -1)); - - lua_pop(gL, 8); - hooked = true; - } - - lua_settop(gL, 0); - return hooked; -} - -// Hook for linedef executors -boolean LUAh_LinedefExecute(line_t *line, mobj_t *mo, sector_t *sector) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_LinedefExecute/8] & (1<<(hook_LinedefExecute%8)))) - return 0; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = linedefexecutorhooks; hookp; hookp = hookp->next) - { - if (strcmp(hookp->s.funcname, line->text)) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, line, META_LINE); - LUA_PushUserdata(gL, mo, META_MOBJ); - LUA_PushUserdata(gL, sector, META_SECTOR); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 0, 1)) { - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - } - hooked = true; - } - - lua_settop(gL, 0); - return hooked; -} - -// Hook for player chat -// Added the "mute" field. It's set to true if the message was supposed to be eaten by spam protection. -// But for netgame consistency purposes, this hook is ran first reguardless, so this boolean allows for modders to adapt if they so desire. -boolean LUAh_PlayerMsg(int source, int target, int flags, char *msg, int mute) -{ - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_PlayerMsg/8] & (1<<(hook_PlayerMsg%8)))) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_PlayerMsg) - continue; - - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, &players[source], META_PLAYER); // Source player - if (flags & 2 /*HU_CSAY*/) { // csay TODO: make HU_CSAY accessible outside hu_stuff.c - lua_pushinteger(gL, 3); // type - lua_pushnil(gL); // target - } else if (target == -1) { // sayteam - lua_pushinteger(gL, 1); // type - lua_pushnil(gL); // target - } else if (target == 0) { // say - lua_pushinteger(gL, 0); // type - lua_pushnil(gL); // target - } else { // sayto - lua_pushinteger(gL, 2); // type - LUA_PushUserdata(gL, &players[target-1], META_PLAYER); // target + if (cv_perfstats.value == 3) + { + lua_pushvalue(gL, -1);/* need the function again */ + time_taken = I_GetPreciseTime(); } - lua_pushstring(gL, msg); // msg - if (mute) - lua_pushboolean(gL, true); // the message was supposed to be eaten by spamprotecc. - else - lua_pushboolean(gL, false); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -6); - lua_pushvalue(gL, -6); - lua_pushvalue(gL, -6); - lua_pushvalue(gL, -6); - lua_pushvalue(gL, -6); - if (lua_pcall(gL, 5, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - lua_settop(gL, 0); - return hooked; + call_single_hook(&hook); + + if (cv_perfstats.value == 3) + { + lua_Debug ar; + time_taken = I_GetPreciseTime() - time_taken; + lua_getinfo(gL, ">S", &ar); + PS_SetThinkFrameHookInfo(hook_index, time_taken, ar.short_src); + hook_index++; + } + } + + lua_settop(gL, 0); + } } -// Hook for hurt messages -boolean LUAh_HurtMsg(player_t *player, mobj_t *inflictor, mobj_t *source) +int LUA_HookTouchSpecial(mobj_t *special, mobj_t *toucher) { - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_HurtMsg/8] & (1<<(hook_HurtMsg%8)))) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) + Hook_State hook; + if (prepare_mobj_hook(&hook, false, MOBJ_HOOK(TouchSpecial), special->type)) { - if (hookp->type != hook_HurtMsg - || (hookp->s.mt && !(inflictor && hookp->s.mt == inflictor->type))) - continue; + LUA_PushUserdata(gL, special, META_MOBJ); + LUA_PushUserdata(gL, toucher, META_MOBJ); + call_hooks(&hook, 2, 1, res_true); + } + return hook.status; +} - if (lua_gettop(gL) == 2) +static int damage_hook +( + mobj_t *target, + mobj_t *inflictor, + mobj_t *source, + INT32 damage, + int hook_type, + int values, + Hook_Callback results_handler +){ + Hook_State hook; + if (prepare_mobj_hook(&hook, 0, hook_type, target->type)) + { + LUA_PushUserdata(gL, target, META_MOBJ); + LUA_PushUserdata(gL, inflictor, META_MOBJ); + LUA_PushUserdata(gL, source, META_MOBJ); + if (values == 5) + lua_pushinteger(gL, damage); + call_hooks(&hook, values, 1, results_handler); + } + return hook.status; +} + +int LUA_HookShouldDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage) +{ + return damage_hook(target, inflictor, source, damage, + MOBJ_HOOK(ShouldDamage), 5, res_force); +} + +int LUA_HookMobjDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage) +{ + return damage_hook(target, inflictor, source, damage, + MOBJ_HOOK(MobjDamage), 5, res_true); +} + +int LUA_HookMobjDeath(mobj_t *target, mobj_t *inflictor, mobj_t *source) +{ + return damage_hook(target, inflictor, source, 0, + MOBJ_HOOK(MobjDeath), 4, res_true); +} + +typedef struct { + mobj_t * tails; + ticcmd_t * cmd; +} BotAI_State; + +static boolean checkbotkey(const char *field) +{ + return lua_toboolean(gL, -1) && strcmp(lua_tostring(gL, -2), field) == 0; +} + +static void res_botai(Hook_State *hook) +{ + BotAI_State *botai = hook->userdata; + + int k[8]; + + int fields = 0; + + // This turns forward, backward, left, right, jump, and spin into a proper ticcmd for tails. + if (lua_istable(gL, -8)) { + lua_pushnil(gL); // key + while (lua_next(gL, -9)) { +#define CHECK(n, f) (checkbotkey(f) ? (k[(n)-1] = 1) : 0) + if ( + CHECK(1, "forward") || CHECK(2, "backward") || + CHECK(3, "left") || CHECK(4, "right") || + CHECK(5, "strafeleft") || CHECK(6, "straferight") || + CHECK(7, "jump") || CHECK(8, "spin") + ){ + if (8 <= ++fields) + { + lua_pop(gL, 2); // pop key and value + break; + } + } + + lua_pop(gL, 1); // pop value +#undef CHECK + } + } else { + while (fields < 8) { - LUA_PushUserdata(gL, player, META_PLAYER); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; -} - -void LUAh_NetArchiveHook(lua_CFunction archFunc) -{ - hook_p hookp; - int errorhandlerindex; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_NetVars/8] & (1<<(hook_NetVars%8)))) - return; - - // stack: tables - I_Assert(lua_gettop(gL) > 0); - I_Assert(lua_istable(gL, -1)); - - lua_pushcfunction(gL, LUA_GetErrorMessage); - errorhandlerindex = lua_gettop(gL); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // tables becomes an upvalue of archFunc - lua_pushvalue(gL, -3); - lua_pushcclosure(gL, archFunc, 1); - // stack: tables, archFunc - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_NetVars) - continue; - - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -2); // archFunc - if (lua_pcall(gL, 1, 0, errorhandlerindex)) { - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); + k[fields] = lua_toboolean(gL, -8 + fields); + fields++; } } - lua_pop(gL, 3); // Pop archFunc, error handler and hooks table - // stack: tables + B_KeysToTiccmd(botai->tails, botai->cmd, + k[0],k[1],k[2],k[3],k[4],k[5],k[6],k[7]); + + hook->status = true; } -void LUAh_PlayerQuit(player_t *plr, int reason) +int LUA_HookBotAI(mobj_t *sonic, mobj_t *tails, ticcmd_t *cmd) { - hook_p hookp; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_PlayerQuit/8] & (1<<(hook_PlayerQuit%8)))) - return; + const char *skin = ((skin_t *)tails->skin)->name; - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); + Hook_State hook; + BotAI_State botai; - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) + if (prepare_string_hook(&hook, false, STRING_HOOK(BotAI), skin)) { - if (hookp->type != hook_PlayerQuit) - continue; + LUA_PushUserdata(gL, sonic, META_MOBJ); + LUA_PushUserdata(gL, tails, META_MOBJ); - if (lua_gettop(gL) == 2) + botai.tails = tails; + botai.cmd = cmd; + + hook.userdata = &botai; + + call_hooks(&hook, 2, 8, res_botai); + } + + return hook.status; +} + +void LUA_HookLinedefExecute(line_t *line, mobj_t *mo, sector_t *sector) +{ + Hook_State hook; + if (prepare_string_hook + (&hook, 0, STRING_HOOK(LinedefExecute), line->text)) + { + LUA_PushUserdata(gL, line, META_LINE); + LUA_PushUserdata(gL, mo, META_MOBJ); + LUA_PushUserdata(gL, sector, META_SECTOR); + ps_lua_mobjhooks.value.i += call_hooks(&hook, 3, 0, res_none); + } +} + +int LUA_HookPlayerMsg(int source, int target, int flags, char *msg, int mute) +{ + Hook_State hook; + if (prepare_hook(&hook, false, HOOK(PlayerMsg))) + { + LUA_PushUserdata(gL, &players[source], META_PLAYER); // Source player + if (flags & 2 /*HU_CSAY*/) { // csay TODO: make HU_CSAY accessible outside hu_stuff.c + lua_pushinteger(gL, 3); // type + lua_pushnil(gL); // target + } else if (target == -1) { // sayteam + lua_pushinteger(gL, 1); // type + lua_pushnil(gL); // target + } else if (target == 0) { // say + lua_pushinteger(gL, 0); // type + lua_pushnil(gL); // target + } else { // sayto + lua_pushinteger(gL, 2); // type + LUA_PushUserdata(gL, &players[target-1], META_PLAYER); // target + } + lua_pushstring(gL, msg); // msg + if (mute) + lua_pushboolean(gL, true); // the message was supposed to be eaten by spamprotecc. + else + lua_pushboolean(gL, false); + call_hooks(&hook, 4, 1, res_true); + } + return hook.status; +} + +int LUA_HookHurtMsg(player_t *player, mobj_t *inflictor, mobj_t *source) +{ + Hook_State hook; + if (prepare_hook(&hook, false, HOOK(HurtMsg))) + { + LUA_PushUserdata(gL, player, META_PLAYER); + LUA_PushUserdata(gL, inflictor, META_MOBJ); + LUA_PushUserdata(gL, source, META_MOBJ); + call_hooks(&hook, 4, 1, res_true); + } + return hook.status; +} + +void LUA_HookNetArchive(lua_CFunction archFunc) +{ + const hook_t * map = &hookIds[HOOK(NetVars)]; + Hook_State hook; + /* this is a remarkable case where the stack isn't reset */ + if (map->numHooks > 0) + { + // stack: tables + I_Assert(lua_gettop(gL) > 0); + I_Assert(lua_istable(gL, -1)); + + push_error_handler(); + lua_insert(gL, EINDEX); + + // tables becomes an upvalue of archFunc + lua_pushvalue(gL, -1); + lua_pushcclosure(gL, archFunc, 1); + // stack: tables, archFunc + + init_hook_call(&hook, 1, 0, res_none); + call_mapped(&hook, map); + + lua_pop(gL, 1); // pop archFunc + lua_remove(gL, EINDEX); // pop error handler + // stack: tables + } +} + +void LUA_HookPlayerQuit(player_t *plr, int reason) +{ + Hook_State hook; + if (prepare_hook(&hook, 0, HOOK(PlayerQuit))) + { + LUA_PushUserdata(gL, plr, META_PLAYER); // Player that quit + lua_pushinteger(gL, reason); // Reason for quitting + call_hooks(&hook, 2, 0, res_none); + } +} + +boolean hook_cmd_running = false; + +static void update_music_name(struct MusicChange *musicchange) +{ + size_t length; + const char * new = lua_tolstring(gL, -6, &length); + + if (length < 7) + { + strcpy(musicchange->newname, new); + lua_pushvalue(gL, -6);/* may as well keep it for next call */ + } + else + { + memcpy(musicchange->newname, new, 6); + musicchange->newname[6] = '\0'; + lua_pushlstring(gL, new, 6); + } + + lua_replace(gL, -7); +} + +static void res_musicchange(Hook_State *hook) +{ + struct MusicChange *musicchange = hook->userdata; + + // output 1: true, false, or string musicname override + if (lua_isstring(gL, -6)) + update_music_name(musicchange); + else if (lua_isboolean(gL, -6) && lua_toboolean(gL, -6)) + hook->status = true; + + // output 2: mflags override + if (lua_isnumber(gL, -5)) + *musicchange->mflags = lua_tonumber(gL, -5); + // output 3: looping override + if (lua_isboolean(gL, -4)) + *musicchange->looping = lua_toboolean(gL, -4); + // output 4: position override + if (lua_isnumber(gL, -3)) + *musicchange->position = lua_tonumber(gL, -3); + // output 5: prefadems override + if (lua_isnumber(gL, -2)) + *musicchange->prefadems = lua_tonumber(gL, -2); + // output 6: fadeinms override + if (lua_isnumber(gL, -1)) + *musicchange->fadeinms = lua_tonumber(gL, -1); +} + +int LUA_HookMusicChange(const char *oldname, struct MusicChange *param) +{ + const int type = HOOK(MusicChange); + const hook_t * map = &hookIds[type]; + + Hook_State hook; + + int k; + + if (prepare_hook(&hook, false, type)) + { + init_hook_call(&hook, 7, 6, res_musicchange); + hook.userdata = param; + + lua_pushstring(gL, oldname);/* the only constant value */ + lua_pushstring(gL, param->newname);/* semi constant */ + + for (k = 0; k <= map->numHooks; ++k) { - LUA_PushUserdata(gL, plr, META_PLAYER); // Player that quit - lua_pushinteger(gL, reason); // Reason for quitting - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -3); - lua_pushvalue(gL, -3); - if (lua_pcall(gL, 2, 0, 1)) { - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); + get_hook(&hook, map->ids, k); + + lua_pushvalue(gL, -3); + lua_pushvalue(gL, -3); + lua_pushinteger(gL, *param->mflags); + lua_pushboolean(gL, *param->looping); + lua_pushinteger(gL, *param->position); + lua_pushinteger(gL, *param->prefadems); + lua_pushinteger(gL, *param->fadeinms); + + call_single_hook_no_copy(&hook); } + + lua_settop(gL, 0); } - lua_settop(gL, 0); + return hook.status; } -// Hook for music changes -boolean LUAh_MusicChange(const char *oldname, char *newname, UINT16 *mflags, boolean *looping, - UINT32 *position, UINT32 *prefadems, UINT32 *fadeinms) +int LUA_HookKey(INT32 keycode, int hooktype) { - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - - if (!gL || !(hooksAvailable[hook_MusicChange/8] & (1<<(hook_MusicChange%8)))) - return false; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - for (hookp = roothook; hookp; hookp = hookp->next) + Hook_State hook; + if (prepare_hook(&hook, 0, hooktype)) { - if (hookp->type != hook_MusicChange) - continue; - - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushstring(gL, oldname); - lua_pushstring(gL, newname); - lua_pushinteger(gL, *mflags); - lua_pushboolean(gL, *looping); - lua_pushinteger(gL, *position); - lua_pushinteger(gL, *prefadems); - lua_pushinteger(gL, *fadeinms); - if (lua_pcall(gL, 7, 6, 1)) { - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL,-1)); - lua_pop(gL, 1); - continue; - } - - // output 1: true, false, or string musicname override - if (lua_isboolean(gL, -6) && lua_toboolean(gL, -6)) - hooked = true; - else if (lua_isstring(gL, -6)) - strncpy(newname, lua_tostring(gL, -6), 7); - // output 2: mflags override - if (lua_isnumber(gL, -5)) - *mflags = lua_tonumber(gL, -5); - // output 3: looping override - if (lua_isboolean(gL, -4)) - *looping = lua_toboolean(gL, -4); - // output 4: position override - if (lua_isnumber(gL, -3)) - *position = lua_tonumber(gL, -3); - // output 5: prefadems override - if (lua_isnumber(gL, -2)) - *prefadems = lua_tonumber(gL, -2); - // output 6: fadeinms override - if (lua_isnumber(gL, -1)) - *fadeinms = lua_tonumber(gL, -1); - - lua_pop(gL, 6); + lua_pushinteger(gL, keycode); + call_hooks(&hook, 1, 0, res_true); } - - lua_settop(gL, 0); - newname[6] = 0; - return hooked; + return hook.status; } -// Hook for K_SpinPlayer. Determines if yes or no we should get damaged reguardless of circumstances. -UINT8 LUAh_ShouldSpin(player_t *player, mobj_t *inflictor, mobj_t *source) -{ - hook_p hookp; - UINT8 shouldDamage = 0; // 0 = default, 1 = force yes, 2 = force no. - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_ShouldSpin/8] & (1<<(hook_ShouldSpin%8)))) - return 0; - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // We can afford not to check for mobj type because it will always be MT_PLAYER in this case. - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_ShouldSpin) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, player, META_PLAYER); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (!lua_isnil(gL, -1)) - { - if (lua_toboolean(gL, -1)) - shouldDamage = 1; // Force yes - else - shouldDamage = 2; // Force no - } - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return shouldDamage; -} +//// SNED HELP PLS // Hook for K_ExplodePlayer. Determines if yes or no we should get damaged reguardless of circumstances. UINT8 LUAh_ShouldExplode(player_t *player, mobj_t *inflictor, mobj_t *source) { + /* hook_p hookp; UINT8 shouldDamage = 0; // 0 = default, 1 = force yes, 2 = force no. int HOOKSINDEX; @@ -1731,11 +1034,13 @@ UINT8 LUAh_ShouldExplode(player_t *player, mobj_t *inflictor, mobj_t *source) lua_settop(gL, 0); return shouldDamage; + */ } // Hook for K_SquishPlayer. Determines if yes or no we should get damaged reguardless of circumstances. UINT8 LUAh_ShouldSquish(player_t *player, mobj_t *inflictor, mobj_t *source) { + /* hook_p hookp; UINT8 shouldDamage = 0; // 0 = default, 1 = force yes, 2 = force no. int HOOKSINDEX; @@ -1786,11 +1091,13 @@ UINT8 LUAh_ShouldSquish(player_t *player, mobj_t *inflictor, mobj_t *source) lua_settop(gL, 0); return shouldDamage; + */ } // Hook for K_SpinPlayer. This is used when the player has actually been spun out, but before anything has actually been done. This allows Lua to overwrite the behavior or to just perform actions. boolean LUAh_PlayerSpin(player_t *player, mobj_t *inflictor, mobj_t *source) { + /* hook_p hookp; boolean hooked = false; int HOOKSINDEX; @@ -1836,11 +1143,13 @@ boolean LUAh_PlayerSpin(player_t *player, mobj_t *inflictor, mobj_t *source) lua_settop(gL, 0); return hooked; + */ } // Hook for K_SquishPlayer. This is used when the player has actually been spun out, but before anything has actually been done. This allows Lua to overwrite the behavior or to just perform actions. boolean LUAh_PlayerSquish(player_t *player, mobj_t *inflictor, mobj_t *source) { + /* hook_p hookp; boolean hooked = false; int HOOKSINDEX; @@ -1886,11 +1195,13 @@ boolean LUAh_PlayerSquish(player_t *player, mobj_t *inflictor, mobj_t *source) lua_settop(gL, 0); return hooked; + */ } // Hook for K_ExplodePlayer. This is used when the player has actually been spun out, but before anything has actually been done. This allows Lua to overwrite the behavior or to just perform actions. boolean LUAh_PlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source) { + /* hook_p hookp; boolean hooked = false; int HOOKSINDEX; @@ -1936,10 +1247,12 @@ boolean LUAh_PlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source) lua_settop(gL, 0); return hooked; + */ } void LUAh_ServerJoin(void) { + /* hook_p hookp; int HOOKSINDEX; if (!gL || !(hooksAvailable[hook_ServerJoin/8] & (1<<(hook_ServerJoin%8)))) @@ -1970,4 +1283,5 @@ void LUAh_ServerJoin(void) } lua_settop(gL, 0); + */ } diff --git a/src/lua_script.c b/src/lua_script.c index fb16ad169..b03a34d32 100644 --- a/src/lua_script.c +++ b/src/lua_script.c @@ -1659,7 +1659,7 @@ void LUA_Archive(void) } WRITEUINT32(save_p, UINT32_MAX); // end of mobjs marker, replaces mobjnum. - LUAh_NetArchiveHook(NetArchive); // call the NetArchive hook in archive mode + LUA_HookNetArchive(NetArchive); // call the NetArchive hook in archive mode ArchiveTables(); if (gL) @@ -1694,7 +1694,7 @@ void LUA_UnArchive(void) } } while(mobjnum != UINT32_MAX); // repeat until end of mobjs marker. - LUAh_NetArchiveHook(NetUnArchive); // call the NetArchive hook in unarchive mode + LUA_HookNetArchive(NetUnArchive); // call the NetArchive hook in unarchive mode UnArchiveTables(); if (gL) diff --git a/src/lua_script.h b/src/lua_script.h index 9903315c2..6c8a0c09c 100644 --- a/src/lua_script.h +++ b/src/lua_script.h @@ -65,7 +65,7 @@ void Got_Luacmd(UINT8 **cp, INT32 playernum); // lua_consolelib.c void LUA_CVarChanged(const char *name); // lua_consolelib.c int Lua_optoption(lua_State *L, int narg, int def, int list_ref); int Lua_CreateFieldTable(lua_State *L, const char *const lst[]); -void LUAh_NetArchiveHook(lua_CFunction archFunc); +void LUA_HookNetArchive(lua_CFunction archFunc); // Console wrapper void COM_Lua_f(void); diff --git a/src/p_enemy.c b/src/p_enemy.c index caa85e331..fcd5e4630 100644 --- a/src/p_enemy.c +++ b/src/p_enemy.c @@ -2658,7 +2658,7 @@ void A_BossDeath(mobj_t *mo) } bossjustdie: - if (LUAh_BossDeath(mo)) + if (LUA_HookMobj(mo, MOBJ_HOOK(BossDeath))) return; else if (P_MobjWasRemoved(mo)) return; diff --git a/src/p_inter.c b/src/p_inter.c index 29d7e4739..749568e3c 100644 --- a/src/p_inter.c +++ b/src/p_inter.c @@ -284,7 +284,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) if (special->flags & MF_BOSS && special->flags2 & MF2_FRET) return; - if (LUAh_TouchSpecial(special, toucher) || P_MobjWasRemoved(special)) + if (LUA_HookTouchSpecial(special, toucher) || P_MobjWasRemoved(special)) return; if (special->flags & MF_BOSS) @@ -1641,7 +1641,7 @@ void P_KillMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source) target->flags2 &= ~(MF2_SKULLFLY|MF2_NIGHTSPULL); target->health = 0; // This makes it easy to check if something's dead elsewhere. - if (LUAh_MobjDeath(target, inflictor, source) || P_MobjWasRemoved(target)) + if (LUA_HookMobjDeath(target, inflictor, source) || P_MobjWasRemoved(target)) return; // SRB2kart @@ -2397,7 +2397,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da // Everything above here can't be forced. if (!metalrecording) { - UINT8 shouldForce = LUAh_ShouldDamage(target, inflictor, source, damage); + UINT8 shouldForce = LUA_HookShouldDamage(target, inflictor, source, damage); if (P_MobjWasRemoved(target)) return (shouldForce == 1); // mobj was removed if (shouldForce == 1) @@ -2438,7 +2438,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da if (!force && target->fuse) // Invincible return false; - if (LUAh_MobjDamage(target, inflictor, source, damage) || P_MobjWasRemoved(target)) + if (LUA_HookMobjDamage(target, inflictor, source, damage) || P_MobjWasRemoved(target)) return true; if (target->health > 1) @@ -2464,7 +2464,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da if (!force && target->flags2 & MF2_FRET) // Currently flashing from being hit return false; - if (LUAh_MobjDamage(target, inflictor, source, damage) || P_MobjWasRemoved(target)) + if (LUA_HookMobjDamage(target, inflictor, source, damage) || P_MobjWasRemoved(target)) return true; if (target->health > 1) @@ -2472,7 +2472,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da } else if (target->flags & MF_ENEMY) { - if (LUAh_MobjDamage(target, inflictor, source, damage) || P_MobjWasRemoved(target)) + if (LUA_HookMobjDamage(target, inflictor, source, damage) || P_MobjWasRemoved(target)) return true; } @@ -2501,14 +2501,14 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da return false; // Don't run eachother over in special stages and team games and such } - if (LUAh_MobjDamage(target, inflictor, source, damage)) + if (LUA_HookMobjDamage(target, inflictor, source, damage)) return true; P_NiGHTSDamage(target, source); // -5s :( return true; } - if (LUAh_MobjDamage(target, inflictor, source, damage)) + if (LUA_HookMobjDamage(target, inflictor, source, damage)) return true; if (!force && inflictor && (inflictor->flags & MF_FIRE)) diff --git a/src/p_map.c b/src/p_map.c index bd551829d..3d1fc8442 100644 --- a/src/p_map.c +++ b/src/p_map.c @@ -449,7 +449,7 @@ static boolean PIT_CheckThing(mobj_t *thing) } { - UINT8 shouldCollide = LUAh_MobjCollide(thing, tmthing); // checks hook for thing's type + UINT8 shouldCollide = LUA_Hook2Mobj(thing, tmthing, MOBJ_HOOK(MobjCollide)); // checks hook for thing's type if (P_MobjWasRemoved(tmthing) || P_MobjWasRemoved(thing)) return true; // one of them was removed??? if (shouldCollide == 1) @@ -458,7 +458,7 @@ static boolean PIT_CheckThing(mobj_t *thing) return true; // force no collide } { - UINT8 shouldCollide = LUAh_MobjMoveCollide(tmthing, thing); // checks hook for tmthing's type + UINT8 shouldCollide = LUA_Hook2Mobj(tmthing, thing, MOBJ_HOOK(MobjMoveCollide)); // checks hook for tmthing's type if (P_MobjWasRemoved(tmthing) || P_MobjWasRemoved(thing)) return true; // one of them was removed??? if (shouldCollide == 1) diff --git a/src/p_mobj.c b/src/p_mobj.c index 9da7b0235..e29622f22 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -6165,7 +6165,7 @@ void P_MobjThinker(mobj_t *mobj) // Special thinker for scenery objects if (mobj->flags & MF_SCENERY) { - if (LUAh_MobjThinker(mobj)) + if (LUA_HookMobj(mobj, MOBJ_HOOK(MobjThinker))) return; if (P_MobjWasRemoved(mobj)) @@ -6863,7 +6863,7 @@ void P_MobjThinker(mobj_t *mobj) mobj->fuse--; if (!mobj->fuse) { - if (!LUAh_MobjFuse(mobj)) + if (!LUA_HookMobj(mobj, MOBJ_HOOK(MobjFuse))) P_RemoveMobj(mobj); return; } @@ -6878,13 +6878,13 @@ void P_MobjThinker(mobj_t *mobj) // Check for a Lua thinker first if (!mobj->player) { - if (LUAh_MobjThinker(mobj) || P_MobjWasRemoved(mobj)) + if (LUA_HookMobj(mobj, MOBJ_HOOK(MobjThinker)) || P_MobjWasRemoved(mobj)) return; } else if (!mobj->player->spectator) { // You cannot short-circuit the player thinker like you can other thinkers. - LUAh_MobjThinker(mobj); + LUA_HookMobj(mobj, MOBJ_HOOK(MobjThinker)); if (P_MobjWasRemoved(mobj)) return; } @@ -6909,7 +6909,7 @@ void P_MobjThinker(mobj_t *mobj) } else if (mobj->flags & MF_BOSS) { - if (LUAh_BossThinker(mobj)) + if (LUA_HookMobj(mobj, MOBJ_HOOK(BossThinker))) { if (P_MobjWasRemoved(mobj)) return; @@ -8876,7 +8876,7 @@ void P_MobjThinker(mobj_t *mobj) fixed_t x, y, z; mobj_t *flagmo, *newmobj; - if (!LUAh_MobjFuse(mobj) && !P_MobjWasRemoved(mobj)) + if (!LUA_HookMobj(mobj, MOBJ_HOOK(MobjFuse)) && !P_MobjWasRemoved(mobj)) { switch (mobj->type) { @@ -9467,7 +9467,7 @@ mobj_t *P_SpawnMobj(fixed_t x, fixed_t y, fixed_t z, mobjtype_t type) // DANGER! This can cause P_SpawnMobj to return NULL! // Avoid using P_RemoveMobj on the newly created mobj in "MobjSpawn" Lua hooks! - if (LUAh_MobjSpawn(mobj)) + if (LUA_HookMobj(mobj, MOBJ_HOOK(MobjSpawn))) { if (P_MobjWasRemoved(mobj)) return NULL; @@ -10002,7 +10002,7 @@ void P_RemoveMobj(mobj_t *mobj) return; // something already removing this mobj. mobj->thinker.function.acp1 = (actionf_p1)P_RemoveThinkerDelayed; // shh. no recursing. - LUAh_MobjRemoved(mobj); + LUA_HookMobj(mobj, MOBJ_HOOK(MobjRemoved)); mobj->thinker.function.acp1 = (actionf_p1)P_MobjThinker; // needed for P_UnsetThingPosition, etc. to work. // Rings only, please! diff --git a/src/p_setup.c b/src/p_setup.c index 93207a3c1..10639e13d 100644 --- a/src/p_setup.c +++ b/src/p_setup.c @@ -63,7 +63,7 @@ #include "md5.h" // map MD5 -// for LUAh_MapLoad +// for MapLoad hook #include "lua_script.h" #include "lua_hook.h" @@ -3017,7 +3017,7 @@ boolean P_SetupLevel(boolean skipprecip, boolean reloadinggamestate) } P_PreTicker(2); if (!reloadinggamestate) - LUAh_MapLoad(); + LUA_HookInt(gamemap, HOOK(MapLoad)); } if (rendermode != render_none && !reloadinggamestate) diff --git a/src/p_spec.c b/src/p_spec.c index 5f9ef78a6..cda5f9e63 100644 --- a/src/p_spec.c +++ b/src/p_spec.c @@ -35,7 +35,7 @@ #include "hu_stuff.h" #include "m_misc.h" #include "m_cond.h" //unlock triggers -#include "lua_hook.h" // LUAh_LinedefExecute +#include "lua_hook.h" // LUA_HookLinedefExecute #include "k_kart.h" // SRB2kart #include "console.h" // CON_LogMessage @@ -2856,7 +2856,7 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) case 443: // Calls a named Lua function if (line->text) - LUAh_LinedefExecute(line, mo, callsec); + LUA_HookLinedefExecute(line, mo, callsec); else CONS_Alert(CONS_WARNING, "Linedef %s is missing the hook name of the Lua function to call! (This should be given in the front texture fields)\n", sizeu1(line-lines)); break; diff --git a/src/p_tick.c b/src/p_tick.c index d6243fde9..49d51774e 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -528,7 +528,7 @@ void P_Ticker(boolean run) ps_checkposition_calls.value.i = 0; PS_START_TIMING(ps_lua_prethinkframe_time); - LUAh_PreThinkFrame(); + LUA_HOOK(PreThinkFrame); PS_STOP_TIMING(ps_lua_prethinkframe_time); PS_START_TIMING(ps_playerthink_time); @@ -564,7 +564,7 @@ void P_Ticker(boolean run) } PS_START_TIMING(ps_lua_thinkframe_time); - LUAh_ThinkFrame(); + LUA_HookThinkFrame(); PS_STOP_TIMING(ps_lua_thinkframe_time); } @@ -668,7 +668,7 @@ void P_Ticker(boolean run) D_MapChange(gamemap, gametype, encoremode, true, 0, false, false); PS_START_TIMING(ps_lua_postthinkframe_time); - LUAh_PostThinkFrame(); + LUA_HOOK(PostThinkFrame); PS_STOP_TIMING(ps_lua_postthinkframe_time); } @@ -723,7 +723,7 @@ void P_PreTicker(INT32 frames) R_UpdateMobjInterpolators(); - LUAh_PreThinkFrame(); + LUA_HOOK(PreThinkFrame); for (i = 0; i < MAXPLAYERS; i++) if (playeringame[i] && players[i].mo && !P_MobjWasRemoved(players[i].mo)) @@ -752,7 +752,7 @@ void P_PreTicker(INT32 frames) if (playeringame[i] && players[i].mo && !P_MobjWasRemoved(players[i].mo)) P_PlayerAfterThink(&players[i]); - LUAh_ThinkFrame(); + LUA_HookThinkFrame(); P_RunOverlays(); P_RunShadows(); @@ -760,7 +760,7 @@ void P_PreTicker(INT32 frames) P_UpdateSpecials(); P_RespawnSpecials(); - LUAh_PostThinkFrame(); + LUA_HOOK(PostThinkFrame); R_UpdateLevelInterpolators(); R_UpdateViewInterpolation(); diff --git a/src/p_user.c b/src/p_user.c index f8e4de294..027eb5632 100644 --- a/src/p_user.c +++ b/src/p_user.c @@ -4368,7 +4368,7 @@ void P_PlayerThink(player_t *player) } if (player->playerstate == PST_REBORN) { - LUAh_PlayerThink(player); + LUA_HookPlayer(player, HOOK(PlayerThink)); return; } } @@ -4475,7 +4475,7 @@ void P_PlayerThink(player_t *player) if (player->playerstate == PST_DEAD) { - LUAh_PlayerThink(player); + LUA_HookPlayer(player, HOOK(PlayerThink)); return; } } @@ -4541,7 +4541,7 @@ void P_PlayerThink(player_t *player) else player->mo->flags2 &= ~MF2_SHADOW; P_DeathThink(player); - LUAh_PlayerThink(player); + LUA_HookPlayer(player, HOOK(PlayerThink)); return; } @@ -4713,7 +4713,7 @@ void P_PlayerThink(player_t *player) if (!player->mo) { - LUAh_PlayerThink(player); + LUA_HookPlayer(player, HOOK(PlayerThink)); return; // P_MovePlayer removed player->mo. } @@ -4896,7 +4896,7 @@ void P_PlayerThink(player_t *player) if (rendermode != render_none) DoABarrelRoll(player); - LUAh_PlayerThink(player); + LUA_HookPlayer(player, HOOK(PlayerThink)); } // diff --git a/src/r_patch.c b/src/r_patch.c index 37e7a2321..44dd29725 100644 --- a/src/r_patch.c +++ b/src/r_patch.c @@ -14,6 +14,7 @@ #include "byteptr.h" #include "dehacked.h" +#include "doomdef.h" #include "i_video.h" #include "r_data.h" #include "r_draw.h" diff --git a/src/s_sound.c b/src/s_sound.c index 868bccc77..7824051c4 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -1966,6 +1966,15 @@ void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32 { char newmusic[7] = {0}; + struct MusicChange hook_param = { + newmusic, + &mflags, + &looping, + &position, + &prefadems, + &fadeinms + }; + if (S_MusicDisabled() || demo.rewinding // Don't mess with music while rewinding! || demo.title) // SRB2Kart: Demos don't interrupt title screen music @@ -1975,7 +1984,7 @@ void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32 S_CheckEventMus(newmusic); - if (LUAh_MusicChange(music_name, newmusic, &mflags, &looping, &position, &prefadems, &fadeinms)) + if (LUA_HookMusicChange(music_name, &hook_param)) return; // No Music (empty string) diff --git a/src/s_sound.h b/src/s_sound.h index 887cdd878..9756028d3 100644 --- a/src/s_sound.h +++ b/src/s_sound.h @@ -228,6 +228,16 @@ UINT32 S_GetMusicPosition(void); // Music Playback // +/* this is for the sake of the hook */ +struct MusicChange { + char * newname; + UINT16 * mflags; + boolean * looping; + UINT32 * position; + UINT32 * prefadems; + UINT32 * fadeinms; +}; + // Start music track, arbitrary, given its name, and set whether looping // note: music flags 12 bits for tracknum (gme, other formats with more than one track) // 13-15 aren't used yet diff --git a/src/y_inter.c b/src/y_inter.c index 12fc705ad..456b87168 100644 --- a/src/y_inter.c +++ b/src/y_inter.c @@ -642,7 +642,8 @@ void Y_Ticker(void) if (paused || P_AutoPause()) return; - LUAh_IntermissionThinker(); + LUA_HookBool(HOOK(IntermissionThinker)); + intertic++; @@ -1280,7 +1281,7 @@ void Y_VoteTicker(void) if (paused || P_AutoPause() || !voteclient.loaded) return; - LUAh_VoteThinker(); + LUA_HOOK(VoteThinker); votetic++; -- 2.54.0 From 14ec6e067411c0d32f7bae34c1d75a91f6319521 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 18:35:50 +0100 Subject: [PATCH 036/143] serverjoin hook --- src/d_clisrv.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 5b1997e90..d4b0347ef 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -4474,8 +4474,8 @@ static void Got_AddPlayer(UINT8 **p, INT32 playernum) LUA_HookInt(newplayernum, HOOK(PlayerJoin)); - //if (newplayernum == consoleplayer) - //LUA_ServerJoin(); + if (newplayernum == consoleplayer) + LUA_HookInt(newplayernum, HOOK(ServerJoin)); #ifdef HAVE_DISCORDRPC DRPC_UpdatePresence(); -- 2.54.0 From 5598526f521f5f2f3329e7dbe916aefe75a5995a Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 18:39:28 +0100 Subject: [PATCH 037/143] delet serverjoin stuff i forgor and add old should spin stuff --- src/lua_hooklib.c | 93 +++++++++++++++++++++++++++++------------------ 1 file changed, 57 insertions(+), 36 deletions(-) diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 18466bc30..fcc5662ff 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -980,6 +980,63 @@ int LUA_HookKey(INT32 keycode, int hooktype) //// SNED HELP PLS + +UINT8 LUAh_ShouldSpin(player_t *player, mobj_t *inflictor, mobj_t *source) +{ + /* + hook_p hookp; + UINT8 shouldDamage = 0; // 0 = default, 1 = force yes, 2 = force no. + int HOOKSINDEX; + if (!gL || !(hooksAvailable[hook_ShouldSpin/8] & (1<<(hook_ShouldSpin%8)))) + return 0; + + lua_settop(gL, 0); + lua_pushcfunction(gL, LUA_GetErrorMessage); + + lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); + HOOKSINDEX = lua_gettop(gL); + I_Assert(lua_istable(L, HOOKSINDEX)); + + // We can afford not to check for mobj type because it will always be MT_PLAYER in this case. + + for (hookp = roothook; hookp; hookp = hookp->next) + { + if (hookp->type != hook_ShouldSpin) + continue; + + ps_lua_mobjhooks.value.i++; + if (lua_gettop(gL) == 2) + { + LUA_PushUserdata(gL, player, META_PLAYER); + LUA_PushUserdata(gL, inflictor, META_MOBJ); + LUA_PushUserdata(gL, source, META_MOBJ); + } + lua_rawgeti(gL, HOOKSINDEX, hookp->id); + lua_pushvalue(gL, -4); + lua_pushvalue(gL, -4); + lua_pushvalue(gL, -4); + if (lua_pcall(gL, 3, 1, 1)) { + if (!hookp->error || cv_debug & DBG_LUA) + CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); + lua_pop(gL, 1); + hookp->error = true; + continue; + } + if (!lua_isnil(gL, -1)) + { + if (lua_toboolean(gL, -1)) + shouldDamage = 1; // Force yes + else + shouldDamage = 2; // Force no + } + lua_pop(gL, 1); + } + + lua_settop(gL, 0); + return shouldDamage; + */ +} + // Hook for K_ExplodePlayer. Determines if yes or no we should get damaged reguardless of circumstances. UINT8 LUAh_ShouldExplode(player_t *player, mobj_t *inflictor, mobj_t *source) { @@ -1249,39 +1306,3 @@ boolean LUAh_PlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source) return hooked; */ } - -void LUAh_ServerJoin(void) -{ - /* - hook_p hookp; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_ServerJoin/8] & (1<<(hook_ServerJoin%8)))) - return; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // We can afford not to look for target->type because it will always be MT_PLAYER. - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_ServerJoin) - continue; - - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - if (lua_pcall(gL, 0, 0, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - } - - lua_settop(gL, 0); - */ -} -- 2.54.0 From 66518ced7538d5769e53a408a63642df86d56a94 Mon Sep 17 00:00:00 2001 From: Indev Date: Thu, 21 Nov 2024 20:53:28 +0300 Subject: [PATCH 038/143] Add Should- and Player- Spin/Explode/Squish, and ServerJoin hooks into new hook system --- src/d_clisrv.c | 2 +- src/lua_hooklib.c | 325 ++++------------------------------------------ 2 files changed, 26 insertions(+), 301 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index d4b0347ef..2b7e25fd3 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -4475,7 +4475,7 @@ static void Got_AddPlayer(UINT8 **p, INT32 playernum) LUA_HookInt(newplayernum, HOOK(PlayerJoin)); if (newplayernum == consoleplayer) - LUA_HookInt(newplayernum, HOOK(ServerJoin)); + LUA_HookVoid(HOOK(ServerJoin)); #ifdef HAVE_DISCORDRPC DRPC_UpdatePresence(); diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index fcc5662ff..05be84b82 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -977,332 +977,57 @@ int LUA_HookKey(INT32 keycode, int hooktype) return hook.status; } +static int kartdamage_hook +( + player_t *player, + mobj_t *inflictor, + mobj_t *source, + int hook_type, + Hook_Callback results_handler +){ + Hook_State hook; + if (prepare_hook(&hook, 0, hook_type)) + { + LUA_PushUserdata(gL, player, META_PLAYER); + LUA_PushUserdata(gL, inflictor, META_MOBJ); + LUA_PushUserdata(gL, source, META_MOBJ); + call_hooks(&hook, 3, 1, results_handler); + } + return hook.status; +} -//// SNED HELP PLS - - +// Hook for K_SpinPlayer. Determines if yes or no we should get damaged reguardless of circumstances. UINT8 LUAh_ShouldSpin(player_t *player, mobj_t *inflictor, mobj_t *source) { - /* - hook_p hookp; - UINT8 shouldDamage = 0; // 0 = default, 1 = force yes, 2 = force no. - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_ShouldSpin/8] & (1<<(hook_ShouldSpin%8)))) - return 0; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // We can afford not to check for mobj type because it will always be MT_PLAYER in this case. - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_ShouldSpin) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, player, META_PLAYER); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (!lua_isnil(gL, -1)) - { - if (lua_toboolean(gL, -1)) - shouldDamage = 1; // Force yes - else - shouldDamage = 2; // Force no - } - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return shouldDamage; - */ + return kartdamage_hook(player, inflictor, source, HOOK(ShouldSpin), res_force); } // Hook for K_ExplodePlayer. Determines if yes or no we should get damaged reguardless of circumstances. UINT8 LUAh_ShouldExplode(player_t *player, mobj_t *inflictor, mobj_t *source) { - /* - hook_p hookp; - UINT8 shouldDamage = 0; // 0 = default, 1 = force yes, 2 = force no. - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_ShouldExplode/8] & (1<<(hook_ShouldExplode%8)))) - return 0; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // We can afford not to check for mobj type because it will always be MT_PLAYER in this case. - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_ShouldExplode) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, player, META_PLAYER); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (!lua_isnil(gL, -1)) - { - if (lua_toboolean(gL, -1)) - shouldDamage = 1; // Force yes - else - shouldDamage = 2; // Force no - } - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return shouldDamage; - */ + return kartdamage_hook(player, inflictor, source, HOOK(ShouldExplode), res_force); } // Hook for K_SquishPlayer. Determines if yes or no we should get damaged reguardless of circumstances. UINT8 LUAh_ShouldSquish(player_t *player, mobj_t *inflictor, mobj_t *source) { - /* - hook_p hookp; - UINT8 shouldDamage = 0; // 0 = default, 1 = force yes, 2 = force no. - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_ShouldSquish/8] & (1<<(hook_ShouldSquish%8)))) - return 0; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // We can afford not to check for mobj type because it will always be MT_PLAYER in this case. - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_ShouldSquish) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, player, META_PLAYER); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (!lua_isnil(gL, -1)) - { - if (lua_toboolean(gL, -1)) - shouldDamage = 1; // Force yes - else - shouldDamage = 2; // Force no - } - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return shouldDamage; - */ + return kartdamage_hook(player, inflictor, source, HOOK(ShouldSquish), res_force); } // Hook for K_SpinPlayer. This is used when the player has actually been spun out, but before anything has actually been done. This allows Lua to overwrite the behavior or to just perform actions. boolean LUAh_PlayerSpin(player_t *player, mobj_t *inflictor, mobj_t *source) { - /* - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_PlayerSpin/8] & (1<<(hook_PlayerSpin%8)))) - return 0; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // We can afford not to look for target->type because it will always be MT_PLAYER. - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_PlayerSpin) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, player, META_PLAYER); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; - */ + return kartdamage_hook(player, inflictor, source, HOOK(PlayerSpin), res_true); } // Hook for K_SquishPlayer. This is used when the player has actually been spun out, but before anything has actually been done. This allows Lua to overwrite the behavior or to just perform actions. boolean LUAh_PlayerSquish(player_t *player, mobj_t *inflictor, mobj_t *source) { - /* - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_PlayerSquish/8] & (1<<(hook_PlayerSquish%8)))) - return 0; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // We can afford not to look for target->type because it will always be MT_PLAYER. - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_PlayerSquish) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, player, META_PLAYER); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; - */ + return kartdamage_hook(player, inflictor, source, HOOK(PlayerSquish), res_true); } // Hook for K_ExplodePlayer. This is used when the player has actually been spun out, but before anything has actually been done. This allows Lua to overwrite the behavior or to just perform actions. boolean LUAh_PlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source) { - /* - hook_p hookp; - boolean hooked = false; - int HOOKSINDEX; - if (!gL || !(hooksAvailable[hook_PlayerExplode/8] & (1<<(hook_PlayerExplode%8)))) - return 0; - - lua_settop(gL, 0); - lua_pushcfunction(gL, LUA_GetErrorMessage); - - lua_getfield(gL, LUA_REGISTRYINDEX, "hooks"); - HOOKSINDEX = lua_gettop(gL); - I_Assert(lua_istable(L, HOOKSINDEX)); - - // We can afford not to look for target->type because it will always be MT_PLAYER. - - for (hookp = roothook; hookp; hookp = hookp->next) - { - if (hookp->type != hook_PlayerExplode) - continue; - - ps_lua_mobjhooks.value.i++; - if (lua_gettop(gL) == 2) - { - LUA_PushUserdata(gL, player, META_PLAYER); - LUA_PushUserdata(gL, inflictor, META_MOBJ); - LUA_PushUserdata(gL, source, META_MOBJ); - } - lua_rawgeti(gL, HOOKSINDEX, hookp->id); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - lua_pushvalue(gL, -4); - if (lua_pcall(gL, 3, 1, 1)) { - if (!hookp->error || cv_debug & DBG_LUA) - CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1)); - lua_pop(gL, 1); - hookp->error = true; - continue; - } - if (lua_toboolean(gL, -1)) - hooked = true; - lua_pop(gL, 1); - } - - lua_settop(gL, 0); - return hooked; - */ + return kartdamage_hook(player, inflictor, source, HOOK(PlayerExplode), res_true); } -- 2.54.0 From 3db21bf77810df9b13a523ad9c2ef6038f17634a Mon Sep 17 00:00:00 2001 From: Indev Date: Thu, 21 Nov 2024 21:01:00 +0300 Subject: [PATCH 039/143] Fix warning regarding MusicChange hook --- src/lua_hook.h | 1 + 1 file changed, 1 insertion(+) diff --git a/src/lua_hook.h b/src/lua_hook.h index a54a09f00..697c6726b 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -12,6 +12,7 @@ #include "r_defs.h" #include "d_player.h" +#include "s_sound.h" /* * Do you know what an 'X Macro' is? Such a macro is called over each element of -- 2.54.0 From a4080980ece7c5038a70e2209ca1d3848d02e2ae Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:03:39 +0100 Subject: [PATCH 040/143] make intermissionthinker use LUA_HookVoid comment out hookbool since unused --- src/lua_hook.h | 1 - src/lua_hooklib.c | 5 ++--- src/y_inter.c | 3 +-- 3 files changed, 3 insertions(+), 6 deletions(-) diff --git a/src/lua_hook.h b/src/lua_hook.h index 697c6726b..3ca4b8f35 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -99,7 +99,6 @@ int LUA_HookMobj(mobj_t *, int hook); int LUA_Hook2Mobj(mobj_t *, mobj_t *, int hook); void LUA_HookInt(INT32 integer, int hook); //void LUA_HookBool(boolean value, int hook); -void LUA_HookBool(int hook); int LUA_HookPlayer(player_t *, int hook); int LUA_HookTiccmd(player_t *, ticcmd_t *, int hook); diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 05be84b82..2209803e6 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -568,8 +568,7 @@ void LUA_HookInt(INT32 number, int hook_type) } } -//void LUA_HookBool(boolean value, int hook_type) -void LUA_HookBool(int hook_type) +/*void LUA_HookBool(boolean value, int hook_type) { Hook_State hook; if (prepare_hook(&hook, 0, hook_type)) @@ -577,7 +576,7 @@ void LUA_HookBool(int hook_type) //lua_pushboolean(gL, value); call_hooks(&hook, 1, 0, res_none); } -} +}*/ int LUA_HookPlayer(player_t *player, int hook_type) { diff --git a/src/y_inter.c b/src/y_inter.c index 456b87168..be3a6204b 100644 --- a/src/y_inter.c +++ b/src/y_inter.c @@ -642,8 +642,7 @@ void Y_Ticker(void) if (paused || P_AutoPause()) return; - LUA_HookBool(HOOK(IntermissionThinker)); - + LUA_HookVoid(HOOK(IntermissionThinker)); intertic++; -- 2.54.0 From f26717954eddcf8407cc796d508fe3252cb00fc0 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:10:49 +0100 Subject: [PATCH 041/143] change those to fit rest of style --- src/k_kart.c | 12 ++++++------ src/lua_hook.h | 20 +++++++++----------- src/lua_hooklib.c | 34 +++++++++++++++++----------------- 3 files changed, 32 insertions(+), 34 deletions(-) diff --git a/src/k_kart.c b/src/k_kart.c index 14f9cc580..2950dcccb 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -2312,7 +2312,7 @@ void K_SpinPlayer(player_t *player, mobj_t *source, INT32 type, mobj_t *inflicto UINT8 scoremultiply = 1; // PS: Inflictor is unused for all purposes here and is actually only ever relevant to Lua. It may be nil too. boolean force = false; // Used to check if Lua ShouldSpin should get us damaged reguardless of flashtics or heck knows what. - UINT8 shouldForce = LUAh_ShouldSpin(player, inflictor, source); + UINT8 shouldForce = LUA_HookShouldSpin(player, inflictor, source); if (P_MobjWasRemoved(player->mo)) return; // mobj was removed (in theory that shouldn't happen) @@ -2345,7 +2345,7 @@ void K_SpinPlayer(player_t *player, mobj_t *source, INT32 type, mobj_t *inflicto } } - if (LUAh_PlayerSpin(player, inflictor, source)) // Let Lua do its thing or overwrite if it wants to. Make sure to let any possible instashield happen because we didn't get "damaged" in this case. + if (LUA_HookPlayerSpin(player, inflictor, source)) // Let Lua do its thing or overwrite if it wants to. Make sure to let any possible instashield happen because we didn't get "damaged" in this case. return; if (source && source != player->mo && source->player) @@ -2453,7 +2453,7 @@ void K_SquishPlayer(player_t *player, mobj_t *source, mobj_t *inflictor) UINT8 scoremultiply = 1; // PS: Inflictor is unused for all purposes here and is actually only ever relevant to Lua. It may be nil too. boolean force = false; // Used to check if Lua ShouldSquish should get us damaged reguardless of flashtics or heck knows what. - UINT8 shouldForce = LUAh_ShouldSquish(player, inflictor, source); + UINT8 shouldForce = LUA_HookShouldSquish(player, inflictor, source); if (P_MobjWasRemoved(player->mo)) return; // mobj was removed (in theory that shouldn't happen) if (shouldForce == 1) @@ -2483,7 +2483,7 @@ void K_SquishPlayer(player_t *player, mobj_t *source, mobj_t *inflictor) } } - if (LUAh_PlayerSquish(player, inflictor, source)) // Let Lua do its thing or overwrite if it wants to. Make sure to let any possible instashield happen because we didn't get "damaged" in this case. + if (LUA_HookPlayerSquish(player, inflictor, source)) // Let Lua do its thing or overwrite if it wants to. Make sure to let any possible instashield happen because we didn't get "damaged" in this case. return; player->kartstuff[k_sneakertimer] = 0; @@ -2564,7 +2564,7 @@ void K_ExplodePlayer(player_t *player, mobj_t *source, mobj_t *inflictor) // A b fixed_t upgoer; UINT8 scoremultiply = 1; boolean force = false; // Used to check if Lua ShouldExplode should get us damaged reguardless of flashtics or heck knows what. - UINT8 shouldForce = LUAh_ShouldExplode(player, inflictor, source); + UINT8 shouldForce = LUA_HookShouldExplode(player, inflictor, source); if (P_MobjWasRemoved(player->mo)) return; // mobj was removed (in theory that shouldn't happen) @@ -2597,7 +2597,7 @@ void K_ExplodePlayer(player_t *player, mobj_t *source, mobj_t *inflictor) // A b } } - if (LUAh_PlayerExplode(player, inflictor, source)) // Same thing. Also make sure to let Instashield happen blah blah + if (LUA_HookPlayerExplode(player, inflictor, source)) // Same thing. Also make sure to let Instashield happen blah blah return; if (source && source != player->mo && source->player) diff --git a/src/lua_hook.h b/src/lua_hook.h index 3ca4b8f35..4a322d504 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -115,15 +115,13 @@ int LUA_HookPlayerCanDamage(player_t *, mobj_t *); void LUA_HookPlayerQuit(player_t *, int); int LUA_HookPlayerCmd(player_t *, ticcmd_t *); int LUA_HookMusicChange(const char *oldname, struct MusicChange *); + +int LUA_HookShouldSpin(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Should player be spun out? +int LUA_HookShouldExplode(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Should player be exploded? +int LUA_HookShouldSquish(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Should player be squished? + +boolean LUA_HookPlayerSpin(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_SpinPlayer. Allows Lua to execute code and/or overwrite its behavior. +boolean LUA_HookPlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_ExplodePlayer. Allows Lua to execute code and/or overwrite its behavior. +boolean LUA_HookPlayerSquish(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_SquishPlayer. Allows Lua to execute code and/or overwrite its behavior. + int LUA_HookKey(INT32 keycode, int hooktype); // Hooks for key events - - -// No clue what to do about these - -UINT8 LUAh_ShouldSpin(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Should player be spun out? -UINT8 LUAh_ShouldExplode(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Should player be exploded? -UINT8 LUAh_ShouldSquish(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Should player be squished? - -boolean LUAh_PlayerSpin(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_SpinPlayer. Allows Lua to execute code and/or overwrite its behavior. -boolean LUAh_PlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_ExplodePlayer. Allows Lua to execute code and/or overwrite its behavior. -boolean LUAh_PlayerSquish(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_SquishPlayer. Allows Lua to execute code and/or overwrite its behavior. diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 2209803e6..4e83e23ee 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -965,17 +965,6 @@ int LUA_HookMusicChange(const char *oldname, struct MusicChange *param) return hook.status; } -int LUA_HookKey(INT32 keycode, int hooktype) -{ - Hook_State hook; - if (prepare_hook(&hook, 0, hooktype)) - { - lua_pushinteger(gL, keycode); - call_hooks(&hook, 1, 0, res_true); - } - return hook.status; -} - static int kartdamage_hook ( player_t *player, @@ -996,37 +985,48 @@ static int kartdamage_hook } // Hook for K_SpinPlayer. Determines if yes or no we should get damaged reguardless of circumstances. -UINT8 LUAh_ShouldSpin(player_t *player, mobj_t *inflictor, mobj_t *source) +int LUA_HookShouldSpin(player_t *player, mobj_t *inflictor, mobj_t *source) { return kartdamage_hook(player, inflictor, source, HOOK(ShouldSpin), res_force); } // Hook for K_ExplodePlayer. Determines if yes or no we should get damaged reguardless of circumstances. -UINT8 LUAh_ShouldExplode(player_t *player, mobj_t *inflictor, mobj_t *source) +int LUA_HookShouldExplode(player_t *player, mobj_t *inflictor, mobj_t *source) { return kartdamage_hook(player, inflictor, source, HOOK(ShouldExplode), res_force); } // Hook for K_SquishPlayer. Determines if yes or no we should get damaged reguardless of circumstances. -UINT8 LUAh_ShouldSquish(player_t *player, mobj_t *inflictor, mobj_t *source) +int LUA_HookShouldSquish(player_t *player, mobj_t *inflictor, mobj_t *source) { return kartdamage_hook(player, inflictor, source, HOOK(ShouldSquish), res_force); } // Hook for K_SpinPlayer. This is used when the player has actually been spun out, but before anything has actually been done. This allows Lua to overwrite the behavior or to just perform actions. -boolean LUAh_PlayerSpin(player_t *player, mobj_t *inflictor, mobj_t *source) +boolean LUA_HookPlayerSpin(player_t *player, mobj_t *inflictor, mobj_t *source) { return kartdamage_hook(player, inflictor, source, HOOK(PlayerSpin), res_true); } // Hook for K_SquishPlayer. This is used when the player has actually been spun out, but before anything has actually been done. This allows Lua to overwrite the behavior or to just perform actions. -boolean LUAh_PlayerSquish(player_t *player, mobj_t *inflictor, mobj_t *source) +boolean LUA_HookPlayerSquish(player_t *player, mobj_t *inflictor, mobj_t *source) { return kartdamage_hook(player, inflictor, source, HOOK(PlayerSquish), res_true); } // Hook for K_ExplodePlayer. This is used when the player has actually been spun out, but before anything has actually been done. This allows Lua to overwrite the behavior or to just perform actions. -boolean LUAh_PlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source) +boolean LUA_HookPlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source) { return kartdamage_hook(player, inflictor, source, HOOK(PlayerExplode), res_true); } + +int LUA_HookKey(INT32 keycode, int hooktype) +{ + Hook_State hook; + if (prepare_hook(&hook, 0, hooktype)) + { + lua_pushinteger(gL, keycode); + call_hooks(&hook, 1, 0, res_true); + } + return hook.status; +} -- 2.54.0 From ecae607b5987981608da6663f9c7ea16ee36a7c7 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:17:26 +0100 Subject: [PATCH 042/143] this is unused for now --- src/lua_hooklib.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 4e83e23ee..6edbe9488 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -507,11 +507,11 @@ static void res_true(Hook_State *hook) hook->status = true; } -static void res_false(Hook_State *hook) +/*static void res_false(Hook_State *hook) { if (!lua_isnil(gL, -1) && !lua_toboolean(gL, -1)) hook->status = false; -} +}*/ static void res_force(Hook_State *hook) { -- 2.54.0 From da06c84aa4ccd332a9ceef9f4d036ad2c968b521 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:17:36 +0100 Subject: [PATCH 043/143] we dont have key event hooks --- src/lua_hook.h | 2 -- src/lua_hooklib.c | 11 ----------- 2 files changed, 13 deletions(-) diff --git a/src/lua_hook.h b/src/lua_hook.h index 4a322d504..9e91c82b9 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -123,5 +123,3 @@ int LUA_HookShouldSquish(player_t *player, mobj_t *inflictor, mobj_t *source); / boolean LUA_HookPlayerSpin(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_SpinPlayer. Allows Lua to execute code and/or overwrite its behavior. boolean LUA_HookPlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_ExplodePlayer. Allows Lua to execute code and/or overwrite its behavior. boolean LUA_HookPlayerSquish(player_t *player, mobj_t *inflictor, mobj_t *source); // SRB2KART: Hook for K_SquishPlayer. Allows Lua to execute code and/or overwrite its behavior. - -int LUA_HookKey(INT32 keycode, int hooktype); // Hooks for key events diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 6edbe9488..75533142b 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -1019,14 +1019,3 @@ boolean LUA_HookPlayerExplode(player_t *player, mobj_t *inflictor, mobj_t *sourc { return kartdamage_hook(player, inflictor, source, HOOK(PlayerExplode), res_true); } - -int LUA_HookKey(INT32 keycode, int hooktype) -{ - Hook_State hook; - if (prepare_hook(&hook, 0, hooktype)) - { - lua_pushinteger(gL, keycode); - call_hooks(&hook, 1, 0, res_true); - } - return hook.status; -} -- 2.54.0 From 06d0f5b95b277ba756f90a09e85144dc20ab7090 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:37:30 +0100 Subject: [PATCH 044/143] Automatically count hook values --- src/lua_hooklib.c | 71 ++++++++++++++++++++++++++--------------------- 1 file changed, 39 insertions(+), 32 deletions(-) diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 75533142b..8bf506236 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -279,11 +279,16 @@ static void push_string(void) lua_pushvalue(gL, SINDEX); } -static boolean start_hook_stack(void) +static boolean begin_hook_values(Hook_State *hook) +{ + hook->top = lua_gettop(gL); + return true; +} + +static void start_hook_stack(void) { lua_settop(gL, 0); push_error_handler(); - return true; } static boolean init_hook_type @@ -299,10 +304,11 @@ static boolean init_hook_type if (nonzero) { + start_hook_stack(); hook->hook_type = hook_type; hook->mobj_type = mobj_type; hook->string = string; - return start_hook_stack(); + return begin_hook_values(hook); } else return false; @@ -343,7 +349,7 @@ static boolean prepare_string_hook stringHooks[hook_type].ref)) { lua_pushstring(gL, string); - return true; + return begin_hook_values(hook); } else return false; @@ -352,12 +358,12 @@ static boolean prepare_string_hook static void init_hook_call ( Hook_State * hook, - int values, int results, Hook_Callback results_handler ){ - hook->top = lua_gettop(gL); - hook->values = values; + const int top = lua_gettop(gL); + hook->values = (top - hook->top); + hook->top = top; hook->results = results; hook->results_handler = results_handler; } @@ -467,13 +473,12 @@ static int call_mobj_type_hooks(Hook_State *hook, mobjtype_t mobj_type) static int call_hooks ( Hook_State * hook, - int values, int results, Hook_Callback results_handler ){ int calls = 0; - init_hook_call(hook, values, results, results_handler); + init_hook_call(hook, results, results_handler); if (hook->string) { @@ -534,7 +539,7 @@ int LUA_HookMobj(mobj_t *mobj, int hook_type) if (prepare_mobj_hook(&hook, false, hook_type, mobj->type)) { LUA_PushUserdata(gL, mobj, META_MOBJ); - call_hooks(&hook, 1, 1, res_true); + call_hooks(&hook, 1, res_true); } return hook.status; } @@ -546,7 +551,7 @@ int LUA_Hook2Mobj(mobj_t *t1, mobj_t *t2, int hook_type) { LUA_PushUserdata(gL, t1, META_MOBJ); LUA_PushUserdata(gL, t2, META_MOBJ); - call_hooks(&hook, 2, 1, res_force); + call_hooks(&hook, 1, res_force); } return hook.status; } @@ -555,7 +560,7 @@ void LUA_HookVoid(int type) { Hook_State hook; if (prepare_hook(&hook, 0, type)) - call_hooks(&hook, 0, 0, res_none); + call_hooks(&hook, 0, res_none); } void LUA_HookInt(INT32 number, int hook_type) @@ -564,7 +569,7 @@ void LUA_HookInt(INT32 number, int hook_type) if (prepare_hook(&hook, 0, hook_type)) { lua_pushinteger(gL, number); - call_hooks(&hook, 1, 0, res_none); + call_hooks(&hook, 0, res_none); } } @@ -574,7 +579,7 @@ void LUA_HookInt(INT32 number, int hook_type) if (prepare_hook(&hook, 0, hook_type)) { //lua_pushboolean(gL, value); - call_hooks(&hook, 1, 0, res_none); + call_hooks(&hook, 0, res_none); } }*/ @@ -584,7 +589,7 @@ int LUA_HookPlayer(player_t *player, int hook_type) if (prepare_hook(&hook, false, hook_type)) { LUA_PushUserdata(gL, player, META_PLAYER); - call_hooks(&hook, 1, 1, res_true); + call_hooks(&hook, 1, res_true); } return hook.status; } @@ -600,7 +605,7 @@ int LUA_HookTiccmd(player_t *player, ticcmd_t *cmd, int hook_type) if (hook_type == HOOK(PlayerCmd)) hook_cmd_running = true; - call_hooks(&hook, 2, 1, res_true); + call_hooks(&hook, 1, res_true); if (hook_type == HOOK(PlayerCmd)) hook_cmd_running = false; @@ -627,7 +632,7 @@ void LUA_HookThinkFrame(void) if (prepare_hook(&hook, 0, type)) { - init_hook_call(&hook, 0, 0, res_none); + init_hook_call(&hook, 0, res_none); for (k = 0; k < map->numHooks; ++k) { @@ -662,7 +667,7 @@ int LUA_HookTouchSpecial(mobj_t *special, mobj_t *toucher) { LUA_PushUserdata(gL, special, META_MOBJ); LUA_PushUserdata(gL, toucher, META_MOBJ); - call_hooks(&hook, 2, 1, res_true); + call_hooks(&hook, 1, res_true); } return hook.status; } @@ -674,7 +679,6 @@ static int damage_hook mobj_t *source, INT32 damage, int hook_type, - int values, Hook_Callback results_handler ){ Hook_State hook; @@ -683,9 +687,9 @@ static int damage_hook LUA_PushUserdata(gL, target, META_MOBJ); LUA_PushUserdata(gL, inflictor, META_MOBJ); LUA_PushUserdata(gL, source, META_MOBJ); - if (values == 5) + if (hook_type != MOBJ_HOOK(MobjDeath)) lua_pushinteger(gL, damage); - call_hooks(&hook, values, 1, results_handler); + call_hooks(&hook, 1, results_handler); } return hook.status; } @@ -693,19 +697,19 @@ static int damage_hook int LUA_HookShouldDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage) { return damage_hook(target, inflictor, source, damage, - MOBJ_HOOK(ShouldDamage), 5, res_force); + MOBJ_HOOK(ShouldDamage), res_force); } int LUA_HookMobjDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage) { return damage_hook(target, inflictor, source, damage, - MOBJ_HOOK(MobjDamage), 5, res_true); + MOBJ_HOOK(MobjDamage), res_true); } int LUA_HookMobjDeath(mobj_t *target, mobj_t *inflictor, mobj_t *source) { return damage_hook(target, inflictor, source, 0, - MOBJ_HOOK(MobjDeath), 4, res_true); + MOBJ_HOOK(MobjDeath), res_true); } typedef struct { @@ -778,7 +782,7 @@ int LUA_HookBotAI(mobj_t *sonic, mobj_t *tails, ticcmd_t *cmd) hook.userdata = &botai; - call_hooks(&hook, 2, 8, res_botai); + call_hooks(&hook, 8, res_botai); } return hook.status; @@ -793,7 +797,7 @@ void LUA_HookLinedefExecute(line_t *line, mobj_t *mo, sector_t *sector) LUA_PushUserdata(gL, line, META_LINE); LUA_PushUserdata(gL, mo, META_MOBJ); LUA_PushUserdata(gL, sector, META_SECTOR); - ps_lua_mobjhooks.value.i += call_hooks(&hook, 3, 0, res_none); + ps_lua_mobjhooks.value.i += call_hooks(&hook, 0, res_none); } } @@ -821,7 +825,7 @@ int LUA_HookPlayerMsg(int source, int target, int flags, char *msg, int mute) lua_pushboolean(gL, true); // the message was supposed to be eaten by spamprotecc. else lua_pushboolean(gL, false); - call_hooks(&hook, 4, 1, res_true); + call_hooks(&hook, 1, res_true); } return hook.status; } @@ -834,7 +838,7 @@ int LUA_HookHurtMsg(player_t *player, mobj_t *inflictor, mobj_t *source) LUA_PushUserdata(gL, player, META_PLAYER); LUA_PushUserdata(gL, inflictor, META_MOBJ); LUA_PushUserdata(gL, source, META_MOBJ); - call_hooks(&hook, 4, 1, res_true); + call_hooks(&hook, 1, res_true); } return hook.status; } @@ -853,12 +857,14 @@ void LUA_HookNetArchive(lua_CFunction archFunc) push_error_handler(); lua_insert(gL, EINDEX); + begin_hook_values(&hook); + // tables becomes an upvalue of archFunc lua_pushvalue(gL, -1); lua_pushcclosure(gL, archFunc, 1); // stack: tables, archFunc - init_hook_call(&hook, 1, 0, res_none); + init_hook_call(&hook, 0, res_none); call_mapped(&hook, map); lua_pop(gL, 1); // pop archFunc @@ -874,7 +880,7 @@ void LUA_HookPlayerQuit(player_t *plr, int reason) { LUA_PushUserdata(gL, plr, META_PLAYER); // Player that quit lua_pushinteger(gL, reason); // Reason for quitting - call_hooks(&hook, 2, 0, res_none); + call_hooks(&hook, 0, res_none); } } @@ -938,7 +944,8 @@ int LUA_HookMusicChange(const char *oldname, struct MusicChange *param) if (prepare_hook(&hook, false, type)) { - init_hook_call(&hook, 7, 6, res_musicchange); + init_hook_call(&hook, 6, res_musicchange); + hook.values = 7;/* values pushed later */ hook.userdata = param; lua_pushstring(gL, oldname);/* the only constant value */ @@ -979,7 +986,7 @@ static int kartdamage_hook LUA_PushUserdata(gL, player, META_PLAYER); LUA_PushUserdata(gL, inflictor, META_MOBJ); LUA_PushUserdata(gL, source, META_MOBJ); - call_hooks(&hook, 3, 1, results_handler); + call_hooks(&hook, 1, results_handler); } return hook.status; } -- 2.54.0 From 802979b81d3cf0fdf375492bd8b6d80b3ffea96d Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:39:26 +0100 Subject: [PATCH 045/143] Refactor hook ref allocation --- src/lua_hooklib.c | 58 +++++++++++++++++++++++++---------------------- 1 file changed, 31 insertions(+), 27 deletions(-) diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 8bf506236..93fc8c198 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -55,6 +55,7 @@ static stringhook_t stringHooks[STRING_HOOK(MAX)]; // This will be indexed by hook id, the value of which fetches the registry. static int * hookRefs; +static int nextid; // After a hook errors once, don't print the error again. static UINT8 * hooksErrored; @@ -103,13 +104,13 @@ static void get_table(lua_State *L) lua_remove(L, -2); } -static void add_hook_to_table(lua_State *L, int id, int n) +static void add_hook_to_table(lua_State *L, int n) { - lua_pushnumber(L, id); + lua_pushnumber(L, nextid); lua_rawseti(L, -2, n); } -static void add_string_hook(lua_State *L, int type, int id) +static void add_string_hook(lua_State *L, int type) { stringhook_t * hook = &stringHooks[type]; @@ -166,33 +167,48 @@ static void add_string_hook(lua_State *L, int type, int id) { lua_pushstring(L, string); get_table(L); - add_hook_to_table(L, id, 1 + lua_objlen(L, -1)); + add_hook_to_table(L, 1 + lua_objlen(L, -1)); } else - add_hook_to_table(L, id, ++hook->numGeneric); + add_hook_to_table(L, ++hook->numGeneric); } -static void add_hook(hook_t *map, int id) +static void add_hook(hook_t *map) { Z_Realloc(map->ids, (map->numHooks + 1) * sizeof *map->ids, PU_STATIC, &map->ids); - map->ids[map->numHooks++] = id; + map->ids[map->numHooks++] = nextid; } -static void add_mobj_hook(lua_State *L, int hook_type, int id) +static void add_mobj_hook(lua_State *L, int hook_type) { mobjtype_t mobj_type = luaL_optnumber(L, 3, MT_NULL); luaL_argcheck(L, mobj_type < NUMMOBJTYPES, 3, "invalid mobjtype_t"); - add_hook(&mobjHookIds[mobj_type][hook_type], id); + add_hook(&mobjHookIds[mobj_type][hook_type]); +} + +static void add_hook_ref(lua_State *L, int idx) +{ + if (!(nextid & 7)) + { + Z_Realloc(hooksErrored, + BIT_ARRAY_SIZE (nextid + 1) * sizeof *hooksErrored, + PU_STATIC, &hooksErrored); + hooksErrored[nextid >> 3] = 0; + } + + Z_Realloc(hookRefs, (nextid + 1) * sizeof *hookRefs, PU_STATIC, &hookRefs); + + // set the hook function in the registry. + lua_pushvalue(L, idx); + hookRefs[nextid++] = luaL_ref(L, LUA_REGISTRYINDEX); } // Takes hook, function, and additional arguments (mobj type to act on, etc.) static int lib_addHook(lua_State *L) { - static int nextid; - const char * name; int type; @@ -205,34 +221,22 @@ static int lib_addHook(lua_State *L) /* this is a very special case */ if (( type = hook_in_list(name, stringHookNames) ) < STRING_HOOK(MAX)) { - add_string_hook(L, type, nextid); + add_string_hook(L, type); } else if (( type = hook_in_list(name, mobjHookNames) ) < MOBJ_HOOK(MAX)) { - add_mobj_hook(L, type, nextid); + add_mobj_hook(L, type); } else if (( type = hook_in_list(name, hookNames) ) < HOOK(MAX)) { - add_hook(&hookIds[type], nextid); + add_hook(&hookIds[type]); } else { return luaL_argerror(L, 1, lua_pushfstring(L, "invalid hook " LUA_QS, name)); } - if (!(nextid & 7)) - { - Z_Realloc(hooksErrored, - BIT_ARRAY_SIZE (nextid + 1) * sizeof *hooksErrored, - PU_STATIC, &hooksErrored); - hooksErrored[nextid >> 3] = 0; - } - - Z_Realloc(hookRefs, (nextid + 1) * sizeof *hookRefs, PU_STATIC, &hookRefs); - - // set the hook function in the registry. - lua_pushvalue(L, 2);/* the function */ - hookRefs[nextid++] = luaL_ref(L, LUA_REGISTRYINDEX); + add_hook_ref(L, 2);/* the function */ return 0; } -- 2.54.0 From 11992d2e083e18b5735d6744c6d17c06042f0aa3 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:40:36 +0100 Subject: [PATCH 046/143] MORE MACROS --- src/lua_hook.h | 11 ++++++++--- src/lua_hooklib.c | 12 +++++++----- 2 files changed, 15 insertions(+), 8 deletions(-) diff --git a/src/lua_hook.h b/src/lua_hook.h index 9e91c82b9..ea0c29e68 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -82,9 +82,14 @@ X (LinedefExecute),\ #define HOOK(name) hook_ ## name #define STRING_HOOK(name) stringhook_ ## name -enum { MOBJ_HOOK_LIST (MOBJ_HOOK) MOBJ_HOOK(MAX) }; -enum { HOOK_LIST (HOOK) HOOK(MAX) }; -enum { STRING_HOOK_LIST (STRING_HOOK) STRING_HOOK(MAX) }; + +#define ENUM(X) enum { X ## _LIST (X) X(MAX) } + +ENUM (MOBJ_HOOK); +ENUM (HOOK); +ENUM (STRING_HOOK); + +#undef ENUM /* dead simple, LUA_HOOK(GameQuit) */ #define LUA_HOOK(type) LUA_HookVoid(HOOK(type)) diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 93fc8c198..49044ffc1 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -30,12 +30,14 @@ ABSTRACTION ========================================================================= */ -static const char * const mobjHookNames[] = { MOBJ_HOOK_LIST (TOSTR) NULL }; -static const char * const hookNames[] = { HOOK_LIST (TOSTR) NULL }; +#define LIST(id, M) \ + static const char * const id [] = { M (TOSTR) NULL } -static const char * const stringHookNames[] = { - STRING_HOOK_LIST (TOSTR) NULL -}; +LIST (mobjHookNames, MOBJ_HOOK_LIST); +LIST (hookNames, HOOK_LIST); +LIST (stringHookNames, STRING_HOOK_LIST); + +#undef LIST typedef struct { int numHooks; -- 2.54.0 From 4477f5ab937b655f469bb48e1ab7039dd6db8df3 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:41:14 +0100 Subject: [PATCH 047/143] Fix MusicChange hook crashing when called --- src/lua_hooklib.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 49044ffc1..ababaf356 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -957,7 +957,7 @@ int LUA_HookMusicChange(const char *oldname, struct MusicChange *param) lua_pushstring(gL, oldname);/* the only constant value */ lua_pushstring(gL, param->newname);/* semi constant */ - for (k = 0; k <= map->numHooks; ++k) + for (k = 0; k < map->numHooks; ++k) { get_hook(&hook, map->ids, k); -- 2.54.0 From a4e6b5d177ad82220fbcef84364866ed69c7b43e Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:46:27 +0100 Subject: [PATCH 048/143] Fix HurtMsg inflictor mobj type discriminator https://git.do.srb2.org/STJr/SRB2/-/merge_requests/1903 --- src/lua_hook.h | 2 +- src/lua_hooklib.c | 21 +++++++++++++-------- 2 files changed, 14 insertions(+), 9 deletions(-) diff --git a/src/lua_hook.h b/src/lua_hook.h index ea0c29e68..e465db9bf 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -34,6 +34,7 @@ X (MobjDamage),/* P_DamageMobj (Mobj actually takes damage!) */\ X (MobjDeath),/* P_KillMobj */\ X (BossDeath),/* A_BossDeath */\ X (MobjRemoved),/* P_RemoveMobj */\ +X (HurtMsg),/* imhurttin */\ #define HOOK_LIST(X) \ X (NetVars),/* add to archive table (netsave) */\ @@ -49,7 +50,6 @@ X (SpinSpecial),/* P_DoSpinAbility (Spin button effect) */\ X (JumpSpinSpecial),/* P_DoJumpStuff (Spin button effect (mid-air)) */\ X (BotTiccmd),/* B_BuildTiccmd */\ X (PlayerMsg),/* chat messages */\ -X (HurtMsg),/* imhurttin */\ X (PlayerSpawn),/* G_SpawnPlayer */\ X (PlayerQuit),\ X (IntermissionThinker),/* Y_Ticker */\ diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index ababaf356..817dd333f 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -69,7 +69,7 @@ static boolean mobj_hook_available(int hook_type, mobjtype_t mobj_type) return ( mobjHookIds [MT_NULL] [hook_type].numHooks > 0 || - mobjHookIds[mobj_type][hook_type].numHooks > 0 + (mobj_type < NUMMOBJTYPES && mobjHookIds[mobj_type][hook_type].numHooks > 0) ); } @@ -336,8 +336,11 @@ static boolean prepare_mobj_hook Hook_State * hook, int default_status, int hook_type, - mobjtype_t mobj_type + mobj_t * primary_mobj ){ + const mobjtype_t mobj_type = + primary_mobj ? primary_mobj->type : NUMMOBJTYPES; + return init_hook_type(hook, default_status, hook_type, mobj_type, NULL, mobj_hook_available(hook_type, mobj_type)); @@ -494,7 +497,9 @@ static int call_hooks { /* call generic mobj hooks first */ calls += call_mobj_type_hooks(hook, MT_NULL); - calls += call_mobj_type_hooks(hook, hook->mobj_type); + + if (hook->mobj_type < NUMMOBJTYPES) + calls += call_mobj_type_hooks(hook, hook->mobj_type); ps_lua_mobjhooks.value.i += calls; } @@ -542,7 +547,7 @@ static void res_force(Hook_State *hook) int LUA_HookMobj(mobj_t *mobj, int hook_type) { Hook_State hook; - if (prepare_mobj_hook(&hook, false, hook_type, mobj->type)) + if (prepare_mobj_hook(&hook, false, hook_type, mobj)) { LUA_PushUserdata(gL, mobj, META_MOBJ); call_hooks(&hook, 1, res_true); @@ -553,7 +558,7 @@ int LUA_HookMobj(mobj_t *mobj, int hook_type) int LUA_Hook2Mobj(mobj_t *t1, mobj_t *t2, int hook_type) { Hook_State hook; - if (prepare_mobj_hook(&hook, 0, hook_type, t1->type)) + if (prepare_mobj_hook(&hook, 0, hook_type, t1)) { LUA_PushUserdata(gL, t1, META_MOBJ); LUA_PushUserdata(gL, t2, META_MOBJ); @@ -669,7 +674,7 @@ void LUA_HookThinkFrame(void) int LUA_HookTouchSpecial(mobj_t *special, mobj_t *toucher) { Hook_State hook; - if (prepare_mobj_hook(&hook, false, MOBJ_HOOK(TouchSpecial), special->type)) + if (prepare_mobj_hook(&hook, false, MOBJ_HOOK(TouchSpecial), special)) { LUA_PushUserdata(gL, special, META_MOBJ); LUA_PushUserdata(gL, toucher, META_MOBJ); @@ -688,7 +693,7 @@ static int damage_hook Hook_Callback results_handler ){ Hook_State hook; - if (prepare_mobj_hook(&hook, 0, hook_type, target->type)) + if (prepare_mobj_hook(&hook, 0, hook_type, target)) { LUA_PushUserdata(gL, target, META_MOBJ); LUA_PushUserdata(gL, inflictor, META_MOBJ); @@ -839,7 +844,7 @@ int LUA_HookPlayerMsg(int source, int target, int flags, char *msg, int mute) int LUA_HookHurtMsg(player_t *player, mobj_t *inflictor, mobj_t *source) { Hook_State hook; - if (prepare_hook(&hook, false, HOOK(HurtMsg))) + if (prepare_mobj_hook(&hook, false, MOBJ_HOOK(HurtMsg), inflictor)) { LUA_PushUserdata(gL, player, META_PLAYER); LUA_PushUserdata(gL, inflictor, META_MOBJ); -- 2.54.0 From 1f6096e3ff4aac49a098206fd3db47eaa16abc1d Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:49:42 +0100 Subject: [PATCH 049/143] fix pre and post thinkframe perfstats pages --- src/lua_hook.h | 2 ++ src/lua_hooklib.c | 31 +++++++++++++++++++++++++------ src/p_tick.c | 4 ++-- 3 files changed, 29 insertions(+), 8 deletions(-) diff --git a/src/lua_hook.h b/src/lua_hook.h index e465db9bf..e44140632 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -107,7 +107,9 @@ void LUA_HookInt(INT32 integer, int hook); int LUA_HookPlayer(player_t *, int hook); int LUA_HookTiccmd(player_t *, ticcmd_t *, int hook); +void LUA_HookPreThinkFrame(void); void LUA_HookThinkFrame(void); +void LUA_HookPostThinkFrame(void); int LUA_HookTouchSpecial(mobj_t *special, mobj_t *toucher); int LUA_HookShouldDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage); int LUA_HookMobjDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage); diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 817dd333f..9ea0fdd5f 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -628,10 +628,8 @@ int LUA_HookTiccmd(player_t *player, ticcmd_t *cmd, int hook_type) SPECIALIZED HOOKS ========================================================================= */ -void LUA_HookThinkFrame(void) +static void hook_think_frame(int type) { - const int type = HOOK(ThinkFrame); - // variables used by perf stats int hook_index = 0; precise_t time_taken = 0; @@ -649,7 +647,7 @@ void LUA_HookThinkFrame(void) { get_hook(&hook, map->ids, k); - if (cv_perfstats.value == 3) + if (cv_perfstats.value >= 3) { lua_pushvalue(gL, -1);/* need the function again */ time_taken = I_GetPreciseTime(); @@ -657,12 +655,18 @@ void LUA_HookThinkFrame(void) call_single_hook(&hook); - if (cv_perfstats.value == 3) + if (cv_perfstats.value >= 3) { lua_Debug ar; time_taken = I_GetPreciseTime() - time_taken; lua_getinfo(gL, ">S", &ar); - PS_SetThinkFrameHookInfo(hook_index, time_taken, ar.short_src); + if (type == 4) // sorry for magic numbers + PS_SetPreThinkFrameHookInfo(hook_index, time_taken, ar.short_src); + else if (type == 5) + PS_SetThinkFrameHookInfo(hook_index, time_taken, ar.short_src); + else if (type == 6) + PS_SetPostThinkFrameHookInfo(hook_index, time_taken, ar.short_src); + hook_index++; } } @@ -671,6 +675,21 @@ void LUA_HookThinkFrame(void) } } +void LUA_HookPreThinkFrame(void) +{ + hook_think_frame(HOOK(PreThinkFrame)); +} + +void LUA_HookThinkFrame(void) +{ + hook_think_frame(HOOK(ThinkFrame)); +} + +void LUA_HookPostThinkFrame(void) +{ + hook_think_frame(HOOK(PostThinkFrame)); +} + int LUA_HookTouchSpecial(mobj_t *special, mobj_t *toucher) { Hook_State hook; diff --git a/src/p_tick.c b/src/p_tick.c index 49d51774e..8a12dd6da 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -528,7 +528,7 @@ void P_Ticker(boolean run) ps_checkposition_calls.value.i = 0; PS_START_TIMING(ps_lua_prethinkframe_time); - LUA_HOOK(PreThinkFrame); + LUA_HookPreThinkFrame(); PS_STOP_TIMING(ps_lua_prethinkframe_time); PS_START_TIMING(ps_playerthink_time); @@ -668,7 +668,7 @@ void P_Ticker(boolean run) D_MapChange(gamemap, gametype, encoremode, true, 0, false, false); PS_START_TIMING(ps_lua_postthinkframe_time); - LUA_HOOK(PostThinkFrame); + LUA_HookPostThinkFrame(); PS_STOP_TIMING(ps_lua_postthinkframe_time); } -- 2.54.0 From fb0c88cf5597308839f5394cfe56293d380ed848 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 19:50:35 +0100 Subject: [PATCH 050/143] Fix -Warray-bounds warning in lua_hooklib.c --- src/lua_hooklib.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 9ea0fdd5f..6e4f41d63 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -73,12 +73,12 @@ static boolean mobj_hook_available(int hook_type, mobjtype_t mobj_type) ); } -static int hook_in_list +static unsigned hook_in_list ( const char * const name, const char * const * const list ){ - int type; + unsigned type; for (type = 0; list[type] != NULL; ++type) { @@ -212,7 +212,7 @@ static void add_hook_ref(lua_State *L, int idx) static int lib_addHook(lua_State *L) { const char * name; - int type; + unsigned type; if (hud_running) return luaL_error(L, "HUD rendering code should not call this function!"); -- 2.54.0 From 2de9a6bb9420e896c9f4bf3d812646bec57565ac Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 21 Nov 2024 22:08:50 +0100 Subject: [PATCH 051/143] forgor to remove those --- src/lua_hook.h | 5 ++--- src/lua_hooklib.c | 2 -- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/src/lua_hook.h b/src/lua_hook.h index e44140632..ee43b90d2 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -52,10 +52,7 @@ X (BotTiccmd),/* B_BuildTiccmd */\ X (PlayerMsg),/* chat messages */\ X (PlayerSpawn),/* G_SpawnPlayer */\ X (PlayerQuit),\ -X (IntermissionThinker),/* Y_Ticker */\ X (PlayerThink),/* P_PlayerThink */\ -X (GameQuit),\ -X (PlayerCmd),/* building the player's ticcmd struct (Ported from SRB2Kart) */\ X (MusicChange),\ X (ShouldSpin),/*SRB2KART*/\ X (ShouldExplode),/*SRB2KART*/\ @@ -63,6 +60,8 @@ X (ShouldSquish),/*SRB2KART*/\ X (PlayerSpin),/*SRB2KART*/\ X (PlayerExplode),/*SRB2KART*/\ X (PlayerSquish),/*SRB2KART*/\ +X (PlayerCmd),/* building the player's ticcmd struct (Ported from SRB2Kart) */\ +X (IntermissionThinker),/* Y_Ticker */\ X (VoteThinker),/*SRB2KART*/\ X (ServerJoin),/* SRB2KART - Saturn 32p*/\ diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 6e4f41d63..a38be1ca6 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -24,8 +24,6 @@ #include "lua_hook.h" #include "lua_hud.h" // hud_running errors -#include - /* ========================================================================= ABSTRACTION ========================================================================= */ -- 2.54.0 From b40273842893f2ced849e63652fcab57b4c964bb Mon Sep 17 00:00:00 2001 From: Indev Date: Fri, 22 Nov 2024 01:31:02 +0300 Subject: [PATCH 052/143] Fix mobj hooks called for mobj type 0 being interpreted as regular hooks --- src/lua_hooklib.c | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index a38be1ca6..cc9a61695 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -259,6 +259,7 @@ struct Hook_State { void * userdata; int hook_type; mobjtype_t mobj_type;/* >0 if mobj hook */ + boolean force_mobj;// allows mobj_type equal 0 const char * string;/* used to fetch table, ran first if set */ int top;/* index of last argument passed to hook */ int id;/* id to fetch ref */ @@ -324,6 +325,8 @@ static boolean prepare_hook int default_status, int hook_type ){ + hook->force_mobj = false; + return init_hook_type(hook, default_status, hook_type, 0, NULL, hookIds[hook_type].numHooks); @@ -339,6 +342,8 @@ static boolean prepare_mobj_hook const mobjtype_t mobj_type = primary_mobj ? primary_mobj->type : NUMMOBJTYPES; + hook->force_mobj = true; + return init_hook_type(hook, default_status, hook_type, mobj_type, NULL, mobj_hook_available(hook_type, mobj_type)); @@ -351,6 +356,8 @@ static boolean prepare_string_hook int hook_type, const char * string ){ + hook->force_mobj = false; + if (init_hook_type(hook, default_status, hook_type, 0, string, stringHooks[hook_type].ref)) @@ -491,7 +498,7 @@ static int call_hooks { calls += call_string_hooks(hook); } - else if (hook->mobj_type > 0) + else if (hook->force_mobj) { /* call generic mobj hooks first */ calls += call_mobj_type_hooks(hook, MT_NULL); @@ -875,6 +882,7 @@ void LUA_HookNetArchive(lua_CFunction archFunc) { const hook_t * map = &hookIds[HOOK(NetVars)]; Hook_State hook; + hook.force_mobj = false; /* this is a remarkable case where the stack isn't reset */ if (map->numHooks > 0) { -- 2.54.0 From df97bef4b5dd66d39ae8aee7899182a3e26e6a25 Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 22 Nov 2024 00:39:53 +0100 Subject: [PATCH 053/143] Refactor HUD hooks too --- src/hu_stuff.c | 2 +- src/lua_hook.h | 97 +++++++++++---------- src/lua_hooklib.c | 55 ++++++++++++ src/lua_hud.h | 5 +- src/lua_hudlib.c | 210 ++++------------------------------------------ src/st_stuff.c | 2 +- src/y_inter.c | 4 +- 7 files changed, 129 insertions(+), 246 deletions(-) diff --git a/src/hu_stuff.c b/src/hu_stuff.c index 8a999b83f..6cbb46148 100644 --- a/src/hu_stuff.c +++ b/src/hu_stuff.c @@ -2274,7 +2274,7 @@ void HU_Drawer(void) if (renderisnewtic) { LUA_HUD_ClearDrawList(luahuddrawlist_scores); - LUAh_ScoresHUD(luahuddrawlist_scores); + LUA_HUDHOOK(scores, luahuddrawlist_scores); } LUA_HUD_DrawList(luahuddrawlist_scores); diff --git a/src/lua_hook.h b/src/lua_hook.h index ee43b90d2..45237aa80 100644 --- a/src/lua_hook.h +++ b/src/lua_hook.h @@ -13,6 +13,7 @@ #include "r_defs.h" #include "d_player.h" #include "s_sound.h" +#include "lua_hudlib_drawlist.h" /* * Do you know what an 'X Macro' is? Such a macro is called over each element of @@ -22,52 +23,58 @@ */ #define MOBJ_HOOK_LIST(X) \ -X (MobjSpawn),/* P_SpawnMobj */\ -X (MobjCollide),/* PIT_CheckThing */\ -X (MobjMoveCollide),/* tritto */\ -X (TouchSpecial),/* P_TouchSpecialThing */\ -X (MobjFuse),/* when mobj->fuse runs out */\ -X (MobjThinker),/* P_MobjThinker, P_SceneryThinker */\ -X (BossThinker),/* P_GenericBossThinker */\ -X (ShouldDamage),/* P_DamageMobj (Should mobj take damage?) */\ -X (MobjDamage),/* P_DamageMobj (Mobj actually takes damage!) */\ -X (MobjDeath),/* P_KillMobj */\ -X (BossDeath),/* A_BossDeath */\ -X (MobjRemoved),/* P_RemoveMobj */\ -X (HurtMsg),/* imhurttin */\ + X (MobjSpawn),/* P_SpawnMobj */\ + X (MobjCollide),/* PIT_CheckThing */\ + X (MobjMoveCollide),/* tritto */\ + X (TouchSpecial),/* P_TouchSpecialThing */\ + X (MobjFuse),/* when mobj->fuse runs out */\ + X (MobjThinker),/* P_MobjThinker, P_SceneryThinker */\ + X (BossThinker),/* P_GenericBossThinker */\ + X (ShouldDamage),/* P_DamageMobj (Should mobj take damage?) */\ + X (MobjDamage),/* P_DamageMobj (Mobj actually takes damage!) */\ + X (MobjDeath),/* P_KillMobj */\ + X (BossDeath),/* A_BossDeath */\ + X (MobjRemoved),/* P_RemoveMobj */\ + X (HurtMsg),/* imhurttin */\ #define HOOK_LIST(X) \ -X (NetVars),/* add to archive table (netsave) */\ -X (MapChange),/* (before map load) */\ -X (MapLoad),\ -X (PlayerJoin),/* Got_AddPlayer */\ -X (PreThinkFrame)/* frame (before mobj and player thinkers) */,\ -X (ThinkFrame),/* frame (after mobj and player thinkers) */\ -X (PostThinkFrame),/* frame (at end of tick, ie after overlays, precipitation, specials) */\ -X (JumpSpecial),/* P_DoJumpStuff (Any-jumping) */\ -X (AbilitySpecial),/* P_DoJumpStuff (Double-jumping) */\ -X (SpinSpecial),/* P_DoSpinAbility (Spin button effect) */\ -X (JumpSpinSpecial),/* P_DoJumpStuff (Spin button effect (mid-air)) */\ -X (BotTiccmd),/* B_BuildTiccmd */\ -X (PlayerMsg),/* chat messages */\ -X (PlayerSpawn),/* G_SpawnPlayer */\ -X (PlayerQuit),\ -X (PlayerThink),/* P_PlayerThink */\ -X (MusicChange),\ -X (ShouldSpin),/*SRB2KART*/\ -X (ShouldExplode),/*SRB2KART*/\ -X (ShouldSquish),/*SRB2KART*/\ -X (PlayerSpin),/*SRB2KART*/\ -X (PlayerExplode),/*SRB2KART*/\ -X (PlayerSquish),/*SRB2KART*/\ -X (PlayerCmd),/* building the player's ticcmd struct (Ported from SRB2Kart) */\ -X (IntermissionThinker),/* Y_Ticker */\ -X (VoteThinker),/*SRB2KART*/\ -X (ServerJoin),/* SRB2KART - Saturn 32p*/\ + X (NetVars),/* add to archive table (netsave) */\ + X (MapChange),/* (before map load) */\ + X (MapLoad),\ + X (PlayerJoin),/* Got_AddPlayer */\ + X (PreThinkFrame)/* frame (before mobj and player thinkers) */,\ + X (ThinkFrame),/* frame (after mobj and player thinkers) */\ + X (PostThinkFrame),/* frame (at end of tick, ie after overlays, precipitation, specials) */\ + X (JumpSpecial),/* P_DoJumpStuff (Any-jumping) */\ + X (AbilitySpecial),/* P_DoJumpStuff (Double-jumping) */\ + X (SpinSpecial),/* P_DoSpinAbility (Spin button effect) */\ + X (JumpSpinSpecial),/* P_DoJumpStuff (Spin button effect (mid-air)) */\ + X (BotTiccmd),/* B_BuildTiccmd */\ + X (PlayerMsg),/* chat messages */\ + X (PlayerSpawn),/* G_SpawnPlayer */\ + X (PlayerQuit),\ + X (PlayerThink),/* P_PlayerThink */\ + X (MusicChange),\ + X (ShouldSpin),/*SRB2KART*/\ + X (ShouldExplode),/*SRB2KART*/\ + X (ShouldSquish),/*SRB2KART*/\ + X (PlayerSpin),/*SRB2KART*/\ + X (PlayerExplode),/*SRB2KART*/\ + X (PlayerSquish),/*SRB2KART*/\ + X (PlayerCmd),/* building the player's ticcmd struct (Ported from SRB2Kart) */\ + X (IntermissionThinker),/* Y_Ticker */\ + X (VoteThinker),/*SRB2KART*/\ + X (ServerJoin),/* SRB2KART - Saturn 32p*/\ #define STRING_HOOK_LIST(X) \ -X (BotAI),/* B_BuildTailsTiccmd by skin name */\ -X (LinedefExecute),\ + X (BotAI),/* B_BuildTailsTiccmd by skin name */\ + X (LinedefExecute),\ + +#define HUD_HOOK_LIST(X) \ + X (game),\ + X (scores),/* emblems/multiplayer list */\ + X (intermission),\ + X (vote),\ /* * I chose to access the hook enums through a macro as well. This could provide @@ -79,25 +86,27 @@ X (LinedefExecute),\ #define MOBJ_HOOK(name) mobjhook_ ## name #define HOOK(name) hook_ ## name +#define HUD_HOOK(name) hudhook_ ## name #define STRING_HOOK(name) stringhook_ ## name - #define ENUM(X) enum { X ## _LIST (X) X(MAX) } ENUM (MOBJ_HOOK); ENUM (HOOK); +ENUM (HUD_HOOK); ENUM (STRING_HOOK); #undef ENUM /* dead simple, LUA_HOOK(GameQuit) */ #define LUA_HOOK(type) LUA_HookVoid(HOOK(type)) - +#define LUA_HUDHOOK(type,drawlist) LUA_HookHUD(HUD_HOOK(type),(drawlist)) extern boolean hook_cmd_running; // This is used by PlayerCmd and lua_playerlib to prevent anything from being wirtten to player while we run PlayerCmd. extern int hook_defrosting; void LUA_HookVoid(int hook); +void LUA_HookHUD(int hook, huddrawlist_h drawlist); int LUA_HookMobj(mobj_t *, int hook); int LUA_Hook2Mobj(mobj_t *, mobj_t *, int hook); diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index cc9a61695..8acc418d3 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -33,6 +33,7 @@ LIST (mobjHookNames, MOBJ_HOOK_LIST); LIST (hookNames, HOOK_LIST); +LIST (hudHookNames, HUD_HOOK_LIST); LIST (stringHookNames, STRING_HOOK_LIST); #undef LIST @@ -48,6 +49,7 @@ typedef struct { } stringhook_t; static hook_t hookIds[HOOK(MAX)]; +static hook_t hudHookIds[HUD_HOOK(MAX)]; static hook_t mobjHookIds[NUMMOBJTYPES][MOBJ_HOOK(MAX)]; // Lua tables are used to lookup string hook ids. @@ -189,6 +191,12 @@ static void add_mobj_hook(lua_State *L, int hook_type) add_hook(&mobjHookIds[mobj_type][hook_type]); } +static void add_hud_hook(lua_State *L, int idx) +{ + add_hook(&hudHookIds[luaL_checkoption(L, + idx, "game", hudHookNames)]); +} + static void add_hook_ref(lua_State *L, int idx) { if (!(nextid & 7)) @@ -231,6 +239,10 @@ static int lib_addHook(lua_State *L) { add_hook(&hookIds[type]); } + /*else if (strcmp(name, "HUD") == 0) // ehh this is cool and all, but i dont want modders potentially breaking vanilla clients lol + { + add_hud_hook(L, 3); + }*/ else { return luaL_argerror(L, 1, lua_pushfstring(L, "invalid hook " LUA_QS, name)); @@ -251,6 +263,18 @@ int LUA_HookLib(lua_State *L) return 0; } + +int lib_hudadd(lua_State *L);/* yeah compiler */ +int lib_hudadd(lua_State *L) +{ + luaL_checktype(L, 1, LUA_TFUNCTION); + + add_hud_hook(L, 2); + add_hook_ref(L, 1); + + return 0; +} + typedef struct Hook_State Hook_State; typedef void (*Hook_Callback)(Hook_State *); @@ -545,6 +569,14 @@ static void res_force(Hook_State *hook) } } +static void res_hud(Hook_State *hook) +{ + (void)hook; + + hud_interpolate = hud_interpstring = hud_interplatch = false; + hud_interpcounter++; +} + /* ========================================================================= GENERALISED HOOKS ========================================================================= */ @@ -629,6 +661,29 @@ int LUA_HookTiccmd(player_t *player, ticcmd_t *cmd, int hook_type) return hook.status; } +void LUA_HookHUD(int hook_type, huddrawlist_h list) +{ + const hook_t * map = &hudHookIds[hook_type]; + Hook_State hook; + if (map->numHooks > 0) + { + start_hook_stack(); + begin_hook_values(&hook); + + LUA_SetHudHook(hook_type, list); + + hud_running = true; // local hook + hud_interpcounter = 0; + hud_interpolate = hud_interpstring = hud_interplatch = false; + init_hook_call(&hook, 1, res_hud); + call_mapped(&hook, map); + hud_running = false; + + lua_pushnil(gL); + lua_setfield(gL, LUA_REGISTRYINDEX, "HUD_DRAW_LIST"); + } +} + /* ========================================================================= SPECIALIZED HOOKS ========================================================================= */ diff --git a/src/lua_hud.h b/src/lua_hud.h index 5d1f41c83..76ce9eb48 100644 --- a/src/lua_hud.h +++ b/src/lua_hud.h @@ -50,9 +50,6 @@ extern boolean hud_interplatch; // string mode was toggled boolean LUA_HudEnabled(enum hud option); -void LUAh_GameHUD(huddrawlist_h list); -void LUAh_ScoresHUD(huddrawlist_h list); -void LUAh_IntermissionHUD(huddrawlist_h list); -void LUAh_VoteHUD(huddrawlist_h list); +void LUA_SetHudHook(int hook, huddrawlist_h list); #endif // __LUA_HUD_H__ diff --git a/src/lua_hudlib.c b/src/lua_hudlib.c index 2ee2297ad..235a89cde 100644 --- a/src/lua_hudlib.c +++ b/src/lua_hudlib.c @@ -28,6 +28,7 @@ #include "lua_script.h" #include "lua_libs.h" #include "lua_hud.h" +#include "lua_hook.h" #define HUDONLY if (!hud_running) return luaL_error(L, "HUD rendering code should not be called outside of rendering hooks!"); @@ -40,8 +41,6 @@ boolean hud_interpstring = false; boolean hud_interplatch = false; static UINT8 hud_enabled[(hud_MAX/8)+1]; -static UINT8 hudAvailable; // hud hooks field - static UINT8 camnum = 1; // must match enum hud in lua_hud.h @@ -93,19 +92,6 @@ static const char *const patch_opt[] = { "topoffset", NULL}; -enum hudhook { - hudhook_game = 0, - hudhook_scores = 1, - hudhook_intermission = 2, - hudhook_vote = 3, -}; -static const char *const hudhook_opt[] = { - "game", - "scores", - "intermission", - "vote", - NULL}; - static int patch_fields_ref = LUA_NOREF; // alignment types for v.drawString @@ -1215,6 +1201,8 @@ static luaL_Reg lib_draw[] = { {NULL, NULL} }; +static int lib_draw_ref; + // // lib_hud // @@ -1248,25 +1236,7 @@ static int lib_hudenabled(lua_State *L) } // add a HUD element for rendering -static int lib_hudadd(lua_State *L) -{ - enum hudhook field; - - luaL_checktype(L, 1, LUA_TFUNCTION); - field = luaL_checkoption(L, 2, "game", hudhook_opt); - - lua_getfield(L, LUA_REGISTRYINDEX, "HUD"); - I_Assert(lua_istable(L, -1)); - lua_rawgeti(L, -1, field+2); // HUD[2+] - I_Assert(lua_istable(L, -1)); - lua_remove(L, -2); - - lua_pushvalue(L, 1); - lua_rawseti(L, -2, (int)(lua_objlen(L, -2) + 1)); - - hudAvailable |= 1< Date: Fri, 22 Nov 2024 16:04:01 +0100 Subject: [PATCH 054/143] make hud hooks clean up after themselves --- src/lua_hooklib.c | 1 + 1 file changed, 1 insertion(+) diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 8acc418d3..9276e61aa 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -677,6 +677,7 @@ void LUA_HookHUD(int hook_type, huddrawlist_h list) hud_interpolate = hud_interpstring = hud_interplatch = false; init_hook_call(&hook, 1, res_hud); call_mapped(&hook, map); + lua_settop(gL, 0); // destroy le stack!! >:3 hud_running = false; lua_pushnil(gL); -- 2.54.0 From 5aff1acea895374bfc3a01861fba9bfa2b27ed3a Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 26 Nov 2024 19:18:34 +0100 Subject: [PATCH 055/143] mobjcache with explicit "true" check just in case smth throws a garbo value and is not actually a mobj thinker --- src/d_think.h | 1 + src/p_local.h | 1 + src/p_mobj.c | 31 ++++++++++++++++++++++++++++--- src/p_setup.c | 2 ++ src/p_tick.c | 27 +++++++++++++++++++++++++-- 5 files changed, 57 insertions(+), 5 deletions(-) diff --git a/src/d_think.h b/src/d_think.h index b907c17fd..6b8ee113a 100644 --- a/src/d_think.h +++ b/src/d_think.h @@ -49,6 +49,7 @@ typedef struct thinker_s // killough 11/98: count of how many other objects reference // this one using pointers. Used for garbage collection. INT32 references; + boolean cachable; } thinker_t; #endif diff --git a/src/p_local.h b/src/p_local.h index fe1d10d73..de90447bd 100644 --- a/src/p_local.h +++ b/src/p_local.h @@ -66,6 +66,7 @@ // both the head and tail of the thinker list extern thinker_t thinkercap; +extern mobj_t *mobjcache; void P_InitThinkers(void); void P_AddThinker(thinker_t *thinker); diff --git a/src/p_mobj.c b/src/p_mobj.c index 9da7b0235..937898ff6 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -48,6 +48,7 @@ actioncache_t actioncachehead; static mobj_t *overlaycap = NULL; static mobj_t *shadowcap = NULL; mobj_t *waypointcap = NULL; +mobj_t *mobjcache = NULL; void P_InitCachedActions(void) { @@ -9362,7 +9363,18 @@ mobj_t *P_SpawnMobj(fixed_t x, fixed_t y, fixed_t z, mobjtype_t type) { const mobjinfo_t *info = &mobjinfo[type]; state_t *st; - mobj_t *mobj = Z_Calloc(sizeof (*mobj), PU_LEVEL, NULL); + mobj_t *mobj; + + if (mobjcache != NULL) + { + mobj = mobjcache; + mobjcache = mobjcache->hnext; + memset(mobj, 0, sizeof(*mobj)); + } + else + { + mobj = Z_Calloc(sizeof (*mobj), PU_LEVEL, NULL); + } // this is officially a mobj, declared as soon as possible. mobj->thinker.function.acp1 = (actionf_p1)P_MobjThinker; @@ -9823,7 +9835,18 @@ mobj_t *P_SpawnShadowMobj(mobj_t * caster) { const mobjinfo_t *info = &mobjinfo[MT_SHADOW]; state_t *st; - mobj_t *mobj = Z_Calloc(sizeof (*mobj), PU_LEVEL, NULL); + mobj_t *mobj; + + if (mobjcache != NULL) + { + mobj = mobjcache; + mobjcache = mobjcache->hnext; + memset(mobj, 0, sizeof(*mobj)); + } + else + { + mobj = Z_Calloc(sizeof (*mobj), PU_LEVEL, NULL); + } // this is officially a mobj, declared as soon as possible. mobj->thinker.function.acp1 = (actionf_p1)P_MobjThinker; @@ -10097,7 +10120,9 @@ void P_RemoveMobj(mobj_t *mobj) // Invalidate mobj_t data to cause crashes if accessed! memset(mobj, 0xff, sizeof(mobj_t)); #endif - Z_Free(mobj); // No refrences? Can be removed immediately! :D + // no references, dump it directly in the mobj cache + mobj->hnext = mobjcache; + mobjcache = mobj; } else { // Add thinker just to delay removing it until refrences are gone. diff --git a/src/p_setup.c b/src/p_setup.c index 93207a3c1..2d910aecb 100644 --- a/src/p_setup.c +++ b/src/p_setup.c @@ -2753,6 +2753,8 @@ boolean P_SetupLevel(boolean skipprecip, boolean reloadinggamestate) R_ClearLevelSplats(); #endif + mobjcache = NULL; + R_InitializeLevelInterpolators(); P_InitThinkers(); diff --git a/src/p_tick.c b/src/p_tick.c index d6243fde9..119b1dce0 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -196,6 +196,8 @@ void P_AddThinker(thinker_t *thinker) thinkercap.prev = thinker; thinker->references = 0; // killough 11/98: init reference counter to 0 + + thinker->cachable = (thinker->function.acp1 == (actionf_p1)P_MobjThinker); } // @@ -235,7 +237,17 @@ void P_RemoveThinkerDelayed(thinker_t *thinker) * thinker->prev->next = thinker->next */ (next->prev = currentthinker = thinker->prev)->next = next; R_DestroyLevelInterpolators(thinker); - Z_Free(thinker); + + if (thinker->cachable == true) + { + // put cachable thinkers in the mobj cache, so we can avoid allocations + ((mobj_t *)thinker)->hnext = mobjcache; + mobjcache = (mobj_t *)thinker; + } + else + { + Z_Free(thinker); + } } // @@ -250,9 +262,20 @@ void P_UnlinkThinker(thinker_t *thinker) I_Assert(thinker->references == 0); (next->prev = thinker->prev)->next = next; - Z_Free(thinker); + + if (thinker->cachable == true) + { + // put cachable thinkers in the mobj cache, so we can avoid allocations + ((mobj_t *)thinker)->hnext = mobjcache; + mobjcache = (mobj_t *)thinker; + } + else + { + Z_Free(thinker); + } } + // // P_RemoveThinker // -- 2.54.0 From f973e6cd7299e5711f374cb705b5945105a983f4 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 26 Nov 2024 18:21:10 +0100 Subject: [PATCH 056/143] init polyobj thinker cachable bool otherwise shit will die lol --- src/p_polyobj.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/p_polyobj.c b/src/p_polyobj.c index f890b0bd0..6f1259677 100644 --- a/src/p_polyobj.c +++ b/src/p_polyobj.c @@ -153,6 +153,9 @@ FUNCINLINE static ATTRINLINE void PolyObj_AddThinker(thinker_t *th) th->next = thinkercap.next; th->prev = &thinkercap; thinkercap.next = th; + + //th->references = 0; + th->cachable = false; // not initialising this made the mobjcache die thx! } static void FreeSideLists(void) -- 2.54.0 From 403b60240f0223bb7d8a7b43dda12c3dad95ba2d Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 26 Nov 2024 05:33:00 +0100 Subject: [PATCH 057/143] check for titlescreen music --- src/s_sound.c | 27 ++++++++++++++------------- 1 file changed, 14 insertions(+), 13 deletions(-) diff --git a/src/s_sound.c b/src/s_sound.c index 868bccc77..0a6a5ba0c 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -2191,11 +2191,11 @@ static boolean oldencore = false; static boolean skipmusic = false; boolean skipintromus = false; -static const char *musicexception_list[16] = { +static const char *musicexception_list[17] = { "vote", "voteea", "voteeb", "racent", "krwin", "krok", "krlose", "krfail", "kbwin", "kbok", - "kblose", "kstart", "estart", "wait2j", "CHRSHP", - "CHRSHF" + "kblose", "kstart", "estart", "wait2j", "titles", + "CHRSHF", "CHRSHP" // no clue what those are tbh }; //checks for any kind of event music like intermission, vote etc. @@ -2207,7 +2207,7 @@ static void S_CheckEventMus(const char *newmus) if (!cv_keepmusic.value) return; - for (int i = 0; i < 16; i++) + for (int i = 0; i < 17; i++) if (stricmp(music_name, musicexception_list[i]) == 0 || stricmp(newmus, musicexception_list[i]) == 0) // weird? sure! but were lucky enough newmus reflects whats being replaced { skipmusic = true; @@ -2242,15 +2242,7 @@ void S_CheckMap(void) // void S_InitMapMusic(void) { - if (!cv_skipintromusic.value) - skipintromus = false; - else - { - char *maptitle = G_BuildMapTitle(gamemap); - skipintromus = cv_skipintromusic.value && stricmp(maptitle, "Wandering Falls") != 0; // thanks diggle! - if (maptitle) - Z_Free(maptitle); - } + skipintromus = false; if (mapmusflags & MUSIC_RELOADRESET) { @@ -2268,6 +2260,15 @@ void S_InitMapMusic(void) // lug: but not when we keep the map music lol S_StopMusic(); + if (cv_skipintromusic.value) + { + char *maptitle = G_BuildMapTitle(gamemap); + // for some reason, occasionally the title screen music doesent seem to be reset in time, so skipping the intro may make it just continue playing it instead, weird.. + skipintromus = (stricmp(music_name, "titles") != 0) && (stricmp(maptitle, "Wandering Falls") != 0); // thanks diggle! + if (maptitle) + Z_Free(maptitle); + } + if (skipintromus) return; -- 2.54.0 From 80697046d55ed4f516cd408e3e42ccf0bca1ada9 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 26 Nov 2024 20:31:20 +0100 Subject: [PATCH 058/143] clean up spriteclip fix + fix papersprites being affected by it its now its own function HWR_ApplyDispoffset papersprites are now also unaffected by it, which caused some minor visual issues before (ex zfighting signposts) also just check for papersprite once and put it into a bool so we dont have to recheck sprite frames and flags 10 times --- src/hardware/hw_main.c | 164 ++++++++++++++++++++++------------------- 1 file changed, 89 insertions(+), 75 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index e96c9e36a..d8875c4ea 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -3379,74 +3379,109 @@ static void HWR_DrawSpriteShadow(gl_vissprite_t *spr, GLPatch_t *gpatch) } // This is expecting a pointer to an array containing 4 wallVerts for a sprite -static void HWR_RotateSpritePolyToAim(gl_vissprite_t *spr, FOutVector *wallVerts, const boolean precip) +static void HWR_RotateSpritePolyToAim(gl_vissprite_t *spr, FOutVector *wallVerts, const boolean precip, const boolean papersprite) { - if (cv_glspritebillboarding.value && spr && spr->mobj && !(spr->mobj->frame & FF_PAPERSPRITE) && wallVerts) + if (!cv_glspritebillboarding.value || !spr || !spr->mobj || papersprite || !wallVerts) { - // uncapped/interpolation - interpmobjstate_t interp = {0}; - float basey, lowy; - INT32 dist = -1; + return; + } - if (cv_maxinterpdist.value) - dist = R_QuickCamDist(spr->mobj->x, spr->mobj->y); + // uncapped/interpolation + interpmobjstate_t interp = {0}; + float basey, lowy; + INT32 dist = -1; - // do interpolation - if (R_UsingFrameInterpolation() && !paused && (!cv_maxinterpdist.value || dist < cv_maxinterpdist.value)) + if (cv_maxinterpdist.value) + dist = R_QuickCamDist(spr->mobj->x, spr->mobj->y); + + // do interpolation + if (R_UsingFrameInterpolation() && !paused && (!cv_maxinterpdist.value || dist < cv_maxinterpdist.value)) + { + if (precip) { - if (precip) - { - R_InterpolatePrecipMobjState((precipmobj_t *)spr->mobj, rendertimefrac, &interp); - } - else - { - R_InterpolateMobjState(spr->mobj, rendertimefrac, &interp); - } + R_InterpolatePrecipMobjState((precipmobj_t *)spr->mobj, rendertimefrac, &interp); } else { - if (precip) - { - R_InterpolatePrecipMobjState((precipmobj_t *)spr->mobj, FRACUNIT, &interp); - } - else - { - R_InterpolateMobjState(spr->mobj, FRACUNIT, &interp); - } + R_InterpolateMobjState(spr->mobj, rendertimefrac, &interp); } - - if (!precip && P_MobjFlip(spr->mobj) == -1) // precip doesn't have eflags so they can't flip + } + else + { + if (precip) { - basey = FIXED_TO_FLOAT(interp.z + spr->mobj->height); + R_InterpolatePrecipMobjState((precipmobj_t *)spr->mobj, FRACUNIT, &interp); } else { - basey = FIXED_TO_FLOAT(interp.z); + R_InterpolateMobjState(spr->mobj, FRACUNIT, &interp); } - lowy = wallVerts[0].y; + } - // Rotate sprites to fully billboard with the camera - // X, Y, AND Z need to be manipulated for the polys to rotate around the - // origin, because of how the origin setting works I believe that should - // be mobj->z or mobj->z + mobj->height - wallVerts[2].y = wallVerts[3].y = (spr->gzt - basey) * gl_viewludsin + basey; - wallVerts[0].y = wallVerts[1].y = (lowy - basey) * gl_viewludsin + basey; - // translate back to be around 0 before translating back - wallVerts[3].x += ((spr->gzt - basey) * gl_viewludcos) * gl_viewcos; - wallVerts[2].x += ((spr->gzt - basey) * gl_viewludcos) * gl_viewcos; + if (!precip && P_MobjFlip(spr->mobj) == -1) // precip doesn't have eflags so they can't flip + { + basey = FIXED_TO_FLOAT(interp.z + spr->mobj->height); + } + else + { + basey = FIXED_TO_FLOAT(interp.z); + } + lowy = wallVerts[0].y; - wallVerts[0].x += ((lowy - basey) * gl_viewludcos) * gl_viewcos; - wallVerts[1].x += ((lowy - basey) * gl_viewludcos) * gl_viewcos; + // Rotate sprites to fully billboard with the camera + // X, Y, AND Z need to be manipulated for the polys to rotate around the + // origin, because of how the origin setting works I believe that should + // be mobj->z or mobj->z + mobj->height + wallVerts[2].y = wallVerts[3].y = (spr->gzt - basey) * gl_viewludsin + basey; + wallVerts[0].y = wallVerts[1].y = (lowy - basey) * gl_viewludsin + basey; + // translate back to be around 0 before translating back + wallVerts[3].x += ((spr->gzt - basey) * gl_viewludcos) * gl_viewcos; + wallVerts[2].x += ((spr->gzt - basey) * gl_viewludcos) * gl_viewcos; - wallVerts[3].z += ((spr->gzt - basey) * gl_viewludcos) * gl_viewsin; - wallVerts[2].z += ((spr->gzt - basey) * gl_viewludcos) * gl_viewsin; + wallVerts[0].x += ((lowy - basey) * gl_viewludcos) * gl_viewcos; + wallVerts[1].x += ((lowy - basey) * gl_viewludcos) * gl_viewcos; - wallVerts[0].z += ((lowy - basey) * gl_viewludcos) * gl_viewsin; - wallVerts[1].z += ((lowy - basey) * gl_viewludcos) * gl_viewsin; + wallVerts[3].z += ((spr->gzt - basey) * gl_viewludcos) * gl_viewsin; + wallVerts[2].z += ((spr->gzt - basey) * gl_viewludcos) * gl_viewsin; + + wallVerts[0].z += ((lowy - basey) * gl_viewludcos) * gl_viewsin; + wallVerts[1].z += ((lowy - basey) * gl_viewludcos) * gl_viewsin; +} + +static inline void HWR_ApplyDispoffset(gl_vissprite_t *spr, FOutVector *wallVerts, const boolean papersprite) +{ + // dont push papersprites near the cam unless they have a dispoffset + if (papersprite) + { + // if it has a dispoffset, push it a little towards the camera + if (spr->dispoffset) + { + float co = -gl_viewcos*(0.05f*spr->dispoffset); + float si = -gl_viewsin*(0.05f*spr->dispoffset); + wallVerts[0].z = wallVerts[3].z = wallVerts[0].z+si; + wallVerts[1].z = wallVerts[2].z = wallVerts[1].z+si; + wallVerts[0].x = wallVerts[3].x = wallVerts[0].x+co; + wallVerts[1].x = wallVerts[2].x = wallVerts[1].x+co; + } + + HWR_RotateSpritePolyToAim(spr, wallVerts, false, papersprite); + return; + } + + HWR_RotateSpritePolyToAim(spr, wallVerts, false, papersprite); + + float sprdist = sqrtf((spr->x1 - gl_viewx)*(spr->x1 - gl_viewx) + (spr->z1 - gl_viewy)*(spr->z1 - gl_viewy) + (spr->gzt - gl_viewz)*(spr->gzt - gl_viewz)); + float distfact = ((2.0f*spr->dispoffset) + 20.0f) / sprdist; + + for (size_t i = 0; i < 4; i++) + { + wallVerts[i].x += (gl_viewx - wallVerts[i].x)*distfact; + wallVerts[i].z += (gl_viewy - wallVerts[i].z)*distfact; + wallVerts[i].y += (gl_viewz - wallVerts[i].y)*distfact; } } -static void HWR_SplitSprite(gl_vissprite_t *spr) +static void HWR_SplitSprite(gl_vissprite_t *spr, const boolean papersprite) { FOutVector wallVerts[4]; FOutVector baseWallVerts[4]; // This is what the verts should end up as @@ -3526,18 +3561,8 @@ static void HWR_SplitSprite(gl_vissprite_t *spr) baseWallVerts[0].t = baseWallVerts[1].t = gpatch->max_t; } - // Let dispoffset work first since this adjust each vertex - HWR_RotateSpritePolyToAim(spr, baseWallVerts, false); - // push it toward the camera to mitigate floor-clipping sprites - float sprdist = sqrtf((spr->x1 - gl_viewx)*(spr->x1 - gl_viewx) + (spr->z1 - gl_viewy)*(spr->z1 - gl_viewy) + (spr->gzt - gl_viewz)*(spr->gzt - gl_viewz)); - float distfact = ((2.0f*spr->dispoffset) + 20.0f) / sprdist; - for (i = 0; i < 4; i++) - { - baseWallVerts[i].x += (gl_viewx - baseWallVerts[i].x)*distfact; - baseWallVerts[i].z += (gl_viewy - baseWallVerts[i].z)*distfact; - baseWallVerts[i].y += (gl_viewz - baseWallVerts[i].y)*distfact; - } + HWR_ApplyDispoffset(spr, baseWallVerts, papersprite); realtop = top = baseWallVerts[3].y; realbot = bot = baseWallVerts[0].y; @@ -3655,7 +3680,7 @@ static void HWR_SplitSprite(gl_vissprite_t *spr) wallVerts[1].y = endbot; // The x and y only need to be adjusted in the case that it's not a papersprite - if (cv_glspritebillboarding.value && spr->mobj && !(spr->mobj->frame & FF_PAPERSPRITE)) + if (cv_glspritebillboarding.value && spr->mobj && !papersprite) { // Get the x and z of the vertices so billboarding draws correctly realheight = realbot - realtop; @@ -3731,9 +3756,11 @@ static void HWR_DrawSprite(gl_vissprite_t *spr) if (!spr->mobj->subsector) return; + const boolean papersprite = (spr->mobj->frame & FF_PAPERSPRITE); + if (spr->mobj->subsector->sector->numlights) { - HWR_SplitSprite(spr); + HWR_SplitSprite(spr, papersprite); return; } @@ -3799,20 +3826,8 @@ static void HWR_DrawSprite(gl_vissprite_t *spr) HWR_DrawSpriteShadow(spr, gpatch); } - // Let dispoffset work first since this adjust each vertex - // ...nah - HWR_RotateSpritePolyToAim(spr, wallVerts, false); - // push it toward the camera to mitigate floor-clipping sprites - float sprdist = sqrtf((spr->x1 - gl_viewx)*(spr->x1 - gl_viewx) + (spr->z1 - gl_viewy)*(spr->z1 - gl_viewy) + (spr->gzt - gl_viewz)*(spr->gzt - gl_viewz)); - float distfact = ((2.0f*spr->dispoffset) + 20.0f) / sprdist; - size_t i; - for (i = 0; i < 4; i++) - { - wallVerts[i].x += (gl_viewx - wallVerts[i].x)*distfact; - wallVerts[i].z += (gl_viewy - wallVerts[i].z)*distfact; - wallVerts[i].y += (gl_viewz - wallVerts[i].y)*distfact; - } + HWR_ApplyDispoffset(spr, wallVerts, papersprite); // This needs to be AFTER the shadows so that the regular sprites aren't drawn completely black. // sprite lighting by modulating the RGB components @@ -3894,8 +3909,7 @@ static inline void HWR_DrawPrecipitationSprite(gl_vissprite_t *spr) wallVerts[0].z = wallVerts[3].z = spr->z1; wallVerts[1].z = wallVerts[2].z = spr->z2; - // Let dispoffset work first since this adjust each vertex - HWR_RotateSpritePolyToAim(spr, wallVerts, true); + HWR_RotateSpritePolyToAim(spr, wallVerts, true, false); wallVerts[0].s = wallVerts[3].s = 0; wallVerts[2].s = wallVerts[1].s = gpatch->max_s; -- 2.54.0 From 0d39c2a0f6ca586d555b2629c5703013c651d03a Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 26 Nov 2024 22:30:29 +0100 Subject: [PATCH 059/143] we dont even need to check this this doesent do anything with papersprites so dont even call it kek --- src/hardware/hw_main.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index d8875c4ea..53df1ce5f 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -3379,9 +3379,9 @@ static void HWR_DrawSpriteShadow(gl_vissprite_t *spr, GLPatch_t *gpatch) } // This is expecting a pointer to an array containing 4 wallVerts for a sprite -static void HWR_RotateSpritePolyToAim(gl_vissprite_t *spr, FOutVector *wallVerts, const boolean precip, const boolean papersprite) +static void HWR_RotateSpritePolyToAim(gl_vissprite_t *spr, FOutVector *wallVerts, const boolean precip) { - if (!cv_glspritebillboarding.value || !spr || !spr->mobj || papersprite || !wallVerts) + if (!cv_glspritebillboarding.value || !spr || !spr->mobj || !wallVerts) { return; } @@ -3464,11 +3464,10 @@ static inline void HWR_ApplyDispoffset(gl_vissprite_t *spr, FOutVector *wallVert wallVerts[1].x = wallVerts[2].x = wallVerts[1].x+co; } - HWR_RotateSpritePolyToAim(spr, wallVerts, false, papersprite); return; } - HWR_RotateSpritePolyToAim(spr, wallVerts, false, papersprite); + HWR_RotateSpritePolyToAim(spr, wallVerts, false); float sprdist = sqrtf((spr->x1 - gl_viewx)*(spr->x1 - gl_viewx) + (spr->z1 - gl_viewy)*(spr->z1 - gl_viewy) + (spr->gzt - gl_viewz)*(spr->gzt - gl_viewz)); float distfact = ((2.0f*spr->dispoffset) + 20.0f) / sprdist; @@ -3909,7 +3908,7 @@ static inline void HWR_DrawPrecipitationSprite(gl_vissprite_t *spr) wallVerts[0].z = wallVerts[3].z = spr->z1; wallVerts[1].z = wallVerts[2].z = spr->z2; - HWR_RotateSpritePolyToAim(spr, wallVerts, true, false); + HWR_RotateSpritePolyToAim(spr, wallVerts, true); wallVerts[0].s = wallVerts[3].s = 0; wallVerts[2].s = wallVerts[1].s = gpatch->max_s; -- 2.54.0 From 82c18be71708b37f0989ad0ec484a45207b59a1d Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 27 Nov 2024 00:36:19 +0100 Subject: [PATCH 060/143] why do replay play commands only have netgame check??????? bad things will happen if theyre played ingame regardless of netgame or not --- src/d_netcmd.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/d_netcmd.c b/src/d_netcmd.c index 281fb8856..87b8e8bcf 100644 --- a/src/d_netcmd.c +++ b/src/d_netcmd.c @@ -2515,9 +2515,9 @@ static void Command_Playdemo_f(void) return; } - if (netgame) + if (gamestate == GS_LEVEL) { - CONS_Printf(M_GetText("You can't play a demo while in a netgame.\n")); + CONS_Printf(M_GetText("You can't play a demo while in a game.\n")); return; } @@ -2554,9 +2554,9 @@ static void Command_Timedemo_f(void) return; } - if (netgame) + if (gamestate == GS_LEVEL) { - CONS_Printf(M_GetText("You can't play a demo while in a netgame.\n")); + CONS_Printf(M_GetText("You can't time a demo while in a game.\n")); return; } -- 2.54.0 From 3a9082a694174f8808888e66f65e01fedda65068 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 27 Nov 2024 17:10:56 +0100 Subject: [PATCH 061/143] memset screentex to 0 in FlushScreenTextures --- src/hardware/r_opengl/r_opengl.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index 4b98f332d..364edcd72 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -3109,10 +3109,8 @@ EXPORT void HWRAPI(PostImgRedraw) (float points[SCREENVERTS][SCREENVERTS][2]) // a new size EXPORT void HWRAPI(FlushScreenTextures) (void) { - int i; pglDeleteTextures(NUMSCREENTEXTURES, screenTextures); - for (i = 0; i < NUMSCREENTEXTURES; i++) - screenTextures[i] = 0; + memset(screenTextures, 0 , sizeof(screenTextures)); } EXPORT void HWRAPI(DrawScreenTexture)(int tex, FSurfaceInfo *surf, FBITFIELD polyflags) -- 2.54.0 From 70105ccefced2428e72d1a8b4a1009c6a4716636 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 27 Nov 2024 17:12:25 +0100 Subject: [PATCH 062/143] make own screentex for vhs effect idk if its really needed tbh, but also doesent hurt --- src/hardware/hw_defs.h | 1 + src/hardware/r_opengl/r_opengl.c | 14 ++++++++------ 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/src/hardware/hw_defs.h b/src/hardware/hw_defs.h index 5d23099cb..f36631690 100644 --- a/src/hardware/hw_defs.h +++ b/src/hardware/hw_defs.h @@ -340,6 +340,7 @@ enum hwdscreentexture HWD_SCREENTEXTURE_WIPE_END, // destination image for the wipe/fade effect HWD_SCREENTEXTURE_GENERIC1, // underwater/heat effect, intermission background HWD_SCREENTEXTURE_GENERIC2, // palette-based colormap fade, final screen texture + HWD_SCREENTEXTURE_VHS, NUMSCREENTEXTURES, // (generic3 is unused if palette rendering is disabled) }; typedef enum hwdscreentexture hwdscreentexture_t; diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index 364edcd72..df99f4437 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -3261,6 +3261,7 @@ EXPORT void HWRAPI(DoScreenWipe)(int wipeStart, int wipeEnd) EXPORT void HWRAPI(RenderVhsEffect) (fixed_t upbary, fixed_t downbary, UINT8 updistort, UINT8 downdistort, UINT8 barsize) { INT32 texsize = 512; + int tex = HWD_SCREENTEXTURE_VHS; float xfix, yfix; float fix[8]; GLubyte color[4] = {255, 255, 255, 255}; @@ -3285,9 +3286,9 @@ EXPORT void HWRAPI(RenderVhsEffect) (fixed_t upbary, fixed_t downbary, UINT8 upd yfix = 1/((float)(texsize)/((float)((screen_height)))); // Slight fuzziness - MakeScreenTexture(HWD_SCREENTEXTURE_GENERIC1); + MakeScreenTexture(tex); SetBlend(PF_Modulated|PF_Translucent|PF_NoDepthTest); - //pglBindTexture(GL_TEXTURE_2D, screentexture); + pglBindTexture(GL_TEXTURE_2D, screenTextures[tex]); for (i = 0; i < 1; i += 2.f/vid.height) { @@ -3309,8 +3310,9 @@ EXPORT void HWRAPI(RenderVhsEffect) (fixed_t upbary, fixed_t downbary, UINT8 upd } // Upward bar - MakeScreenTexture(HWD_SCREENTEXTURE_GENERIC1); - //pglBindTexture(GL_TEXTURE_2D, screentexture); + MakeScreenTexture(tex); + pglBindTexture(GL_TEXTURE_2D, screenTextures[tex]); + color[0] = color[1] = color[2] = 190; color[3] = 250; pglColor4ubv(color); @@ -3337,8 +3339,8 @@ EXPORT void HWRAPI(RenderVhsEffect) (fixed_t upbary, fixed_t downbary, UINT8 upd pglDrawArrays(GL_TRIANGLE_FAN, 0, 4); // Downward bar - MakeScreenTexture(HWD_SCREENTEXTURE_GENERIC1); - //pglBindTexture(GL_TEXTURE_2D, screentexture); + MakeScreenTexture(tex); + pglBindTexture(GL_TEXTURE_2D, screenTextures[tex]); fix[0] = 0.0f; fix[6] = xfix; -- 2.54.0 From b8483376c42474fff3e3a561aefc4d3d03d7e821 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 27 Nov 2024 22:29:49 +0100 Subject: [PATCH 063/143] dont draw final screen texture twice if you use native res no need to saves some performance --- src/i_video.h | 2 ++ src/sdl/i_video.c | 27 ++++++++++++++++++++++++++- src/sdl/ogl_sdl.c | 7 ++++++- 3 files changed, 34 insertions(+), 2 deletions(-) diff --git a/src/i_video.h b/src/i_video.h index fc71df557..76055a6aa 100644 --- a/src/i_video.h +++ b/src/i_video.h @@ -139,6 +139,8 @@ UINT32 I_GetRefreshRate(void); boolean I_UseNativeKeyboard(void); +boolean I_CheckNativeRes(void); + #ifdef USE_FBO_OGL #if defined (__unix__) extern boolean xwaylandcrap; diff --git a/src/sdl/i_video.c b/src/sdl/i_video.c index 73a1f992d..1dcfe57a7 100644 --- a/src/sdl/i_video.c +++ b/src/sdl/i_video.c @@ -755,10 +755,35 @@ static INT32 SDLJoyAxis(const Sint16 axis, evtype_t which) return raxis; } +boolean I_CheckNativeRes(void) +{ + static int oldwidth = 0, oldheight = 0; + static boolean resstate = false; + int currentDisplayIndex = 0; + SDL_DisplayMode curmode; + + if (oldwidth == vid.width && oldheight == vid.height) + { + return resstate; + } + + currentDisplayIndex = SDL_GetWindowDisplayIndex(window); + + if (SDL_GetCurrentDisplayMode(currentDisplayIndex, &curmode) != 0) + { + return resstate; + } + + resstate = ((vid.width == curmode.w) && (vid.height == curmode.h)); + oldwidth = vid.width; + oldheight = vid.height; + return resstate; +} + #ifdef USE_FBO_OGL void I_DownSample(void) { - if (!cv_glframebuffer.value || !supportFBO) //no sense to do this crap if we cant benefit from it + if (!cv_glframebuffer.value || !supportFBO || I_CheckNativeRes()) //no sense to do this crap if we cant benefit from it { downsample = false; return; diff --git a/src/sdl/ogl_sdl.c b/src/sdl/ogl_sdl.c index 2b94669ed..3d57b1f14 100644 --- a/src/sdl/ogl_sdl.c +++ b/src/sdl/ogl_sdl.c @@ -271,7 +271,12 @@ void OglSdlFinishUpdate(boolean waitvbl) // Sryder: We need to draw the final screen texture again into the other buffer in the original position so that // effects that want to take the old screen can do so after this - HWR_DrawScreenFinalTexture(realwidth, realheight); + if ((!I_CheckNativeRes()) // well we dont need it on native res it seems +#ifdef USE_FBO_OGL + && (!UseScreenFBO()) +#endif + ) + HWR_DrawScreenFinalTexture(realwidth, realheight); } EXPORT void HWRAPI(OglSdlSetPalette) (RGBA_t *palette) -- 2.54.0 From dbdd5b8b6ea63e8caee27ded9b0b619bfb8dfae8 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 27 Nov 2024 22:34:48 +0100 Subject: [PATCH 064/143] only apply palrender postprocess shader once --- src/hardware/hw_drv.h | 2 +- src/hardware/hw_main.c | 4 ++-- src/hardware/hw_main.h | 2 +- src/hardware/r_opengl/r_opengl.c | 6 +++--- src/sdl/ogl_sdl.c | 4 ++-- 5 files changed, 9 insertions(+), 9 deletions(-) diff --git a/src/hardware/hw_drv.h b/src/hardware/hw_drv.h index 8376ab405..335940142 100644 --- a/src/hardware/hw_drv.h +++ b/src/hardware/hw_drv.h @@ -60,7 +60,7 @@ EXPORT void HWRAPI(FlushScreenTextures) (void); EXPORT void HWRAPI(DoScreenWipe) (int wipeStart, int wipeEnd); EXPORT void HWRAPI(DrawScreenTexture) (int tex, FSurfaceInfo *surf, FBITFIELD polyflags); EXPORT void HWRAPI(MakeScreenTexture) (int tex); -EXPORT void HWRAPI(DrawScreenFinalTexture) (int tex, INT32 width, INT32 height); +EXPORT void HWRAPI(DrawScreenFinalTexture) (int tex, INT32 width, INT32 height, boolean useshader); EXPORT void HWRAPI(RenderVhsEffect) (fixed_t upbary, fixed_t downbary, UINT8 updistort, UINT8 downdistort, UINT8 barsize); diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 53df1ce5f..203c62432 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -5626,9 +5626,9 @@ void HWR_MakeScreenFinalTexture(void) HWD.pfnMakeScreenTexture(HWD_SCREENTEXTURE_GENERIC2); } -void HWR_DrawScreenFinalTexture(INT32 width, INT32 height) +void HWR_DrawScreenFinalTexture(INT32 width, INT32 height, boolean useshader) { - HWD.pfnDrawScreenFinalTexture(HWD_SCREENTEXTURE_GENERIC2, width, height); + HWD.pfnDrawScreenFinalTexture(HWD_SCREENTEXTURE_GENERIC2, width, height, useshader); } #endif // HWRENDER diff --git a/src/hardware/hw_main.h b/src/hardware/hw_main.h index daa837e10..8d4228a26 100644 --- a/src/hardware/hw_main.h +++ b/src/hardware/hw_main.h @@ -131,7 +131,7 @@ void HWR_DrawIntermissionBG(void); void HWR_DoWipe(UINT8 wipenum, UINT8 scrnnum); void HWR_RenderVhsEffect(fixed_t upbary, fixed_t downbary, UINT8 updistort, UINT8 downdistort, UINT8 barsize); void HWR_MakeScreenFinalTexture(void); -void HWR_DrawScreenFinalTexture(INT32 width, INT32 height); +void HWR_DrawScreenFinalTexture(INT32 width, INT32 height, boolean useshader); // hw_main.c: Segs void HWR_ProcessSeg(void); // Sort of like GLWall::Process in GZDoom diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index df99f4437..d918addef 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -3396,7 +3396,7 @@ EXPORT void HWRAPI(MakeScreenTexture) (int tex) tex_downloaded = screenTextures[tex]; } -EXPORT void HWRAPI(DrawScreenFinalTexture)(int tex, INT32 width, INT32 height) +EXPORT void HWRAPI(DrawScreenFinalTexture)(int tex, INT32 width, INT32 height, boolean useshader) { float xfix, yfix; float origaspect, newaspect; @@ -3463,7 +3463,7 @@ EXPORT void HWRAPI(DrawScreenFinalTexture)(int tex, INT32 width, INT32 height) pglBindTexture(GL_TEXTURE_2D, screenTextures[tex]); - if (HWR_ShouldUsePaletteRendering()) + if (useshader) pglUseProgram(gl_shaders[SHADER_PALETTE_POSTPROCESS].program); // palette postprocess shader pglColor4ubv(white); @@ -3473,7 +3473,7 @@ EXPORT void HWRAPI(DrawScreenFinalTexture)(int tex, INT32 width, INT32 height) pglDrawArrays(GL_TRIANGLE_FAN, 0, 4); - if (HWR_ShouldUsePaletteRendering()) + if (useshader) pglUseProgram(0); tex_downloaded = screenTextures[tex]; diff --git a/src/sdl/ogl_sdl.c b/src/sdl/ogl_sdl.c index 3d57b1f14..e1e484bcc 100644 --- a/src/sdl/ogl_sdl.c +++ b/src/sdl/ogl_sdl.c @@ -258,7 +258,7 @@ void OglSdlFinishUpdate(boolean waitvbl) GLFramebuffer_Unbind(); #endif - HWR_DrawScreenFinalTexture(sdlw, sdlh); + HWR_DrawScreenFinalTexture(sdlw, sdlh, HWR_ShouldUsePaletteRendering()); #ifdef USE_FBO_OGL if (UseScreenFBO()) @@ -276,7 +276,7 @@ void OglSdlFinishUpdate(boolean waitvbl) && (!UseScreenFBO()) #endif ) - HWR_DrawScreenFinalTexture(realwidth, realheight); + HWR_DrawScreenFinalTexture(realwidth, realheight, false); } EXPORT void HWRAPI(OglSdlSetPalette) (RGBA_t *palette) -- 2.54.0 From 2a7e4425448429bcf549a6b2fe6ff9c070c6d184 Mon Sep 17 00:00:00 2001 From: Indev Date: Thu, 28 Nov 2024 00:54:12 +0300 Subject: [PATCH 065/143] Use textinput_t for addon search --- src/filesrch.c | 11 +++++----- src/filesrch.h | 4 +++- src/m_menu.c | 51 +++++++---------------------------------------- src/m_textinput.c | 2 ++ 4 files changed, 18 insertions(+), 50 deletions(-) diff --git a/src/filesrch.c b/src/filesrch.c index 3a3a576ce..84766f395 100644 --- a/src/filesrch.c +++ b/src/filesrch.c @@ -327,7 +327,8 @@ char menupath[1024]; size_t menupathindex[menudepth]; size_t menudepthleft = menudepth; -char menusearch[MAXSTRINGLENGTH+1]; +char menusearchbuf[MAXSTRINGLENGTH+1]; +textinput_t menusearch; char **dirmenu, **coredirmenu; // core only local for this file size_t sizedirmenu, sizecoredirmenu; // ditto @@ -497,7 +498,7 @@ static boolean filemenucmp(char *haystack, char *needle) strupr(localhaystack); if (cv_addons_search_type.value) return (strstr(localhaystack, needle) != 0); - return (!strncmp(localhaystack, needle, menusearch[0])); + return (!strncmp(localhaystack, needle, menusearch.length)); } void closefilemenu(boolean validsize) @@ -563,7 +564,7 @@ void searchfilemenu(char *tempname) first = (((UINT8)(coredirmenu[0][DIR_TYPE]) == EXT_UP) ? 1 : 0); // skip UP... - if (!menusearch[0]) + if (!menusearch.length) { if (dirmenu) Z_Free(dirmenu); @@ -590,7 +591,7 @@ void searchfilemenu(char *tempname) return; } - strcpy(localmenusearch, menusearch+1); + strcpy(localmenusearch, menusearch.buffer); if (!cv_addons_search_case.value) strupr(localmenusearch); @@ -652,7 +653,7 @@ boolean preparefilemenu(boolean samedepth, boolean replayhut) tempname = Z_StrDup(dirmenu[dir_on[menudepthleft]]+DIR_STRING); // don't need to I_Error if can't make - not important, just QoL } else - menusearch[0] = menusearch[1] = 0; // clear search + M_TextInputInit(&menusearch, menusearchbuf, MAXSTRINGLENGTH+1); if (!(dirhandle = opendir(menupath))) // get directory { diff --git a/src/filesrch.h b/src/filesrch.h index dd0fb404a..76d5700c0 100644 --- a/src/filesrch.h +++ b/src/filesrch.h @@ -7,6 +7,7 @@ #include "doomdef.h" #include "d_netfil.h" #include "m_menu.h" // MAXSTRINGLENGTH +#include "m_textinput.h" extern consvar_t cv_addons_option, cv_addons_folder, cv_addons_md5, cv_addons_showall, cv_addons_search_case, cv_addons_search_type; @@ -34,7 +35,8 @@ extern char menupath[1024]; extern size_t menupathindex[menudepth]; extern size_t menudepthleft; -extern char menusearch[MAXSTRINGLENGTH+1]; +extern char menusearchbuf[MAXSTRINGLENGTH+1]; +extern textinput_t menusearch; extern char **dirmenu; extern size_t sizedirmenu; diff --git a/src/m_menu.c b/src/m_menu.c index 86c64eccb..6fea58256 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -6371,16 +6371,14 @@ static void M_DrawAddons(void) y = BASEVIDHEIGHT - currentMenu->y + 1; M_DrawTextBox(x - (21 + 5), y, MAXSTRINGLENGTH, 1); - if (menusearch[0]) - V_DrawString(x - 18, y + 8, V_ALLOWLOWERCASE, menusearch+1); + + if (menusearch.length) + M_DrawTextInput(x - 18, y + 8, &menusearch, 0); else V_DrawString(x - 18, y + 8, V_ALLOWLOWERCASE|V_TRANSLUCENT, "Type to search..."); - if (skullAnimCounter < 4) - V_DrawCharacter(x - 18 + V_StringWidth(menusearch+1, 0), y + 8, - '_' | 0x80, false); x -= (21 + 5 + 16); - V_DrawSmallScaledPatch(x, y + 4, (menusearch[0] ? 0 : V_TRANSLUCENT), addonsp[NUM_EXT+3]); + V_DrawSmallScaledPatch(x, y + 4, (menusearch.length ? 0 : V_TRANSLUCENT), addonsp[NUM_EXT+3]); x = BASEVIDWIDTH - x - 16; V_DrawSmallScaledPatch(x, y + 4, ((!majormods) ? 0 : V_TRANSLUCENT), addonsp[NUM_EXT+4]); @@ -6456,43 +6454,6 @@ static void M_AddonAutoLoad(INT32 ch) fclose(autoloadconfigfile); } -#define len menusearch[0] -static boolean M_ChangeStringAddons(INT32 choice) -{ - choice = M_ShiftChar(choice); - - switch (choice) - { - case KEY_DEL: - if (len) - { - len = menusearch[1] = 0; - return true; - } - break; - case KEY_BACKSPACE: - if (len) - { - menusearch[1+--len] = 0; - return true; - } - break; - default: - if (choice >= 32 && choice <= 127) - { - if (len < MAXSTRINGLENGTH - 1) - { - menusearch[1+len++] = (char)choice; - menusearch[1+len] = 0; - return true; - } - } - break; - } - return false; -} -#undef len - // i hate myself static boolean DumbStartsWith(const char *pre, const char *str) { @@ -6505,8 +6466,10 @@ static void M_HandleAddons(INT32 choice) { boolean exitmenu = false; // exit to previous menu - if (M_ChangeStringAddons(choice)) + if (M_TextInputHandle(&menusearch, choice)) { + S_StartSound(NULL,sfx_menu1); + char *tempname = NULL; if (dirmenu && dirmenu[dir_on[menudepthleft]]) tempname = Z_StrDup(dirmenu[dir_on[menudepthleft]]+DIR_STRING); // don't need to I_Error if can't make - not important, just QoL diff --git a/src/m_textinput.c b/src/m_textinput.c index 83adbf8bf..266a8f300 100644 --- a/src/m_textinput.c +++ b/src/m_textinput.c @@ -140,6 +140,8 @@ void M_TextInputClear(textinput_t *input) input->cursor = 0; input->select = 0; input->length = 0; + + input->buffer[0] = 0; } void M_TextInputSetString(textinput_t *input, const char *c) -- 2.54.0 From 51808b8cedc74082a3d7926a1d967d37959cf001 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 27 Nov 2024 23:00:16 +0100 Subject: [PATCH 066/143] init polyobject thinker->references to 0 otherwise they wont get removed alot of the time --- src/p_polyobj.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/p_polyobj.c b/src/p_polyobj.c index f890b0bd0..5ea1e4074 100644 --- a/src/p_polyobj.c +++ b/src/p_polyobj.c @@ -153,6 +153,8 @@ FUNCINLINE static ATTRINLINE void PolyObj_AddThinker(thinker_t *th) th->next = thinkercap.next; th->prev = &thinkercap; thinkercap.next = th; + + th->references = 0; } static void FreeSideLists(void) -- 2.54.0 From 8662648ef5ff4ad7a42df7eb5e429641447788eb Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 26 Nov 2024 22:31:58 +0100 Subject: [PATCH 067/143] init polyobject thinker->references to 0 otherwise they wont get removed alot of the time --- src/p_polyobj.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/p_polyobj.c b/src/p_polyobj.c index 6f1259677..ffc6651b8 100644 --- a/src/p_polyobj.c +++ b/src/p_polyobj.c @@ -154,7 +154,7 @@ FUNCINLINE static ATTRINLINE void PolyObj_AddThinker(thinker_t *th) th->prev = &thinkercap; thinkercap.next = th; - //th->references = 0; + th->references = 0; th->cachable = false; // not initialising this made the mobjcache die thx! } -- 2.54.0 From 0ab732c9b29252a83aaa09c3c63a6742509f5697 Mon Sep 17 00:00:00 2001 From: Indev Date: Thu, 28 Nov 2024 22:03:21 +0300 Subject: [PATCH 068/143] Only check nodes that are in game in SV_ResendingSavegameToAnyone --- src/d_clisrv.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 6efeffc6f..722e81d6c 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -1796,7 +1796,7 @@ static boolean SV_ResendingSavegameToAnyone(void) INT32 i; for (i = 0; i < MAXNETNODES; i++) - if (resendingsavegame[i]) + if (nodeingame[i] && resendingsavegame[i]) return true; return false; } -- 2.54.0 From 9b6034853fca9b6b3e86dc821e2ce75ddfd91615 Mon Sep 17 00:00:00 2001 From: Indev Date: Thu, 28 Nov 2024 22:24:51 +0300 Subject: [PATCH 069/143] Simplify consistency check a bit --- src/d_clisrv.c | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 722e81d6c..839e2b97c 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -5399,11 +5399,10 @@ static void HandlePacketFromPlayer(SINT8 node) } // Check player consistancy during the level - if (((!can_receive_gamestate[node]) && realstart <= gametic && realstart > gametic - TICQUEUE+1 && gamestate == GS_LEVEL - && consistancy[realstart%TICQUEUE] != SHORT(netbuffer->u.clientpak.consistancy)) || (can_receive_gamestate[node] && realstart <= gametic && realstart + TICQUEUE - 1 > gametic && gamestate == GS_LEVEL + if (gamestate == GS_LEVEL + && (realstart > gametic - TICQUEUE+1 && realstart <= gametic) && consistancy[realstart%TICQUEUE] != SHORT(netbuffer->u.clientpak.consistancy) - && !resendingsavegame[node] && savegameresendcooldown[node] <= I_GetTime() - && !SV_ResendingSavegameToAnyone())) + && (!can_receive_gamestate[node] || (!resendingsavegame[node] && savegameresendcooldown[node] <= I_GetTime() && !SV_ResendingSavegameToAnyone()))) { //#ifndef SATURNPAK // lug: keep this behaviour for v7.1 atleast // we need to send this so the client can tell us if it can receive the savegame -- 2.54.0 From 85464921ba9d9286c74f4cd15e5b27d5186a63b2 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 28 Nov 2024 08:01:24 +0100 Subject: [PATCH 070/143] eh this looks better --- src/p_local.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/p_local.h b/src/p_local.h index fe1d10d73..7bc343775 100644 --- a/src/p_local.h +++ b/src/p_local.h @@ -265,7 +265,7 @@ void P_SceneryThinker(mobj_t *mobj); // To test it in Lua, check mobj.valid FUNCINLINE static ATTRINLINE boolean P_MobjWasRemoved(const mobj_t *mobj) { - return !(mobj && mobj->thinker.function.acp1 == (actionf_p1)P_MobjThinker); + return (!mobj || mobj->thinker.function.acp1 != (actionf_p1)P_MobjThinker); } fixed_t P_MobjFloorZ(mobj_t *mobj, sector_t *sector, sector_t *boundsec, fixed_t x, fixed_t y, line_t *line, boolean lowest, boolean perfect); -- 2.54.0 From 8b764268257a70f546cdcad02e0757fe84de301a Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 28 Nov 2024 08:09:36 +0100 Subject: [PATCH 071/143] remove dupes --- src/p_saveg.c | 5 ----- 1 file changed, 5 deletions(-) diff --git a/src/p_saveg.c b/src/p_saveg.c index dc0276bb5..04f00c63d 100644 --- a/src/p_saveg.c +++ b/src/p_saveg.c @@ -2173,11 +2173,6 @@ static void LoadMobjThinker(actionf_p1 thinker) mobj->realyscale = FRACUNIT; mobj->stretchslam = 0; - mobj->stretchslam = 0; - mobj->slamsoundtimer = 0; - - mobj->mirrored = 0; - // Timer for slam sound effect mobj->slamsoundtimer = 0; -- 2.54.0 From 1bd0c5d9bfb941791444051cd203ff606ef5d098 Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 29 Nov 2024 09:36:05 +0100 Subject: [PATCH 072/143] those dont need to be inlined tbh --- src/p_tick.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/p_tick.c b/src/p_tick.c index d6243fde9..700424b17 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -327,7 +327,7 @@ static inline void P_RunThinkers(void) } } -static inline void P_DeviceRumbleTick(void) +static void P_DeviceRumbleTick(void) { UINT8 i; @@ -397,7 +397,7 @@ void P_RunChaseCameras(void) } } -static inline void P_RunQuakes(void) +static void P_RunQuakes(void) { fixed_t ir; @@ -434,7 +434,7 @@ void P_Ticker(boolean run) { INT32 i; - // Increment jointime and quittime even if paused + // Increment jointime even if paused for (i = 0; i < MAXPLAYERS; i++) { if (playeringame[i]) -- 2.54.0 From 91bb601ecbb558a2a0015c727cca88986eabe07a Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 29 Nov 2024 09:51:58 +0100 Subject: [PATCH 073/143] why? --- src/d_netcmd.c | 4 ---- 1 file changed, 4 deletions(-) diff --git a/src/d_netcmd.c b/src/d_netcmd.c index 87b8e8bcf..c440cf6bf 100644 --- a/src/d_netcmd.c +++ b/src/d_netcmd.c @@ -4886,10 +4886,6 @@ static void Got_RequestAddfilecmd(UINT8 **cp, INT32 playernum) boolean kick = false; boolean toomany = false; INT32 i,j; - serverinfo_pak *dummycheck = NULL; - - // Shut the compiler up. - (void)dummycheck; READSTRINGN(*cp, filename, 240); READMEM(*cp, md5sum, 16); -- 2.54.0 From 3c0899263fa7c46dd26214ee8c3afbfd8baec319 Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 29 Nov 2024 10:07:20 +0100 Subject: [PATCH 074/143] those are redundant --- src/d_clisrv.c | 11 +---------- 1 file changed, 1 insertion(+), 10 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 839e2b97c..b30bbe042 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -3249,13 +3249,7 @@ void CL_RemovePlayer(INT32 playernum, INT32 reason) { SV_InitResynchVars(node); // If a resynch was in progress, well, it no longer needs to be. - nodeingame[node] = false; -#ifdef SATURNPAK - is_client_saturn[node] = false; -#endif -#ifdef SATURNSYNCH - can_receive_gamestate[node] = false; -#endif + nodeingame[node] = false; // do we even need this? Net_CloseConnection(node); ResetNode(node); } @@ -3361,9 +3355,6 @@ void CL_Reset(void) if (servernode > 0 && servernode < MAXNETNODES) { nodeingame[(UINT8)servernode] = false; -#ifdef SATURNPAK - is_client_saturn[(UINT8)servernode] = false; -#endif Net_CloseConnection(servernode); } D_CloseConnection(); // netgame = false -- 2.54.0 From a2aa43e7fc90372f547640a9542394d00ae7ff79 Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 29 Nov 2024 10:39:40 +0100 Subject: [PATCH 075/143] dont think we need to reset anything here kick cmd gets send out which should clear stuff in theory --- src/d_clisrv.c | 6 ------ 1 file changed, 6 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index b30bbe042..f680c9cc8 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -5605,12 +5605,6 @@ static void HandlePacketFromPlayer(SINT8 node) } Net_CloseConnection(node); nodeingame[node] = false; -#ifdef SATURNPAK - is_client_saturn[node] = false; -#endif -#ifdef SATURNSYNCH - can_receive_gamestate[node] = false; -#endif break; // -------------------------------------------- CLIENT RECEIVE ---------- case PT_RESYNCHEND: -- 2.54.0 From 4a837d33396af97921a5406a1796249b2b67837f Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 29 Nov 2024 10:14:34 +0100 Subject: [PATCH 076/143] Fix buffer overrun with players with no associated node https://git.do.srb2.org/STJr/SRB2/-/merge_requests/810/diffs?commit_id=af9164f336a65634f6908e677b47773d88f583af --- src/d_clisrv.c | 59 +++++++++++++++++++++++++------------------------- 1 file changed, 29 insertions(+), 30 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index f680c9cc8..8e144eab0 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -3240,7 +3240,7 @@ void CL_RemovePlayer(INT32 playernum, INT32 reason) demo_extradata[playernum] |= DXD_PLAYSTATE; - if (server && !demo.playback) + if (server && !demo.playback && playernode[playernum] != UINT8_MAX) { INT32 node = playernode[playernum]; //playerpernode[node] = 0; // It'd be better to remove them all at once, but ghosting happened, so continue to let CL_RemovePlayer do it one-by-one @@ -3699,16 +3699,13 @@ static void Command_Kick(void) if (pn == -1 || pn == 0) return; - if (server) + // Special case if we are trying to kick a player who is downloading the game state: + // trigger a timeout instead of kicking them, because a kick would only + // take effect after they have finished downloading + if (server && playernode[pn] != UINT8_MAX && sendingsavegame[playernode[pn]]) { - // Special case if we are trying to kick a player who is downloading the game state: - // trigger a timeout instead of kicking them, because a kick would only - // take effect after they have finished downloading - if (sendingsavegame[playernode[pn]]) - { - Net_ConnectionTimeout(playernode[pn]); - return; - } + Net_ConnectionTimeout(playernode[pn]); + return; } WRITESINT8(p, pn); @@ -3764,7 +3761,7 @@ static void Got_KickCmd(UINT8 **p, INT32 playernum) // Is playernum authorized to make this kick? if (playernum != serverplayer && !IsPlayerAdmin(playernum) - /*&& !(playerpernode[playernode[playernum]] == 2 + /*&& !(playernode[playernum] != UINT8_MAX && playerpernode[playernode[playernum]] == 2 //&& nodetoplayer2[playernode[playernum]] == pnum)*/) { // We received a kick command from someone who isn't the @@ -6318,29 +6315,31 @@ static void SV_Maketic(void) INT32 j; for (j = 0; j < MAXNETNODES; j++) - if (playerpernode[j]) - { - INT32 player = nodetoplayer[j]; - if ((netcmds[maketic%TICQUEUE][player].angleturn & TICCMD_RECEIVED) == 0) - { // we didn't receive this tic - INT32 i; + { + if (!playerpernode[j]) + continue; - DEBFILE(va("MISS tic%4d for node %d\n", maketic, j)); + INT32 player = nodetoplayer[j]; + if ((netcmds[maketic%TICQUEUE][player].angleturn & TICCMD_RECEIVED) == 0) + { // we didn't receive this tic + INT32 i; + + DEBFILE(va("MISS tic%4d for node %d\n", maketic, j)); #if defined(PARANOIA) && 0 - CONS_Debug(DBG_NETPLAY, "Client Misstic %d\n", maketic); + CONS_Debug(DBG_NETPLAY, "Client Misstic %d\n", maketic); #endif - // copy the old tic - for (i = 0; i < playerpernode[j]; i++) - { - if (i == 0) player = nodetoplayer[j]; - else if (i == 1) player = nodetoplayer2[j]; - else if (i == 2) player = nodetoplayer3[j]; - else if (i == 3) player = nodetoplayer4[j]; - netcmds[maketic%TICQUEUE][player] = netcmds[(maketic-1)%TICQUEUE][player]; - netcmds[maketic%TICQUEUE][player].angleturn &= ~TICCMD_RECEIVED; - } + // copy the old tic + for (i = 0; i < playerpernode[j]; i++) + { + if (i == 0) player = nodetoplayer[j]; + else if (i == 1) player = nodetoplayer2[j]; + else if (i == 2) player = nodetoplayer3[j]; + else if (i == 3) player = nodetoplayer4[j]; + netcmds[maketic%TICQUEUE][player] = netcmds[(maketic-1)%TICQUEUE][player]; + netcmds[maketic%TICQUEUE][player].angleturn &= ~TICCMD_RECEIVED; } } + } // all tic are now proceed make the next maketic++; @@ -6569,7 +6568,7 @@ static void UpdatePingTable(void) PingUpdate(); // update node latency values so we can take an average later. for (i = 0; i < MAXPLAYERS; i++) - if (playeringame[i]) + if (playeringame[i] && playernode[i] != UINT8_MAX) realpingtable[i] += GetLag(playernode[i]); pingmeasurecount++; } -- 2.54.0 From 3b2251017c407e6356289f0083fbf0af8f2b7f4e Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 29 Nov 2024 12:14:15 +0100 Subject: [PATCH 077/143] use continue instead of huge if block --- src/d_clisrv.c | 198 +++++++++++++++++++++++++------------------------ src/g_game.c | 2 +- 2 files changed, 101 insertions(+), 99 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 8e144eab0..e5a61845c 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -6149,106 +6149,108 @@ static void SV_SendTics(void) // for each node create a packet with x tics and send it // x is computed using supposedtics[n], max packet size and maketic for (n = 1; n < MAXNETNODES; n++) - if (nodeingame[n]) + { + if (!nodeingame[n]) + continue; + + // assert supposedtics[n]>=nettics[n] + realfirsttic = supposedtics[n]; + lasttictosend = maketic; + + if (lasttictosend - nettics[n] >= BACKUPTICS) + lasttictosend = nettics[n] + BACKUPTICS-1; + + if (realfirsttic >= lasttictosend) { - // assert supposedtics[n]>=nettics[n] - realfirsttic = supposedtics[n]; - lasttictosend = maketic; - - if (lasttictosend - nettics[n] >= BACKUPTICS) - lasttictosend = nettics[n] + BACKUPTICS-1; - - if (realfirsttic >= lasttictosend) - { - // well we have sent all tics we will so use extrabandwidth - // to resent packet that are supposed lost (this is necessary since lost - // packet detection work when we have received packet with firsttic > neededtic - // (getpacket servertics case) - DEBFILE(va("Nothing to send node %u mak=%u sup=%u net=%u \n", - n, lasttictosend, supposedtics[n], nettics[n])); - realfirsttic = nettics[n]; - if (realfirsttic >= lasttictosend || (I_GetTime() + n)&3) - // all tic are ok - continue; - DEBFILE(va("Sent %d anyway\n", realfirsttic)); - } - if (realfirsttic < firstticstosend) - realfirsttic = firstticstosend; - - // compute the length of the packet and cut it if too large - packsize = BASESERVERTICSSIZE; - for (i = realfirsttic; i < lasttictosend; i++) - { - packsize += sizeof (ticcmd_t) * doomcom->numslots; - packsize += TotalTextCmdPerTic(i); - - if (packsize > software_MAXPACKETLENGTH) - { - DEBFILE(va("packet too large (%s) at tic %d (should be from %d to %d)\n", - sizeu1(packsize), i, realfirsttic, lasttictosend)); - lasttictosend = i; - - // too bad: too much player have send extradata and there is too - // much data in one tic. - // To avoid it put the data on the next tic. (see getpacket - // textcmd case) but when numplayer changes the computation can be different - if (lasttictosend == realfirsttic) - { - if (packsize > MAXPACKETLENGTH) - I_Error("Too many players: can't send %s data for %d players to node %d\n" - "Well sorry nobody is perfect....\n", - sizeu1(packsize), doomcom->numslots, n); - else - { - lasttictosend++; // send it anyway! - DEBFILE("sending it anyway\n"); - } - } - break; - } - } - - // Send the tics - netbuffer->packettype = PT_SERVERTICS; - netbuffer->u.serverpak.starttic = (UINT8)realfirsttic; - netbuffer->u.serverpak.numtics = (UINT8)(lasttictosend - realfirsttic); - netbuffer->u.serverpak.numslots = (UINT8)SHORT(doomcom->numslots); - bufpos = (UINT8 *)&netbuffer->u.serverpak.cmds; - - for (i = realfirsttic; i < lasttictosend; i++) - { - bufpos = G_DcpyTiccmd(bufpos, netcmds[i%TICQUEUE], doomcom->numslots * sizeof (ticcmd_t)); - } - - // add textcmds - for (i = realfirsttic; i < lasttictosend; i++) - { - ntextcmd = bufpos++; - *ntextcmd = 0; - for (j = 0; j < MAXPLAYERS; j++) - { - UINT8 *textcmd = D_GetExistingTextcmd(i, j); - INT32 size = textcmd ? textcmd[0] : 0; - - if ((!j || playeringame[j]) && size) - { - (*ntextcmd)++; - WRITEUINT8(bufpos, j); - M_Memcpy(bufpos, textcmd, size + 1); - bufpos += size + 1; - } - } - } - packsize = bufpos - (UINT8 *)&(netbuffer->u); - - HSendPacket(n, false, 0, packsize); - // when tic are too large, only one tic is sent so don't go backward! - if (lasttictosend-doomcom->extratics > realfirsttic) - supposedtics[n] = lasttictosend-doomcom->extratics; - else - supposedtics[n] = lasttictosend; - if (supposedtics[n] < nettics[n]) supposedtics[n] = nettics[n]; + // well we have sent all tics we will so use extrabandwidth + // to resent packet that are supposed lost (this is necessary since lost + // packet detection work when we have received packet with firsttic > neededtic + // (getpacket servertics case) + DEBFILE(va("Nothing to send node %u mak=%u sup=%u net=%u \n", + n, lasttictosend, supposedtics[n], nettics[n])); + realfirsttic = nettics[n]; + if (realfirsttic >= lasttictosend || (I_GetTime() + n)&3) + // all tic are ok + continue; + DEBFILE(va("Sent %d anyway\n", realfirsttic)); } + if (realfirsttic < firstticstosend) + realfirsttic = firstticstosend; + + // compute the length of the packet and cut it if too large + packsize = BASESERVERTICSSIZE; + for (i = realfirsttic; i < lasttictosend; i++) + { + packsize += sizeof (ticcmd_t) * doomcom->numslots; + packsize += TotalTextCmdPerTic(i); + + if (packsize > software_MAXPACKETLENGTH) + { + DEBFILE(va("packet too large (%s) at tic %d (should be from %d to %d)\n", + sizeu1(packsize), i, realfirsttic, lasttictosend)); + lasttictosend = i; + + // too bad: too much player have send extradata and there is too + // much data in one tic. + // To avoid it put the data on the next tic. (see getpacket + // textcmd case) but when numplayer changes the computation can be different + if (lasttictosend == realfirsttic) + { + if (packsize > MAXPACKETLENGTH) + I_Error("Too many players: can't send %s data for %d players to node %d\n" + "Well sorry nobody is perfect....\n", + sizeu1(packsize), doomcom->numslots, n); + else + { + lasttictosend++; // send it anyway! + DEBFILE("sending it anyway\n"); + } + } + break; + } + } + + // Send the tics + netbuffer->packettype = PT_SERVERTICS; + netbuffer->u.serverpak.starttic = (UINT8)realfirsttic; + netbuffer->u.serverpak.numtics = (UINT8)(lasttictosend - realfirsttic); + netbuffer->u.serverpak.numslots = (UINT8)SHORT(doomcom->numslots); + bufpos = (UINT8 *)&netbuffer->u.serverpak.cmds; + + for (i = realfirsttic; i < lasttictosend; i++) + { + bufpos = G_DcpyTiccmd(bufpos, netcmds[i%TICQUEUE], doomcom->numslots * sizeof (ticcmd_t)); + } + + // add textcmds + for (i = realfirsttic; i < lasttictosend; i++) + { + ntextcmd = bufpos++; + *ntextcmd = 0; + for (j = 0; j < MAXPLAYERS; j++) + { + UINT8 *textcmd = D_GetExistingTextcmd(i, j); + INT32 size = textcmd ? textcmd[0] : 0; + + if ((!j || playeringame[j]) && size) + { + (*ntextcmd)++; + WRITEUINT8(bufpos, j); + M_Memcpy(bufpos, textcmd, size + 1); + bufpos += size + 1; + } + } + } + packsize = bufpos - (UINT8 *)&(netbuffer->u); + + HSendPacket(n, false, 0, packsize); + // when tic are too large, only one tic is sent so don't go backward! + if (lasttictosend-doomcom->extratics > realfirsttic) + supposedtics[n] = lasttictosend-doomcom->extratics; + else + supposedtics[n] = lasttictosend; + if (supposedtics[n] < nettics[n]) supposedtics[n] = nettics[n]; + } // node 0 is me! supposedtics[0] = maketic; } diff --git a/src/g_game.c b/src/g_game.c index f807b724c..1b5626669 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -1285,7 +1285,7 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) if (player->spectator || cv_mouseturn.value) { - //THIS WORKS WTF???????? + //THIS WORKS WTF???????? cmd->angleturn = (INT16)(cmd->angleturn - ((mousex*(encoremode ? -1 : 1)*8))); cmd->driftturn = (INT16)(cmd->driftturn - ((mousex*(encoremode ? -1 : 1)*8))); } -- 2.54.0 From 8baa972bb21cd0564a6b87d2e69d610128844d48 Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 29 Nov 2024 13:15:46 +0100 Subject: [PATCH 078/143] this is also redundant --- src/d_clisrv.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index e5a61845c..47294e8c3 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -5448,8 +5448,6 @@ static void HandlePacketFromPlayer(SINT8 node) DEBFILE(va("player %d kicked (synch failure) [%u] %d!=%d\n", netconsole, realstart, consistancy[realstart%TICQUEUE], SHORT(netbuffer->u.clientpak.consistancy))); - gamestate_resend_counter[node] = 0; - DEBFILE(va("gamestate counter %d for node %d\n", gamestate_resend_counter[node], netconsole)); break; } } -- 2.54.0 From b784fc58d0db3033c422df2a1d8ac769d0d556a9 Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 29 Nov 2024 22:25:13 +0100 Subject: [PATCH 079/143] loading not sending just to clarify --- src/p_saveg.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/p_saveg.c b/src/p_saveg.c index 04f00c63d..83f607bf2 100644 --- a/src/p_saveg.c +++ b/src/p_saveg.c @@ -298,7 +298,7 @@ static void P_NetArchivePlayers(boolean resending) // // P_NetUnArchivePlayers // -static void P_NetUnArchivePlayers(boolean resending) +static void P_NetUnArchivePlayers(boolean reloading) { INT32 i, j; UINT16 flags; @@ -308,8 +308,9 @@ static void P_NetUnArchivePlayers(boolean resending) for (i = 0; i < MAXPLAYERS; i++) { - if (resending) + if (reloading) adminplayers[i] = (INT32)READSINT8(save_p); + // Do NOT memset player struct to 0 // other areas may initialize data elsewhere //memset(&players[i], 0, sizeof (player_t)); @@ -320,7 +321,7 @@ static void P_NetUnArchivePlayers(boolean resending) // sending player names, skin and color should not be necessary at all! // (that data is handled in the server config now) - if (resending) + if (reloading) READSTRINGN(save_p, player_names[i], MAXPLAYERNAME); players[i].aiming = READANGLE(save_p); @@ -347,7 +348,7 @@ static void P_NetUnArchivePlayers(boolean resending) players[i].flashpal = READUINT16(save_p); players[i].flashcount = READUINT16(save_p); - if (resending) + if (reloading) { players[i].skincolor = READUINT8(save_p); players[i].skin = READINT32(save_p); -- 2.54.0 From e3084cc28e8c60a0759c2a6aaf3b41b078034939 Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 29 Nov 2024 23:25:50 +0100 Subject: [PATCH 080/143] allow demo play commands while watching a demo again --- src/d_netcmd.c | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/src/d_netcmd.c b/src/d_netcmd.c index c440cf6bf..478b857c4 100644 --- a/src/d_netcmd.c +++ b/src/d_netcmd.c @@ -2515,9 +2515,15 @@ static void Command_Playdemo_f(void) return; } - if (gamestate == GS_LEVEL) + if (netgame) { - CONS_Printf(M_GetText("You can't play a demo while in a game.\n")); + CONS_Printf(M_GetText("You can't play a demo while in a netgame.\n")); + return; + } + + if (!demo.playback && gamestate == GS_LEVEL) // special case: allow starting another demo while watching a demo + { + CONS_Printf(M_GetText("You can't time a demo while in a game.\n")); return; } @@ -2554,7 +2560,13 @@ static void Command_Timedemo_f(void) return; } - if (gamestate == GS_LEVEL) + if (netgame) + { + CONS_Printf(M_GetText("You can't play a demo while in a netgame.\n")); + return; + } + + if (!demo.playback && gamestate == GS_LEVEL) // special case: allow starting another demo while watching a demo { CONS_Printf(M_GetText("You can't time a demo while in a game.\n")); return; -- 2.54.0 From 7730b69ef4b385b34fcc59d964cf71cf31c908ed Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 19:45:19 +0100 Subject: [PATCH 081/143] delete A_RollAngle things they cant be used, since theyre not synchsafe and nothing uses those anyways --- src/dehacked.c | 3 -- src/info.h | 3 -- src/p_enemy.c | 77 -------------------------------------------------- 3 files changed, 83 deletions(-) diff --git a/src/dehacked.c b/src/dehacked.c index dc4288be5..185694770 100644 --- a/src/dehacked.c +++ b/src/dehacked.c @@ -1493,9 +1493,6 @@ actionpointer_t actionpointers[] = {{A_SpawnObjectRelative}, "A_SPAWNOBJECTRELATIVE"}, {{A_ChangeAngleRelative}, "A_CHANGEANGLERELATIVE"}, {{A_ChangeAngleAbsolute}, "A_CHANGEANGLEABSOLUTE"}, - {{A_RollAngle}, "A_ROLLANGLE"}, - {{A_ChangeRollAngleRelative},"A_CHANGEROLLANGLERELATIVE"}, - {{A_ChangeRollAngleAbsolute},"A_CHANGEROLLANGLEABSOLUTE"}, {{A_PlaySound}, "A_PLAYSOUND"}, {{A_FindTarget}, "A_FINDTARGET"}, {{A_FindTracer}, "A_FINDTRACER"}, diff --git a/src/info.h b/src/info.h index aff87a663..6b2726f7e 100644 --- a/src/info.h +++ b/src/info.h @@ -159,9 +159,6 @@ enum actionnum A_SPAWNOBJECTRELATIVE, A_CHANGEANGLERELATIVE, A_CHANGEANGLEABSOLUTE, - A_ROLLANGLE, - A_CHANGEROLLANGLERELATIVE, - A_CHANGEROLLANGLEABSOLUTE, A_PLAYSOUND, A_FINDTARGET, A_FINDTRACER, diff --git a/src/p_enemy.c b/src/p_enemy.c index caa85e331..567342df9 100644 --- a/src/p_enemy.c +++ b/src/p_enemy.c @@ -165,9 +165,6 @@ void A_SpawnObjectAbsolute(mobj_t *actor); void A_SpawnObjectRelative(mobj_t *actor); void A_ChangeAngleRelative(mobj_t *actor); void A_ChangeAngleAbsolute(mobj_t *actor); -void A_RollAngle(mobj_t *actor); -void A_ChangeRollAngleRelative(mobj_t *actor); -void A_ChangeRollAngleAbsolute(mobj_t *actor); void A_PlaySound(mobj_t *actor); void A_FindTarget(mobj_t *actor); void A_FindTracer(mobj_t *actor); @@ -7183,80 +7180,6 @@ void A_ChangeAngleAbsolute(mobj_t *actor) actor->angle = FixedAngle(P_RandomRange(amin, amax)); } -// Function: A_RollAngle -// -// Description: Changes the roll angle. -// -// var1 = angle -// var2 = relative? (default) -// -void A_RollAngle(mobj_t *actor) -{ - INT32 locvar1 = var1; - INT32 locvar2 = var2; - const angle_t angle = FixedAngle(locvar1*FRACUNIT); - - if (LUA_CallAction(A_ROLLANGLE, actor)) - return; - - // relative (default) - if (!locvar2) - actor->rollangle += angle; - // absolute - else - actor->rollangle = angle; -} - -// Function: A_ChangeRollAngleRelative -// -// Description: Changes the roll angle to a random relative value between the min and max. Set min and max to the same value to eliminate randomness -// -// var1 = min -// var2 = max -// -void A_ChangeRollAngleRelative(mobj_t *actor) -{ - INT32 locvar1 = var1; - INT32 locvar2 = var2; - const fixed_t amin = locvar1*FRACUNIT; - const fixed_t amax = locvar2*FRACUNIT; - - if (LUA_CallAction(A_CHANGEROLLANGLERELATIVE, actor)) - return; - -#ifdef PARANOIA - if (amin > amax) - I_Error("A_ChangeRollAngleRelative: var1 is greater than var2"); -#endif - - actor->rollangle += FixedAngle(P_RandomRange(amin, amax)); -} - -// Function: A_ChangeRollAngleAbsolute -// -// Description: Changes the roll angle to a random absolute value between the min and max. Set min and max to the same value to eliminate randomness -// -// var1 = min -// var2 = max -// -void A_ChangeRollAngleAbsolute(mobj_t *actor) -{ - INT32 locvar1 = var1; - INT32 locvar2 = var2; - const fixed_t amin = locvar1*FRACUNIT; - const fixed_t amax = locvar2*FRACUNIT; - - if (LUA_CallAction(A_CHANGEROLLANGLEABSOLUTE, actor)) - return; - -#ifdef PARANOIA - if (amin > amax) - I_Error("A_ChangeRollAngleAbsolute: var1 is greater than var2"); -#endif - - actor->rollangle = FixedAngle(P_RandomRange(amin, amax)); -} - // Function: A_PlaySound // // Description: Plays a sound -- 2.54.0 From 6f6066906e076f98a10ea5d3e24dc293b730aeea Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 20:04:58 +0100 Subject: [PATCH 082/143] optimize sprite rotation / sprite drawing a bit - make software and ogl use same variable names - let papersprites also roll in ogl not just software - throw pitchnroll calc into a function to reduce code dupe - save some calcs when having sliptide roll disabled - fix software not calculating camang when just player roll is enabled (did that ever work right before? oops) - determine early if the sprite is supposed to rotate, and only if it really does, run the rotation stuff --- src/hardware/hw_main.c | 61 ++++++++++++++++++++++++++++-------------- src/r_patch.c | 9 +++++++ src/r_patch.h | 3 +++ src/r_things.c | 56 +++++++++++++++++++++++--------------- 4 files changed, 87 insertions(+), 42 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 203c62432..967d52cc5 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4437,7 +4437,10 @@ static void HWR_ProjectSprite(mobj_t *thing) boolean mirrored; boolean hflip; - angle_t ang, camang; + angle_t ang = 0; +#ifdef ROTSPRITE + angle_t camang = 0; +#endif boolean papersprite; INT32 heightsec, phs; INT32 dist = -1; @@ -4447,7 +4450,7 @@ static void HWR_ProjectSprite(mobj_t *thing) #ifdef ROTSPRITE patch_t *rotsprite = NULL; INT32 rollangle = 0; - angle_t rollsum = 0; + angle_t pitchnroll = 0; angle_t sliptiderollangle = 0; #endif @@ -4502,7 +4505,12 @@ static void HWR_ProjectSprite(mobj_t *thing) I_Error("HWR_ProjectSprite: invalid sprite number %i ", thing->sprite); #endif - rot = thing->frame&FF_FRAMEMASK; + rot = (thing->frame & FF_FRAMEMASK); + +#ifdef ROTSPRITE + // determine here if sprite should rotate for optimization + const boolean shouldrotate = (cv_spriteroll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle)); +#endif //Fab : 02-08-98: 'skin' override spritedef currently used for skin if ((thing->skin || thing->localskin) && thing->sprite == SPR_PLAY) @@ -4530,7 +4538,7 @@ static void HWR_ProjectSprite(mobj_t *thing) #ifdef ROTSPRITE sprinfo = &spriteinfo[thing->sprite]; #endif - rot = thing->frame&FF_FRAMEMASK; + rot = (thing->frame & FF_FRAMEMASK); thing->state->sprite = thing->sprite; thing->state->frame = thing->frame; } @@ -4543,7 +4551,13 @@ static void HWR_ProjectSprite(mobj_t *thing) #endif ang = R_PointToAngle (interp.x, interp.y) - interp.angle; - camang = R_PointToAngle (interp.x, interp.y); + +#ifdef ROTSPRITE + if (shouldrotate) + { + camang = R_PointToAngle (interp.x, interp.y); + } +#endif if (mirrored) ang = InvAngle(ang); @@ -4585,33 +4599,40 @@ static void HWR_ProjectSprite(mobj_t *thing) spr_topoffset = spritecachedinfo[lumpoff].topoffset; #ifdef ROTSPRITE - if (cv_spriteroll.value) + if (shouldrotate) { - rollangle = FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), interp.roll) - + FixedMul(FINESINE((ang) >> ANGLETOFINESHIFT), interp.pitch) - + FixedMul(FINECOSINE((camang) >> ANGLETOFINESHIFT), interp.sloperoll) - + FixedMul(FINESINE((camang) >> ANGLETOFINESHIFT), interp.slopepitch) - + thing->rollangle; - - if ((rollangle)||(thing->player && thing->player->sliproll)) + if (papersprite) { - if (thing->player) + // a positive rollangle should should pitch papersprites upwards relative to their facing angle + rollangle = InvAngle(thing->rollangle); + } + else + { + // this is very messy, but it on-the-fly calculates rotations for all the + // pitch and roll variables + pitchnroll = R_RotationAngle(ang, camang, &interp); + rollangle = thing->rollangle; + } + + if (rollangle || pitchnroll || (thing->player && thing->player->sliproll)) + { + if (thing->player && cv_sliptideroll.value) { - sliptiderollangle = cv_sliptideroll.value ? thing->player->sliproll*(thing->player->sliptidemem) : 0; - rollsum = rollangle+FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), sliptiderollangle); + sliptiderollangle = thing->player->sliproll * (thing->player->sliptidemem); + pitchnroll += rollangle + FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), sliptiderollangle); } else - rollsum = rollangle; + pitchnroll += rollangle; // this is kinda dumb lkmao, but try to mitigate shadows being weirdly offset on slopes if (thing->type == MT_SHADOW) { sprinfo->available = true; // < lmao sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].x = spr_offset>>FRACBITS; - sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].y = -8; // noones gonna replace shadow sprite anyways, right? that random value ftw, otherwise this clips into the ground Zzz... + sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].y = -8; // noones gonna replace shadow sprite anyways, right? this random value works, cant get any better otherwise this clips into the ground Zzz... } - rollangle = R_GetRollAngle(rollsum); + rollangle = R_GetRollAngle(pitchnroll); rotsprite = Patch_GetRotatedSprite(sprframe, (thing->frame & FF_FRAMEMASK), rot, flip, false, sprinfo, rollangle); if (rotsprite != NULL) @@ -4718,7 +4739,7 @@ static void HWR_ProjectSprite(mobj_t *thing) vis->spriteyoffset = FIXED_TO_FLOAT(spr_topoffset); #ifdef ROTSPRITE - if ((rotsprite) && (cv_spriteroll.value)) + if (rotsprite && cv_spriteroll.value) vis->gpatch = (GLPatch_t *)rotsprite; else #endif diff --git a/src/r_patch.c b/src/r_patch.c index 37e7a2321..ae8ec4f5e 100644 --- a/src/r_patch.c +++ b/src/r_patch.c @@ -17,6 +17,7 @@ #include "i_video.h" #include "r_data.h" #include "r_draw.h" +#include "r_fps.h" #include "r_patch.h" #include "r_things.h" #include "z_zone.h" @@ -803,6 +804,14 @@ INT32 R_GetRollAngle(angle_t rollangle) return ra; } +angle_t R_RotationAngle(angle_t ang, angle_t camang, interpmobjstate_t *interp) +{ + return FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), interp->roll) + + FixedMul(FINESINE((ang) >> ANGLETOFINESHIFT), interp->pitch) + + FixedMul(FINECOSINE((camang) >> ANGLETOFINESHIFT), interp->sloperoll) + + FixedMul(FINESINE((camang) >> ANGLETOFINESHIFT), interp->slopepitch); +} + patch_t *Patch_GetRotatedSprite(spriteframe_t *sprite, size_t frame, size_t spriteangle, boolean flip, boolean adjustfeet, void *info, INT32 rotationangle) { rotsprite_t *rotsprite; diff --git a/src/r_patch.h b/src/r_patch.h index ac8072a43..5edaa46fb 100644 --- a/src/r_patch.h +++ b/src/r_patch.h @@ -15,6 +15,7 @@ #define __R_PATCH__ #include "r_defs.h" +#include "r_fps.h" #include "doomdef.h" // Structs @@ -53,6 +54,8 @@ void R_ParseSPRTINFOLump(UINT16 wadNum, UINT16 lumpNum); // Sprite rotation #ifdef ROTSPRITE INT32 R_GetRollAngle(angle_t rollangle); +angle_t R_RotationAngle(angle_t ang, angle_t camang, interpmobjstate_t *interp); + patch_t *Patch_GetRotatedSprite( spriteframe_t *sprite, size_t frame, size_t spriteangle, diff --git a/src/r_things.c b/src/r_things.c index f3c698b9d..1e8c33d32 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -1142,7 +1142,9 @@ static void R_ProjectSprite(mobj_t *thing) vissprite_t *vis; angle_t ang = 0; // gcc 4.6 and lower fix +#ifdef ROTSPRITE angle_t camang = 0; +#endif fixed_t iscale; fixed_t scalestep; // toast '16 fixed_t offset, offset2; @@ -1163,7 +1165,6 @@ static void R_ProjectSprite(mobj_t *thing) #ifdef ROTSPRITE patch_t *rotsprite = NULL; INT32 rollangle = 0; - angle_t rollsum = 0; angle_t pitchnroll = 0; angle_t sliptiderollangle = 0; #endif @@ -1219,7 +1220,12 @@ static void R_ProjectSprite(mobj_t *thing) I_Error("R_ProjectSprite: invalid sprite number %d ", thing->sprite); #endif - rot = thing->frame&FF_FRAMEMASK; + rot = (thing->frame & FF_FRAMEMASK); + +#ifdef ROTSPRITE + // determine here if sprite should rotate for optimization + const boolean shouldrotate = (cv_spriteroll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle)); +#endif //Fab : 02-08-98: 'skin' override spritedef currently used for skin if ((thing->skin || thing->localskin) && thing->sprite == SPR_PLAY) @@ -1250,7 +1256,7 @@ static void R_ProjectSprite(mobj_t *thing) #ifdef ROTSPRITE sprinfo = &spriteinfo[thing->sprite]; #endif - rot = thing->frame&FF_FRAMEMASK; + rot = (thing->frame & FF_FRAMEMASK); if (!thing->skin) { thing->state->sprite = thing->sprite; @@ -1265,10 +1271,18 @@ static void R_ProjectSprite(mobj_t *thing) I_Error("R_ProjectSprite: sprframes NULL for sprite %d\n", thing->sprite); #endif - if (sprframe->rotate != SRF_SINGLE || papersprite || (cv_sloperoll.value == 2 && cv_spriteroll.value)) + if (sprframe->rotate != SRF_SINGLE || papersprite || +#ifdef ROTSPRITE + (shouldrotate) +#endif + ) { ang = R_PointToAngle (interp.x, interp.y) - interp.angle; - camang = R_PointToAngle (interp.x, interp.y); + +#ifdef ROTSPRITE + if (shouldrotate) + camang = R_PointToAngle (interp.x, interp.y); +#endif if (mirrored) ang = InvAngle(ang); @@ -1311,9 +1325,7 @@ static void R_ProjectSprite(mobj_t *thing) spr_topoffset = spritecachedinfo[lump].topoffset; #ifdef ROTSPRITE - pitchnroll = 0; // set this to 0, non-paper sprites will affect this value - - if (cv_spriteroll.value) + if (shouldrotate) { if (papersprite) { @@ -1331,29 +1343,29 @@ static void R_ProjectSprite(mobj_t *thing) { // this is very messy, but it on-the-fly calculates rotations for all the // pitch and roll variables - pitchnroll = FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), interp.roll) + - FixedMul(FINESINE((ang) >> ANGLETOFINESHIFT), interp.pitch) + - FixedMul(FINECOSINE((camang) >> ANGLETOFINESHIFT), interp.sloperoll) + - FixedMul(FINESINE((camang) >> ANGLETOFINESHIFT), interp.slopepitch); - + pitchnroll = R_RotationAngle(ang, camang, &interp); rollangle = thing->rollangle; } if (rollangle || pitchnroll || (thing->player && thing->player->sliproll)) { - rollsum = pitchnroll; - - if (thing->player) + if (thing->player && cv_sliptideroll.value) { - sliptiderollangle = - cv_sliptideroll.value ? thing->player->sliproll * (thing->player->sliptidemem) : 0; - rollsum += thing->rollangle + - FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), sliptiderollangle); + sliptiderollangle = thing->player->sliproll * (thing->player->sliptidemem); + pitchnroll += rollangle + FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), sliptiderollangle); } else - rollsum += thing->rollangle; + pitchnroll += rollangle; - rollangle = R_GetRollAngle(rollsum); + // this is kinda dumb lkmao, but try to mitigate shadows being weirdly offset on slopes + if (thing->type == MT_SHADOW) + { + sprinfo->available = true; // < lmao + sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].x = spr_offset>>FRACBITS; + sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].y = -12; // noones gonna replace shadow sprite anyways, right? + } + + rollangle = R_GetRollAngle(pitchnroll); rotsprite = Patch_GetRotatedSprite(sprframe, (thing->frame & FF_FRAMEMASK), rot, flip, false, sprinfo, rollangle); if (rotsprite != NULL) -- 2.54.0 From 00773a0c10b0a9d1a7f659e9518d555b84daeaea Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 20:09:04 +0100 Subject: [PATCH 083/143] okay? shut up compiler --- src/http-mserv.c | 36 ++++++++++++++++++------------------ 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/src/http-mserv.c b/src/http-mserv.c index 9e32f9ea7..30a6f977d 100644 --- a/src/http-mserv.c +++ b/src/http-mserv.c @@ -289,7 +289,7 @@ int HMS_register (void) { struct HMS_buffer *hms; - int ok; + int okay; char post[256]; @@ -316,23 +316,23 @@ HMS_register (void) curl_easy_setopt(hms->curl, CURLOPT_POSTFIELDS, post); - ok = HMS_do(hms); + okay = HMS_do(hms); - if (ok) + if (okay) { hms_server_token = strdup(strtok(hms->buffer, "\n")); } HMS_end(hms); - return ok; + return okay; } int HMS_unlist (void) { struct HMS_buffer *hms; - int ok; + int okay; hms = HMS_connect("servers/%s/unlist", hms_server_token); @@ -342,19 +342,19 @@ HMS_unlist (void) curl_easy_setopt(hms->curl, CURLOPT_POST, 1); curl_easy_setopt(hms->curl, CURLOPT_POSTFIELDSIZE, 0); - ok = HMS_do(hms); + okay = HMS_do(hms); HMS_end(hms); free(hms_server_token); - return ok; + return okay; } int HMS_update (void) { struct HMS_buffer *hms; - int ok; + int okay; char post[256]; @@ -376,10 +376,10 @@ HMS_update (void) curl_easy_setopt(hms->curl, CURLOPT_POSTFIELDS, post); - ok = HMS_do(hms); + okay = HMS_do(hms); HMS_end(hms); - return ok; + return okay; } void @@ -488,7 +488,7 @@ int HMS_compare_mod_version (char *buffer, size_t buffer_size) { struct HMS_buffer *hms; - int ok; + int okay; char *version; char *version_name; @@ -498,7 +498,7 @@ HMS_compare_mod_version (char *buffer, size_t buffer_size) if (! hms) return 0; - ok = 0; + okay = 0; if (HMS_do(hms)) { @@ -510,16 +510,16 @@ HMS_compare_mod_version (char *buffer, size_t buffer_size) if (atoi(version) != MODVERSION) { strlcpy(buffer, version_name, buffer_size); - ok = 1; + okay = 1; } else - ok = -1; + okay = -1; } } HMS_end(hms); - return ok; + return okay; } const char * @@ -532,9 +532,9 @@ HMS_fetch_rules (char *buffer, size_t buffer_size) if (! hms) return NULL; - boolean ok = HMS_do(hms); + boolean okay = HMS_do(hms); - if (ok) + if (okay) { char *p = strstr(hms->buffer, "\n\n"); @@ -552,7 +552,7 @@ HMS_fetch_rules (char *buffer, size_t buffer_size) HMS_end(hms); - if (!ok) + if (!okay) return NULL; return buffer; -- 2.54.0 From 11f8b974df84203132b991b2b7e4d298bffb27f3 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 20:28:19 +0100 Subject: [PATCH 084/143] forgor sliptide roll --- src/hardware/hw_main.c | 7 ++++--- src/r_things.c | 7 ++++--- 2 files changed, 8 insertions(+), 6 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 967d52cc5..edf6381c4 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4509,7 +4509,8 @@ static void HWR_ProjectSprite(mobj_t *thing) #ifdef ROTSPRITE // determine here if sprite should rotate for optimization - const boolean shouldrotate = (cv_spriteroll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle)); + const boolean sliprollrotate = (cv_spriteroll.value && cv_sliptideroll.value && (thing->player && thing->player->sliproll)); + const boolean shouldrotate = (cv_spriteroll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle || sliprollrotate)); #endif //Fab : 02-08-98: 'skin' override spritedef currently used for skin @@ -4614,9 +4615,9 @@ static void HWR_ProjectSprite(mobj_t *thing) rollangle = thing->rollangle; } - if (rollangle || pitchnroll || (thing->player && thing->player->sliproll)) + if (rollangle || pitchnroll || sliprollrotate) { - if (thing->player && cv_sliptideroll.value) + if (sliprollrotate) { sliptiderollangle = thing->player->sliproll * (thing->player->sliptidemem); pitchnroll += rollangle + FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), sliptiderollangle); diff --git a/src/r_things.c b/src/r_things.c index 1e8c33d32..10a9c57b6 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -1224,7 +1224,8 @@ static void R_ProjectSprite(mobj_t *thing) #ifdef ROTSPRITE // determine here if sprite should rotate for optimization - const boolean shouldrotate = (cv_spriteroll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle)); + const boolean sliprollrotate = (cv_spriteroll.value && cv_sliptideroll.value && (thing->player && thing->player->sliproll)); + const boolean shouldrotate = (cv_spriteroll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle || sliprollrotate)); #endif //Fab : 02-08-98: 'skin' override spritedef currently used for skin @@ -1347,9 +1348,9 @@ static void R_ProjectSprite(mobj_t *thing) rollangle = thing->rollangle; } - if (rollangle || pitchnroll || (thing->player && thing->player->sliproll)) + if (rollangle || pitchnroll || sliprollrotate) { - if (thing->player && cv_sliptideroll.value) + if (sliprollrotate) { sliptiderollangle = thing->player->sliproll * (thing->player->sliptidemem); pitchnroll += rollangle + FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), sliptiderollangle); -- 2.54.0 From dad630f3eb028d560299ac017dd856287f020b61 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 20:29:08 +0100 Subject: [PATCH 085/143] delet this --- src/hardware/hw_main.c | 8 -------- src/r_things.c | 8 -------- 2 files changed, 16 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index edf6381c4..60a7b6788 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4625,14 +4625,6 @@ static void HWR_ProjectSprite(mobj_t *thing) else pitchnroll += rollangle; - // this is kinda dumb lkmao, but try to mitigate shadows being weirdly offset on slopes - if (thing->type == MT_SHADOW) - { - sprinfo->available = true; // < lmao - sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].x = spr_offset>>FRACBITS; - sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].y = -8; // noones gonna replace shadow sprite anyways, right? this random value works, cant get any better otherwise this clips into the ground Zzz... - } - rollangle = R_GetRollAngle(pitchnroll); rotsprite = Patch_GetRotatedSprite(sprframe, (thing->frame & FF_FRAMEMASK), rot, flip, false, sprinfo, rollangle); diff --git a/src/r_things.c b/src/r_things.c index 10a9c57b6..fafab358d 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -1358,14 +1358,6 @@ static void R_ProjectSprite(mobj_t *thing) else pitchnroll += rollangle; - // this is kinda dumb lkmao, but try to mitigate shadows being weirdly offset on slopes - if (thing->type == MT_SHADOW) - { - sprinfo->available = true; // < lmao - sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].x = spr_offset>>FRACBITS; - sprinfo->pivot[(thing->frame & FF_FRAMEMASK)].y = -12; // noones gonna replace shadow sprite anyways, right? - } - rollangle = R_GetRollAngle(pitchnroll); rotsprite = Patch_GetRotatedSprite(sprframe, (thing->frame & FF_FRAMEMASK), rot, flip, false, sprinfo, rollangle); -- 2.54.0 From 975978ca9c4ca5723818acfd0d3b4afb128efe5e Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 21:44:23 +0100 Subject: [PATCH 086/143] this is null anyways if disabled --- src/hardware/hw_main.c | 2 +- src/r_things.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 60a7b6788..79e817ae1 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4732,7 +4732,7 @@ static void HWR_ProjectSprite(mobj_t *thing) vis->spriteyoffset = FIXED_TO_FLOAT(spr_topoffset); #ifdef ROTSPRITE - if (rotsprite && cv_spriteroll.value) + if (rotsprite != NULL) vis->gpatch = (GLPatch_t *)rotsprite; else #endif diff --git a/src/r_things.c b/src/r_things.c index fafab358d..fa2b02293 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -1669,7 +1669,7 @@ static void R_ProjectSprite(mobj_t *thing) //Fab: lumppat is the lump number of the patch to use, this is different // than lumpid for sprites-in-pwad : the graphics are patched #ifdef ROTSPRITE - if ((rotsprite != NULL) && (cv_spriteroll.value)) + if (rotsprite != NULL) vis->patch = rotsprite; else #endif -- 2.54.0 From 43f8a0213af92f899b86b237eed53ebbddf263ae Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 21:46:41 +0100 Subject: [PATCH 087/143] sloperoll already has "off" setting, delet spriteroll cvar since redundant --- src/g_game.c | 1 - src/g_game.h | 1 - src/hardware/hw_main.c | 4 ++-- src/m_menu.c | 30 +++++++++++------------------- src/p_mobj.c | 14 ++++++++------ src/r_main.c | 1 - src/r_things.c | 4 ++-- 7 files changed, 23 insertions(+), 32 deletions(-) diff --git a/src/g_game.c b/src/g_game.c index 1b5626669..03a022339 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -524,7 +524,6 @@ static CV_PossibleValue_t sloperolldist_cons_t[] = { {8192, "8192"}, {0, "Infinite"}, {0, NULL}}; consvar_t cv_sloperolldist = {"sloperolldist", "Infinite", CV_SAVE, sloperolldist_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; static CV_PossibleValue_t sloperoll_cons_t[] = {{0, "Off"}, {1, "Players"}, {2, "Everything"}, {0, NULL}}; -consvar_t cv_spriteroll = {"spriteroll", "Off", CV_SAVE|CV_CALL, CV_OnOff, PDistort_menu_Onchange, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_sloperoll = {"sloperoll", "Off", CV_SAVE|CV_CALL, sloperoll_cons_t, PDistort_menu_Onchange, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_sparkroll = {"sparkroll", "Off", CV_SAVE|CV_CALL, CV_OnOff, PDistort_menu_Onchange, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_sliptideroll = {"sliptideroll", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; diff --git a/src/g_game.h b/src/g_game.h index b00bf1343..81d653774 100644 --- a/src/g_game.h +++ b/src/g_game.h @@ -166,7 +166,6 @@ extern consvar_t cv_saltysquish; extern consvar_t cv_driftsparkpulse; extern consvar_t cv_gravstretch; extern consvar_t cv_sloperoll; -extern consvar_t cv_spriteroll; extern consvar_t cv_sliptideroll; extern consvar_t cv_slamsound; extern consvar_t cv_sloperolldist; diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 79e817ae1..9cbcfe9e9 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4509,8 +4509,8 @@ static void HWR_ProjectSprite(mobj_t *thing) #ifdef ROTSPRITE // determine here if sprite should rotate for optimization - const boolean sliprollrotate = (cv_spriteroll.value && cv_sliptideroll.value && (thing->player && thing->player->sliproll)); - const boolean shouldrotate = (cv_spriteroll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle || sliprollrotate)); + const boolean sliprollrotate = (cv_sloperoll.value && cv_sliptideroll.value && (thing->player && thing->player->sliproll)); + const boolean shouldrotate = (cv_sloperoll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle || sliprollrotate)); #endif //Fab : 02-08-98: 'skin' override spritedef currently used for skin diff --git a/src/m_menu.c b/src/m_menu.c index 6fea58256..530cb98fb 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -2224,22 +2224,20 @@ static menuitem_t OP_PlayerDistortMenu[] = { {IT_HEADER, NULL, "Sprite Distortion", NULL, 0}, - {IT_STRING | IT_CVAR, NULL, "Sprite Rotation", &cv_spriteroll, 15}, - {IT_STRING | IT_CVAR, NULL, "Sprite Slope Rotation", &cv_sloperoll, 30}, - {IT_STRING | IT_CVAR, NULL, "Slope Rotation Distance", &cv_sloperolldist, 45}, - {IT_STRING | IT_CVAR, NULL, "Rotate Players when Sliptiding", &cv_sliptideroll, 60}, - {IT_STRING | IT_CVAR, NULL, "Rotate Sparks and Boost Trails", &cv_sparkroll, 75}, - {IT_STRING | IT_CVAR, NULL, "Player Stretch Factor", &cv_gravstretch, 90}, - {IT_STRING | IT_CVAR, NULL, "Squish Sound Effect", &cv_slamsound, 105}, - {IT_STRING | IT_CVAR, NULL, "Saltyhop", &cv_saltyhop, 120}, - {IT_STRING | IT_CVAR, NULL, "Saltyhop Sound Effect", &cv_saltyhopsfx, 135}, - {IT_STRING | IT_CVAR, NULL, "Saltyhop Squish", &cv_saltysquish, 150}, + {IT_STRING | IT_CVAR, NULL, "Sprite Slope Rotation", &cv_sloperoll, 15}, + {IT_STRING | IT_CVAR, NULL, "Slope Rotation Distance", &cv_sloperolldist, 30}, + {IT_STRING | IT_CVAR, NULL, "Rotate Players when Sliptiding", &cv_sliptideroll, 45}, + {IT_STRING | IT_CVAR, NULL, "Rotate Sparks and Boost Trails", &cv_sparkroll, 60}, + {IT_STRING | IT_CVAR, NULL, "Player Stretch Factor", &cv_gravstretch, 75}, + {IT_STRING | IT_CVAR, NULL, "Squish Sound Effect", &cv_slamsound, 90}, + {IT_STRING | IT_CVAR, NULL, "Saltyhop", &cv_saltyhop, 105}, + {IT_STRING | IT_CVAR, NULL, "Saltyhop Sound Effect", &cv_saltyhopsfx, 120}, + {IT_STRING | IT_CVAR, NULL, "Saltyhop Squish", &cv_saltysquish, 135}, }; static const char* OP_PlayerDistortTooltips[] = { NULL, - "Sprite rotation features.", "Sprite rotation on slopes. Can either be just players or all objects.", "Distance object rotation should be visable.", "Player rotation when sliptiding.", @@ -2254,7 +2252,6 @@ static const char* OP_PlayerDistortTooltips[] = enum { spriteheader, - spriterotate, sloperotate, slrotatedist, sliptide, @@ -3397,7 +3394,7 @@ void Addons_option_Onchange(void) void PDistort_menu_Onchange(void) { - if (!cv_spriteroll.value) + if (!cv_sloperoll.value) { OP_PlayerDistortMenu[sloperotate].status = IT_GRAYEDOUT; OP_PlayerDistortMenu[sliptide].status = IT_GRAYEDOUT; @@ -3408,15 +3405,10 @@ void PDistort_menu_Onchange(void) OP_PlayerDistortMenu[sliptide].status = IT_STRING | IT_CVAR; } - if ((cv_sloperoll.value) && (cv_spriteroll.value)) //enable/disable sloperotate distance + if (cv_sloperoll.value) //enable/disable sloperotate distance OP_PlayerDistortMenu[slrotatedist].status = IT_STRING | IT_CVAR; else OP_PlayerDistortMenu[slrotatedist].status = IT_GRAYEDOUT; - - if ((cv_sloperoll.value == 2) && (cv_spriteroll.value)) //enable/disable sparkroll depending on which setting - OP_PlayerDistortMenu[sparkrotate].status = IT_STRING | IT_CVAR; - else - OP_PlayerDistortMenu[sparkrotate].status = IT_GRAYEDOUT; } void Bird_menu_Onchange(void) diff --git a/src/p_mobj.c b/src/p_mobj.c index 9da7b0235..eab9629b2 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -6014,15 +6014,17 @@ void P_RollPitchMobj(mobj_t* mobj) if (!mobj || P_MobjWasRemoved(mobj)) return; - if (cv_spriteroll.value && cv_sloperoll.value == 2) - { - K_RollMobjBySlopes(mobj, cv_sloperolldist.value && !splitscreen); - } - else + I_Assert(mo->subsector != NULL); + I_Assert(mo->subsector->sector != NULL); + + if (cv_sloperoll.value != 2) { mobj->sloperoll = FixedAngle(0); mobj->slopepitch = FixedAngle(0); + return; } + + K_RollMobjBySlopes(mobj, cv_sloperolldist.value && !splitscreen); } angle_t P_MobjPitchAndRoll(mobj_t *mobj) @@ -6033,7 +6035,7 @@ angle_t P_MobjPitchAndRoll(mobj_t *mobj) angle_t camang = 0; angle_t return_angle = 0; - if (!cv_spriteroll.value) + if (!cv_sloperoll.value) return 0; if (P_MobjWasRemoved(mobj)) diff --git a/src/r_main.c b/src/r_main.c index 1c45d4112..1cba82f2c 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -1749,7 +1749,6 @@ void R_RegisterEngineStuff(void) CV_RegisterVar(&cv_driftsparkpulse); CV_RegisterVar(&cv_gravstretch); CV_RegisterVar(&cv_sloperoll); - CV_RegisterVar(&cv_spriteroll); CV_RegisterVar(&cv_sliptideroll); CV_RegisterVar(&cv_sloperolldist); CV_RegisterVar(&cv_sparkroll); diff --git a/src/r_things.c b/src/r_things.c index fa2b02293..e6c175d4a 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -1224,8 +1224,8 @@ static void R_ProjectSprite(mobj_t *thing) #ifdef ROTSPRITE // determine here if sprite should rotate for optimization - const boolean sliprollrotate = (cv_spriteroll.value && cv_sliptideroll.value && (thing->player && thing->player->sliproll)); - const boolean shouldrotate = (cv_spriteroll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle || sliprollrotate)); + const boolean sliprollrotate = (cv_sloperoll.value && cv_sliptideroll.value && (thing->player && thing->player->sliproll)); + const boolean shouldrotate = (cv_sloperoll.value && (interp.roll || interp.pitch || interp.sloperoll || interp.slopepitch || thing->rollangle || sliprollrotate)); #endif //Fab : 02-08-98: 'skin' override spritedef currently used for skin -- 2.54.0 From 9e2a48cae1867fe89e09c9c2139739d9e9f2c97c Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 21:46:56 +0100 Subject: [PATCH 088/143] whoops --- src/lua_hudlib.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/lua_hudlib.c b/src/lua_hudlib.c index 2ee2297ad..5618727af 100644 --- a/src/lua_hudlib.c +++ b/src/lua_hudlib.c @@ -503,7 +503,7 @@ static int libd_getSpritePatch(lua_State *L) angle = (angle & 7); // modulus angle by 8 // rotsprite????? - if (lua_isnumber(L, 4) && (cv_spriteroll.value)) + if (lua_isnumber(L, 4) && cv_sloperoll.value) { angle_t rollangle = luaL_checkangle(L, 4); INT32 rot = R_GetRollAngle(rollangle); -- 2.54.0 From 6633dfe1e24267442a59aa60bf536898c65471b6 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 21:54:37 +0100 Subject: [PATCH 089/143] smol cleanup --- src/k_kart.c | 20 ++++++++------------ src/p_mobj.c | 21 ++++++++++----------- 2 files changed, 18 insertions(+), 23 deletions(-) diff --git a/src/k_kart.c b/src/k_kart.c index c27ffec4c..eec5299c0 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -3082,7 +3082,7 @@ static void K_SpawnDriftSparks(player_t *player) //spark->momz = player->mo->momz/2; // rotate the sparks based on pitch and roll; it just looks neat - if (cv_sparkroll.value == 1) + if (cv_sparkroll.value) { spark->slopepitch = player->mo->slopepitch; spark->sloperoll = player->mo->sloperoll; @@ -3296,20 +3296,16 @@ static void K_QuiteSaltyHop(player_t *p) } #define SLOPEROLL_DIV 3 - void K_RollMobjBySlopes(mobj_t* mo, boolean usedistance) { - I_Assert(mo->subsector != NULL); - I_Assert(mo->subsector->sector != NULL); - - angle_t an; - const boolean flip = mo->eflags & MFE_VERTICALFLIP; - const fixed_t m_dist = usedistance ? R_PointToDist(mo->x, mo->y) : 0; - const fixed_t rolldist = cv_sloperolldist.value * mapobjectscale; - // lifted from hw_md2 if (mo->standingslope) { + angle_t an; + const boolean flip = (mo->eflags & MFE_VERTICALFLIP); + const fixed_t m_dist = usedistance ? R_PointToDist(mo->x, mo->y) : 0; + const fixed_t rolldist = cv_sloperolldist.value * mapobjectscale; + fixed_t tempz = mo->standingslope->normal.z; fixed_t tempy = mo->standingslope->normal.y; fixed_t tempx = mo->standingslope->normal.x; @@ -3318,7 +3314,7 @@ void K_RollMobjBySlopes(mobj_t* mo, boolean usedistance) // admittedly this is a very hacky way to do the pitch and roll easing // pitch - if ((!usedistance) || (m_dist <= (rolldist))) + if (!usedistance || (m_dist <= (rolldist))) { an = (INT32)((angle_t)tempangle - mo->pitch_sprite) / SLOPEROLL_DIV; @@ -3401,7 +3397,7 @@ void K_SpawnBoostTrail(player_t *player) flame->momx = 8; // since you have to be on the ground for sneaker trails, this should be fine(?) - if (cv_sparkroll.value == 1) + if (cv_sparkroll.value) { flame->slopepitch = player->mo->slopepitch; flame->sloperoll = player->mo->sloperoll; diff --git a/src/p_mobj.c b/src/p_mobj.c index eab9629b2..e24b5df8e 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -6041,8 +6041,11 @@ angle_t P_MobjPitchAndRoll(mobj_t *mobj) if (P_MobjWasRemoved(mobj)) return 0; - size_t rot = mobj->frame & FF_FRAMEMASK; - boolean papersprite = (mobj->frame & FF_PAPERSPRITE); + // if mobj doesent have any of those, no need to do the rest + if (mobj->roll == 0 && mobj->pitch == 0 && mobj->sloperoll == 0 && mobj->slopepitch == 0) + return 0; + + size_t rot = (mobj->frame & FF_FRAMEMASK); if (mobj->skin && mobj->sprite == SPR_PLAY) { @@ -6059,7 +6062,7 @@ angle_t P_MobjPitchAndRoll(mobj_t *mobj) if (rot >= sprdef->numframes) { sprdef = &sprites[states[S_UNKNOWN].sprite]; - rot = states[S_UNKNOWN].frame&FF_FRAMEMASK; + rot = (states[S_UNKNOWN].frame & FF_FRAMEMASK); } sprframe = &sprdef->spriteframes[rot]; @@ -6067,20 +6070,16 @@ angle_t P_MobjPitchAndRoll(mobj_t *mobj) // No sprite frame? I guess it is possible if (!sprframe) return 0; - if (sprframe->rotate != SRF_SINGLE || papersprite) + if (sprframe->rotate != SRF_SINGLE || (mobj->frame & FF_PAPERSPRITE)) { ang = R_PointToAngle(mobj->x, mobj->y) - mobj->angle; camang = R_PointToAngle(mobj->x, mobj->y); } return_angle = FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), mobj->roll) - + FixedMul(FINESINE((ang) >> ANGLETOFINESHIFT), mobj->pitch); - - if (cv_sloperoll.value) - { - return_angle += FixedMul(FINECOSINE((camang) >> ANGLETOFINESHIFT), mobj->sloperoll) - + FixedMul(FINESINE((camang) >> ANGLETOFINESHIFT), mobj->slopepitch); - } + + FixedMul(FINESINE((ang) >> ANGLETOFINESHIFT), mobj->pitch) + + FixedMul(FINECOSINE((camang) >> ANGLETOFINESHIFT), mobj->sloperoll) + + FixedMul(FINESINE((camang) >> ANGLETOFINESHIFT), mobj->slopepitch); return return_angle; } -- 2.54.0 From c4211045f2c000283879ea0c94b3ea43fc370074 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 21:59:47 +0100 Subject: [PATCH 090/143] oops this gets directly called in one instance also why do we keep checking for null mobj when P_MobjWasRemoved checks that anyways? --- src/k_kart.c | 14 +++++++++----- src/p_mobj.c | 5 +---- 2 files changed, 10 insertions(+), 9 deletions(-) diff --git a/src/k_kart.c b/src/k_kart.c index eec5299c0..1956dfb12 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -3298,6 +3298,12 @@ static void K_QuiteSaltyHop(player_t *p) #define SLOPEROLL_DIV 3 void K_RollMobjBySlopes(mobj_t* mo, boolean usedistance) { + if (P_MobjWasRemoved(mo)) + return; + + I_Assert(mo->subsector != NULL); + I_Assert(mo->subsector->sector != NULL); + // lifted from hw_md2 if (mo->standingslope) { @@ -6475,7 +6481,7 @@ void K_MoveKartPlayer(player_t *player, boolean onground) K_KartDrift(player, onground); - if ((!player->kartstuff[k_aizdriftstrat])||(!P_IsObjectOnGround(player->mo))||(player->kartstuff[k_drift])) + if ((!player->kartstuff[k_aizdriftstrat]) || (!P_IsObjectOnGround(player->mo)) || (player->kartstuff[k_drift])) { if (player->sliproll && (player->sliproll > 0)) player->sliproll -= (4*ANG1); @@ -6489,10 +6495,9 @@ void K_MoveKartPlayer(player_t *player, boolean onground) player->mo->spriteyscale = player->mo->realyscale; } - if (cv_spriteroll.value && cv_sloperoll.value) + if (cv_sloperoll.value && !player->mo->salty_jump) // seeing a character rotate mid-hop looks really janky { - if ((!player->mo->salty_jump)) // seeing a character rotate mid-hop looks really janky - K_RollMobjBySlopes(player->mo, (cv_sloperolldist.value && !splitscreen)); + K_RollMobjBySlopes(player->mo, (cv_sloperolldist.value && !splitscreen)); } else { @@ -6500,7 +6505,6 @@ void K_MoveKartPlayer(player_t *player, boolean onground) player->mo->slopepitch = FixedAngle(0); } - // Quick Turning // You can't turn your kart when you're not moving. // So now it's time to burn some rubber! diff --git a/src/p_mobj.c b/src/p_mobj.c index e24b5df8e..f4515da9a 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -6011,12 +6011,9 @@ static void P_KoopaThinker(mobj_t *koopa) // void P_RollPitchMobj(mobj_t* mobj) { - if (!mobj || P_MobjWasRemoved(mobj)) + if (P_MobjWasRemoved(mobj)) return; - I_Assert(mo->subsector != NULL); - I_Assert(mo->subsector->sector != NULL); - if (cv_sloperoll.value != 2) { mobj->sloperoll = FixedAngle(0); -- 2.54.0 From 3139dff6ba82e686e88ab5bb73f8580a68db66ff Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 22:04:47 +0100 Subject: [PATCH 091/143] missed this --- src/r_main.c | 24 +++++++++++++----------- 1 file changed, 13 insertions(+), 11 deletions(-) diff --git a/src/r_main.c b/src/r_main.c index 1cba82f2c..c2c7210e2 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -383,17 +383,19 @@ angle_t R_PointToAngle2(fixed_t pviewx, fixed_t pviewy, fixed_t x, fixed_t y) angle_t R_PlayerSliptideAngle(player_t *player) { mobj_t *mo; - spritedef_t *sprdef; - spriteframe_t *sprframe; - angle_t ang = 0; + spritedef_t *sprdef; + spriteframe_t *sprframe; + angle_t ang = 0; - if (!cv_sliptideroll.value || !player || P_MobjWasRemoved(player->mo)) - return 0; + if (!cv_sloperoll.value || !cv_sliptideroll.value || !player || P_MobjWasRemoved(player->mo)) + return 0; - mo = player->mo; + mo = player->mo; - size_t rot = mo->frame & FF_FRAMEMASK; - boolean papersprite = (mo->frame & FF_PAPERSPRITE); + if (mo->player->sliproll == 0 && mo->player->sliptidemem == 0) + return 0; + + size_t rot = (mo->frame & FF_FRAMEMASK); if (mo->skin && mo->sprite == SPR_PLAY) { @@ -410,7 +412,7 @@ angle_t R_PlayerSliptideAngle(player_t *player) if (rot >= sprdef->numframes) { sprdef = &sprites[states[S_UNKNOWN].sprite]; - rot = states[S_UNKNOWN].frame&FF_FRAMEMASK; + rot = (states[S_UNKNOWN].frame & FF_FRAMEMASK); } sprframe = &sprdef->spriteframes[rot]; @@ -418,10 +420,10 @@ angle_t R_PlayerSliptideAngle(player_t *player) // No sprite frame? I guess it is possible if (!sprframe) return 0; - if (sprframe->rotate != SRF_SINGLE || papersprite) + if (sprframe->rotate != SRF_SINGLE || (mo->frame & FF_PAPERSPRITE)) ang = R_PointToAngle(mo->x, mo->y) - mo->angle; - return FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), mo->player->sliproll*(mo->player->sliptidemem)); + return FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), mo->player->sliproll * mo->player->sliptidemem); } INT32 R_GetHudUncap(void) -- 2.54.0 From 7de8b2d8814f98080b8d8f1048fdb4980d2beb9e Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 22:31:36 +0100 Subject: [PATCH 092/143] save one R_PointToAngle call very smol optimisation lul --- src/hardware/hw_main.c | 9 ++++----- src/r_things.c | 7 +++---- 2 files changed, 7 insertions(+), 9 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 9cbcfe9e9..16418c58d 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4551,15 +4551,14 @@ static void HWR_ProjectSprite(mobj_t *thing) I_Error("sprframes NULL for sprite %d\n", thing->sprite); #endif - ang = R_PointToAngle (interp.x, interp.y) - interp.angle; + ang = R_PointToAngle(interp.x, interp.y); #ifdef ROTSPRITE - if (shouldrotate) - { - camang = R_PointToAngle (interp.x, interp.y); - } + camang = ang; #endif + ang -= interp.angle; + if (mirrored) ang = InvAngle(ang); diff --git a/src/r_things.c b/src/r_things.c index e6c175d4a..6813955e2 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -1278,12 +1278,11 @@ static void R_ProjectSprite(mobj_t *thing) #endif ) { - ang = R_PointToAngle (interp.x, interp.y) - interp.angle; - + ang = R_PointToAngle(interp.x, interp.y); #ifdef ROTSPRITE - if (shouldrotate) - camang = R_PointToAngle (interp.x, interp.y); + camang = ang; #endif + ang -= interp.angle; if (mirrored) ang = InvAngle(ang); -- 2.54.0 From bd3a5ac28419cf10833714d0d5e94121f4603126 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 23:23:05 +0100 Subject: [PATCH 093/143] give those better names --- src/hardware/hw_cache.c | 122 ++++++++++++++++++++-------------------- src/hardware/hw_main.c | 2 +- src/hardware/hw_md2.c | 58 +++++++++---------- 3 files changed, 91 insertions(+), 91 deletions(-) diff --git a/src/hardware/hw_cache.c b/src/hardware/hw_cache.c index 1182348c9..a5b03e78d 100644 --- a/src/hardware/hw_cache.c +++ b/src/hardware/hw_cache.c @@ -641,117 +641,117 @@ static void HWR_CacheFlat(GLMipmap_t *glMipmap, lumpnum_t flatlumpnum) // Download a Doom 'flat' to the hardware cache and make it ready for use void HWR_GetFlat(lumpnum_t flatlumpnum, boolean noencoremap) { - GLMipmap_t *glmip; + GLMipmap_t *glMipmap; if (flatlumpnum == LUMPERROR) return; - glmip = HWR_GetCachedGLPatch(flatlumpnum)->mipmap; + glMipmap = HWR_GetCachedGLPatch(flatlumpnum)->mipmap; - glmip->colormap = colormaps; + glMipmap->colormap = colormaps; #ifdef GLENCORE if (!noencoremap && encoremap) - glmip->colormap += COLORMAP_REMAPOFFSET; + glMipmap->colormap += COLORMAP_REMAPOFFSET; #endif - if (!glmip->downloaded && !glmip->data) - HWR_CacheFlat(glmip, flatlumpnum); + if (!glMipmap->downloaded && !glMipmap->data) + HWR_CacheFlat(glMipmap, flatlumpnum); // If hardware does not have the texture, then call pfnSetTexture to upload it - if (!glmip->downloaded) - HWD.pfnSetTexture(glmip); - HWR_SetCurrentTexture(glmip); + if (!glMipmap->downloaded) + HWD.pfnSetTexture(glMipmap); + HWR_SetCurrentTexture(glMipmap); // The system-memory data can be purged now. - Z_ChangeTag(glmip->data, PU_HWRCACHE_UNLOCKED); + Z_ChangeTag(glMipmap->data, PU_HWRCACHE_UNLOCKED); } // // HWR_LoadMappedPatch(): replace the skin color of the sprite in cache // : load it first in doom cache if not already // -static void HWR_LoadMappedPatch(GLMipmap_t *glmip, GLPatch_t *gpatch) +static void HWR_LoadMappedPatch(GLMipmap_t *glMipmap, GLPatch_t *glPatch) { - if (!glmip->downloaded && !glmip->data) + if (!glMipmap->downloaded && !glMipmap->data) { - patch_t *patch = gpatch->rawpatch; + patch_t *patch = glPatch->rawpatch; if (!patch) - patch = W_CacheLumpNumPwad(gpatch->wadnum, gpatch->lumpnum, PU_STATIC); - HWR_MakePatch(patch, gpatch, glmip, true); + patch = W_CacheLumpNumPwad(glPatch->wadnum, glPatch->lumpnum, PU_STATIC); + HWR_MakePatch(patch, glPatch, glMipmap, true); // You can't free rawpatch for some reason? // (Obviously I can't, sprite rotation needs that...) - if (!gpatch->rawpatch) + if (!glPatch->rawpatch) Z_Free(patch); } // If hardware does not have the texture, then call pfnSetTexture to upload it - if (!glmip->downloaded) - HWD.pfnSetTexture(glmip); - HWR_SetCurrentTexture(glmip); + if (!glMipmap->downloaded) + HWD.pfnSetTexture(glMipmap); + HWR_SetCurrentTexture(glMipmap); // The system-memory data can be purged now. - Z_ChangeTag(glmip->data, PU_HWRCACHE_UNLOCKED); + Z_ChangeTag(glMipmap->data, PU_HWRCACHE_UNLOCKED); } // -----------------+ -// HWR_GetPatch : Download a patch to the hardware cache and make it ready for use +// HWR_GetPatch : Downloads a patch to the hardware cache and make it ready for use // -----------------+ -void HWR_GetPatch(GLPatch_t *gpatch) +void HWR_GetPatch(GLPatch_t *glPatch) { // is it in hardware cache - if (!gpatch->mipmap->downloaded && !gpatch->mipmap->data) + if (!glPatch->mipmap->downloaded && !glPatch->mipmap->data) { // load the software patch, PU_STATIC or the Z_Malloc for hardware patch will // flush the software patch before the conversion! oh yeah I suffered - patch_t *ptr = gpatch->rawpatch; + patch_t *ptr = glPatch->rawpatch; if (!ptr) - ptr = W_CacheLumpNumPwad(gpatch->wadnum, gpatch->lumpnum, PU_STATIC); - HWR_MakePatch(ptr, gpatch, gpatch->mipmap, true); + ptr = W_CacheLumpNumPwad(glPatch->wadnum, glPatch->lumpnum, PU_STATIC); + HWR_MakePatch(ptr, glPatch, glPatch->mipmap, true); // this is inefficient.. but the hardware patch in heap is purgeable so it should // not fragment memory, and besides the REAL cache here is the hardware memory - if (!gpatch->rawpatch) + if (!glPatch->rawpatch) Z_Free(ptr); } // If hardware does not have the texture, then call pfnSetTexture to upload it - if (!gpatch->mipmap->downloaded) - HWD.pfnSetTexture(gpatch->mipmap); - HWR_SetCurrentTexture(gpatch->mipmap); + if (!glPatch->mipmap->downloaded) + HWD.pfnSetTexture(glPatch->mipmap); + HWR_SetCurrentTexture(glPatch->mipmap); // The system-memory patch data can be purged now. - Z_ChangeTag(gpatch->mipmap->data, PU_HWRCACHE_UNLOCKED); + Z_ChangeTag(glPatch->mipmap->data, PU_HWRCACHE_UNLOCKED); } // -------------------+ // HWR_GetMappedPatch : Same as HWR_GetPatch for sprite color // -------------------+ -void HWR_GetMappedPatch(GLPatch_t *gpatch, const UINT8 *colormap) +void HWR_GetMappedPatch(GLPatch_t *glPatch, const UINT8 *colormap) { - GLMipmap_t *glmip, *newmip; + GLMipmap_t *glMipmap, *newMipmap; // Blatant hack for encore colormapping aside... if (colormap == colormaps || colormap == NULL || colormap == (const UINT8*)(COLORMAP_REMAPOFFSET)) { // Load the default (green) color in doom cache (temporary?) AND hardware cache - HWR_GetPatch(gpatch); + HWR_GetPatch(glPatch); return; } - // search for the mimmap + // search for the mipmap // skip the first (no colormap translated) - for (glmip = gpatch->mipmap; glmip->nextcolormap; ) + for (glMipmap = glPatch->mipmap; glMipmap->nextcolormap; ) { - glmip = glmip->nextcolormap; + glMipmap = glMipmap->nextcolormap; - if (glmip->colormap != colormap) + if (glMipmap->colormap != colormap) continue; - HWR_LoadMappedPatch(glmip, gpatch); + HWR_LoadMappedPatch(glMipmap, glPatch); return; } // not found, create it! @@ -761,38 +761,38 @@ void HWR_GetMappedPatch(GLPatch_t *gpatch, const UINT8 *colormap) // (it have a liste of mipmap) // this malloc is cleared in HWR_FreeTextureCache // (...) unfortunately z_malloc fragment alot the memory :(so malloc is better - newmip = calloc(1, sizeof (*newmip)); - if (newmip == NULL) + newMipmap = calloc(1, sizeof (*newMipmap)); + if (newMipmap == NULL) I_Error("%s: Out of memory", "HWR_GetMappedPatch"); - glmip->nextcolormap = newmip; + glMipmap->nextcolormap = newMipmap; - newmip->colormap = colormap; - HWR_LoadMappedPatch(newmip, gpatch); + newMipmap->colormap = colormap; + HWR_LoadMappedPatch(newMipmap, glPatch); } -void HWR_UnlockCachedPatch(GLPatch_t *gpatch) +void HWR_UnlockCachedPatch(GLPatch_t *glPatch) { - if (!gpatch) + if (!glPatch) return; - Z_ChangeTag(gpatch->mipmap->data, PU_HWRCACHE_UNLOCKED); + Z_ChangeTag(glPatch->mipmap->data, PU_HWRCACHE_UNLOCKED); } GLPatch_t *HWR_GetCachedGLPatchPwad(UINT16 wadnum, UINT16 lumpnum) { aatree_t *hwrcache = wadfiles[wadnum]->hwrcache; - GLPatch_t *glpatch; + GLPatch_t *glPatch; - if (!(glpatch = M_AATreeGet(hwrcache, lumpnum))) + if (!(glPatch = M_AATreeGet(hwrcache, lumpnum))) { - glpatch = Z_Calloc(sizeof(GLPatch_t), PU_HWRPATCHINFO, NULL); - glpatch->wadnum = wadnum; - glpatch->lumpnum = lumpnum; - glpatch->mipmap = Z_Calloc(sizeof(GLMipmap_t), PU_HWRPATCHINFO, NULL); - M_AATreeSet(hwrcache, lumpnum, glpatch); + glPatch = Z_Calloc(sizeof(GLPatch_t), PU_HWRPATCHINFO, NULL); + glPatch->wadnum = wadnum; + glPatch->lumpnum = lumpnum; + glPatch->mipmap = Z_Calloc(sizeof(GLMipmap_t), PU_HWRPATCHINFO, NULL); + M_AATreeSet(hwrcache, lumpnum, glPatch); } - return glpatch; + return glPatch; } GLPatch_t *HWR_GetCachedGLPatch(lumpnum_t lumpnum) @@ -887,17 +887,17 @@ static void HWR_CacheFadeMask(GLMipmap_t *glMipmap, lumpnum_t fademasklumpnum) void HWR_GetFadeMask(lumpnum_t fademasklumpnum) { - GLMipmap_t *glmip; + GLMipmap_t *glMipmap; - glmip = HWR_GetCachedGLPatch(fademasklumpnum)->mipmap; + glMipmap = HWR_GetCachedGLPatch(fademasklumpnum)->mipmap; - if (!glmip->downloaded && !glmip->data) - HWR_CacheFadeMask(glmip, fademasklumpnum); + if (!glMipmap->downloaded && !glMipmap->data) + HWR_CacheFadeMask(glMipmap, fademasklumpnum); - HWD.pfnSetTexture(glmip); + HWD.pfnSetTexture(glMipmap); // The system-memory data can be purged now. - Z_ChangeTag(glmip->data, PU_HWRCACHE_UNLOCKED); + Z_ChangeTag(glMipmap->data, PU_HWRCACHE_UNLOCKED); } // ================================================= diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 16418c58d..239cbdbfb 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4857,7 +4857,7 @@ static void HWR_ProjectPrecipitationSprite(precipmobj_t *thing) return; #endif - sprframe = &sprdef->spriteframes[ thing->frame & FF_FRAMEMASK]; + sprframe = &sprdef->spriteframes[thing->frame & FF_FRAMEMASK]; // use single rotation for all views lumpoff = sprframe->lumpid[0]; diff --git a/src/hardware/hw_md2.c b/src/hardware/hw_md2.c index 485836cf2..337bf1d80 100644 --- a/src/hardware/hw_md2.c +++ b/src/hardware/hw_md2.c @@ -680,7 +680,7 @@ spritemd2found: #define SETBRIGHTNESS(brightness,r,g,b) \ brightness = (UINT8)(((1063*(UINT32)(r))/5000) + ((3576*(UINT32)(g))/5000) + ((361*(UINT32)(b))/5000)) -static void HWR_CreateBlendedTexture(GLPatch_t *gpatch, GLPatch_t *blendgpatch, GLMipmap_t *glmip, INT32 skinnum, skincolors_t color) +static void HWR_CreateBlendedTexture(GLPatch_t *gpatch, GLPatch_t *blendgpatch, GLMipmap_t *glMipmap, INT32 skinnum, skincolors_t color) { UINT16 w = gpatch->width, h = gpatch->height; UINT32 size = w*h; @@ -696,24 +696,24 @@ static void HWR_CreateBlendedTexture(GLPatch_t *gpatch, GLPatch_t *blendgpatch, memset(translation, 0, sizeof(translation)); memset(cutoff, 0, sizeof(cutoff)); - if (glmip->width == 0) + if (glMipmap->width == 0) { - glmip->width = gpatch->width; - glmip->height = gpatch->height; + glMipmap->width = gpatch->width; + glMipmap->height = gpatch->height; // no wrap around, no chroma key - glmip->flags = 0; + glMipmap->flags = 0; // setup the texture info - glmip->format = GL_TEXFMT_RGBA; + glMipmap->format = GL_TEXFMT_RGBA; } - if (glmip->data) + if (glMipmap->data) { - Z_Free(glmip->data); - glmip->data = NULL; + Z_Free(glMipmap->data); + glMipmap->data = NULL; } - cur = Z_Malloc(size*4, PU_HWRCACHE, &glmip->data); + cur = Z_Malloc(size*4, PU_HWRCACHE, &glMipmap->data); memset(cur, 0x00, size*4); image = gpatch->mipmap->data; @@ -1044,7 +1044,7 @@ skippixel: static void HWR_GetBlendedTexture(GLPatch_t *gpatch, GLPatch_t *blendgpatch, INT32 skinnum, const UINT8 *colormap, skincolors_t color) { // mostly copied from HWR_GetMappedPatch, hence the similarities and comment - GLMipmap_t *glmip, *newmip; + GLMipmap_t *glMipmap, *newMipmap; if (colormap == colormaps || colormap == NULL) { @@ -1053,19 +1053,20 @@ static void HWR_GetBlendedTexture(GLPatch_t *gpatch, GLPatch_t *blendgpatch, INT return; } - // search for the mimmap + // search for the Mipmap // skip the first (no colormap translated) - for (glmip = gpatch->mipmap; glmip->nextcolormap; ) + for (glMipmap = gpatch->mipmap; glMipmap->nextcolormap; ) { - glmip = glmip->nextcolormap; - if (glmip->colormap == colormap) + glMipmap = glMipmap->nextcolormap; + + if (glMipmap->colormap != colormap) + continue; + + if (glMipmap->downloaded && glMipmap->data) { - if (glmip->downloaded && glmip->data) - { - HWD.pfnSetTexture(glmip); // found the colormap, set it to the correct texture - Z_ChangeTag(glmip->data, PU_HWRCACHE_UNLOCKED); - return; - } + HWD.pfnSetTexture(glMipmap); // found the colormap, set it to the correct texture + Z_ChangeTag(glMipmap->data, PU_HWRCACHE_UNLOCKED); + return; } } @@ -1076,19 +1077,18 @@ static void HWR_GetBlendedTexture(GLPatch_t *gpatch, GLPatch_t *blendgpatch, INT // (it have a liste of mipmap) // this malloc is cleared in HWR_FreeTextureCache // (...) unfortunately z_malloc fragment alot the memory :(so malloc is better - newmip = calloc(1, sizeof (*newmip)); - if (newmip == NULL) + newMipmap = calloc(1, sizeof (*newMipmap)); + if (newMipmap == NULL) I_Error("%s: Out of memory", "HWR_GetMappedPatch"); - glmip->nextcolormap = newmip; - newmip->colormap = colormap; + glMipmap->nextcolormap = newMipmap; + newMipmap->colormap = colormap; - HWR_CreateBlendedTexture(gpatch, blendgpatch, newmip, skinnum, color); + HWR_CreateBlendedTexture(gpatch, blendgpatch, newMipmap, skinnum, color); - HWD.pfnSetTexture(newmip); - Z_ChangeTag(newmip->data, PU_HWRCACHE_UNLOCKED); + HWD.pfnSetTexture(newMipmap); + Z_ChangeTag(newMipmap->data, PU_HWRCACHE_UNLOCKED); } - // -----------------+ // HWR_DrawMD2 : Draw MD2 // : -- 2.54.0 From b29a3ecfbacc2f5c553569330733de155484c754 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 30 Nov 2024 23:39:10 +0100 Subject: [PATCH 094/143] this only ever applies to ogl no need in software lol --- src/r_fps.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/r_fps.c b/src/r_fps.c index 0f86160a6..feb2ac8f2 100644 --- a/src/r_fps.c +++ b/src/r_fps.c @@ -331,7 +331,7 @@ void R_InterpolateMobjState(mobj_t *mobj, fixed_t frac, interpmobjstate_t *out) out->angle = mobj->resetinterp ? mobj->angle : R_LerpAngle(mobj->old_angle, mobj->angle, frac); #ifdef HWRENDER - if (cv_glmdls.value) + if (rendermode == render_opengl && cv_glmdls.value) { // pitch roll stuff out->pitch = mobj->resetinterp ? mobj->pitch : R_LerpAngle(mobj->old_pitch, mobj->pitch, frac); -- 2.54.0 From e1fbe8d6576f658b37649a3569cc257d3cd6db70 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 1 Dec 2024 10:18:10 +0100 Subject: [PATCH 095/143] seems like player not always have mobjs titledemo moment --- src/g_game.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/g_game.c b/src/g_game.c index 03a022339..a8734eaae 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -2009,7 +2009,10 @@ static void G_FixCamera(UINT8 view) // The order of displayplayers can change, which would // invalidate localangle. - localangle[view - 1] = player->mo->angle; // Players *always* have mobjs, right? + if (player->mo) + localangle[view - 1] = player->mo->angle; // Players *always* have mobjs, right? // nope it seems + else + localangle[view - 1] = player->cmd.angleturn; P_ResetCamera(player, &camera[view - 1]); -- 2.54.0 From 12558740a48cd0faabc54275440b4a2531133241 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 1 Dec 2024 10:28:58 +0100 Subject: [PATCH 096/143] better fix for G_FixCamera completely forgor in kart and srb2.1 cmd.angleturn needs to be bitshifted to accomidate localangle using it again is better, since player mobj angle is not always suitable for localangle and may slightly mismatch where a player is steering --- src/d_clisrv.c | 2 +- src/g_game.c | 5 +---- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 47294e8c3..af9e57083 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -2008,7 +2008,7 @@ static void CL_ReloadReceivedSavegame(void) // we dont have P_ForceLocalAngle so were setting it manually here for (i = 0; i <= splitscreen; i++) { - localangle[i] = (angle_t)(players[displayplayers[i]].cmd.angleturn<<16); + localangle[i] = (angle_t)(players[displayplayers[i]].cmd.angleturn << 16); } for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) diff --git a/src/g_game.c b/src/g_game.c index a8734eaae..711f7eb1a 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -2009,10 +2009,7 @@ static void G_FixCamera(UINT8 view) // The order of displayplayers can change, which would // invalidate localangle. - if (player->mo) - localangle[view - 1] = player->mo->angle; // Players *always* have mobjs, right? // nope it seems - else - localangle[view - 1] = player->cmd.angleturn; + localangle[view - 1] = (angle_t)(player->cmd.angleturn << 16); P_ResetCamera(player, &camera[view - 1]); -- 2.54.0 From 252cd5cde533b870122cadf618056920cef6a427 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 1 Dec 2024 22:06:23 +0100 Subject: [PATCH 097/143] better fix for netgame join hoop crash this actually works and makes em animate apparently somehow on netjoin some hprev entries get mangled but are not null? no clue why that happens since hoops arent even netsynched only their "spawnpoint" is --- src/g_game.c | 2 +- src/p_inter.c | 5 ++--- src/p_mobj.c | 11 +---------- 3 files changed, 4 insertions(+), 14 deletions(-) diff --git a/src/g_game.c b/src/g_game.c index 711f7eb1a..8c28a58a0 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -2029,7 +2029,7 @@ void G_ResetView(UINT8 viewnum, INT32 playernum, boolean onlyactive) UINT8 splits; UINT8 viewd; - INT32 *displayplayerp; + INT32 *displayplayerp; INT32 olddisplayplayer; INT32 playersviewable; diff --git a/src/p_inter.c b/src/p_inter.c index 29d7e4739..378cec557 100644 --- a/src/p_inter.c +++ b/src/p_inter.c @@ -976,11 +976,10 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) break; case MT_HOOPCOLLIDE: // This produces a kind of 'domino effect' with the hoop's pieces. - if (!midgamejoin) - for (; special->hprev != NULL; special = special->hprev); // Move to the first sprite in the hoop + for (; !P_MobjWasRemoved(special->hprev); special = special->hprev); // Move to the first sprite in the hoop i = 0; - for (; special->type == MT_HOOP; special = special->hnext) + for (; !P_MobjWasRemoved(special->hnext) && special->type == MT_HOOP; special = special->hnext) { special->fuse = 11; special->movedir = i; diff --git a/src/p_mobj.c b/src/p_mobj.c index f4515da9a..c1b8b4a6f 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -11778,12 +11778,8 @@ void P_SpawnHoopsAndRings(mapthing_t *mthing) z = mthing->options << FRACBITS; hoopcenter = P_SpawnMobj(x, y, z, MT_HOOPCENTER); - hoopcenter->spawnpoint = mthing; - // Screw these damn hoops, I need this thinker. - //hoopcenter->flags |= MF_NOTHINK; - z += sec->f_slope ? P_GetZAt(sec->f_slope, x, y) : sec->floorheight; @@ -11829,10 +11825,8 @@ void P_SpawnHoopsAndRings(mapthing_t *mthing) mobj = P_SpawnMobj(finalx, finaly, finalz, MT_HOOP); - //if (maptol & TOL_XMAS) - //P_SetMobjState(mobj, mobj->info->seestate + (i & 1)); - mobj->z -= mobj->height/2; + P_SetTarget(&mobj->target, hoopcenter); // Link the sprite to the center. mobj->fuse = 0; @@ -11969,9 +11963,6 @@ void P_SpawnHoopsAndRings(mapthing_t *mthing) mobj = P_SpawnMobj(finalx, finaly, finalz, MT_HOOP); - //if (maptol & TOL_XMAS) - //P_SetMobjState(mobj, mobj->info->seestate + (i & 1)); - mobj->z -= mobj->height/2; P_SetTarget(&mobj->target, hoopcenter); // Link the sprite to the center. mobj->fuse = 0; -- 2.54.0 From 1ae5bb9d272430bbd53cc8532e94623ac4190466 Mon Sep 17 00:00:00 2001 From: Alug Date: Mon, 2 Dec 2024 20:49:53 +0100 Subject: [PATCH 098/143] lugstuff merge - Completely refactor player camera handling - Refactor ALOT of gamepad code - Refactor local cmds - Refactor automap and add minimap generator ("minigen" command) - Remove a bunch of unused netcode - Remove ALOT of unused gametype code - Remove alot of unused bot code - Optimize some sectorspecial code slightly - Remove a bunch of nights mode related stuff that was unused - Bunch of smaller optimizations and code improvements --- src/Makefile | 1 + src/am_map.c | 483 +++++++--- src/am_map.h | 25 +- src/b_bot.c | 66 +- src/d_clisrv.c | 348 ++----- src/d_clisrv.h | 16 +- src/d_main.c | 15 +- src/d_net.c | 14 +- src/d_netcmd.c | 851 +++-------------- src/d_netcmd.h | 10 +- src/dehacked.c | 22 +- src/doomstat.h | 9 - src/g_game.c | 772 ++++------------ src/g_game.h | 24 +- src/g_input.c | 32 +- src/hardware/hw_batching.c | 2 +- src/hardware/hw_cache.c | 3 + src/hardware/hw_draw.c | 26 +- src/hardware/hw_main.c | 17 +- src/hardware/hw_md2.c | 3 +- src/hardware/hw_portal.c | 6 +- src/hardware/r_opengl/r_opengl.c | 1 + src/hu_stuff.c | 27 +- src/i_joy.h | 2 +- src/i_net.h | 8 - src/i_system.h | 22 +- src/i_tcp.c | 81 +- src/info.c | 2 +- src/k_kart.c | 94 +- src/lua_baselib.c | 27 +- src/lua_consolelib.c | 2 +- src/m_cheat.c | 5 +- src/m_menu.c | 379 ++++---- src/m_misc.c | 78 ++ src/m_misc.h | 2 + src/p_enemy.c | 57 +- src/p_floor.c | 150 +-- src/p_inter.c | 293 +----- src/p_local.h | 30 +- src/p_map.c | 45 +- src/p_mobj.c | 199 +--- src/p_setup.c | 195 +--- src/p_setup.h | 7 - src/p_spec.c | 111 +-- src/p_tick.c | 14 +- src/p_user.c | 514 +++-------- src/r_bsp.c | 19 +- src/r_main.c | 489 ++++------ src/r_main.h | 11 +- src/r_patch.c | 1 + src/r_segs.c | 52 +- src/r_things.c | 5 +- src/s_sound.c | 59 -- src/screen.c | 7 +- src/sdl/i_system.c | 1479 +++--------------------------- src/sdl/i_video.c | 545 ++++------- src/sdl/sdlmain.h | 22 +- src/st_stuff.c | 17 +- src/y_inter.c | 26 +- 59 files changed, 1978 insertions(+), 5844 deletions(-) diff --git a/src/Makefile b/src/Makefile index 63239dfbe..4df4e1fe8 100644 --- a/src/Makefile +++ b/src/Makefile @@ -229,6 +229,7 @@ endif ifdef LINUX UNIXCOMMON=1 +NOOBJDUMP=1 ifndef NOGME HAVE_LIBGME=1 endif diff --git a/src/am_map.c b/src/am_map.c index ac8236b41..3c10f710d 100644 --- a/src/am_map.c +++ b/src/am_map.c @@ -1,8 +1,10 @@ -// SONIC ROBO BLAST 2 +// SONIC ROBO BLAST 2 KART //----------------------------------------------------------------------------- // Copyright (C) 1993-1996 by id Software, Inc. -// Copyright (C) 1998-2000 by DooM Legacy Team. -// Copyright (C) 1999-2018 by Sonic Team Junior. +// Copyright (C) 2024 by Vivian "toastergrl" Grannell. +// Copyright (C) 2024 by Kart Krew. +// Copyright (C) 2020 by Sonic Team Junior. +// Copyright (C) 2000 by DooM Legacy Team. // // This program is free software distributed under the // terms of the GNU General Public License, version 2. @@ -26,43 +28,37 @@ #endif // For use if I do walls with outsides/insides -static const UINT8 REDS = (8*16); +static const UINT8 REDS = (2*16); static const UINT8 REDRANGE = 16; static const UINT8 GRAYS = (1*16); static const UINT8 GRAYSRANGE = 16; -static const UINT8 BROWNS = (3*16); -static const UINT8 YELLOWS = (7*16); -static const UINT8 GREENS = (10*16); +static const UINT8 BROWNS = (15*16); +static const UINT8 YELLOWS = (5*16)+8; +static const UINT8 GREENS = (6*16); +static const UINT8 BLUES = (9*16); static const UINT8 DBLACK = 31; static const UINT8 DWHITE = 0; -static const UINT8 NOCLIMBREDS = 248; -static const UINT8 NOCLIMBREDRANGE = 8; -static const UINT8 NOCLIMBGRAYS = 204; -static const UINT8 NOCLIMBBROWNS = (2*16); -static const UINT8 NOCLIMBYELLOWS = (11*16); - // Automap colors #define BACKGROUND DBLACK #define WALLCOLORS (REDS + REDRANGE/2) #define WALLRANGE (REDRANGE/2) -#define NOCLIMBWALLCOLORS (NOCLIMBREDS + NOCLIMBREDRANGE/2) -#define NOCLIMBWALLRANGE (NOCLIMBREDRANGE/2) #define THOKWALLCOLORS REDS #define THOKWALLRANGE REDRANGE -#define NOCLIMBTHOKWALLCOLORS NOCLIMBREDS -#define NOCLIMBTHOKWALLRANGE NOCLIMBREDRANGE -#define TSWALLCOLORS GRAYS -#define TSWALLRANGE GRAYSRANGE -#define NOCLIMBTSWALLCOLORS NOCLIMBGRAYS +#define TSWALLCOLORS DWHITE +#define TSFINISHLINE GRAYS +#define TSFOFINFO (BLUES + 4) #define FDWALLCOLORS BROWNS -#define NOCLIMBFDWALLCOLORS NOCLIMBBROWNS #define CDWALLCOLORS YELLOWS -#define NOCLIMBCDWALLCOLORS NOCLIMBYELLOWS #define THINGCOLORS GREENS #define GRIDCOLORS (GRAYS + GRAYSRANGE/2) #define XHAIRCOLORS GRAYS +// Automap passes +#define PASS_SOLID 1 +#define PASS_INTANGIBLE 2 +#define PASS_FOF 4 + // controls #define AM_PANUPKEY KEY_UPARROW #define AM_PANDOWNKEY KEY_DOWNARROW @@ -110,11 +106,6 @@ typedef struct mpoint_t a, b; } mline_t; -typedef struct -{ - fixed_t slp, islp; -} islope_t; - // // The vector graphics for the automap. // A line drawing of the player pointing right, @@ -136,16 +127,14 @@ static const mline_t player_arrow[] = { #undef R #define NUMPLYRLINES (sizeof (player_arrow)/sizeof (mline_t)) -#if 0 #define R (FRACUNIT) -static mline_t triangle_guy[] = { - { { (fixed_t)-.867f*R, (fixed_t)-.5f*R }, { (fixed_t) .867f*R, (fixed_t)-.5f*R } }, - { { (fixed_t) .867f*R, (fixed_t)-.5f*R }, { (fixed_t) 0, (fixed_t) R } }, - { { (fixed_t) 0, (fixed_t) R }, { (fixed_t)-.867f*R, (fixed_t)-.5f*R } } +static const mline_t cross_mark[] = +{ + { { -R, 0 }, { R, 0} }, + { { 0, -R }, { 0, R } }, }; #undef R -#define NUMTRIANGLEGUYLINES (sizeof (triangle_guy)/sizeof (mline_t)) -#endif +#define NUMCROSSMARKLINES (sizeof(cross_mark)/sizeof(mline_t)) #define R (FRACUNIT) static const mline_t thintriangle_guy[] = { @@ -162,10 +151,14 @@ static boolean draw_grid = false; boolean automapactive = false; boolean am_recalc = false; //added : 05-02-98 : true when screen size changes static boolean am_stopped = true; +static boolean am_minigen = false; + +static UINT8 *am_buf = NULL; static INT32 f_x, f_y; // location of window on screen (always zero for both) static INT32 f_w, f_h; // size of window on screen (always the screen width and height respectively) +static boolean m_keydown[4]; // which window panning keys are being pressed down? static mpoint_t m_paninc; // how far the window pans each tic (map coords) static fixed_t mtof_zoommul; // how far the window zooms in each tic (map coords) static fixed_t ftom_zoommul; // how far the window zooms in each tic (fb coords) @@ -205,12 +198,13 @@ static fixed_t scale_ftom; static player_t *plr; // the player represented by an arrow -static INT32 followplayer = true; // specifies whether to follow the player around +static boolean followplayer = true; // specifies whether to follow the player around // function for drawing lines, depends on rendermode typedef void (*AMDRAWFLINEFUNC) (const fline_t *fl, INT32 color); static AMDRAWFLINEFUNC AM_drawFline; +static void AM_drawPixel(INT32 xx, INT32 yy, INT32 cc); static void AM_drawFline_soft(const fline_t *fl, INT32 color); static void AM_activateNewScale(void) @@ -340,22 +334,23 @@ static void AM_initVariables(void) old_m_h = m_h; } +// +// Called when the screen size changes. +// +static void AM_FrameBufferInit(void) +{ + f_x = f_y = 0; + f_w = vid.width; + f_h = vid.height; + am_buf = screens[0]; +} + // // should be called at the start of every level // right now, i figure it out myself // static void AM_LevelInit(void) { - f_x = f_y = 0; - f_w = vid.width; - f_h = vid.height; - - AM_drawFline = AM_drawFline_soft; -#ifdef HWRENDER - if (rendermode == render_opengl) - AM_drawFline = HWR_drawAMline; -#endif - AM_findMinMaxBoundaries(); scale_mtof = FixedDiv(min_scale_mtof*10, 7*FRACUNIT); if (scale_mtof > max_scale_mtof) @@ -377,7 +372,7 @@ void AM_Stop(void) * * \sa AM_Stop */ -static inline void AM_Start(void) +void AM_Start(void) { static INT32 lastlevel = -1; @@ -386,8 +381,12 @@ static inline void AM_Start(void) am_stopped = false; if (lastlevel != gamemap || am_recalc) // screen size changed { - AM_LevelInit(); - lastlevel = gamemap; + AM_FrameBufferInit(); + if (lastlevel != gamemap) + { + AM_LevelInit(); + lastlevel = gamemap; + } am_recalc = false; } AM_initVariables(); @@ -413,6 +412,27 @@ static void AM_maxOutWindowScale(void) AM_activateNewScale(); } +// +// set window panning +// +static void AM_setWindowPanning(void) +{ + // up and down + if (m_keydown[2]) // pan up + m_paninc.y = FTOM(F_PANINC); + else if (m_keydown[3]) // pan down + m_paninc.y = -FTOM(F_PANINC); + else + m_paninc.y = 0; + // left and right + if (m_keydown[0]) // pan right + m_paninc.x = FTOM(F_PANINC); + else if (m_keydown[1]) // pan left + m_paninc.x = -FTOM(F_PANINC); + else + m_paninc.x = 0; +} + /** Responds to user inputs in automap mode. * * \param ev Event to possibly respond to. @@ -445,35 +465,49 @@ boolean AM_Responder(event_t *ev) { case AM_PANRIGHTKEY: // pan right if (!followplayer) - m_paninc.x = FTOM(F_PANINC); + { + m_keydown[0] = true; + AM_setWindowPanning(); + } else rc = false; break; case AM_PANLEFTKEY: // pan left if (!followplayer) - m_paninc.x = -FTOM(F_PANINC); + { + m_keydown[1] = true; + AM_setWindowPanning(); + } else rc = false; break; case AM_PANUPKEY: // pan up if (!followplayer) - m_paninc.y = FTOM(F_PANINC); + { + m_keydown[2] = true; + AM_setWindowPanning(); + } else rc = false; break; case AM_PANDOWNKEY: // pan down if (!followplayer) - m_paninc.y = -FTOM(F_PANINC); + { + m_keydown[3] = true; + AM_setWindowPanning(); + } else rc = false; break; case AM_ZOOMOUTKEY: // zoom out mtof_zoommul = M_ZOOMOUT; ftom_zoommul = M_ZOOMIN; + AM_setWindowPanning(); break; case AM_ZOOMINKEY: // zoom in mtof_zoommul = M_ZOOMIN; ftom_zoommul = M_ZOOMOUT; + AM_setWindowPanning(); break; case AM_TOGGLEKEY: AM_Stop(); @@ -487,6 +521,7 @@ boolean AM_Responder(event_t *ev) } else AM_restoreScaleAndLoc(); + AM_setWindowPanning(); break; case AM_FOLLOWKEY: followplayer = !followplayer; @@ -506,14 +541,32 @@ boolean AM_Responder(event_t *ev) switch (ev->data1) { case AM_PANRIGHTKEY: + if (!followplayer) + { + m_keydown[0] = false; + AM_setWindowPanning(); + } + break; case AM_PANLEFTKEY: if (!followplayer) - m_paninc.x = 0; + { + m_keydown[1] = false; + AM_setWindowPanning(); + } break; case AM_PANUPKEY: + if (!followplayer) + { + m_keydown[2] = false; + AM_setWindowPanning(); + } + break; case AM_PANDOWNKEY: if (!followplayer) - m_paninc.y = 0; + { + m_keydown[3] = false; + AM_setWindowPanning(); + } break; case AM_ZOOMOUTKEY: case AM_ZOOMINKEY: @@ -714,6 +767,16 @@ static boolean AM_clipMline(const mline_t *ml, fline_t *fl) } #undef DOOUTCODE +// +// Draws a pixel. +// +static void AM_drawPixel(INT32 xx, INT32 yy, INT32 cc) +{ + if (xx < 0 || yy < 0 || xx >= f_w || yy >= f_h) + return; // off the screen + am_buf[(yy*f_w) + xx] = cc; +} + // // Classic Bresenham w/ whatever optimizations needed for speed // @@ -735,8 +798,6 @@ static void AM_drawFline_soft(const fline_t *fl, INT32 color) } #endif - #define PUTDOT(xx,yy,cc) V_DrawFill(xx,yy,1,1,cc|V_NOSCALESTART); - dx = fl->b.x - fl->a.x; ax = 2 * (dx < 0 ? -dx : dx); sx = dx < 0 ? -1 : 1; @@ -753,7 +814,7 @@ static void AM_drawFline_soft(const fline_t *fl, INT32 color) d = ay - ax/2; for (;;) { - PUTDOT(x, y, color) + AM_drawPixel(x, y, color); if (x == fl->b.x) return; if (d >= 0) @@ -770,7 +831,7 @@ static void AM_drawFline_soft(const fline_t *fl, INT32 color) d = ax - ay/2; for (;;) { - PUTDOT(x, y, color) + AM_drawPixel(x, y, color); if (y == fl->b.y) return; if (d >= 0) @@ -782,8 +843,6 @@ static void AM_drawFline_soft(const fline_t *fl, INT32 color) d += ax; } } - - #undef PUTDOT } // @@ -805,17 +864,18 @@ static void AM_drawGrid(INT32 color) fixed_t x, y; fixed_t start, end; mline_t ml; + fixed_t gridsize = (MAPBLOCKUNITS<>FRACTOMAPBITS)) % gridsize) + start += gridsize - ((start - (bmaporgx>>FRACTOMAPBITS)) % gridsize); end = m_x + m_w; // draw vertical gridlines ml.a.y = m_y; ml.b.y = m_y + m_h; - for (x = start; x < end; x += (MAPBLOCKUNITS<>FRACTOMAPBITS)) % gridsize) + start += gridsize - ((start - (bmaporgy>>FRACTOMAPBITS)) % gridsize); end = m_y + m_h; // draw horizontal gridlines ml.a.x = m_x; ml.b.x = m_x + m_w; - for (y = start; y < end; y += (MAPBLOCKUNITS<x, lines[i].v1->y) + FRACUNIT/2) >> FRACBITS; \ + end2 = (P_GetZAt(slope, lines[i].v2->x, lines[i].v2->y) + FRACUNIT/2) >> FRACBITS; \ + } else \ + end1 = end2 = (normalheight + FRACUNIT/2) >> FRACBITS; + +static ffloor_t *AM_CompareFOFs(size_t i, ffloor_t *rover, ffloor_t *secondarystore) +{ + ffloor_t *secondaryrover = NULL; + for (; rover; rover = rover->next) + { + fixed_t rovt1, rovt2; + fixed_t rovb1, rovb2; + if (!(rover->flags & FF_EXISTS)) + continue; + if (!(rover->flags & FF_BLOCKPLAYER)) + continue; + SLOPEPARAMS(*rover->t_slope, rovt1, rovt2, *rover->topheight) + SLOPEPARAMS(*rover->b_slope, rovb1, rovb2, *rover->bottomheight) + for (secondaryrover = secondarystore; secondaryrover; secondaryrover = secondaryrover->next) + { + fixed_t sect1, sect2; + fixed_t secb1, secb2; + if (!(secondaryrover->flags & FF_EXISTS)) + continue; + if (!(secondaryrover->flags & FF_BLOCKPLAYER)) + continue; + if (secondaryrover->secnum == rover->secnum) + break; + SLOPEPARAMS(*secondaryrover->t_slope, sect1, sect2, *secondaryrover->topheight) + SLOPEPARAMS(*secondaryrover->b_slope, secb1, secb2, *secondaryrover->bottomheight) + if (rovt1 != sect1) + continue; + if (rovt2 != sect2) + continue; + if (rovb1 != secb1) + continue; + if (rovb2 != secb2) + continue; + break; + } + if (secondaryrover == NULL) + break; + } + return rover; +} + // // Determines visible lines, draws them. // This is LineDef based, not LineSeg based. // -static inline void AM_drawWalls(void) +static void AM_drawWalls(UINT8 pass) { size_t i; static mline_t l; + const fixed_t maxstep = FixedMul(MAXSTEPMOVE, mapobjectscale)>>FRACBITS; fixed_t frontf1,frontf2, frontc1, frontc2; // front floor/ceiling ends fixed_t backf1 = 0, backf2 = 0, backc1 = 0, backc2 = 0; // back floor ceiling ends @@ -856,74 +965,143 @@ static inline void AM_drawWalls(void) l.a.y = lines[i].v1->y >> FRACTOMAPBITS; l.b.x = lines[i].v2->x >> FRACTOMAPBITS; l.b.y = lines[i].v2->y >> FRACTOMAPBITS; -#define SLOPEPARAMS(slope, end1, end2, normalheight) \ - if (slope) { \ - end1 = P_GetZAt(slope, lines[i].v1->x, lines[i].v1->y); \ - end2 = P_GetZAt(slope, lines[i].v2->x, lines[i].v2->y); \ - } else \ - end1 = end2 = normalheight; SLOPEPARAMS(lines[i].frontsector->f_slope, frontf1, frontf2, lines[i].frontsector->floorheight) SLOPEPARAMS(lines[i].frontsector->c_slope, frontc1, frontc2, lines[i].frontsector->ceilingheight) - if (lines[i].backsector) { - SLOPEPARAMS(lines[i].backsector->f_slope, backf1, backf2, lines[i].backsector->floorheight) - SLOPEPARAMS(lines[i].backsector->c_slope, backc1, backc2, lines[i].backsector->ceilingheight) - } -#undef SLOPEPARAMS if (!lines[i].backsector) // 1-sided { - if (lines[i].flags & ML_NOCLIMB) - AM_drawMline(&l, NOCLIMBWALLCOLORS); - else + if (!(pass & PASS_SOLID)) + ; + else if (frontf1 != frontc1 || frontf2 != frontc2 || lines[i].frontsector->f_slope) + { + AM_drawMline(&l, TSWALLCOLORS); + } + else if (!am_minigen) + { AM_drawMline(&l, WALLCOLORS); + } + continue; } - else if ((backf1 == backc1 && backf2 == backc2) // Back is thok barrier + SLOPEPARAMS(lines[i].backsector->f_slope, backf1, backf2, lines[i].backsector->floorheight) + SLOPEPARAMS(lines[i].backsector->c_slope, backc1, backc2, lines[i].backsector->ceilingheight) + if ((backf1 == backc1 && backf2 == backc2) // Back is thok barrier || (frontf1 == frontc1 && frontf2 == frontc2)) // Front is thok barrier { if (backf1 == backc1 && backf2 == backc2 && frontf1 == frontc1 && frontf2 == frontc2) // BOTH are thok barriers { - if (lines[i].flags & ML_NOCLIMB) - AM_drawMline(&l, NOCLIMBTSWALLCOLORS); - else - AM_drawMline(&l, TSWALLCOLORS); + if (!am_minigen && (pass & PASS_INTANGIBLE)) + { + AM_drawMline(&l, GRIDCOLORS); + } } - else + else if (pass & PASS_SOLID) { - if (lines[i].flags & ML_NOCLIMB) - AM_drawMline(&l, NOCLIMBTHOKWALLCOLORS); - else - AM_drawMline(&l, THOKWALLCOLORS); + AM_drawMline(&l, TSWALLCOLORS); } } else { - if (lines[i].flags & ML_NOCLIMB) { - if (backf1 != frontf1 || backf2 != frontf2) { - AM_drawMline(&l, NOCLIMBFDWALLCOLORS); // floor level change - } - else if (backc1 != frontc1 || backc2 != frontc2) { - AM_drawMline(&l, NOCLIMBCDWALLCOLORS); // ceiling level change + //dont think kart even supports those idk? + /*if (lines[i].flags & (ML_IMPASSABLE|ML_BLOCKPLAYERS)) + { + if (pass & PASS_SOLID) + AM_drawMline(&l, TSWALLCOLORS); // Completely solid course boundary + } + else if ((lines[i].flags & ML_MIDSOLID) + && sides[lines->sidenum[0]].midtexture) + { + if (pass & PASS_SOLID) + AM_drawMline(&l, TSWALLCOLORS); // solid midtexture, likely a course boundary + }*/ + if ((backf1 != frontf1 && abs(backf1 - frontf1) > maxstep) + || (backf2 != frontf2 && abs(backf2 - frontf2) > maxstep)) + { + if (pass & PASS_SOLID) + AM_drawMline(&l, TSWALLCOLORS); // floor-wall, likely a course boundary + } + /*else if (lines[i].special == 2001) // guh its a sector effect in kart idk how to make it work tbh lol + { + if (pass & PASS_SOLID) + AM_drawMline(&l, TSFINISHLINE); // finish line + }*/ + else if (backf1 != frontf1 || backf2 != frontf2) + { + if (pass & PASS_INTANGIBLE) + AM_drawMline(&l, FDWALLCOLORS); // floorlevel change + } + else if (backc1 != frontc1 || backc2 != frontc2) + { + if (!(pass & PASS_INTANGIBLE)) + ; + else if (abs(backc1 - frontc1) < maxstep + || abs(backc2 - frontc2) < maxstep) + { + AM_drawMline(&l, CDWALLCOLORS); // ceilinglevel change } else - AM_drawMline(&l, NOCLIMBTSWALLCOLORS); + { + AM_drawMline(&l, GRIDCOLORS); // ceiling-wall, not likely to be a course boundary but flagged up just in case + } } else { - if (backf1 != frontf1 || backf2 != frontf2) { - AM_drawMline(&l, FDWALLCOLORS); // floor level change + { + ffloor_t *rover = NULL; + + if (lines[i].frontsector->ffloors || lines[i].backsector->ffloors) + { + if (lines[i].backsector->ffloors == NULL) + { + // Check frontside for one solid + for (rover = lines[i].frontsector->ffloors; rover; rover = rover->next) + { + if (!(rover->flags & FF_EXISTS)) + continue; + if (!(rover->flags & FF_BLOCKPLAYER)) + continue; + break; + } + } + else if (lines[i].frontsector->ffloors == NULL) + { + // Check backside for one solid + for (rover = lines[i].backsector->ffloors; rover; rover = rover->next) + { + if (!(rover->flags & FF_EXISTS)) + continue; + if (!(rover->flags & FF_BLOCKPLAYER)) + continue; + break; + } + } + else + { + // Check to see if any secnums exist in one but not the other. + rover = AM_CompareFOFs(i, lines[i].frontsector->ffloors, lines[i].backsector->ffloors); + if (rover == NULL) + rover = AM_CompareFOFs(i, lines[i].backsector->ffloors, lines[i].frontsector->ffloors); + } + } + if (rover != NULL) + { + if (pass & PASS_FOF) + AM_drawMline(&l, TSFOFINFO); // a FOF is here but we don't know how to distinguish them yet + } + else if (!am_minigen) + { + if (pass & PASS_INTANGIBLE) + AM_drawMline(&l, GRIDCOLORS); // likely low-relevance line + } } - else if (backc1 != frontc1 || backc2 != frontc2) { - AM_drawMline(&l, CDWALLCOLORS); // ceiling level change - } - else - AM_drawMline(&l, TSWALLCOLORS); } } } } +#undef SLOPEPARAMS + // // Rotation in 2D. // Used to rotate player arrow line character. @@ -996,7 +1174,7 @@ static inline void AM_drawPlayers(void) if (!multiplayer) { - AM_drawLineCharacter(player_arrow, NUMPLYRLINES, 0, plr->mo->angle, DWHITE, plr->mo->x, plr->mo->y); + AM_drawLineCharacter(player_arrow, NUMPLYRLINES, 16<mo->angle, DWHITE, plr->mo->x, plr->mo->y); return; } @@ -1013,7 +1191,7 @@ static inline void AM_drawPlayers(void) if (p->skincolor > 0) color = R_GetTranslationColormap(TC_DEFAULT, p->skincolor, GTC_CACHE)[GREENS + 8]; - AM_drawLineCharacter(player_arrow, NUMPLYRLINES, 0, p->mo->angle, color, p->mo->x, p->mo->y); + AM_drawLineCharacter(player_arrow, NUMPLYRLINES, 16<mo->angle, color, p->mo->x, p->mo->y); } } @@ -1033,13 +1211,27 @@ static inline void AM_drawThings(UINT8 colors) } } -/** Draws the crosshair, actually just a dot in software mode. +/** Draws the crosshair. * * \param color Color for the crosshair. */ static inline void AM_drawCrosshair(UINT8 color) { - V_DrawFill(f_w/2 + f_x, f_h/2 + f_y, 1, 1, color|V_NOSCALESTART); + const fixed_t scale = 4<> FRACBITS; + fl.a.y = FixedMul(cross_mark[i].a.y, scale) >> FRACBITS; + fl.b.x = FixedMul(cross_mark[i].b.x, scale) >> FRACBITS; + fl.b.y = FixedMul(cross_mark[i].b.y, scale) >> FRACBITS; + fl.a.x += f_x + (f_w / 2); + fl.a.y += f_y + (f_h / 2); + fl.b.x += f_x + (f_w / 2); + fl.b.y += f_y + (f_h / 2); + AM_drawFline(&fl, color); + } } /** Draws the automap. @@ -1049,11 +1241,80 @@ void AM_Drawer(void) if (!automapactive) return; + AM_drawFline = AM_drawFline_soft; +#ifdef HWRENDER + if (rendermode == render_opengl) + AM_drawFline = HWR_drawAMline; +#endif + AM_clearFB(BACKGROUND); if (draw_grid) AM_drawGrid(GRIDCOLORS); - AM_drawWalls(); + AM_drawWalls(PASS_FOF|PASS_INTANGIBLE|PASS_SOLID); AM_drawPlayers(); AM_drawThings(THINGCOLORS); - AM_drawCrosshair(XHAIRCOLORS); + if (!followplayer) AM_drawCrosshair(XHAIRCOLORS); +} + +minigen_t *AM_MinimapGenerate(INT32 mul) +{ + static minigen_t ret = {0}; + + if (automapactive) + return NULL; + + am_minigen = true; + + AM_drawFline = AM_drawFline_soft; // yes, even in GL + + //AM_FrameBufferInit(); + f_x = f_y = 0; + ret.w = f_w = minimapinfo.minimap_w * mul; + ret.h = f_h = minimapinfo.minimap_h * mul; + am_buf = ret.buf = NULL; + + //AM_LevelInit(); + AM_findMinMaxBoundaries(); + scale_mtof = min_scale_mtof - (min_scale_mtof/20); + scale_ftom = FixedDiv(FRACUNIT, scale_mtof); + + //AM_initVariables(); + f_oldloc.x = INT32_MAX; + + m_paninc.x = m_paninc.y = 0; + ftom_zoommul = FRACUNIT; + mtof_zoommul = FRACUNIT; + + m_w = FTOM(f_w); + m_h = FTOM(f_h); + + //AM_changeWindowLoc(); + m_x = min_x - FixedMul(m_w, FRACUNIT/40); + m_y = min_y - FixedMul(m_h, FRACUNIT/40); + m_x2 = m_x + m_w; + m_y2 = m_y + m_h; + + // for saving & restoring + old_m_x = m_x; + old_m_y = m_y; + old_m_w = m_w; + old_m_h = m_h; + + am_buf = ret.buf = malloc((f_w*f_h)); + + if (ret.buf == NULL) + return NULL; + + //AM_clearFB(BACKGROUND); + memset(am_buf, 0xff, (f_w*f_h)); + AM_drawWalls(PASS_FOF); + AM_drawWalls(PASS_INTANGIBLE); + AM_drawWalls(PASS_SOLID); + + am_buf = NULL; + am_recalc = true; + + am_minigen = false; + + return &ret; } diff --git a/src/am_map.h b/src/am_map.h index 4e8c782a9..112ba345f 100644 --- a/src/am_map.h +++ b/src/am_map.h @@ -1,8 +1,10 @@ -// SONIC ROBO BLAST 2 +// SONIC ROBO BLAST 2 KART //----------------------------------------------------------------------------- // Copyright (C) 1993-1996 by id Software, Inc. -// Copyright (C) 1998-2000 by DooM Legacy Team. -// Copyright (C) 1999-2018 by Sonic Team Junior. +// Copyright (C) 2024 by Vivian "toastergrl" Grannell. +// Copyright (C) 2024 by Kart Krew. +// Copyright (C) 2020 by Sonic Team Junior. +// Copyright (C) 2000 by DooM Legacy Team. // // This program is free software distributed under the // terms of the GNU General Public License, version 2. @@ -26,11 +28,6 @@ typedef struct fpoint_t a, b; } fline_t; -// Used by ST StatusBar stuff. -#define AM_MSGHEADER (('a'<<24)+('m'<<16)) -#define AM_MSGENTERED (AM_MSGHEADER | ('e'<<8)) -#define AM_MSGEXITED (AM_MSGHEADER | ('x'<<8)) - extern boolean am_recalc; // true if screen size changes extern boolean automapactive; // In AutoMap mode? @@ -43,7 +40,19 @@ void AM_Ticker(void); // Called by main loop, instead of view drawer if automap is active. void AM_Drawer(void); +// Enables the automap. +void AM_Start(void); + // Called to force the automap to quit if the level is completed while it is up. void AM_Stop(void); +typedef struct +{ + INT32 w, h; + UINT8 *buf; +} minigen_t; + +// Minimap generation +minigen_t *AM_MinimapGenerate(INT32 mul); + #endif diff --git a/src/b_bot.c b/src/b_bot.c index edaf477ad..7281013be 100644 --- a/src/b_bot.c +++ b/src/b_bot.c @@ -118,9 +118,6 @@ void B_BuildTiccmd(player_t *player, ticcmd_t *cmd) return; } - // Bot AI isn't programmed in analog. - //CV_SetValue(&cv_analog2, false); - // Let Lua scripts build ticcmds if (LUAh_BotTiccmd(player, cmd)) return; @@ -135,55 +132,20 @@ void B_BuildTiccmd(player_t *player, ticcmd_t *cmd) void B_KeysToTiccmd(mobj_t *mo, ticcmd_t *cmd, boolean forward, boolean backward, boolean left, boolean right, boolean strafeleft, boolean straferight, boolean jump, boolean spin) { - // Turn the virtual keypresses into ticcmd_t. - if (twodlevel || mo->flags2 & MF2_TWOD) { - if (players[consoleplayer].climbing - || mo->player->pflags & PF_GLIDING) { - // Don't mess with bot inputs during these unhandled movement conditions. - // The normal AI doesn't use abilities, so custom AI should be sending us exactly what it wants anyway. - if (forward) - cmd->forwardmove += MAXPLMOVE<>16; - if (backward) - cmd->forwardmove -= MAXPLMOVE<>16; - if (left || strafeleft) - cmd->sidemove -= MAXPLMOVE<>16; - if (right || straferight) - cmd->sidemove += MAXPLMOVE<>16; - } else { - // In standard 2D mode, interpret "forward" as "the way you're facing" and everything else as "the way you're not facing" - if (left || right) - backward = true; - left = right = false; - if (forward) { - if (mo->angle < ANGLE_90 || mo->angle > ANGLE_270) - right = true; - else - left = true; - } else if (backward) { - if (mo->angle < ANGLE_90 || mo->angle > ANGLE_270) - left = true; - else - right = true; - } - if (left || strafeleft) - cmd->sidemove -= MAXPLMOVE<>16; - if (right || straferight) - cmd->sidemove += MAXPLMOVE<>16; - } - } else { - if (forward) - cmd->forwardmove += MAXPLMOVE<>16; - if (backward) - cmd->forwardmove -= MAXPLMOVE<>16; - if (left) - cmd->angleturn += 1280; - if (right) - cmd->angleturn -= 1280; - if (strafeleft) - cmd->sidemove -= MAXPLMOVE<>16; - if (straferight) - cmd->sidemove += MAXPLMOVE<>16; - } + (void)mo; + + if (forward) + cmd->forwardmove += MAXPLMOVE<>16; + if (backward) + cmd->forwardmove -= MAXPLMOVE<>16; + if (left) + cmd->angleturn += 1280; + if (right) + cmd->angleturn -= 1280; + if (strafeleft) + cmd->sidemove -= MAXPLMOVE<>16; + if (straferight) + cmd->sidemove += MAXPLMOVE<>16; if (jump) cmd->buttons |= BT_DRIFT; if (spin) diff --git a/src/d_clisrv.c b/src/d_clisrv.c index af9e57083..5feef98b2 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -50,6 +50,7 @@ #include "s_sound.h" // sfx_syfail #include "m_perfstats.h" #include "d_main.h" +#include "r_fps.h" #ifdef CLIENT_LOADINGSCREEN // cl loading screen @@ -139,10 +140,7 @@ static UINT8 gamestate_resend_counter[MAXNETNODES]; boolean hu_stopped = false; // Client specific -static ticcmd_t localcmds; -static ticcmd_t localcmds2; -static ticcmd_t localcmds3; -static ticcmd_t localcmds4; +static ticcmd_t localcmds[MAXSPLITSCREENPLAYERS]; static boolean cl_packetmissed; // here it is for the secondary local player (splitscreen) static UINT8 mynode; // my address pointofview server @@ -159,10 +157,7 @@ boolean is_client_saturn[MAXNETNODES]; #define ISSATURN 69 #endif -static UINT8 localtextcmd[MAXTEXTCMD]; -static UINT8 localtextcmd2[MAXTEXTCMD]; // splitscreen -static UINT8 localtextcmd3[MAXTEXTCMD]; // splitscreen == 2 -static UINT8 localtextcmd4[MAXTEXTCMD]; // splitscreen == 3 +static UINT8 localtextcmd[MAXSPLITSCREENPLAYERS][MAXTEXTCMD]; static tic_t neededtic; SINT8 servernode = 0; // the number of the server node char connectedservername[MAXSERVERNAME+1]; @@ -276,77 +271,30 @@ void RegisterNetXCmd(netxcmd_t id, void (*cmd_f)(UINT8 **p, INT32 playernum)) listnetxcmd[id] = cmd_f; } -void SendNetXCmd(netxcmd_t id, const void *param, size_t nparam) +void SendNetXCmdForPlayer(UINT8 playerid, netxcmd_t id, const void *param, size_t nparam) { - if (localtextcmd[0]+2+nparam > MAXTEXTCMD) + if ((localtextcmd[playerid])[0]+2+nparam > MAXTEXTCMD) { - // for future reference: if (cv_debug) != debug disabled. - CONS_Alert(CONS_ERROR, M_GetText("NetXCmd buffer full, cannot add netcmd %d! (size: %d, needed: %s)\n"), id, localtextcmd[0], sizeu1(nparam)); + // for future reference: if (cht_debug) != debug disabled. + CONS_Alert(CONS_ERROR, M_GetText("NetXCmd buffer full, cannot add netcmd %d! (size: %d, needed: %s)\n"), id, localtextcmd[playerid][0], sizeu1(nparam)); return; } - localtextcmd[0]++; - localtextcmd[localtextcmd[0]] = (UINT8)id; + + localtextcmd[playerid][0]++; + localtextcmd[playerid][localtextcmd[playerid][0]] = (UINT8)id; + if (param && nparam) { - M_Memcpy(&localtextcmd[localtextcmd[0]+1], param, nparam); - localtextcmd[0] = (UINT8)(localtextcmd[0] + (UINT8)nparam); + M_Memcpy(&localtextcmd[playerid][localtextcmd[playerid][0] + 1], param, nparam); + localtextcmd[playerid][0] = (UINT8)(localtextcmd[playerid][0] + (UINT8)nparam); } } -// splitscreen player -void SendNetXCmd2(netxcmd_t id, const void *param, size_t nparam) -{ - if (localtextcmd2[0]+2+nparam > MAXTEXTCMD) - { - I_Error("No more place in the buffer for netcmd %d\n",id); - return; - } - localtextcmd2[0]++; - localtextcmd2[localtextcmd2[0]] = (UINT8)id; - if (param && nparam) - { - M_Memcpy(&localtextcmd2[localtextcmd2[0]+1], param, nparam); - localtextcmd2[0] = (UINT8)(localtextcmd2[0] + (UINT8)nparam); - } -} - -void SendNetXCmd3(netxcmd_t id, const void *param, size_t nparam) -{ - if (localtextcmd3[0]+2+nparam > MAXTEXTCMD) - { - I_Error("No more place in the buffer for netcmd %d\n",id); - return; - } - localtextcmd3[0]++; - localtextcmd3[localtextcmd3[0]] = (UINT8)id; - if (param && nparam) - { - M_Memcpy(&localtextcmd3[localtextcmd3[0]+1], param, nparam); - localtextcmd3[0] = (UINT8)(localtextcmd3[0] + (UINT8)nparam); - } -} - -void SendNetXCmd4(netxcmd_t id, const void *param, size_t nparam) -{ - if (localtextcmd4[0]+2+nparam > MAXTEXTCMD) - { - I_Error("No more place in the buffer for netcmd %d\n",id); - return; - } - localtextcmd4[0]++; - localtextcmd4[localtextcmd4[0]] = (UINT8)id; - if (param && nparam) - { - M_Memcpy(&localtextcmd4[localtextcmd4[0]+1], param, nparam); - localtextcmd4[0] = (UINT8)(localtextcmd4[0] + (UINT8)nparam); - } -} - -UINT8 GetFreeXCmdSize(void) +/*UINT8 GetFreeXCmdSize(UINT8 playerid) { // -1 for the size and another -1 for the ID. - return (UINT8)(localtextcmd[0] - 2); -} + return (UINT8)(localtextcmd[playerid][0] - 2); +}*/ // Frees all textcmd memory for the specified tic static void D_FreeTextcmd(tic_t tic) @@ -510,10 +458,8 @@ void D_ResetTiccmds(void) { INT32 i; - memset(&localcmds, 0, sizeof(ticcmd_t)); - memset(&localcmds2, 0, sizeof(ticcmd_t)); - memset(&localcmds3, 0, sizeof(ticcmd_t)); - memset(&localcmds4, 0, sizeof(ticcmd_t)); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + memset(&localcmds[i], 0, sizeof(ticcmd_t)); // Reset the net command list for (i = 0; i < TEXTCMD_HASH_SIZE; i++) @@ -856,110 +802,6 @@ static void resynch_read_player(resynch_pak *rsp) P_SetThingPosition(players[i].mo); } -static inline void resynch_write_ctf(resynchend_pak *rst) -{ - mobj_t *mflag; - UINT8 i, j; - - for (i = 0, mflag = redflag; i < 2; ++i, mflag = blueflag) - { - rst->flagx[i] = rst->flagy[i] = rst->flagz[i] = 0; - rst->flagloose[i] = rst->flagflags[i] = 0; - rst->flagplayer[i] = -1; - - if (!mflag) - { - // Should be held by a player - for (j = 0; j < MAXPLAYERS; ++j) - { - // GF_REDFLAG is 1, GF_BLUEFLAG is 2 - // redflag handling is i=0, blueflag is i=1 - // so check for gotflag == (i+1) - if (!playeringame[j] || players[j].gotflag != (i+1)) - continue; - rst->flagplayer[i] = (SINT8)j; - break; - } - if (j == MAXPLAYERS) // fine, no I_Error - { - CONS_Alert(CONS_ERROR, "One of the flags has gone completely missing...\n"); - rst->flagplayer[i] = -2; - } - continue; - } - - rst->flagx[i] = (fixed_t)LONG(mflag->x); - rst->flagy[i] = (fixed_t)LONG(mflag->y); - rst->flagz[i] = (fixed_t)LONG(mflag->z); - rst->flagflags[i] = LONG(mflag->flags2); - rst->flagloose[i] = LONG(mflag->fuse); // Dropped or not? - } -} - -static inline void resynch_read_ctf(resynchend_pak *p) -{ - UINT8 i; - - for (i = 0; i < MAXPLAYERS; ++i) - players[i].gotflag = 0; - - // Red flag - if (p->flagplayer[0] == -2) - ; // The server doesn't even know what happened to it... - else if (p->flagplayer[0] != -1) // Held by a player - { - if (!playeringame[p->flagplayer[0]]) - I_Error("Invalid red flag player %d who isn't in the game!", (INT32)p->flagplayer[0]); - players[p->flagplayer[0]].gotflag = GF_REDFLAG; - if (redflag) - { - P_RemoveMobj(redflag); - redflag = NULL; - } - } - else - { - if (!redflag) - redflag = P_SpawnMobj(0,0,0,MT_REDFLAG); - - P_UnsetThingPosition(redflag); - redflag->x = (fixed_t)LONG(p->flagx[0]); - redflag->y = (fixed_t)LONG(p->flagy[0]); - redflag->z = (fixed_t)LONG(p->flagz[0]); - redflag->flags2 = LONG(p->flagflags[0]); - redflag->fuse = LONG(p->flagloose[0]); - P_SetThingPosition(redflag); - } - - // Blue flag - if (p->flagplayer[1] == -2) - ; // The server doesn't even know what happened to it... - else if (p->flagplayer[1] != -1) // Held by a player - { - if (!playeringame[p->flagplayer[1]]) - I_Error("Invalid blue flag player %d who isn't in the game!", (INT32)p->flagplayer[1]); - players[p->flagplayer[1]].gotflag = GF_BLUEFLAG; - if (blueflag) - { - P_RemoveMobj(blueflag); - blueflag = NULL; - } - } - else - { - if (!blueflag) - blueflag = P_SpawnMobj(0,0,0,MT_BLUEFLAG); - - P_UnsetThingPosition(blueflag); - blueflag->x = (fixed_t)LONG(p->flagx[1]); - blueflag->y = (fixed_t)LONG(p->flagy[1]); - blueflag->z = (fixed_t)LONG(p->flagz[1]); - blueflag->flags2 = LONG(p->flagflags[1]); - blueflag->fuse = LONG(p->flagloose[1]); - P_SetThingPosition(blueflag); - } -} - static inline void resynch_write_others(resynchend_pak *rst) { UINT8 i; @@ -1060,8 +902,6 @@ static void SV_SendResynch(INT32 node) netbuffer->packettype = PT_RESYNCHEND; netbuffer->u.resynchend.randomseed = P_GetRandSeed(); - if (gametype == GT_CTF) - resynch_write_ctf(&netbuffer->u.resynchend); resynch_write_others(&netbuffer->u.resynchend); HSendPacket(node, true, 0, (sizeof(resynchend_pak))); @@ -1668,20 +1508,10 @@ static void SV_SendPlayerInfo(INT32 node) //No, don't do that, you fuckface. memset(netbuffer->u.playerinfo[i].address, 0, 4); - if (G_GametypeHasTeams()) - { - if (!players[i].ctfteam) - netbuffer->u.playerinfo[i].team = 255; - else - netbuffer->u.playerinfo[i].team = (UINT8)players[i].ctfteam; - } + if (players[i].spectator) + netbuffer->u.playerinfo[i].team = 255; else - { - if (players[i].spectator) - netbuffer->u.playerinfo[i].team = 255; - else - netbuffer->u.playerinfo[i].team = 0; - } + netbuffer->u.playerinfo[i].team = 0; netbuffer->u.playerinfo[i].score = LONG(players[i].score); netbuffer->u.playerinfo[i].timeinserver = SHORT((UINT16)(players[i].jointime / TICRATE)); @@ -3258,9 +3088,6 @@ void CL_RemovePlayer(INT32 playernum, INT32 reason) if (K_IsPlayerWanted(&players[playernum])) K_CalculateBattleWanted(); - if (gametype == GT_CTF) - P_PlayerFlagBurst(&players[playernum], false); // Don't take the flag with you! - // If in a special stage, redistribute the player's rings across // the remaining players. if (G_IsSpecialStage(gamemap)) @@ -3293,6 +3120,9 @@ void CL_RemovePlayer(INT32 playernum, INT32 reason) LUAh_PlayerQuit(&players[playernum], reason); // Lua hook for player quitting + if (playernum == displayplayers[0] && !demo.playback) + displayplayers[0] = consoleplayer; // don't look through someone's view who isn't there + // Reset player data CL_ClearPlayer(playernum); @@ -3312,9 +3142,6 @@ void CL_RemovePlayer(INT32 playernum, INT32 reason) RemoveAdminPlayer(playernum); // don't stay admin after you're gone } - if (playernum == displayplayers[0] && !demo.playback) - displayplayers[0] = consoleplayer; // don't look through someone's view who isn't there - LUA_InvalidatePlayer(&players[playernum]); if (G_BattleGametype()) // SRB2Kart @@ -4266,17 +4093,17 @@ void SV_ResetServer(void) sprintf(player_names[i], "Player %d", i + 1); } + memset(player_name_changes, 0, sizeof player_name_changes); + memset(playeringame, false, sizeof playeringame); memset(playernode, UINT8_MAX, sizeof playernode); - ClearAdminPlayers(); // Populate the entire adminplayers array with -1. - - memset(player_name_changes, 0, sizeof player_name_changes); - pingmeasurecount = 1; memset(realpingtable, 0, sizeof realpingtable); memset(playerpingtable, 0, sizeof playerpingtable); + ClearAdminPlayers(); + mynode = 0; cl_packetmissed = false; #ifdef SATURNSYNCH @@ -4645,10 +4472,8 @@ void SV_StopServer(void) Y_EndVote(); gamestate = wipegamestate = GS_NULL; - localtextcmd[0] = 0; - localtextcmd2[0] = 0; - localtextcmd3[0] = 0; - localtextcmd4[0] = 0; + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + localtextcmd[i][0] = 0; for (i = firstticstosend; i < firstticstosend + TICQUEUE; i++) D_Clearticcmd(i); @@ -5621,9 +5446,6 @@ static void HandlePacketFromPlayer(SINT8 node) resynch_local_inprogress = false; P_SetRandSeed(netbuffer->u.resynchend.randomseed); - - if (gametype == GT_CTF) - resynch_read_ctf(&netbuffer->u.resynchend); resynch_read_others(&netbuffer->u.resynchend); break; @@ -6061,26 +5883,26 @@ static void CL_SendClientCmd(void) else if (gamestate != GS_NULL) { packetsize = sizeof (clientcmd_pak); - G_MoveTiccmd(&netbuffer->u.clientpak.cmd, &localcmds, 1); + G_MoveTiccmd(&netbuffer->u.clientpak.cmd, &localcmds[0], 1); netbuffer->u.clientpak.consistancy = SHORT(consistancy[gametic%TICQUEUE]); if (splitscreen || botingame) // Send a special packet with 2 cmd for splitscreen { netbuffer->packettype = (mis ? PT_CLIENT2MIS : PT_CLIENT2CMD); packetsize = sizeof (client2cmd_pak); - G_MoveTiccmd(&netbuffer->u.client2pak.cmd2, &localcmds2, 1); + G_MoveTiccmd(&netbuffer->u.client2pak.cmd2, &localcmds[1], 1); if (splitscreen > 1) { netbuffer->packettype = (mis ? PT_CLIENT3MIS : PT_CLIENT3CMD); packetsize = sizeof (client3cmd_pak); - G_MoveTiccmd(&netbuffer->u.client3pak.cmd3, &localcmds3, 1); + G_MoveTiccmd(&netbuffer->u.client3pak.cmd3, &localcmds[2], 1); if (splitscreen > 2) { netbuffer->packettype = (mis ? PT_CLIENT4MIS : PT_CLIENT4CMD); packetsize = sizeof (client4cmd_pak); - G_MoveTiccmd(&netbuffer->u.client4pak.cmd4, &localcmds4, 1); + G_MoveTiccmd(&netbuffer->u.client4pak.cmd4, &localcmds[3], 1); } } } @@ -6090,44 +5912,33 @@ static void CL_SendClientCmd(void) if (cl_mode == CL_CONNECTED || dedicated) { + UINT8 i; // Send extra data if needed - if (localtextcmd[0]) + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) { - netbuffer->packettype = PT_TEXTCMD; - M_Memcpy(netbuffer->u.textcmd,localtextcmd, localtextcmd[0]+1); - // All extra data have been sent - if (HSendPacket(servernode, true, 0, localtextcmd[0]+1)) // Send can fail... - localtextcmd[0] = 0; - } + if (localtextcmd[i][0]) + { + switch (i) + { + case 3: + netbuffer->packettype = PT_TEXTCMD4; + break; + case 2: + netbuffer->packettype = PT_TEXTCMD3; + break; + case 1: + netbuffer->packettype = PT_TEXTCMD2; + break; + default: + netbuffer->packettype = PT_TEXTCMD; + break; + } - // Send extra data if needed for player 2 (splitscreen == 1) - if (localtextcmd2[0]) - { - netbuffer->packettype = PT_TEXTCMD2; - M_Memcpy(netbuffer->u.textcmd, localtextcmd2, localtextcmd2[0]+1); - // All extra data have been sent - if (HSendPacket(servernode, true, 0, localtextcmd2[0]+1)) // Send can fail... - localtextcmd2[0] = 0; - } - - // Send extra data if needed for player 3 (splitscreen == 2) - if (localtextcmd3[0]) - { - netbuffer->packettype = PT_TEXTCMD3; - M_Memcpy(netbuffer->u.textcmd, localtextcmd3, localtextcmd3[0]+1); - // All extra data have been sent - if (HSendPacket(servernode, true, 0, localtextcmd3[0]+1)) // Send can fail... - localtextcmd3[0] = 0; - } - - // Send extra data if needed for player 4 (splitscreen == 3) - if (localtextcmd4[0]) - { - netbuffer->packettype = PT_TEXTCMD4; - M_Memcpy(netbuffer->u.textcmd, localtextcmd4, localtextcmd4[0]+1); - // All extra data have been sent - if (HSendPacket(servernode, true, 0, localtextcmd4[0]+1)) // Send can fail... - localtextcmd4[0] = 0; + M_Memcpy(netbuffer->u.textcmd, localtextcmd[i], localtextcmd[i][0]+1); + // All extra data have been sent + if (HSendPacket(servernode, true, 0, localtextcmd[i][0]+1)) // Send can fail... + localtextcmd[i][0] = 0; + } } } } @@ -6256,27 +6067,27 @@ static void SV_SendTics(void) // // TryRunTics // +static inline void CreateNewLocalCMD(UINT8 p, INT32 realtics) +{ + G_BuildTiccmd(&localcmds[p], realtics, p+1); + localcmds[p].angleturn |= TICCMD_RECEIVED; +} + static void Local_Maketic(INT32 realtics) { + INT32 i; + I_OsPolling(); // I_Getevent D_ProcessEvents(); // menu responder, cons responder, // game responder calls HU_Responder, AM_Responder, F_Responder, // and G_MapEventsToControls if (!dedicated) rendergametic = gametic; // translate inputs (keyboard/mouse/joystick) into game controls - G_BuildTiccmd(&localcmds, realtics, 1); - if (splitscreen || botingame) - { - G_BuildTiccmd(&localcmds2, realtics, 2); - if (splitscreen > 1) - { - G_BuildTiccmd(&localcmds3, realtics, 3); - if (splitscreen > 2) - G_BuildTiccmd(&localcmds4, realtics, 4); - } - } - localcmds.angleturn |= TICCMD_RECEIVED; + for (i = 0; i <= splitscreen; i++) + { + CreateNewLocalCMD(i, realtics); + } } void SV_SpawnPlayer(INT32 playernum, INT32 x, INT32 y, angle_t angle) @@ -6666,6 +6477,14 @@ void NetUpdate(void) if (realtics <= 0) // nothing new to update return; + if (realtics > 5) + { + if (server) + realtics = 1; + else + realtics = 5; + } + #ifdef DEDICATEDIDLETIME if (server && dedicated && gamestate == GS_LEVEL) { @@ -6714,14 +6533,6 @@ void NetUpdate(void) } #endif - if (realtics > 5) - { - if (server) - realtics = 1; - else - realtics = 5; - } - gametime = nowtime; UpdatePingTable(); @@ -6814,6 +6625,9 @@ void NetUpdate(void) } Net_AckTicker(); HandleNodeTimeouts(); + + nowtime /= NEWTICRATERATIO; + if (nowtime > resptime) { resptime = nowtime; diff --git a/src/d_clisrv.h b/src/d_clisrv.h index 197f3b794..5ddec0437 100644 --- a/src/d_clisrv.h +++ b/src/d_clisrv.h @@ -182,14 +182,6 @@ typedef struct { UINT32 randomseed; - // CTF flag stuff - SINT8 flagplayer[2]; - INT32 flagloose[2]; - INT32 flagflags[2]; - fixed_t flagx[2]; - fixed_t flagy[2]; - fixed_t flagz[2]; - UINT32 ingame; // Spectator bit for each player INT32 ctfteam[MAXPLAYERS]; // Which team? (can't be 1 bit, since in regular Match there are no teams) @@ -600,10 +592,8 @@ void D_ClientServerInit(void); // Initialise the other field void RegisterNetXCmd(netxcmd_t id, void (*cmd_f)(UINT8 **p, INT32 playernum)); -void SendNetXCmd(netxcmd_t id, const void *param, size_t nparam); -void SendNetXCmd2(netxcmd_t id, const void *param, size_t nparam); // splitsreen player -void SendNetXCmd3(netxcmd_t id, const void *param, size_t nparam); // splitsreen3 player -void SendNetXCmd4(netxcmd_t id, const void *param, size_t nparam); // splitsreen4 player +void SendNetXCmdForPlayer(UINT8 playerid, netxcmd_t id, const void *param, size_t nparam); +#define SendNetXCmd(id, param, nparam) SendNetXCmdForPlayer(0, id, param, nparam) // Shortcut for P1 // Create any new ticcmds and broadcast to other players. void NetKeepAlive(void); @@ -650,7 +640,7 @@ INT32 D_NumPlayers(void); void D_ResetTiccmds(void); tic_t GetLag(INT32 node); -UINT8 GetFreeXCmdSize(void); +//UINT8 GetFreeXCmdSize(UINT8 playerid); extern UINT8 hu_resynching; #ifdef SATURNSYNCH diff --git a/src/d_main.c b/src/d_main.c index 207e1ca56..a19f581eb 100644 --- a/src/d_main.c +++ b/src/d_main.c @@ -15,6 +15,7 @@ /// plus functions to parse command line parameters, configure game /// parameters, and call the startup functions. +#include "d_netcmd.h" #if defined (__unix__) || defined (__APPLE__) || defined (UNIXCOMMON) #include #include @@ -181,7 +182,7 @@ static inline void D_DeviceLEDTick(void) for (i = 0; i <= splitscreen; i++) { - if (G_GetDeviceForPlayer(i) == 0) + if (cv_usejoystick[i].value == 0) continue; color[i] = G_GetSkinColor(i); @@ -449,6 +450,8 @@ static boolean D_Display(void) { if (players[displayplayers[i]].mo || players[displayplayers[i]].playerstate == PST_DEAD) { + viewssnum = i; + if (i == 0) // Initialize for P1 { viewwindowy = 0; @@ -458,8 +461,6 @@ static boolean D_Display(void) objectsdrawn = 0; } - viewssnum = i; - #ifdef HWRENDER if (rendermode == render_opengl) HWR_RenderPlayerView(i, &players[displayplayers[i]]); @@ -537,6 +538,8 @@ static boolean D_Display(void) PS_START_TIMING(ps_uitime); ST_Drawer(); HU_Drawer(); + + NetUpdate(); // TEST: run this EVERY frame } else { @@ -740,10 +743,10 @@ void D_SRB2Loop(void) renderisnewtic = (realtics > 0 || singletics); - refreshdirmenu = 0; // not sure where to put this, here as good as any? - if (renderisnewtic) { + refreshdirmenu = 0; // not sure where to put this, here as good as any? + // don't skip more than 10 frames at a time // (fadein / fadeout cause massive frame skip!) if (realtics > 8) @@ -852,7 +855,7 @@ void D_SRB2Loop(void) LUA_Step(); #ifdef HAVE_DISCORDRPC - if (! dedicated) + if (!dedicated) { Discord_RunCallbacks(); } diff --git a/src/d_net.c b/src/d_net.c index a8602f567..2725fca14 100644 --- a/src/d_net.c +++ b/src/d_net.c @@ -69,8 +69,6 @@ INT16 hardware_MAXPACKETLENGTH; boolean (*I_NetGet)(void) = NULL; void (*I_NetSend)(void) = NULL; -boolean (*I_NetCanSend)(void) = NULL; -boolean (*I_NetCanGet)(void) = NULL; void (*I_NetCloseSocket)(void) = NULL; void (*I_NetFreeNodenum)(INT32 nodenum) = NULL; SINT8 (*I_NetMakeNodewPort)(const char *address, const char* port) = NULL; @@ -1087,15 +1085,7 @@ boolean HSendPacket(INT32 node, boolean reliable, UINT8 acknum, size_t packetlen netbuffer->ackreturn = 0; if (reliable) { - if (I_NetCanSend && !I_NetCanSend()) - { - if (netbuffer->packettype < PT_CANFAIL) - GetFreeAcknum(&netbuffer->ack, true); - - DEBFILE("HSendPacket: Out of bandwidth\n"); - return false; - } - else if (!GetFreeAcknum(&netbuffer->ack, false)) + if (!GetFreeAcknum(&netbuffer->ack, false)) return false; } else @@ -1292,7 +1282,6 @@ boolean D_CheckNetGame(void) I_NetGet = Internal_Get; I_NetSend = Internal_Send; - I_NetCanSend = NULL; I_NetCloseSocket = NULL; I_NetFreeNodenum = Internal_FreeNodenum; I_NetMakeNodewPort = NULL; @@ -1491,7 +1480,6 @@ void D_CloseConnection(void) I_NetGet = Internal_Get; I_NetSend = Internal_Send; - I_NetCanSend = NULL; I_NetCloseSocket = NULL; I_NetFreeNodenum = Internal_FreeNodenum; I_NetMakeNodewPort = NULL; diff --git a/src/d_netcmd.c b/src/d_netcmd.c index 478b857c4..174bb4d9f 100644 --- a/src/d_netcmd.c +++ b/src/d_netcmd.c @@ -303,14 +303,12 @@ consvar_t cv_mouseturn = {"mouseturn", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, consvar_t cv_laglesscam = {"laglesscamera", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; #if defined(HAVE_SDL) || defined(_WINDOWS) //joystick 1 and 2 -consvar_t cv_usejoystick = {"use_joystick", "1", CV_SAVE|CV_CALL, usejoystick_cons_t, - I_InitJoystick, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_usejoystick2 = {"use_joystick2", "2", CV_SAVE|CV_CALL, usejoystick_cons_t, - I_InitJoystick2, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_usejoystick3 = {"use_joystick3", "3", CV_SAVE|CV_CALL, usejoystick_cons_t, - I_InitJoystick3, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_usejoystick4 = {"use_joystick4", "4", CV_SAVE|CV_CALL, usejoystick_cons_t, - I_InitJoystick4, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_usejoystick[MAXSPLITSCREENPLAYERS] = { + {"use_joystick", "1", CV_SAVE|CV_CALL, usejoystick_cons_t, I_InitJoystick1, 0, NULL, NULL, 0, 0, NULL}, + {"use_joystick2", "2", CV_SAVE|CV_CALL, usejoystick_cons_t, I_InitJoystick2, 0, NULL, NULL, 0, 0, NULL}, + {"use_joystick3", "3", CV_SAVE|CV_CALL, usejoystick_cons_t, I_InitJoystick3, 0, NULL, NULL, 0, 0, NULL}, + {"use_joystick4", "4", CV_SAVE|CV_CALL, usejoystick_cons_t, I_InitJoystick4, 0, NULL, NULL, 0, 0, NULL} +}; #endif #if (defined (LJOYSTICK) || defined (HAVE_SDL)) @@ -318,13 +316,17 @@ consvar_t cv_usejoystick4 = {"use_joystick4", "4", CV_SAVE|CV_CALL, usejoystick_ consvar_t cv_joyport = {"joyport", "/dev/js0", CV_SAVE, joyport_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_joyport2 = {"joyport2", "/dev/js0", CV_SAVE, joyport_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; //Alam: for later #endif -consvar_t cv_joyscale = {"joyscale", "1", CV_SAVE|CV_CALL, NULL, I_JoyScale, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_joyscale2 = {"joyscale2", "1", CV_SAVE|CV_CALL, NULL, I_JoyScale2, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_joyscale3 = {"joyscale3", "1", CV_SAVE|CV_CALL, NULL, I_JoyScale3, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_joyscale4 = {"joyscale4", "1", CV_SAVE|CV_CALL, NULL, I_JoyScale4, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_joyscale[MAXSPLITSCREENPLAYERS] = { + {"joyscale", "1", CV_SAVE|CV_CALL, NULL, I_JoyScale, 0, NULL, NULL, 0, 0, NULL}, + {"joyscale2", "1", CV_SAVE|CV_CALL, NULL, I_JoyScale2, 0, NULL, NULL, 0, 0, NULL}, + {"joyscale3", "1", CV_SAVE|CV_CALL, NULL, I_JoyScale3, 0, NULL, NULL, 0, 0, NULL}, + {"joyscale4", "1", CV_SAVE|CV_CALL, NULL, I_JoyScale4, 0, NULL, NULL, 0, 0, NULL} +}; #else -consvar_t cv_joyscale = {"joyscale", "1", CV_SAVE|CV_HIDEN, NULL, NULL, 0, NULL, NULL, 0, 0, NULL}; //Alam: Dummy for save -consvar_t cv_joyscale2 = {"joyscale2", "1", CV_SAVE|CV_HIDEN, NULL, NULL, 0, NULL, NULL, 0, 0, NULL}; //Alam: Dummy for save +consvar_t cv_joyscale[2] = { //Alam: Dummy for save + {"joyscale", "1", CV_SAVE|CV_HIDEN, NULL, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyscale", "1", CV_SAVE|CV_HIDEN, NULL, NULL, 0, NULL, NULL, 0, 0, NULL} +}; #endif #if defined (__unix__) || defined (__APPLE__) || defined (UNIXCOMMON) consvar_t cv_mouse2port = {"mouse2port", "/dev/gpmdata", CV_SAVE, mouse2port_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; @@ -539,9 +541,9 @@ consvar_t cv_nametagscore = {"kartnametagscore", "Off", CV_SAVE, CV_OnOff, NULL, consvar_t cv_shownametagfinish = {"kartshownametagfinished", "No", CV_SAVE, CV_YesNo, NULL, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_shownametagspectator = {"kartshownametagspectator", "No", CV_SAVE, CV_YesNo, NULL, 0, NULL, NULL, 0, 0, NULL}; + static CV_PossibleValue_t driftgaugeoffset_cons_t[] = { {-FRACUNIT*128, "MIN"}, {FRACUNIT*128, "MAX"}, {0, NULL}}; - static CV_PossibleValue_t driftgaugestyle_cons_t[] = { {1, "Default"}, {2, "Small"}, {3, "Big Numbers"}, {4, "Numbers Only"}, {0, NULL}}; @@ -900,6 +902,7 @@ void D_RegisterClientCommands(void) COM_AddCommand("screenshot", M_ScreenShot); COM_AddCommand("startmovie", Command_StartMovie_f); COM_AddCommand("stopmovie", Command_StopMovie_f); + COM_AddCommand("minigen", M_MinimapGenerate); CV_RegisterVar(&cv_screenshot_option); CV_RegisterVar(&cv_screenshot_folder); @@ -1019,58 +1022,22 @@ void D_RegisterClientCommands(void) CV_RegisterVar(&cv_pauseifunfocused); // g_input.c - CV_RegisterVar(&cv_turnaxis); - CV_RegisterVar(&cv_turnaxis2); - CV_RegisterVar(&cv_turnaxis3); - CV_RegisterVar(&cv_turnaxis4); - CV_RegisterVar(&cv_moveaxis); - CV_RegisterVar(&cv_moveaxis2); - CV_RegisterVar(&cv_moveaxis3); - CV_RegisterVar(&cv_moveaxis4); - CV_RegisterVar(&cv_brakeaxis); - CV_RegisterVar(&cv_brakeaxis2); - CV_RegisterVar(&cv_brakeaxis3); - CV_RegisterVar(&cv_brakeaxis4); - CV_RegisterVar(&cv_aimaxis); - CV_RegisterVar(&cv_aimaxis2); - CV_RegisterVar(&cv_aimaxis3); - CV_RegisterVar(&cv_aimaxis4); - CV_RegisterVar(&cv_lookaxis); - CV_RegisterVar(&cv_lookaxis2); - CV_RegisterVar(&cv_lookaxis3); - CV_RegisterVar(&cv_lookaxis4); - CV_RegisterVar(&cv_fireaxis); - CV_RegisterVar(&cv_fireaxis2); - CV_RegisterVar(&cv_fireaxis3); - CV_RegisterVar(&cv_fireaxis4); - CV_RegisterVar(&cv_driftaxis); - CV_RegisterVar(&cv_driftaxis2); - CV_RegisterVar(&cv_driftaxis3); - CV_RegisterVar(&cv_driftaxis4); - CV_RegisterVar(&cv_lookbackaxis); - CV_RegisterVar(&cv_lookbackaxis2); - CV_RegisterVar(&cv_lookbackaxis3); - CV_RegisterVar(&cv_lookbackaxis4); - CV_RegisterVar(&cv_custom1axis); - CV_RegisterVar(&cv_custom1axis2); - CV_RegisterVar(&cv_custom1axis3); - CV_RegisterVar(&cv_custom1axis4); - CV_RegisterVar(&cv_custom2axis); - CV_RegisterVar(&cv_custom2axis2); - CV_RegisterVar(&cv_custom2axis3); - CV_RegisterVar(&cv_custom2axis4); - CV_RegisterVar(&cv_custom3axis); - CV_RegisterVar(&cv_custom3axis2); - CV_RegisterVar(&cv_custom3axis3); - CV_RegisterVar(&cv_custom3axis4); - CV_RegisterVar(&cv_xdeadzone); - CV_RegisterVar(&cv_ydeadzone); - CV_RegisterVar(&cv_xdeadzone2); - CV_RegisterVar(&cv_ydeadzone2); - CV_RegisterVar(&cv_xdeadzone3); - CV_RegisterVar(&cv_ydeadzone3); - CV_RegisterVar(&cv_xdeadzone4); - CV_RegisterVar(&cv_ydeadzone4); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + CV_RegisterVar(&cv_turnaxis[i]); + CV_RegisterVar(&cv_moveaxis[i]); + CV_RegisterVar(&cv_brakeaxis[i]); + CV_RegisterVar(&cv_aimaxis[i]); + CV_RegisterVar(&cv_lookaxis[i]); + CV_RegisterVar(&cv_fireaxis[i]); + CV_RegisterVar(&cv_driftaxis[i]); + CV_RegisterVar(&cv_lookbackaxis[i]); + CV_RegisterVar(&cv_custom1axis[i]); + CV_RegisterVar(&cv_custom2axis[i]); + CV_RegisterVar(&cv_custom3axis[i]); + CV_RegisterVar(&cv_xdeadzone[i]); + CV_RegisterVar(&cv_ydeadzone[i]); + } // filesrch.c CV_RegisterVar(&cv_addons_option); @@ -1107,28 +1074,19 @@ void D_RegisterClientCommands(void) //CV_RegisterVar(&cv_mousemove); //CV_RegisterVar(&cv_mousemove2); - CV_RegisterVar(&cv_usejoystick); - CV_RegisterVar(&cv_usejoystick2); - CV_RegisterVar(&cv_usejoystick3); - CV_RegisterVar(&cv_usejoystick4); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + CV_RegisterVar(&cv_usejoystick[i]); + } #ifdef LJOYSTICK CV_RegisterVar(&cv_joyport); CV_RegisterVar(&cv_joyport2); #endif - CV_RegisterVar(&cv_joyscale); - CV_RegisterVar(&cv_joyscale2); - CV_RegisterVar(&cv_joyscale3); - CV_RegisterVar(&cv_joyscale4); - // Analog Control - /*CV_RegisterVar(&cv_analog); - CV_RegisterVar(&cv_analog2); - CV_RegisterVar(&cv_analog3); - CV_RegisterVar(&cv_analog4); - CV_RegisterVar(&cv_useranalog); - CV_RegisterVar(&cv_useranalog2); - CV_RegisterVar(&cv_useranalog3); - CV_RegisterVar(&cv_useranalog4);*/ + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + CV_RegisterVar(&cv_joyscale[i]); + } // s_sound.c CV_RegisterVar(&cv_soundvolume); @@ -1157,7 +1115,7 @@ void D_RegisterClientCommands(void) CV_RegisterVar(&cv_scr_height); CV_RegisterVar(&cv_soundtest); - + CV_RegisterVar(&cv_nametag); CV_RegisterVar(&cv_nametagtrans); CV_RegisterVar(&cv_nametagfacerank); @@ -1172,7 +1130,7 @@ void D_RegisterClientCommands(void) CV_RegisterVar(&cv_nametagscore); CV_RegisterVar(&cv_shownametagfinish); CV_RegisterVar(&cv_shownametagspectator); - + CV_RegisterVar(&cv_driftgauge); CV_RegisterVar(&cv_driftgaugeofs); CV_RegisterVar(&cv_driftgaugetrans); @@ -1563,24 +1521,10 @@ UINT8 CanChangeSkin(INT32 playernum) // Server has skin change restrictions. if (cv_restrictskinchange.value) { - if (gametype == GT_COOP) - return true; - // Can change skin during initial countdown. if (leveltime < starttime) return true; - if (G_TagGametype()) - { - // Can change skin during hidetime. - if (leveltime < hidetime * TICRATE) - return true; - - // IT players can always change skins to persue players hiding in character only locations. - if (players[playernum].pflags & PF_TAGIT) - return true; - } - if (players[playernum].spectator || players[playernum].playerstate == PST_DEAD || players[playernum].playerstate == PST_REBORN) return true; @@ -1626,15 +1570,6 @@ static void SendNameAndColor(void) p = buf; - // normal player colors - if (G_GametypeHasTeams()) - { - if (players[consoleplayer].ctfteam == 1 && cv_playercolor.value != skincolor_redteam) - CV_StealthSetValue(&cv_playercolor, skincolor_redteam); - else if (players[consoleplayer].ctfteam == 2 && cv_playercolor.value != skincolor_blueteam) - CV_StealthSetValue(&cv_playercolor, skincolor_blueteam); - } - // never allow the color "none" if (!cv_playercolor.value) { @@ -1675,25 +1610,9 @@ static void SendNameAndColor(void) } else if ((foundskin = R_SkinAvailable(cv_skin.string)) != -1) { - //boolean notsame; - cv_skin.value = foundskin; - - //notsame = (cv_skin.value != players[consoleplayer].skin); - SetPlayerSkin(consoleplayer, cv_skin.string); CV_StealthSet(&cv_skin, skins[cv_skin.value].name); - - // SRB2Kart - /*if (notsame) - { - CV_StealthSetValue(&cv_playercolor, skins[cv_skin.value].prefcolor); - - players[consoleplayer].skincolor = (cv_playercolor.value&0x3F) % MAXSKINCOLORS; - - if (players[consoleplayer].mo) - players[consoleplayer].mo->color = (UINT8)players[consoleplayer].skincolor; - }*/ } else { @@ -1737,7 +1656,7 @@ static void SendNameAndColor(void) WRITESTRINGN(p, cv_playername.zstring, MAXPLAYERNAME); WRITEUINT8(p, (UINT8)cv_playercolor.value); WRITEUINT8(p, (UINT8)cv_skin.value); - SendNetXCmd(XD_NAMEANDCOLOR, buf, p - buf); + SendNetXCmdForPlayer(0, XD_NAMEANDCOLOR, buf, p - buf); } // splitscreen @@ -1760,15 +1679,6 @@ static void SendNameAndColor2(void) p = buf; - // normal player colors - if (G_GametypeHasTeams()) - { - if (players[secondplaya].ctfteam == 1 && cv_playercolor2.value != skincolor_redteam) - CV_StealthSetValue(&cv_playercolor2, skincolor_redteam); - else if (players[secondplaya].ctfteam == 2 && cv_playercolor2.value != skincolor_blueteam) - CV_StealthSetValue(&cv_playercolor2, skincolor_blueteam); - } - // never allow the color "none" if (!cv_playercolor2.value) { @@ -1807,24 +1717,8 @@ static void SendNameAndColor2(void) if ((foundskin = R_SkinAvailable(cv_skin2.string)) != -1) { - //boolean notsame; - cv_skin2.value = foundskin; - - //notsame = (cv_skin2.value != players[secondplaya].skin); - SetPlayerSkin(secondplaya, cv_skin2.string); - - // SRB2Kart - /*if (notsame) - { - CV_StealthSetValue(&cv_playercolor2, skins[players[secondplaya].skin].prefcolor); - - players[secondplaya].skincolor = (cv_playercolor2.value&0x3F) % MAXSKINCOLORS; - - if (players[secondplaya].mo) - players[secondplaya].mo->color = players[secondplaya].skincolor; - }*/ } else { @@ -1867,7 +1761,7 @@ static void SendNameAndColor2(void) WRITESTRINGN(p, cv_playername2.zstring, MAXPLAYERNAME); WRITEUINT8(p, (UINT8)cv_playercolor2.value); WRITEUINT8(p, (UINT8)cv_skin2.value); - SendNetXCmd2(XD_NAMEANDCOLOR, buf, p - buf); + SendNetXCmdForPlayer(1, XD_NAMEANDCOLOR, buf, p - buf); } static void SendNameAndColor3(void) @@ -1889,15 +1783,6 @@ static void SendNameAndColor3(void) p = buf; - // normal player colors - if (G_GametypeHasTeams()) - { - if (players[thirdplaya].ctfteam == 1 && cv_playercolor3.value != skincolor_redteam) - CV_StealthSetValue(&cv_playercolor3, skincolor_redteam); - else if (players[thirdplaya].ctfteam == 2 && cv_playercolor3.value != skincolor_blueteam) - CV_StealthSetValue(&cv_playercolor3, skincolor_blueteam); - } - // never allow the color "none" if (!cv_playercolor3.value) { @@ -1988,7 +1873,7 @@ static void SendNameAndColor3(void) WRITESTRINGN(p, cv_playername3.zstring, MAXPLAYERNAME); WRITEUINT8(p, (UINT8)cv_playercolor3.value); WRITEUINT8(p, (UINT8)cv_skin3.value); - SendNetXCmd3(XD_NAMEANDCOLOR, buf, p - buf); + SendNetXCmdForPlayer(2, XD_NAMEANDCOLOR, buf, p - buf); } static void SendNameAndColor4(void) @@ -2010,15 +1895,6 @@ static void SendNameAndColor4(void) p = buf; - // normal player colors - if (G_GametypeHasTeams()) - { - if (players[fourthplaya].ctfteam == 1 && cv_playercolor4.value != skincolor_redteam) - CV_StealthSetValue(&cv_playercolor4, skincolor_redteam); - else if (players[fourthplaya].ctfteam == 2 && cv_playercolor4.value != skincolor_blueteam) - CV_StealthSetValue(&cv_playercolor4, skincolor_blueteam); - } - // never allow the color "none" if (!cv_playercolor4.value) { @@ -2057,24 +1933,8 @@ static void SendNameAndColor4(void) if ((foundskin = R_SkinAvailable(cv_skin4.string)) != -1) { - //boolean notsame; - cv_skin4.value = foundskin; - - //notsame = (cv_skin4.value != players[fourthplaya].skin); - SetPlayerSkin(fourthplaya, cv_skin4.string); - - // SRB2Kart - /*if (notsame) - { - CV_StealthSetValue(&cv_playercolor4, skins[players[fourthplaya].skin].prefcolor); - - players[fourthplaya].skincolor = (cv_playercolor4.value&0x3F) % MAXSKINCOLORS; - - if (players[fourthplaya].mo) - players[fourthplaya].mo->color = players[fourthplaya].skincolor; - }*/ } else { @@ -2117,7 +1977,7 @@ static void SendNameAndColor4(void) WRITESTRINGN(p, cv_playername4.zstring, MAXPLAYERNAME); WRITEUINT8(p, (UINT8)cv_playercolor4.value); WRITEUINT8(p, (UINT8)cv_skin4.value); - SendNetXCmd4(XD_NAMEANDCOLOR, buf, p - buf); + SendNetXCmdForPlayer(3, XD_NAMEANDCOLOR, buf, p - buf); } static void Got_NameAndColor(UINT8 **cp, INT32 playernum) @@ -2168,15 +2028,6 @@ static void Got_NameAndColor(UINT8 **cp, INT32 playernum) { boolean kick = false; - // team colors - if (G_GametypeHasTeams()) - { - if (p->ctfteam == 1 && p->skincolor != skincolor_redteam) - kick = true; - else if (p->ctfteam == 2 && p->skincolor != skincolor_blueteam) - kick = true; - } - // don't allow color "none" if (!p->skincolor) kick = true; @@ -2222,11 +2073,9 @@ void SendWeaponPref(void) UINT8 buf[1]; buf[0] = 0; - if (cv_flipcam.value) + if (cv_flipcam[0].value) buf[0] |= 1; - if (cv_analog.value) - buf[0] |= 2; - SendNetXCmd(XD_WEAPONPREF, buf, 1); + SendNetXCmdForPlayer(0, XD_WEAPONPREF, buf, 1); } void SendWeaponPref2(void) @@ -2234,11 +2083,9 @@ void SendWeaponPref2(void) UINT8 buf[1]; buf[0] = 0; - if (cv_flipcam2.value) + if (cv_flipcam[1].value) buf[0] |= 1; - if (cv_analog2.value) - buf[0] |= 2; - SendNetXCmd2(XD_WEAPONPREF, buf, 1); + SendNetXCmdForPlayer(1, XD_WEAPONPREF, buf, 1); } void SendWeaponPref3(void) @@ -2246,11 +2093,9 @@ void SendWeaponPref3(void) UINT8 buf[1]; buf[0] = 0; - if (cv_flipcam3.value) + if (cv_flipcam[2].value) buf[0] |= 1; - if (cv_analog3.value) - buf[0] |= 2; - SendNetXCmd3(XD_WEAPONPREF, buf, 1); + SendNetXCmdForPlayer(2, XD_WEAPONPREF, buf, 1); } void SendWeaponPref4(void) @@ -2258,11 +2103,9 @@ void SendWeaponPref4(void) UINT8 buf[1]; buf[0] = 0; - if (cv_flipcam4.value) + if (cv_flipcam[3].value) buf[0] |= 1; - if (cv_analog4.value) - buf[0] |= 2; - SendNetXCmd4(XD_WEAPONPREF, buf, 1); + SendNetXCmdForPlayer(3, XD_WEAPONPREF, buf, 1); } static void Got_WeaponPref(UINT8 **cp,INT32 playernum) @@ -3126,7 +2969,7 @@ static void Got_Mapcmd(UINT8 **cp, INT32 playernum) SetPlayerSkinByNum(0, cv_chooseskin.value-1); //mapnumber = M_MapNumber(mapname[3], mapname[4]); - //LUAh_MapChange(mapnumber); + //LUA_HookInt(mapnumber, HOOK(MapChange)); demo.savemode = (cv_recordmultiplayerdemos.value == 2) ? DSM_WILLAUTOSAVE : DSM_NOTSAVING; demo.savebutton = 0; @@ -3411,27 +3254,14 @@ static void Command_Teamchange_f(void) if (COM_Argc() <= 1) { - if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("changeteam : switch to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("changeteam : switch to a new team (%s)\n"), "spectator or playing"); else CONS_Alert(CONS_NOTICE, M_GetText("This command cannot be used in this gametype.\n")); return; } - if (G_GametypeHasTeams()) - { - if (!strcasecmp(COM_Argv(1), "red") || !strcasecmp(COM_Argv(1), "1")) - NetPacket.packet.newteam = 1; - else if (!strcasecmp(COM_Argv(1), "blue") || !strcasecmp(COM_Argv(1), "2")) - NetPacket.packet.newteam = 2; - else if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")) - NetPacket.packet.newteam = 0; - else - error = true; - } - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) { if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")) NetPacket.packet.newteam = 0; @@ -3448,17 +3278,13 @@ static void Command_Teamchange_f(void) if (error) { - if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("changeteam : switch to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("changeteam : switch to a new team (%s)\n"), "spectator or playing"); return; } if (players[consoleplayer].spectator) error = !(NetPacket.packet.newteam || (players[consoleplayer].pflags & PF_WANTSTOJOIN)); // :lancer: - else if (G_GametypeHasTeams()) - error = (NetPacket.packet.newteam == (unsigned)players[consoleplayer].ctfteam); else if (G_GametypeHasSpectators() && !players[consoleplayer].spectator) error = (NetPacket.packet.newteam == 3); #ifdef PARANOIA @@ -3478,15 +3304,8 @@ static void Command_Teamchange_f(void) return; } - //additional check for hide and seek. Don't allow change of status after hidetime ends. - if (gametype == GT_HIDEANDSEEK && leveltime >= (hidetime * TICRATE)) - { - CONS_Alert(CONS_NOTICE, M_GetText("Hiding time expired; no Hide and Seek status changes allowed!\n")); - return; - } - usvalue = SHORT(NetPacket.value.l|NetPacket.value.b); - SendNetXCmd(XD_TEAMCHANGE, &usvalue, sizeof(usvalue)); + SendNetXCmdForPlayer(0, XD_TEAMCHANGE, &usvalue, sizeof(usvalue)); } static void Command_Teamchange2_f(void) @@ -3501,27 +3320,14 @@ static void Command_Teamchange2_f(void) if (COM_Argc() <= 1) { - if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("changeteam2 : switch to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("changeteam2 : switch to a new team (%s)\n"), "spectator or playing"); else CONS_Alert(CONS_NOTICE, M_GetText("This command cannot be used in this gametype.\n")); return; } - if (G_GametypeHasTeams()) - { - if (!strcasecmp(COM_Argv(1), "red") || !strcasecmp(COM_Argv(1), "1")) - NetPacket.packet.newteam = 1; - else if (!strcasecmp(COM_Argv(1), "blue") || !strcasecmp(COM_Argv(1), "2")) - NetPacket.packet.newteam = 2; - else if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")) - NetPacket.packet.newteam = 0; - else - error = true; - } - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) { if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")) NetPacket.packet.newteam = 0; @@ -3539,17 +3345,13 @@ static void Command_Teamchange2_f(void) if (error) { - if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("changeteam2 : switch to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("changeteam2 : switch to a new team (%s)\n"), "spectator or playing"); return; } if (players[displayplayers[1]].spectator) error = !(NetPacket.packet.newteam || (players[displayplayers[1]].pflags & PF_WANTSTOJOIN)); - else if (G_GametypeHasTeams()) - error = (NetPacket.packet.newteam == (unsigned)players[displayplayers[1]].ctfteam); else if (G_GametypeHasSpectators() && !players[displayplayers[1]].spectator) error = (NetPacket.packet.newteam == 3); #ifdef PARANOIA @@ -3569,15 +3371,8 @@ static void Command_Teamchange2_f(void) return; } - //additional check for hide and seek. Don't allow change of status after hidetime ends. - if (gametype == GT_HIDEANDSEEK && leveltime >= (hidetime * TICRATE)) - { - CONS_Alert(CONS_NOTICE, M_GetText("Hiding time expired; no Hide and Seek status changes allowed!\n")); - return; - } - usvalue = SHORT(NetPacket.value.l|NetPacket.value.b); - SendNetXCmd2(XD_TEAMCHANGE, &usvalue, sizeof(usvalue)); + SendNetXCmdForPlayer(1, XD_TEAMCHANGE, &usvalue, sizeof(usvalue)); } static void Command_Teamchange3_f(void) @@ -3592,27 +3387,14 @@ static void Command_Teamchange3_f(void) if (COM_Argc() <= 1) { - if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("changeteam3 : switch to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("changeteam3 : switch to a new team (%s)\n"), "spectator or playing"); else CONS_Alert(CONS_NOTICE, M_GetText("This command cannot be used in this gametype.\n")); return; } - if (G_GametypeHasTeams()) - { - if (!strcasecmp(COM_Argv(1), "red") || !strcasecmp(COM_Argv(1), "1")) - NetPacket.packet.newteam = 1; - else if (!strcasecmp(COM_Argv(1), "blue") || !strcasecmp(COM_Argv(1), "2")) - NetPacket.packet.newteam = 2; - else if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")) - NetPacket.packet.newteam = 0; - else - error = true; - } - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) { if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")) NetPacket.packet.newteam = 0; @@ -3630,17 +3412,13 @@ static void Command_Teamchange3_f(void) if (error) { - if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("changeteam3 : switch to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("changeteam3 : switch to a new team (%s)\n"), "spectator or playing"); return; } if (players[displayplayers[2]].spectator) error = !(NetPacket.packet.newteam || (players[displayplayers[2]].pflags & PF_WANTSTOJOIN)); - else if (G_GametypeHasTeams()) - error = (NetPacket.packet.newteam == (unsigned)players[displayplayers[2]].ctfteam); else if (G_GametypeHasSpectators() && !players[displayplayers[2]].spectator) error = (NetPacket.packet.newteam == 3); #ifdef PARANOIA @@ -3660,15 +3438,8 @@ static void Command_Teamchange3_f(void) return; } - //additional check for hide and seek. Don't allow change of status after hidetime ends. - if (gametype == GT_HIDEANDSEEK && leveltime >= (hidetime * TICRATE)) - { - CONS_Alert(CONS_NOTICE, M_GetText("Hiding time expired; no Hide and Seek status changes allowed!\n")); - return; - } - usvalue = SHORT(NetPacket.value.l|NetPacket.value.b); - SendNetXCmd3(XD_TEAMCHANGE, &usvalue, sizeof(usvalue)); + SendNetXCmdForPlayer(2, XD_TEAMCHANGE, &usvalue, sizeof(usvalue)); } static void Command_Teamchange4_f(void) @@ -3683,27 +3454,14 @@ static void Command_Teamchange4_f(void) if (COM_Argc() <= 1) { - if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("changeteam4 : switch to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("changeteam4 : switch to a new team (%s)\n"), "spectator or playing"); else CONS_Alert(CONS_NOTICE, M_GetText("This command cannot be used in this gametype.\n")); return; } - if (G_GametypeHasTeams()) - { - if (!strcasecmp(COM_Argv(1), "red") || !strcasecmp(COM_Argv(1), "1")) - NetPacket.packet.newteam = 1; - else if (!strcasecmp(COM_Argv(1), "blue") || !strcasecmp(COM_Argv(1), "2")) - NetPacket.packet.newteam = 2; - else if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")) - NetPacket.packet.newteam = 0; - else - error = true; - } - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) { if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")) NetPacket.packet.newteam = 0; @@ -3721,17 +3479,13 @@ static void Command_Teamchange4_f(void) if (error) { - if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("changeteam4 : switch to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("changeteam4 : switch to a new team (%s)\n"), "spectator or playing"); return; } if (players[displayplayers[3]].spectator) error = !(NetPacket.packet.newteam || (players[displayplayers[3]].pflags & PF_WANTSTOJOIN)); - else if (G_GametypeHasTeams()) - error = (NetPacket.packet.newteam == (unsigned)players[displayplayers[3]].ctfteam); else if (G_GametypeHasSpectators() && !players[displayplayers[3]].spectator) error = (NetPacket.packet.newteam == 3); #ifdef PARANOIA @@ -3751,15 +3505,8 @@ static void Command_Teamchange4_f(void) return; } - //additional check for hide and seek. Don't allow change of status after hidetime ends. - if (gametype == GT_HIDEANDSEEK && leveltime >= (hidetime * TICRATE)) - { - CONS_Alert(CONS_NOTICE, M_GetText("Hiding time expired; no Hide and Seek status changes allowed!\n")); - return; - } - usvalue = SHORT(NetPacket.value.l|NetPacket.value.b); - SendNetXCmd4(XD_TEAMCHANGE, &usvalue, sizeof(usvalue)); + SendNetXCmdForPlayer(3, XD_TEAMCHANGE, &usvalue, sizeof(usvalue)); } static void Command_ServerTeamChange_f(void) @@ -3780,42 +3527,14 @@ static void Command_ServerTeamChange_f(void) if (COM_Argc() < 3) { - if (G_TagGametype()) - CONS_Printf(M_GetText("serverchangeteam : switch player to a new team (%s)\n"), "it, notit, playing, or spectator"); - else if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("serverchangeteam : switch player to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("serverchangeteam : switch player to a new team (%s)\n"), "spectator or playing"); else CONS_Alert(CONS_NOTICE, M_GetText("This command cannot be used in this gametype.\n")); return; } - if (G_TagGametype()) - { - if (!strcasecmp(COM_Argv(2), "it") || !strcasecmp(COM_Argv(2), "1")) - NetPacket.packet.newteam = 1; - else if (!strcasecmp(COM_Argv(2), "notit") || !strcasecmp(COM_Argv(2), "2")) - NetPacket.packet.newteam = 2; - else if (!strcasecmp(COM_Argv(2), "playing") || !strcasecmp(COM_Argv(2), "3")) - NetPacket.packet.newteam = 3; - else if (!strcasecmp(COM_Argv(2), "spectator") || !strcasecmp(COM_Argv(2), "0")) - NetPacket.packet.newteam = 0; - else - error = true; - } - else if (G_GametypeHasTeams()) - { - if (!strcasecmp(COM_Argv(2), "red") || !strcasecmp(COM_Argv(2), "1")) - NetPacket.packet.newteam = 1; - else if (!strcasecmp(COM_Argv(2), "blue") || !strcasecmp(COM_Argv(2), "2")) - NetPacket.packet.newteam = 2; - else if (!strcasecmp(COM_Argv(2), "spectator") || !strcasecmp(COM_Argv(2), "0")) - NetPacket.packet.newteam = 0; - else - error = true; - } - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) { if (!strcasecmp(COM_Argv(2), "spectator") || !strcasecmp(COM_Argv(2), "0")) NetPacket.packet.newteam = 0; @@ -3832,11 +3551,7 @@ static void Command_ServerTeamChange_f(void) if (error) { - if (G_TagGametype()) - CONS_Printf(M_GetText("serverchangeteam : switch player to a new team (%s)\n"), "it, notit, playing, or spectator"); - else if (G_GametypeHasTeams()) - CONS_Printf(M_GetText("serverchangeteam : switch player to a new team (%s)\n"), "red, blue or spectator"); - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) CONS_Printf(M_GetText("serverchangeteam : switch player to a new team (%s)\n"), "spectator or playing"); return; } @@ -3849,21 +3564,7 @@ static void Command_ServerTeamChange_f(void) return; } - if (G_TagGametype()) - { - if (( (players[NetPacket.packet.playernum].pflags & PF_TAGIT) && NetPacket.packet.newteam == 1) || - (!(players[NetPacket.packet.playernum].pflags & PF_TAGIT) && NetPacket.packet.newteam == 2) || - ( players[NetPacket.packet.playernum].spectator && !NetPacket.packet.newteam) || - (!players[NetPacket.packet.playernum].spectator && NetPacket.packet.newteam == 3)) - error = true; - } - else if (G_GametypeHasTeams()) - { - if (NetPacket.packet.newteam == (unsigned)players[NetPacket.packet.playernum].ctfteam || - (players[NetPacket.packet.playernum].spectator && !NetPacket.packet.newteam)) - error = true; - } - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) { if ((players[NetPacket.packet.playernum].spectator && !NetPacket.packet.newteam) || (!players[NetPacket.packet.playernum].spectator && NetPacket.packet.newteam == 3)) @@ -3880,13 +3581,6 @@ static void Command_ServerTeamChange_f(void) return; } - //additional check for hide and seek. Don't allow change of status after hidetime ends. - if (gametype == GT_HIDEANDSEEK && leveltime >= (hidetime * TICRATE)) - { - CONS_Alert(CONS_NOTICE, M_GetText("Hiding time expired; no Hide and Seek status changes allowed!\n")); - return; - } - NetPacket.packet.verification = true; // This signals that it's a server change usvalue = SHORT(NetPacket.value.l|NetPacket.value.b); @@ -3900,7 +3594,7 @@ static void Got_Teamchange(UINT8 **cp, INT32 playernum) boolean error = false, wasspectator = false; NetPacket.value.l = NetPacket.value.b = READINT16(*cp); - if (!G_GametypeHasTeams() && !G_GametypeHasSpectators()) //Make sure you're in the right gametype. + if (!G_GametypeHasSpectators()) //Make sure you're in the right gametype. { // this should never happen unless the client is hacked/buggy CONS_Alert(CONS_WARNING, M_GetText("Illegal team change received from player %s\n"), player_names[playernum]); @@ -3935,18 +3629,6 @@ static void Got_Teamchange(UINT8 **cp, INT32 playernum) // Prevent multiple changes in one go. if (players[playernum].spectator && !(players[playernum].pflags & PF_WANTSTOJOIN) && !NetPacket.packet.newteam) return; - else if (G_TagGametype()) - { - if (((players[playernum].pflags & PF_TAGIT) && NetPacket.packet.newteam == 1) || - (!(players[playernum].pflags & PF_TAGIT) && NetPacket.packet.newteam == 2) || - (!players[playernum].spectator && NetPacket.packet.newteam == 3)) - return; - } - else if (G_GametypeHasTeams()) - { - if (NetPacket.packet.newteam && (NetPacket.packet.newteam == (unsigned)players[playernum].ctfteam)) - return; - } else if (G_GametypeHasSpectators()) { if (!players[playernum].spectator && NetPacket.packet.newteam == 3) @@ -3969,45 +3651,16 @@ static void Got_Teamchange(UINT8 **cp, INT32 playernum) return; } - //Make sure that the right team number is sent. Keep in mind that normal clients cannot change to certain teams in certain gametypes. - switch (gametype) - { - case GT_HIDEANDSEEK: - //no status changes after hidetime - if (leveltime >= (hidetime * TICRATE)) - { - error = true; - break; - } - /* FALLTHRU */ - case GT_TAG: - switch (NetPacket.packet.newteam) - { - case 0: - break; - case 1: case 2: - if (!NetPacket.packet.verification) - error = true; //Only admin can change player's IT status' in tag. - break; - case 3: //Join game via console. - if (!NetPacket.packet.verification && !cv_allowteamchange.value) - error = true; - break; - } - - break; - default: #ifdef PARANOIA - if (!G_GametypeHasTeams() && !G_GametypeHasSpectators()) - I_Error("Invalid gametype after initial checks!"); + if (!G_GametypeHasSpectators()) + I_Error("Invalid gametype after initial checks!"); #endif - if (!cv_allowteamchange.value) - { - if (!NetPacket.packet.verification && NetPacket.packet.newteam) - error = true; //Only admin can change status, unless changing to spectator. - } - break; //Otherwise, you don't need special permissions. + //Make sure that the right team number is sent. Keep in mind that normal clients cannot change to certain teams in certain gametypes. + if (!cv_allowteamchange.value) + { + if (!NetPacket.packet.verification && NetPacket.packet.newteam) + error = true; //Only admin can change status, unless changing to spectator. } if (server && ((NetPacket.packet.newteam < 0 || NetPacket.packet.newteam > 3) || error)) @@ -4025,19 +3678,7 @@ static void Got_Teamchange(UINT8 **cp, INT32 playernum) if (!players[playernum].spectator) { if (players[playernum].mo) - { - //if (!players[playernum].spectator) - P_DamageMobj(players[playernum].mo, NULL, NULL, 10000); - /*else - { - if (players[playernum].mo) - { - P_RemoveMobj(players[playernum].mo); - players[playernum].mo = NULL; - } - players[playernum].playerstate = PST_REBORN; - }*/ - } + P_DamageMobj(players[playernum].mo, NULL, NULL, 10000); else players[playernum].playerstate = PST_REBORN; } @@ -4048,50 +3689,7 @@ static void Got_Teamchange(UINT8 **cp, INT32 playernum) //Now that we've done our error checking and killed the player //if necessary, put the player on the correct team/status. - if (G_TagGametype()) - { - if (!NetPacket.packet.newteam) - { - players[playernum].spectator = true; - players[playernum].pflags &= ~PF_TAGIT; - players[playernum].pflags &= ~PF_TAGGED; - } - else if (NetPacket.packet.newteam != 3) // .newteam == 1 or 2. - { - players[playernum].pflags |= PF_WANTSTOJOIN; //players[playernum].spectator = false; - players[playernum].pflags &= ~PF_TAGGED;//Just in case. - - if (NetPacket.packet.newteam == 1) //Make the player IT. - players[playernum].pflags |= PF_TAGIT; - else - players[playernum].pflags &= ~PF_TAGIT; - } - else // Just join the game. - { - players[playernum].pflags |= PF_WANTSTOJOIN; //players[playernum].spectator = false; - - //If joining after hidetime in normal tag, default to being IT. - if (gametype == GT_TAG && (leveltime > (hidetime * TICRATE))) - { - NetPacket.packet.newteam = 1; //minor hack, causes the "is it" message to be printed later. - players[playernum].pflags |= PF_TAGIT; //make the player IT. - } - } - } - else if (G_GametypeHasTeams()) - { - if (!NetPacket.packet.newteam) - { - players[playernum].ctfteam = 0; - players[playernum].spectator = true; - } - else - { - players[playernum].ctfteam = NetPacket.packet.newteam; - players[playernum].pflags |= PF_WANTSTOJOIN; //players[playernum].spectator = false; - } - } - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) { if (!NetPacket.packet.newteam) players[playernum].spectator = true; @@ -4115,17 +3713,11 @@ static void Got_Teamchange(UINT8 **cp, INT32 playernum) } else if (NetPacket.packet.newteam == 1) { - if (G_TagGametype()) - CONS_Printf(M_GetText("%s is now IT!\n"), player_names[playernum]); - else - CONS_Printf(M_GetText("%s switched to the %c%s%c.\n"), player_names[playernum], '\x85', M_GetText("Red Team"), '\x80'); + CONS_Printf(M_GetText("%s switched to the %c%s%c.\n"), player_names[playernum], '\x85', M_GetText("Red Team"), '\x80'); } else if (NetPacket.packet.newteam == 2) { - if (G_TagGametype()) - CONS_Printf(M_GetText("%s is no longer IT!\n"), player_names[playernum]); - else - CONS_Printf(M_GetText("%s switched to the %c%s%c.\n"), player_names[playernum], '\x84', M_GetText("Blue Team"), '\x80'); + CONS_Printf(M_GetText("%s switched to the %c%s%c.\n"), player_names[playernum], '\x84', M_GetText("Blue Team"), '\x80'); } else if (NetPacket.packet.newteam == 0 && !wasspectator) HU_AddChatText(va("\x82*%s became a spectator.", player_names[playernum]), false); // "entered the game" text was moved to P_SpectatorJoinGame @@ -4134,21 +3726,6 @@ static void Got_Teamchange(UINT8 **cp, INT32 playernum) if (playernum == consoleplayer || displayplayers[0] == playernum) displayplayers[0] = consoleplayer; - if (G_GametypeHasTeams()) - { - if (NetPacket.packet.newteam) - { - if (playernum == consoleplayer) //CTF and Team Match colors. - CV_SetValue(&cv_playercolor, NetPacket.packet.newteam + 5); - else if (playernum == displayplayers[1]) - CV_SetValue(&cv_playercolor2, NetPacket.packet.newteam + 5); - else if (playernum == displayplayers[2]) - CV_SetValue(&cv_playercolor3, NetPacket.packet.newteam + 5); - else if (playernum == displayplayers[3]) - CV_SetValue(&cv_playercolor4, NetPacket.packet.newteam + 5); - } - } - if (gamestate != GS_LEVEL) return; @@ -4171,10 +3748,7 @@ static void Got_Teamchange(UINT8 **cp, INT32 playernum) players[playernum].mo->health = 1; } - // In tag, check to see if you still have a game. - /*if (G_TagGametype()) - P_CheckSurvivors(); - else*/ if (G_BattleGametype()) + if (G_BattleGametype()) K_CheckBumpers(); // SRB2Kart else if (G_RaceGametype()) P_CheckRacers(); // also SRB2Kart @@ -5171,7 +4745,7 @@ static void PointLimit_OnChange(void) if (cv_pointlimit.value) { CONS_Printf(M_GetText("Levels will end after %s scores %d point%s.\n"), - G_GametypeHasTeams() ? M_GetText("a team") : M_GetText("someone"), + M_GetText("someone"), cv_pointlimit.value, cv_pointlimit.value > 1 ? "s" : ""); } @@ -5226,11 +4800,7 @@ static void TimeLimit_OnChange(void) if (cv_timelimit.value != 0) { CONS_Printf(M_GetText("Levels will end after %d minute%s.\n"),cv_timelimit.value,cv_timelimit.value == 1 ? "" : "s"); // Graue 11-17-2003 - timelimitintics = cv_timelimit.value * 60 * TICRATE; - - //add hidetime for tag too! - if (G_TagGametype()) - timelimitintics += hidetime * TICRATE; + timelimitintics = cv_timelimit.value * 60 * TICRATE;; // Note the deliberate absence of any code preventing // pointlimit and timelimit from being set simultaneously. @@ -5269,54 +4839,24 @@ void D_GameTypeChanged(INT32 lastgametype) // There will always be a server, and this only needs to be done once. if (server && (multiplayer || netgame)) { - if (gametype == GT_COMPETITION || gametype == GT_COOP) - CV_SetValue(&cv_itemrespawn, 0); - else if (!cv_itemrespawn.changed) + if (!cv_itemrespawn.changed) CV_SetValue(&cv_itemrespawn, 1); - switch (gametype) + if (gametype == GT_MATCH) { - case GT_MATCH: - case GT_TEAMMATCH: - if (!cv_timelimit.changed && !cv_pointlimit.changed) // user hasn't changed limits - { - // default settings for match: no timelimit, no pointlimit - CV_SetValue(&cv_pointlimit, 0); - CV_SetValue(&cv_timelimit, 0); - } - if (!cv_itemrespawntime.changed) - CV_Set(&cv_itemrespawntime, cv_itemrespawntime.defaultvalue); // respawn normally - break; - case GT_TAG: - case GT_HIDEANDSEEK: - if (!cv_timelimit.changed && !cv_pointlimit.changed) // user hasn't changed limits - { - // default settings for tag: 5 mins, no pointlimit - // Note that tag mode also uses an alternate timing mechanism in tandem with timelimit. - CV_SetValue(&cv_timelimit, 5); - CV_SetValue(&cv_pointlimit, 0); - } - if (!cv_itemrespawntime.changed) - CV_Set(&cv_itemrespawntime, cv_itemrespawntime.defaultvalue); // respawn normally - break; - case GT_CTF: - if (!cv_timelimit.changed && !cv_pointlimit.changed) // user hasn't changed limits - { - // default settings for CTF: no timelimit, pointlimit 5 - CV_SetValue(&cv_timelimit, 0); - CV_SetValue(&cv_pointlimit, 5); - } - if (!cv_itemrespawntime.changed) - CV_Set(&cv_itemrespawntime, cv_itemrespawntime.defaultvalue); // respawn normally - break; + if (!cv_timelimit.changed && !cv_pointlimit.changed) // user hasn't changed limits + { + // default settings for match: no timelimit, no pointlimit + CV_SetValue(&cv_pointlimit, 0); + CV_SetValue(&cv_timelimit, 0); + } + if (!cv_itemrespawntime.changed) + CV_Set(&cv_itemrespawntime, cv_itemrespawntime.defaultvalue); // respawn normally } } else if (!multiplayer && !netgame) { gametype = GT_RACE; // SRB2kart - // These shouldn't matter anymore - //CV_Set(&cv_itemrespawntime, cv_itemrespawntime.defaultvalue); - //CV_SetValue(&cv_itemrespawn, 0); } // reset timelimit and pointlimit in race/coop, prevent stupid cheats @@ -5329,42 +4869,6 @@ void D_GameTypeChanged(INT32 lastgametype) if (cv_pointlimit.value) CV_SetValue(&cv_pointlimit, 0); } - else if ((cv_pointlimit.changed || cv_timelimit.changed) && cv_pointlimit.value) - { - if (lastgametype != GT_CTF && gametype == GT_CTF) - CV_SetValue(&cv_pointlimit, cv_pointlimit.value / 500); - else if (lastgametype == GT_CTF && gametype != GT_CTF) - CV_SetValue(&cv_pointlimit, cv_pointlimit.value * 500); - } - } - - // When swapping to a gametype that supports spectators, - // make everyone a spectator initially. - /*if (G_GametypeHasSpectators()) - { - INT32 i; - for (i = 0; i < MAXPLAYERS; i++) - if (playeringame[i]) - { - players[i].ctfteam = 0; - players[i].spectator = true; - } - }*/ - - // don't retain teams in other modes or between changes from ctf to team match. - // also, stop any and all forms of team scrambling that might otherwise take place. - if (G_GametypeHasTeams()) - { - INT32 i; - for (i = 0; i < MAXPLAYERS; i++) - if (playeringame[i]) - players[i].ctfteam = 0; - - if (server || (IsPlayerAdmin(consoleplayer))) - { - CV_StealthSetValue(&cv_teamscramble, 0); - teamscramble = 0; - } } } @@ -5428,14 +4932,6 @@ static void AutoBalance_OnChange(void) static void TeamScramble_OnChange(void) { - INT16 i = 0, j = 0, playercount = 0; - boolean repick = true; - INT32 blue = 0, red = 0; - INT32 maxcomposition = 0; - INT16 newteam = 0; - INT32 retries = 0; - boolean success = false; - // Don't trigger outside level or intermission! if (!(gamestate == GS_LEVEL || gamestate == GS_INTERMISSION || gamestate == GS_VOTING)) return; @@ -5443,152 +4939,17 @@ static void TeamScramble_OnChange(void) if (!cv_teamscramble.value) teamscramble = 0; - if (!G_GametypeHasTeams() && (server || IsPlayerAdmin(consoleplayer))) + if (server || IsPlayerAdmin(consoleplayer)) { CONS_Alert(CONS_NOTICE, M_GetText("This command cannot be used in this gametype.\n")); CV_StealthSetValue(&cv_teamscramble, 0); return; } - - // If a team scramble is already in progress, do not allow another one to be started! - if (teamscramble) - return; - -retryscramble: - - // Clear related global variables. These will get used again in p_tick.c/y_inter.c as the teams are scrambled. - memset(&scrambleplayers, 0, sizeof(scrambleplayers)); - memset(&scrambleteams, 0, sizeof(scrambleplayers)); - scrambletotal = scramblecount = 0; - blue = red = maxcomposition = newteam = playercount = 0; - repick = true; - - // Put each player's node in the array. - for (i = 0; i < MAXPLAYERS; i++) - { - if (playeringame[i] && !players[i].spectator) - { - scrambleplayers[playercount] = i; - playercount++; - } - } - - if (playercount < 2) - { - CV_StealthSetValue(&cv_teamscramble, 0); - return; // Don't scramble one or zero players. - } - - // Randomly place players on teams. - if (cv_teamscramble.value == 1) - { - maxcomposition = playercount / 2; - - // Now randomly assign players to teams. - // If the teams get out of hand, assign the rest to the other team. - for (i = 0; i < playercount; i++) - { - if (repick) - newteam = (INT16)((M_RandomByte() % 2) + 1); - - // One team has the most players they can get, assign the rest to the other team. - if (red == maxcomposition || blue == maxcomposition) - { - if (red == maxcomposition) - newteam = 2; - else if (blue == maxcomposition) - newteam = 1; - - repick = false; - } - - scrambleteams[i] = newteam; - - if (newteam == 1) - red++; - else - blue++; - } - } - else if (cv_teamscramble.value == 2) // Same as before, except split teams based on current score. - { - // Now, sort the array based on points scored. - for (i = 1; i < playercount; i++) - { - for (j = i; j < playercount; j++) - { - INT16 tempplayer = 0; - - if ((players[scrambleplayers[i-1]].score > players[scrambleplayers[j]].score)) - { - tempplayer = scrambleplayers[i-1]; - scrambleplayers[i-1] = scrambleplayers[j]; - scrambleplayers[j] = tempplayer; - } - } - } - - // Now assign players to teams based on score. Scramble in pairs. - // If there is an odd number, one team will end up with the unlucky slob who has no points. =( - for (i = 0; i < playercount; i++) - { - if (repick) - { - newteam = (INT16)((M_RandomByte() % 2) + 1); - repick = false; - } - else - { - // We will only randomly pick the team for the first guy. - // Otherwise, just alternate back and forth, distributing players. - if (newteam == 1) - newteam = 2; - else - newteam = 1; - } - - scrambleteams[i] = newteam; - } - } - - // Check to see if our random selection actually - // changed anybody. If not, we run through and try again. - for (i = 0; i < playercount; i++) - { - if (players[scrambleplayers[i]].ctfteam != scrambleteams[i]) - success = true; - } - - if (!success && retries < 5) - { - retries++; - goto retryscramble; //try again - } - - // Display a witty message, but only during scrambles specifically triggered by an admin. - if (cv_teamscramble.value) - { - scrambletotal = playercount; - teamscramble = (INT16)cv_teamscramble.value; - - if (!(gamestate == GS_INTERMISSION && cv_scrambleonchange.value)) - CONS_Printf(M_GetText("Teams will be scrambled next round.\n")); - } } static void Hidetime_OnChange(void) { - if (Playing() && G_TagGametype() && leveltime >= (hidetime * TICRATE)) - { - // Don't allow hidetime changes after it expires. - CV_StealthSetValue(&cv_hidetime, hidetime); - return; - } hidetime = cv_hidetime.value; - - //uh oh, gotta change timelimitintics now too - if (G_TagGametype()) - timelimitintics = (cv_timelimit.value * 60 * TICRATE) + (hidetime * TICRATE); } static void Command_Showmap_f(void) @@ -5630,7 +4991,7 @@ static void Command_Mapmd5_f(void) static void Command_ExitLevel_f(void) { - if (!(netgame || (multiplayer && gametype != GT_COOP)) && !cv_debug) + if (!(netgame || multiplayer) && !cv_debug) CONS_Printf(M_GetText("This only works in a netgame.\n")); else if (!(server || (IsPlayerAdmin(consoleplayer)))) CONS_Printf(M_GetText("Only the server or a remote admin can use this.\n")); @@ -5801,10 +5162,6 @@ void Command_Retry_f(void) CONS_Printf(M_GetText("You must be in a level to use this.\n")); else if (netgame || multiplayer) CONS_Printf(M_GetText("This only works in single player.\n")); - /*else if (!&players[consoleplayer] || players[consoleplayer].lives <= 1) - CONS_Printf(M_GetText("You can't retry without any lives remaining!\n")); - else if (G_IsSpecialStage(gamemap)) - CONS_Printf(M_GetText("You can't retry special stages!\n"));*/ else { M_ClearMenus(true); diff --git a/src/d_netcmd.h b/src/d_netcmd.h index 01fb98243..87d96b40d 100644 --- a/src/d_netcmd.h +++ b/src/d_netcmd.h @@ -43,18 +43,12 @@ extern consvar_t cv_seenames, cv_allowseenames; extern consvar_t cv_usemouse; //WTF extern consvar_t cv_mouseturn; -extern consvar_t cv_usejoystick; -extern consvar_t cv_usejoystick2; -extern consvar_t cv_usejoystick3; -extern consvar_t cv_usejoystick4; +extern consvar_t cv_usejoystick[4]; //MAXSPLITSCREENPLAYERS #ifdef LJOYSTICK extern consvar_t cv_joyport; extern consvar_t cv_joyport2; #endif -extern consvar_t cv_joyscale; -extern consvar_t cv_joyscale2; -extern consvar_t cv_joyscale3; -extern consvar_t cv_joyscale4; +extern consvar_t cv_joyscale[4]; //MAXSPLITSCREENPLAYERS // splitscreen with second mouse extern consvar_t cv_mouse2port; diff --git a/src/dehacked.c b/src/dehacked.c index 185694770..85d3fe319 100644 --- a/src/dehacked.c +++ b/src/dehacked.c @@ -257,8 +257,6 @@ static void clear_levels(void) // Custom map header info // (no need to set num to 0, we're freeing the entire header shortly) Z_Free(mapheaderinfo[i]->customopts); - - P_DeleteGrades(i); Z_Free(mapheaderinfo[i]); mapheaderinfo[i] = NULL; } @@ -802,22 +800,8 @@ static void readlevelheader(MYFILE *f, INT32 num, INT32 wadnum) // Now go to uppercase strupr(word2); - // NiGHTS grades - if (fastncmp(word, "GRADES", 6)) - { - UINT8 mare = (UINT8)atoi(word + 6); - - if (mare <= 0 || mare > 8) - { - deh_warning("Level header %d: unknown word '%s'", num, word); - continue; - } - - P_AddGradesForMare((INT16)(num-1), mare-1, word2); - } - // Strings that can be truncated - else if (fastcmp(word, "SCRIPTNAME")) + if (fastcmp(word, "SCRIPTNAME")) { deh_strlcpy(mapheaderinfo[num-1]->scriptname, word2, sizeof(mapheaderinfo[num-1]->scriptname), va("Level header %d: scriptname", num)); @@ -8538,13 +8522,13 @@ static int lua_enumlib_basic_fallback(lua_State* L) static int lua_enumlib_mariomode_get(lua_State *L) { - lua_pushboolean(L, mariomode != 0); + lua_pushboolean(L, false); return 1; } static int lua_enumlib_twodlevel_get(lua_State *L) { - lua_pushboolean(L, twodlevel); + lua_pushboolean(L, false); return 1; } diff --git a/src/doomstat.h b/src/doomstat.h index f70f97059..524d507f7 100644 --- a/src/doomstat.h +++ b/src/doomstat.h @@ -323,15 +323,6 @@ enum GameType // SRB2Kart GT_RACE = 0, // also used in record attack GT_MATCH, // battle, but renaming would be silly NUMGAMETYPES, - - // TODO: This is *horrid*. Remove this hack ASAP. - // the following have been left in on account of just not wanting to deal with removing all the checks for them - GT_COOP, - GT_COMPETITION, - GT_TEAMMATCH, - GT_TAG, - GT_HIDEANDSEEK, - GT_CTF }; // If you alter this list, update dehacked.c, and Gametype_Names in g_game.c diff --git a/src/g_game.c b/src/g_game.c index 8c28a58a0..6bb369c44 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -66,10 +66,7 @@ boolean botingame; UINT8 botskin; UINT8 botcolor; -JoyType_t Joystick; -JoyType_t Joystick2; -JoyType_t Joystick3; -JoyType_t Joystick4; +JoyType_t Joystick[MAXSPLITSCREENPLAYERS]; // 1024 bytes is plenty for a savegame #define SAVEGAMESIZE (1024) @@ -357,10 +354,6 @@ consvar_t cv_demochangemap = {"netdemo_savemapchange", "Disabled", CV_SAVE, demo static UINT8 *savebuffer; // Analog Control -static void Analog_OnChange(void); -static void Analog2_OnChange(void); -static void Analog3_OnChange(void); -static void Analog4_OnChange(void); void SendWeaponPref(void); void SendWeaponPref2(void); void SendWeaponPref3(void); @@ -368,25 +361,6 @@ void SendWeaponPref4(void); static void G_FixCamera(UINT8 view); -//static CV_PossibleValue_t crosshair_cons_t[] = {{0, "Off"}, {1, "Cross"}, {2, "Angle"}, {3, "Point"}, {0, NULL}}; -static CV_PossibleValue_t joyaxis_cons_t[] = {{0, "None"}, -{1, "Left X"}, {2, "Left Y"}, {-1, "Left X-"}, {-2, "Left Y-"}, -#if JOYAXISSET > 1 -{3, "Right X"}, {4, "Right Y"}, {-3, "Right X-"}, {-4, "Right Y-"}, -#endif -#if JOYAXISSET > 2 -{5, "L Trigger"}, {6, "R Trigger"}, {-5, "L Trigger-"}, {-6, "R Trigger-"}, -#endif -#if JOYAXISSET > 3 -{7, "U-Axis"}, {8, "V-Axis"}, {-7, "U-Axis-"}, {-8, "V-Axis-"}, -#endif - {0, NULL}}; -#if JOYAXISSET > 4 -"More Axis Sets" -#endif - -static CV_PossibleValue_t deadzone_cons_t[] = {{FRACUNIT/16, "MIN"}, {FRACUNIT, "MAX"}, {0, NULL}}; - // don't mind me putting these here, I was lazy to figure out where else I could put those without blowing up the compiler. // chat timer thingy @@ -440,70 +414,116 @@ consvar_t cv_chasefreelook = {"chasemlook", "Off", CV_SAVE, CV_OnOff, NULL, 0, N consvar_t cv_chasefreelook2 = {"chasemlook2", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_mousemove = {"mousemove", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_mousemove2 = {"mousemove2", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL};*/ -consvar_t cv_analog = {"analog", "Off", CV_CALL, CV_OnOff, Analog_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_analog2 = {"analog2", "Off", CV_CALL, CV_OnOff, Analog2_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_analog3 = {"analog3", "Off", CV_CALL, CV_OnOff, Analog3_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_analog4 = {"analog4", "Off", CV_CALL, CV_OnOff, Analog4_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_useranalog = {"useranalog", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_useranalog2 = {"useranalog2", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_useranalog3 = {"useranalog3", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_useranalog4 = {"useranalog4", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_turnaxis = {"joyaxis_turn", "Left X", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_moveaxis = {"joyaxis_move", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_brakeaxis = {"joyaxis_brake", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_aimaxis = {"joyaxis_aim", "Left Y", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_lookaxis = {"joyaxis_look", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_fireaxis = {"joyaxis_fire", "L Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_driftaxis = {"joyaxis_drift", "R Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_lookbackaxis = {"joyaxis_lookback", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom1axis = {"joyaxis_custom1", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom2axis = {"joyaxis_custom2", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom3axis = {"joyaxis_custom3", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_xdeadzone = {"joy_xdeadzone", "0.3", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_ydeadzone = {"joy_ydeadzone", "0.5", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; +//static CV_PossibleValue_t crosshair_cons_t[] = {{0, "Off"}, {1, "Cross"}, {2, "Angle"}, {3, "Point"}, {0, NULL}}; +static CV_PossibleValue_t joyaxis_cons_t[] = {{0, "None"}, +{1, "Left X"}, {2, "Left Y"}, {-1, "Left X-"}, {-2, "Left Y-"}, +#if JOYAXISSET > 1 +{3, "Right X"}, {4, "Right Y"}, {-3, "Right X-"}, {-4, "Right Y-"}, +#endif +#if JOYAXISSET > 2 +{5, "L Trigger"}, {6, "R Trigger"}, {-5, "L Trigger-"}, {-6, "R Trigger-"}, +#endif +#if JOYAXISSET > 3 +{7, "U-Axis"}, {8, "V-Axis"}, {-7, "U-Axis-"}, {-8, "V-Axis-"}, +#endif + {0, NULL}}; +#if JOYAXISSET > 4 +"More Axis Sets" +#endif -consvar_t cv_turnaxis2 = {"joyaxis2_turn", "Left X", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_moveaxis2 = {"joyaxis2_move", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_brakeaxis2 = {"joyaxis2_brake", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_aimaxis2 = {"joyaxis2_aim", "Left Y", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_lookaxis2 = {"joyaxis2_look", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_fireaxis2 = {"joyaxis2_fire", "L Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_driftaxis2 = {"joyaxis2_drift", "R Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_lookbackaxis2 = {"joyaxis2_lookback", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom1axis2 = {"joyaxis2_custom1", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom2axis2 = {"joyaxis2_custom2", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom3axis2 = {"joyaxis2_custom3", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_xdeadzone2 = {"joy2_xdeadzone", "0.3", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_ydeadzone2 = {"joy2_ydeadzone", "0.5", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; +static CV_PossibleValue_t deadzone_cons_t[] = {{FRACUNIT/16, "MIN"}, {FRACUNIT, "MAX"}, {0, NULL}}; -consvar_t cv_turnaxis3 = {"joyaxis3_turn", "Left X", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_moveaxis3 = {"joyaxis3_move", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_brakeaxis3 = {"joyaxis3_brake", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_aimaxis3 = {"joyaxis3_aim", "Left Y", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_lookaxis3 = {"joyaxis3_look", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_fireaxis3 = {"joyaxis3_fire", "L Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_driftaxis3 = {"joyaxis3_drift", "R Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_lookbackaxis3 = {"joyaxis3_lookback", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom1axis3 = {"joyaxis3_custom1", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom2axis3 = {"joyaxis3_custom2", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom3axis3 = {"joyaxis3_custom3", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_xdeadzone3 = {"joy3_xdeadzone", "0.3", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_ydeadzone3 = {"joy3_ydeadzone", "0.5", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_turnaxis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_turn", "Left X", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_turn", "Left X", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_turn", "Left X", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_turn", "Left X", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; -consvar_t cv_turnaxis4 = {"joyaxis4_turn", "Left X", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_moveaxis4 = {"joyaxis4_move", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_brakeaxis4 = {"joyaxis4_brake", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_aimaxis4 = {"joyaxis4_aim", "Left Y", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_lookaxis4 = {"joyaxis4_look", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_fireaxis4 = {"joyaxis4_fire", "L Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_driftaxis4 = {"joyaxis4_drift", "R Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_lookbackaxis4 = {"joyaxis4_lookback", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom1axis4 = {"joyaxis4_custom1", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom2axis4 = {"joyaxis4_custom2", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_custom3axis4 = {"joyaxis4_custom3", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_xdeadzone4 = {"joy4_xdeadzone", "0.3", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_ydeadzone4 = {"joy4_ydeadzone", "0.5", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_moveaxis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_move", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_move", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_move", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_move", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_brakeaxis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_brake", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_brake", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_brake", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_brake", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_aimaxis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_aim", "Left Y", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_aim", "Left Y", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_aim", "Left Y", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_aim", "Left Y", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_lookaxis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_look", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_look", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_look", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_look", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_fireaxis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_fire", "L Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_fire", "L Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_fire", "L Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_fire", "L Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_driftaxis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_drift", "R Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_drift", "R Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_drift", "R Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_drift", "R Trigger", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_lookbackaxis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_lookback", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_lookback", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_lookback", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_lookback", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_custom1axis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_custom1", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_custom1", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_custom1", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_custom1", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_custom2axis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_custom2", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_custom2", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_custom2", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_custom2", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_custom3axis[MAXSPLITSCREENPLAYERS] = { + {"joyaxis_custom3", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis2_custom3", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis3_custom3", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joyaxis4_custom3", "None", CV_SAVE, joyaxis_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_xdeadzone[MAXSPLITSCREENPLAYERS] = { + {"joy_xdeadzone", "0.3", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joy2_xdeadzone", "0.3", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joy3_xdeadzone", "0.3", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joy4_xdeadzone", "0.3", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_ydeadzone[MAXSPLITSCREENPLAYERS] = { + {"joy_ydeadzone", "0.5", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joy2_ydeadzone", "0.5", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joy3_ydeadzone", "0.5", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"joy4_ydeadzone", "0.5", CV_FLOAT|CV_SAVE, deadzone_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; static CV_PossibleValue_t driftsparkpulse_t[] = {{0, "MIN"}, {FRACUNIT*3, "MAX"}, {0, NULL}}; consvar_t cv_driftsparkpulse = {"driftsparkpulse", "1.4", CV_FLOAT | CV_SAVE, driftsparkpulse_t, NULL, 0, NULL, NULL, 0, 0, NULL}; @@ -709,7 +729,7 @@ INT16 G_SoftwareClipAimingPitch(INT32 *aiming) return (INT16)((*aiming)>>16); } -static INT32 Joy1Axis(axis_input_e axissel) +INT32 JoyAxis(axis_input_e axissel, UINT8 player) { INT32 retaxis; INT32 axisval; @@ -719,37 +739,37 @@ static INT32 Joy1Axis(axis_input_e axissel) switch (axissel) { case AXISTURN: - axisval = cv_turnaxis.value; + axisval = cv_turnaxis[player-1].value; break; case AXISMOVE: - axisval = cv_moveaxis.value; + axisval = cv_moveaxis[player-1].value; break; case AXISBRAKE: - axisval = cv_brakeaxis.value; + axisval = cv_brakeaxis[player-1].value; break; case AXISAIM: - axisval = cv_aimaxis.value; + axisval = cv_aimaxis[player-1].value; break; case AXISLOOK: - axisval = cv_lookaxis.value; + axisval = cv_lookaxis[player-1].value; break; case AXISFIRE: - axisval = cv_fireaxis.value; + axisval = cv_fireaxis[player-1].value; break; case AXISDRIFT: - axisval = cv_driftaxis.value; + axisval = cv_driftaxis[player-1].value; break; case AXISLOOKBACK: - axisval = cv_lookbackaxis.value; + axisval = cv_lookbackaxis[player-1].value; break; case AXISCUSTOM1: - axisval = cv_custom1axis.value; + axisval = cv_custom1axis[player-1].value; break; case AXISCUSTOM2: - axisval = cv_custom2axis.value; + axisval = cv_custom2axis[player-1].value; break; case AXISCUSTOM3: - axisval = cv_custom3axis.value; + axisval = cv_custom3axis[player-1].value; break; default: return 0; @@ -772,9 +792,9 @@ static INT32 Joy1Axis(axis_input_e axissel) retaxis = -JOYAXISRANGE; if (retaxis > (+JOYAXISRANGE)) retaxis = +JOYAXISRANGE; - if (!Joystick.bGamepadStyle && axissel < AXISDEAD) + if (!Joystick[player-1].bGamepadStyle && axissel < AXISDEAD) { - const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_xdeadzone.value) >> FRACBITS; + const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_xdeadzone[player-1].value) >> FRACBITS; if (abs(retaxis) <= jdeadzone) return 0; } @@ -791,9 +811,9 @@ static INT32 Joy1Axis(axis_input_e axissel) retaxis = -JOYAXISRANGE; if (retaxis > (+JOYAXISRANGE)) retaxis = +JOYAXISRANGE; - if (!Joystick.bGamepadStyle && axissel < AXISDEAD) + if (!Joystick[player-1].bGamepadStyle && axissel < AXISDEAD) { - const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_ydeadzone.value) >> FRACBITS; + const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_ydeadzone[player-1].value) >> FRACBITS; if (abs(retaxis) <= jdeadzone) return 0; } @@ -802,291 +822,6 @@ static INT32 Joy1Axis(axis_input_e axissel) } } -static INT32 Joy2Axis(axis_input_e axissel) -{ - INT32 retaxis; - INT32 axisval; - boolean flp = false; - - //find what axis to get - switch (axissel) - { - case AXISTURN: - axisval = cv_turnaxis2.value; - break; - case AXISMOVE: - axisval = cv_moveaxis2.value; - break; - case AXISBRAKE: - axisval = cv_brakeaxis2.value; - break; - case AXISAIM: - axisval = cv_aimaxis2.value; - break; - case AXISLOOK: - axisval = cv_lookaxis2.value; - break; - case AXISFIRE: - axisval = cv_fireaxis2.value; - break; - case AXISDRIFT: - axisval = cv_driftaxis2.value; - break; - case AXISLOOKBACK: - axisval = cv_lookbackaxis2.value; - break; - case AXISCUSTOM1: - axisval = cv_custom1axis2.value; - break; - case AXISCUSTOM2: - axisval = cv_custom2axis2.value; - break; - case AXISCUSTOM3: - axisval = cv_custom3axis2.value; - break; - default: - return 0; - } - - if (axisval < 0) //odd -axises - { - axisval = -axisval; - flp = true; - } - if (axisval > JOYAXISSET*2 || axisval == 0) //not there in array or None - return 0; - - if (axisval%2) - { - axisval /= 2; - retaxis = joy2xmove[axisval]; - - if (retaxis < (-JOYAXISRANGE)) - retaxis = -JOYAXISRANGE; - if (retaxis > (+JOYAXISRANGE)) - retaxis = +JOYAXISRANGE; - if (!Joystick2.bGamepadStyle && axissel < AXISDEAD) - { - const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_xdeadzone2.value) >> FRACBITS; - if (-jdeadzone < retaxis && retaxis < jdeadzone) - return 0; - } - if (flp) retaxis = -retaxis; //flip it around - return retaxis; - - } - else - { - axisval--; - axisval /= 2; - retaxis = joy2ymove[axisval]; - - if (retaxis < (-JOYAXISRANGE)) - retaxis = -JOYAXISRANGE; - if (retaxis > (+JOYAXISRANGE)) - retaxis = +JOYAXISRANGE; - if (!Joystick2.bGamepadStyle && axissel < AXISDEAD) - { - const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_ydeadzone2.value) >> FRACBITS; - if (-jdeadzone < retaxis && retaxis < jdeadzone) - return 0; - } - if (flp) retaxis = -retaxis; //flip it around - return retaxis; - - } -} - -static INT32 Joy3Axis(axis_input_e axissel) -{ - INT32 retaxis; - INT32 axisval; - boolean flp = false; - - //find what axis to get - switch (axissel) - { - case AXISTURN: - axisval = cv_turnaxis3.value; - break; - case AXISMOVE: - axisval = cv_moveaxis3.value; - break; - case AXISBRAKE: - axisval = cv_brakeaxis3.value; - break; - case AXISAIM: - axisval = cv_aimaxis3.value; - break; - case AXISLOOK: - axisval = cv_lookaxis3.value; - break; - case AXISFIRE: - axisval = cv_fireaxis3.value; - break; - case AXISDRIFT: - axisval = cv_driftaxis3.value; - break; - case AXISLOOKBACK: - axisval = cv_lookbackaxis3.value; - break; - case AXISCUSTOM1: - axisval = cv_custom1axis3.value; - break; - case AXISCUSTOM2: - axisval = cv_custom2axis3.value; - break; - case AXISCUSTOM3: - axisval = cv_custom3axis3.value; - break; - default: - return 0; - } - - if (axisval < 0) //odd -axises - { - axisval = -axisval; - flp = true; - } - if (axisval > JOYAXISSET*2 || axisval == 0) //not there in array or None - return 0; - - if (axisval%2) - { - axisval /= 2; - retaxis = joy3xmove[axisval]; - - if (retaxis < (-JOYAXISRANGE)) - retaxis = -JOYAXISRANGE; - if (retaxis > (+JOYAXISRANGE)) - retaxis = +JOYAXISRANGE; - if (!Joystick3.bGamepadStyle && axissel < AXISDEAD) - { - const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_xdeadzone3.value) >> FRACBITS; - if (-jdeadzone < retaxis && retaxis < jdeadzone) - return 0; - } - if (flp) retaxis = -retaxis; //flip it around - return retaxis; - - } - else - { - axisval--; - axisval /= 2; - retaxis = joy3ymove[axisval]; - - if (retaxis < (-JOYAXISRANGE)) - retaxis = -JOYAXISRANGE; - if (retaxis > (+JOYAXISRANGE)) - retaxis = +JOYAXISRANGE; - if (!Joystick3.bGamepadStyle && axissel < AXISDEAD) - { - const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_ydeadzone3.value) >> FRACBITS; - if (-jdeadzone < retaxis && retaxis < jdeadzone) - return 0; - } - if (flp) retaxis = -retaxis; //flip it around - return retaxis; - - } -} - -static INT32 Joy4Axis(axis_input_e axissel) -{ - INT32 retaxis; - INT32 axisval; - boolean flp = false; - - //find what axis to get - switch (axissel) - { - case AXISTURN: - axisval = cv_turnaxis4.value; - break; - case AXISMOVE: - axisval = cv_moveaxis4.value; - break; - case AXISBRAKE: - axisval = cv_brakeaxis4.value; - break; - case AXISAIM: - axisval = cv_aimaxis4.value; - break; - case AXISLOOK: - axisval = cv_lookaxis4.value; - break; - case AXISFIRE: - axisval = cv_fireaxis4.value; - break; - case AXISDRIFT: - axisval = cv_driftaxis4.value; - break; - case AXISLOOKBACK: - axisval = cv_lookbackaxis4.value; - break; - case AXISCUSTOM1: - axisval = cv_custom1axis4.value; - break; - case AXISCUSTOM2: - axisval = cv_custom2axis4.value; - break; - case AXISCUSTOM3: - axisval = cv_custom3axis4.value; - break; - default: - return 0; - } - - if (axisval < 0) //odd -axises - { - axisval = -axisval; - flp = true; - } - if (axisval > JOYAXISSET*2 || axisval == 0) //not there in array or None - return 0; - - if (axisval%2) - { - axisval /= 2; - retaxis = joy4xmove[axisval]; - - if (retaxis < (-JOYAXISRANGE)) - retaxis = -JOYAXISRANGE; - if (retaxis > (+JOYAXISRANGE)) - retaxis = +JOYAXISRANGE; - if (!Joystick4.bGamepadStyle && axissel < AXISDEAD) - { - const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_xdeadzone4.value) >> FRACBITS; - if (-jdeadzone < retaxis && retaxis < jdeadzone) - return 0; - } - if (flp) retaxis = -retaxis; //flip it around - return retaxis; - - } - else - { - axisval--; - axisval /= 2; - retaxis = joy4ymove[axisval]; - - if (retaxis < (-JOYAXISRANGE)) - retaxis = -JOYAXISRANGE; - if (retaxis > (+JOYAXISRANGE)) - retaxis = +JOYAXISRANGE; - if (!Joystick4.bGamepadStyle && axissel < AXISDEAD) - { - const INT32 jdeadzone = ((JOYAXISRANGE-1) * cv_ydeadzone4.value) >> FRACBITS; - if (-jdeadzone < retaxis && retaxis < jdeadzone) - return 0; - } - if (flp) retaxis = -retaxis; //flip it around - return retaxis; - - } -} - boolean InputDown(INT32 gc, UINT8 p) { switch (p) @@ -1102,21 +837,6 @@ boolean InputDown(INT32 gc, UINT8 p) } } -INT32 JoyAxis(axis_input_e axissel, UINT8 p) -{ - switch (p) - { - case 2: - return Joy2Axis(axissel); - case 3: - return Joy3Axis(axissel); - case 4: - return Joy4Axis(axissel); - default: - return Joy1Axis(axissel); - } -} - // // G_BuildTiccmd // Builds a ticcmd from all of the available inputs @@ -1135,11 +855,12 @@ static fixed_t angleturn[3] = {KART_FULLTURN/2, KART_FULLTURN, KART_FULLTURN/4}; void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) { + const UINT8 forplayer = ssplayer-1; INT32 laim, th, tspeed, forward, side, axis; //i const INT32 speed = 1; // these ones used for multiple conditions - boolean turnleft, turnright, mouseaiming, analogjoystickmove, gamepadjoystickmove; - boolean invertmouse, lookaxis, usejoystick, kbl, rd; + boolean turnleft, turnright, mouseaiming; + boolean invertmouse, usejoystick, kbl, rd; player_t *player; camera_t *thiscam; angle_t lang; @@ -1148,22 +869,26 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) static boolean keyboard_look[MAXSPLITSCREENPLAYERS]; // true if lookup/down using keyboard static boolean resetdown[MAXSPLITSCREENPLAYERS]; // don't cam reset every frame + const boolean lookaxis = cv_lookaxis[forplayer].value; + const boolean analogjoystickmove = cv_usejoystick[forplayer].value && !Joystick[forplayer].bGamepadStyle; + const boolean gamepadjoystickmove = cv_usejoystick[forplayer].value && Joystick[forplayer].bGamepadStyle; + if (demo.playback) return; if (ssplayer == 1) player = &players[consoleplayer]; else - player = &players[displayplayers[ssplayer-1]]; + player = &players[displayplayers[forplayer]]; if (ssplayer == 2) - thiscam = (player->bot == 2 ? &camera[0] : &camera[ssplayer-1]); + thiscam = (player->bot == 2 ? &camera[0] : &camera[forplayer]); else - thiscam = &camera[ssplayer-1]; - lang = localangle[ssplayer-1]; - laim = localaiming[ssplayer-1]; - th = turnheld[ssplayer-1]; - kbl = keyboard_look[ssplayer-1]; - rd = resetdown[ssplayer-1]; + thiscam = &camera[forplayer]; + lang = localangle[forplayer]; + laim = localaiming[forplayer]; + th = turnheld[forplayer]; + kbl = keyboard_look[forplayer]; + rd = resetdown[forplayer]; switch (ssplayer) { @@ -1197,31 +922,19 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) case 2: mouseaiming = player->spectator; //(PLAYER2INPUTDOWN(gc_mouseaiming)) ^ cv_alwaysfreelook2.value; invertmouse = cv_invertmouse2.value; - lookaxis = cv_lookaxis2.value; - analogjoystickmove = cv_usejoystick2.value && !Joystick2.bGamepadStyle; - gamepadjoystickmove = cv_usejoystick2.value && Joystick2.bGamepadStyle; break; case 3: mouseaiming = false; invertmouse = false; - lookaxis = cv_lookaxis3.value; - analogjoystickmove = cv_usejoystick3.value && !Joystick3.bGamepadStyle; - gamepadjoystickmove = cv_usejoystick3.value && Joystick3.bGamepadStyle; break; case 4: mouseaiming = false; invertmouse = false; - lookaxis = cv_lookaxis4.value; - analogjoystickmove = cv_usejoystick4.value && !Joystick4.bGamepadStyle; - gamepadjoystickmove = cv_usejoystick4.value && Joystick4.bGamepadStyle; break; case 1: default: mouseaiming = player->spectator; //(PLAYER1INPUTDOWN(gc_mouseaiming)) ^ cv_alwaysfreelook.value; invertmouse = cv_invertmouse.value; - lookaxis = cv_lookaxis.value; - analogjoystickmove = cv_usejoystick.value && !Joystick.bGamepadStyle; - gamepadjoystickmove = cv_usejoystick.value && Joystick.bGamepadStyle; break; } @@ -1468,13 +1181,13 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) if (!hu_stopped) { - localangle[ssplayer-1] = lang; - localaiming[ssplayer-1] = laim; - keyboard_look[ssplayer-1] = kbl; - turnheld[ssplayer-1] = th; - resetdown[ssplayer-1] = rd; + localangle[forplayer] = lang; + localaiming[forplayer] = laim; + keyboard_look[forplayer] = kbl; + turnheld[forplayer] = th; + resetdown[forplayer] = rd; axis = JoyAxis(AXISLOOKBACK, ssplayer); - camspin[ssplayer-1] = (InputDown(gc_lookback, ssplayer) || (usejoystick && axis > 0)); + camspin[forplayer] = (InputDown(gc_lookback, ssplayer) || (usejoystick && axis > 0)); } /* Lua: Allow this hook to overwrite ticcmd. @@ -1503,38 +1216,6 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) } -static void Analog_OnChange(void) -{ - if (!cv_cam_dist.string) - return; - - SendWeaponPref(); -} - -static void Analog2_OnChange(void) -{ - if (!(splitscreen || botingame) || !cv_cam2_dist.string) - return; - - SendWeaponPref2(); -} - -static void Analog3_OnChange(void) -{ - if (splitscreen < 2 || !cv_cam3_dist.string) - return; - - SendWeaponPref3(); -} - -static void Analog4_OnChange(void) -{ - if (splitscreen < 3 || !cv_cam4_dist.string) - return; - - SendWeaponPref4(); -} - // // G_DoLoadLevel // @@ -1797,7 +1478,7 @@ boolean G_Responder(event_t *ev) if (!camtoggledelay) { camtoggledelay = NEWTICRATE / 7; - CV_SetValue(&cv_chasecam, cv_chasecam.value ? 0 : 1); + CV_SetValue(&cv_chasecam[0], cv_chasecam[0].value ? 0 : 1); } } if (ev->data1 == gamecontrolbis[gc_camtoggle][0] @@ -1806,7 +1487,7 @@ boolean G_Responder(event_t *ev) if (!camtoggledelay2) { camtoggledelay2 = NEWTICRATE / 7; - CV_SetValue(&cv_chasecam2, cv_chasecam2.value ? 0 : 1); + CV_SetValue(&cv_chasecam[1], cv_chasecam[1].value ? 0 : 1); } } if (ev->data1 == gamecontrol3[gc_camtoggle][0] @@ -1815,7 +1496,7 @@ boolean G_Responder(event_t *ev) if (!camtoggledelay3) { camtoggledelay3 = NEWTICRATE / 7; - CV_SetValue(&cv_chasecam3, cv_chasecam3.value ? 0 : 1); + CV_SetValue(&cv_chasecam[2], cv_chasecam[2].value ? 0 : 1); } } if (ev->data1 == gamecontrol4[gc_camtoggle][0] @@ -1824,7 +1505,7 @@ boolean G_Responder(event_t *ev) if (!camtoggledelay4) { camtoggledelay4 = NEWTICRATE / 7; - CV_SetValue(&cv_chasecam4, cv_chasecam4.value ? 0 : 1); + CV_SetValue(&cv_chasecam[3], cv_chasecam[3].value ? 0 : 1); } } if (ev->data1 == gamecontrol[gc_spectate][0] @@ -2029,6 +1710,8 @@ void G_ResetView(UINT8 viewnum, INT32 playernum, boolean onlyactive) UINT8 splits; UINT8 viewd; + INT32 playernumd; + INT32 *displayplayerp; INT32 olddisplayplayer; @@ -2057,30 +1740,21 @@ void G_ResetView(UINT8 viewnum, INT32 playernum, boolean onlyactive) R_ExecuteSetViewSize(); } - displayplayerp = (&displayplayers[viewnum-1]); - olddisplayplayer = (*displayplayerp); - - /* Check if anyone is available to view. */ - if ((playernum = G_FindView(playernum, viewnum, onlyactive, playernum < olddisplayplayer)) == -1) - return; - - /* Focus our target view first so that we don't take its player. */ - (*displayplayerp) = playernum; - - /* If a viewpoint changes, reset the camera to clear uninitialized memory. */ - if (viewnum > splits) + for (viewd = min(splits+1, viewnum); viewd <= viewnum; ++viewd) { - for (viewd = splits+1; viewd <= viewnum; ++viewd) - { - G_FixCamera(viewd); - } - } - else - { - if ((*displayplayerp) != olddisplayplayer) - { - G_FixCamera(viewnum); - } + playernumd = (viewd == viewnum) ? playernum : displayplayers[viewd-1]; + displayplayerp = (&displayplayers[viewd-1]); + olddisplayplayer = (*displayplayerp); + + /* Check if anyone is available to view. */ + if ((playernumd = G_FindView(playernumd, viewd, onlyactive, playernumd < olddisplayplayer)) == -1) + continue; + + /* Focus our target view first so that we don't take its player. */ + (*displayplayerp) = playernumd; + + /* If a viewpoint changes, reset the camera to clear uninitialized memory. */ + G_FixCamera(viewd); } if (viewnum == 1 && demo.playback) @@ -2657,9 +2331,6 @@ void G_PlayerReborn(INT32 player) if (leveltime > (starttime + (TICRATE/2)) && !p->spectator) p->kartstuff[k_respawn] = 48; // Respawn effect - if (gametype == GT_COOP) - P_FindEmerald(); // scan for emeralds to hunt for - // Reset Nights score and max link to 0 on death p->maxlink = 0; @@ -2730,19 +2401,9 @@ void G_SpawnPlayer(INT32 playernum, boolean starpost) return; } - // -- CTF -- - // Order: CTF->DM->Coop - if (gametype == GT_CTF && players[playernum].ctfteam) - { - if (!(spawnpoint = G_FindCTFStart(playernum)) // find a CTF start - && !(spawnpoint = G_FindMatchStart(playernum))) // find a DM start - spawnpoint = G_FindRaceStart(playernum); // fallback - } - // -- DM/Tag/CTF-spectator/etc -- // Order: DM->CTF->Coop - else if (gametype == GT_MATCH || gametype == GT_TEAMMATCH || gametype == GT_CTF - || ((gametype == GT_TAG || gametype == GT_HIDEANDSEEK) && !(players[playernum].pflags & PF_TAGIT))) + if (gametype == GT_MATCH && !(players[playernum].pflags & PF_TAGIT)) { if (!(spawnpoint = G_FindMatchStart(playernum)) // find a DM start && !(spawnpoint = G_FindCTFStart(playernum))) // find a CTF start @@ -3056,14 +2717,6 @@ void G_ExitLevel(void) gameaction = ga_completed; lastdraw = true; - // If you want your teams scrambled on map change, start the process now. - // The teams will scramble at the start of the next round. - if (cv_scrambleonchange.value && G_GametypeHasTeams()) - { - if (server) - CV_SetValue(&cv_teamscramble, cv_scrambleonchange.value); - } - if (netgame || multiplayer) CON_LogMessage(M_GetText("The round has ended.\n")); @@ -3109,29 +2762,6 @@ boolean G_IsSpecialStage(INT32 mapnum) return false; } -// -// G_GametypeUsesLives -// -// Returns true if the current gametype uses -// the lives system. False otherwise. -// -boolean G_GametypeUsesLives(void) -{ - // SRB2kart NEEDS no lives - return false; -} - -// -// G_GametypeHasTeams -// -// Returns true if the current gametype uses -// Red/Blue teams. False otherwise. -// -boolean G_GametypeHasTeams(void) -{ - return (gametype == GT_TEAMMATCH || gametype == GT_CTF); -} - // // G_GametypeHasSpectators // @@ -3249,16 +2879,6 @@ boolean G_RaceGametype(void) return (gametype == GT_RACE); } -// -// G_TagGametype -// -// For Jazz's Tag/HnS modes that have a lot of special cases... -// SRB2Kart: do we actually want to add Kart tag later? :V -// -boolean G_TagGametype(void) -{ - return (gametype == GT_TAG || gametype == GT_HIDEANDSEEK); -} /** Get the typeoflevel flag needed to indicate support of a gametype. * In single-player, this always returns TOL_SP. @@ -3269,14 +2889,8 @@ boolean G_TagGametype(void) INT16 G_TOLFlag(INT32 pgametype) { if (!multiplayer) return TOL_SP; - if (pgametype == GT_COOP) return TOL_RACE; // SRB2kart - if (pgametype == GT_COMPETITION) return TOL_COMPETITION; if (pgametype == GT_RACE) return TOL_RACE; if (pgametype == GT_MATCH) return TOL_MATCH; - if (pgametype == GT_TEAMMATCH) return TOL_MATCH; - if (pgametype == GT_TAG) return TOL_TAG; - if (pgametype == GT_HIDEANDSEEK) return TOL_TAG; - if (pgametype == GT_CTF) return TOL_CTF; CONS_Alert(CONS_ERROR, M_GetText("Unknown gametype! %d\n"), pgametype); return INT16_MAX; @@ -3555,42 +3169,15 @@ static void G_DoCompleted(void) if (nextmap >= 1100-1 && nextmap <= 1102-1 && G_RaceGametype()) nextmap = (INT16)(spstage_start-1); - if (gametype == GT_COOP && token) - { - token--; - gottoken = true; - - if (!(emeralds & EMERALD1)) - nextmap = (INT16)(sstage_start - 1); // Special Stage 1 - else if (!(emeralds & EMERALD2)) - nextmap = (INT16)(sstage_start); // Special Stage 2 - else if (!(emeralds & EMERALD3)) - nextmap = (INT16)(sstage_start + 1); // Special Stage 3 - else if (!(emeralds & EMERALD4)) - nextmap = (INT16)(sstage_start + 2); // Special Stage 4 - else if (!(emeralds & EMERALD5)) - nextmap = (INT16)(sstage_start + 3); // Special Stage 5 - else if (!(emeralds & EMERALD6)) - nextmap = (INT16)(sstage_start + 4); // Special Stage 6 - else if (!(emeralds & EMERALD7)) - nextmap = (INT16)(sstage_start + 5); // Special Stage 7 - else - gottoken = false; - } - if (G_IsSpecialStage(gamemap) && !gottoken) nextmap = lastmap; // Exiting from a special stage? Go back to the game. Tails 08-11-2001 automapactive = false; - if (gametype != GT_COOP) - { - if (cv_advancemap.value == 0) // Stay on same map. - nextmap = prevmap; - else if (cv_advancemap.value == 2) // Go to random map. - nextmap = G_RandMap(G_TOLFlag(gametype), prevmap, false, 0, false, NULL); - } - + if (cv_advancemap.value == 0) // Stay on same map. + nextmap = prevmap; + else if (cv_advancemap.value == 2) // Go to random map. + nextmap = G_RandMap(G_TOLFlag(gametype), prevmap, false, 0, false, NULL); // We are committed to this map now. // We may as well allocate its header if it doesn't exist @@ -3775,21 +3362,6 @@ void G_EndGame(void) if (demo.recording && (modeattacking || demo.savemode != DSM_NOTSAVING)) G_SaveDemo(); - // Only do evaluation and credits in coop games. - if (gametype == GT_COOP) - { - if (nextmap == 1102-1) // end game with credits - { - F_StartCredits(); - return; - } - if (nextmap == 1101-1) // end game with evaluation - { - F_StartGameEvaluation(); - return; - } - } - // 1100 or competitive multiplayer, so go back to title screen. D_StartTitle(); } @@ -4632,7 +4204,7 @@ INT32 G_FindMapByNameOrCode(const char *mapname, char **realmapnamep) INT32 newmapnum = -1; size_t mapnamelen = strlen(mapname); char *p; - + if (mapnamelen == 1) { if (mapname[0] == '*') // current map @@ -7590,8 +7162,8 @@ void G_DoPlayDemo(char *defdemoname) p = READUINT8(demo_p); } -// end of player read (the 0xFF marker) -// so this is where we are to read our lua variables (if possible!) + // end of player read (the 0xFF marker) + // so this is where we are to read our lua variables (if possible!) if (demoflags & DF_LUAVARS) // again, used for compability, lua shit will be saved to replays regardless of if it's even been loaded { if (!gL) // No Lua state! ...I guess we'll just start one... diff --git a/src/g_game.h b/src/g_game.h index 81d653774..09d9bc3d5 100644 --- a/src/g_game.h +++ b/src/g_game.h @@ -120,12 +120,21 @@ extern consvar_t cv_pauseifunfocused; //extern consvar_t cv_crosshair, cv_crosshair2, cv_crosshair3, cv_crosshair4; extern consvar_t cv_invertmouse/*, cv_alwaysfreelook, cv_chasefreelook, cv_mousemove*/; extern consvar_t cv_invertmouse2/*, cv_alwaysfreelook2, cv_chasefreelook2, cv_mousemove2*/; -extern consvar_t cv_useranalog, cv_useranalog2, cv_useranalog3, cv_useranalog4; -extern consvar_t cv_analog, cv_analog2, cv_analog3, cv_analog4; -extern consvar_t cv_turnaxis,cv_moveaxis,cv_brakeaxis,cv_aimaxis,cv_lookaxis,cv_fireaxis,cv_driftaxis,cv_lookbackaxis,cv_custom1axis,cv_custom2axis,cv_custom3axis,cv_xdeadzone,cv_ydeadzone; -extern consvar_t cv_turnaxis2,cv_moveaxis2,cv_brakeaxis2,cv_aimaxis2,cv_lookaxis2,cv_fireaxis2,cv_driftaxis2,cv_lookbackaxis2,cv_custom1axis2,cv_custom2axis2,cv_custom3axis2,cv_xdeadzone2,cv_ydeadzone2; -extern consvar_t cv_turnaxis3,cv_moveaxis3,cv_brakeaxis3,cv_aimaxis3,cv_lookaxis3,cv_fireaxis3,cv_driftaxis3,cv_lookbackaxis3,cv_custom1axis3,cv_custom2axis3,cv_custom3axis3,cv_xdeadzone3,cv_ydeadzone3; -extern consvar_t cv_turnaxis4,cv_moveaxis4,cv_brakeaxis4,cv_aimaxis4,cv_lookaxis4,cv_fireaxis4,cv_driftaxis4,cv_lookbackaxis4,cv_custom1axis4,cv_custom2axis4,cv_custom3axis4,cv_xdeadzone4,cv_ydeadzone4; + +extern consvar_t cv_turnaxis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_moveaxis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_brakeaxis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_aimaxis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_lookaxis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_lookbackaxis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_fireaxis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_driftaxis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_custom1axis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_custom2axis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_custom3axis[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_xdeadzone[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_ydeadzone[MAXSPLITSCREENPLAYERS]; + extern consvar_t cv_ghost_besttime, cv_ghost_bestlap, cv_ghost_last, cv_ghost_guest, cv_ghost_staff; // Hud offsets @@ -370,14 +379,11 @@ boolean G_DemoTitleResponder(event_t *ev); INT32 G_GetGametypeByName(const char *gametypestr); boolean G_IsSpecialStage(INT32 mapnum); -boolean G_GametypeUsesLives(void); -boolean G_GametypeHasTeams(void); boolean G_GametypeHasSpectators(void); boolean G_BattleGametype(void); UINT8 G_SometimesGetDifferentGametype(UINT8 prefgametype); UINT8 G_GetGametypeColor(INT16 gt); boolean G_RaceGametype(void); -boolean G_TagGametype(void); void G_ExitLevel(void); void G_NextLevel(void); void G_Continue(void); diff --git a/src/g_input.c b/src/g_input.c index ad7758a7a..7f2fff283 100644 --- a/src/g_input.c +++ b/src/g_input.c @@ -908,28 +908,6 @@ static const char *gamecontrolname[num_gamecontrols] = #include "k_kart.h" -INT32 G_GetDeviceForPlayer(INT32 player) -{ - switch (player) - { - case 0: - return cv_usejoystick.value; - break; - case 1: - return cv_usejoystick2.value; - break; - case 2: - return cv_usejoystick3.value; - break; - case 3: - return cv_usejoystick4.value; - break; - default: - return 0; - break; - } -} - inline UINT16 G_GetSkinColor(INT32 player) { // make rgb rainbow vomit when invul or flash blue when grow @@ -972,7 +950,7 @@ void G_SetPlayerGamepadIndicatorColor(INT32 player, UINT16 color) if (cv_gamepadled[player].value == 0) return; - device = G_GetDeviceForPlayer(player); + device = cv_usejoystick[player].value; if (device <= 0) { @@ -989,7 +967,7 @@ static void G_ResetPlayerGamepadIndicatorColor(INT32 player) { if (cv_gamepadled[player].value == 0) { - INT32 device = G_GetDeviceForPlayer(player); + INT32 device = cv_usejoystick[player].value; if (device <= 0) return; @@ -1003,7 +981,7 @@ static void G_ResetPlayerDeviceRumble(INT32 player) { INT32 device_id; - device_id = G_GetDeviceForPlayer(player); + device_id = cv_usejoystick[player].value; if (device_id < 1) { @@ -1022,7 +1000,7 @@ void G_ResetAllDeviceRumbles(void) for (i = 0; i < devices; i++) { - INT32 device_id = G_GetDeviceForPlayer(i); + INT32 device_id = cv_usejoystick[i].value; I_GamepadRumble(device_id, 0, 0, 0); } @@ -1037,7 +1015,7 @@ void G_PlayerDeviceRumble(INT32 player, UINT16 low_strength, UINT16 high_strengt return; } - device_id = G_GetDeviceForPlayer(player); + device_id = cv_usejoystick[player].value; if (device_id < 1) { diff --git a/src/hardware/hw_batching.c b/src/hardware/hw_batching.c index 75b29b697..138c35a5d 100644 --- a/src/hardware/hw_batching.c +++ b/src/hardware/hw_batching.c @@ -227,7 +227,7 @@ void HWR_RenderBatches(void) int currentShader; int nextShader = 0; - GLMipmap_t *currentTexture; + GLMipmap_t *currentTexture = NULL; GLMipmap_t *nextTexture = NULL; FBITFIELD currentPolyFlags = 0; FBITFIELD nextPolyFlags = 0; diff --git a/src/hardware/hw_cache.c b/src/hardware/hw_cache.c index a5b03e78d..c67f1b75c 100644 --- a/src/hardware/hw_cache.c +++ b/src/hardware/hw_cache.c @@ -73,6 +73,9 @@ static void HWR_DrawColumnInCache(const column_t *patchcol, UINT8 *block, GLMipm (void)patchheight; // This parameter is unused + if (!mipmap || mipmap == NULL) + return; + if (originPatch) // originPatch can be NULL here, unlike in the software version originy = originPatch->originy; diff --git a/src/hardware/hw_draw.c b/src/hardware/hw_draw.c index e39398ff2..efb4eeaa3 100644 --- a/src/hardware/hw_draw.c +++ b/src/hardware/hw_draw.c @@ -552,23 +552,23 @@ void HWR_DrawFlatFill (INT32 x, INT32 y, INT32 w, INT32 h, lumpnum_t flatlumpnum // 0--1 void HWR_FadeScreenMenuBack(UINT16 color, UINT8 strength) { - FOutVector v[4]; - FSurfaceInfo Surf; + FOutVector v[4]; + FSurfaceInfo Surf; FBITFIELD poly_flags = PF_NoTexture|PF_Modulated|PF_NoDepthTest; - v[0].x = v[3].x = -1.0f; - v[2].x = v[1].x = 1.0f; - v[0].y = v[1].y = -1.0f; - v[2].y = v[3].y = 1.0f; - v[0].z = v[1].z = v[2].z = v[3].z = 1.0f; + v[0].x = v[3].x = -1.0f; + v[2].x = v[1].x = 1.0f; + v[0].y = v[1].y = -1.0f; + v[2].y = v[3].y = 1.0f; + v[0].z = v[1].z = v[2].z = v[3].z = 1.0f; - v[0].s = v[3].s = 0.0f; - v[2].s = v[1].s = 1.0f; - v[0].t = v[1].t = 1.0f; - v[2].t = v[3].t = 0.0f; + v[0].s = v[3].s = 0.0f; + v[2].s = v[1].s = 1.0f; + v[0].t = v[1].t = 1.0f; + v[2].t = v[3].t = 0.0f; - if (color & 0xFF00) // Do COLORMAP fade. - { + if (color & 0xFF00) // Do COLORMAP fade. + { if (HWR_ShouldUsePaletteRendering() && cv_glscreentextures.value) { const hwdscreentexture_t scr_tex = HWD_SCREENTEXTURE_GENERIC2; diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 239cbdbfb..40b488a8e 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -3225,7 +3225,7 @@ static void HWR_DrawSpriteShadow(gl_vissprite_t *spr, GLPatch_t *gpatch) this_scale = FIXED_TO_FLOAT(spr->mobj->scale); if (hires) this_scale = this_scale * FIXED_TO_FLOAT(((skin_t *)( (spr->mobj->localskin) ? spr->mobj->localskin : spr->mobj->skin ))->highresscale); - + R_GetShadowZ(spr->mobj, &floorslope); mobjfloor = HWR_OpaqueFloorAtPos( @@ -3238,13 +3238,13 @@ static void HWR_DrawSpriteShadow(gl_vissprite_t *spr, GLPatch_t *gpatch) // Set direction if (splitscreen && stplyr == &players[displayplayers[1]]) - shadowdir = localangle[1] + FixedAngle(cv_cam2_rotate.value); + shadowdir = localangle[1] + FixedAngle(cv_cam_rotate[1].value); else if (splitscreen > 1 && stplyr == &players[displayplayers[2]]) - shadowdir = localangle[2] + FixedAngle(cv_cam3_rotate.value); + shadowdir = localangle[2] + FixedAngle(cv_cam_rotate[2].value); else if (splitscreen > 2 && stplyr == &players[displayplayers[3]]) - shadowdir = localangle[3] + FixedAngle(cv_cam4_rotate.value); + shadowdir = localangle[3] + FixedAngle(cv_cam_rotate[3].value); else - shadowdir = localangle[0] + FixedAngle(cv_cam_rotate.value); + shadowdir = localangle[0] + FixedAngle(cv_cam_rotate[0].value); // Find floorheight floorheight = HWR_OpaqueFloorAtPos( @@ -3321,7 +3321,7 @@ static void HWR_DrawSpriteShadow(gl_vissprite_t *spr, GLPatch_t *gpatch) swallVerts[0].z = spr->z1 + offset * gl_viewsin; swallVerts[1].z = spr->z2 + offset * gl_viewsin; } - + if (floorslope) { for (int i = 0; i < 4; i++) @@ -3988,6 +3988,7 @@ static int CompareVisSprites(const void *p1, const void *p2) // make transparent sprites last // "boolean to int" + // check for precip first, because then sprX->mobj is actually a precipmobj_t and does not have flags2 or tracer int transparency1 = (!spr1->precip && (spr1->mobj->flags2 & MF2_SHADOW)) || (spr1->mobj->frame & FF_TRANSMASK); int transparency2 = (!spr2->precip && (spr2->mobj->flags2 & MF2_SHADOW)) || (spr2->mobj->frame & FF_TRANSMASK); @@ -5298,12 +5299,12 @@ void HWR_RenderPlayerView(INT32 viewnumber, player_t *player) drewsky = false; if (skybox) { - R_SkyboxFrame(player); + R_SkyboxFrame(viewssnum); HWR_RenderFrame(viewnumber, player, true); } PS_STOP_TIMING(ps_skyboxtime); - R_SetupFrame(player, false); // This can stay false because it is only used to set viewsky in r_main.c, which isn't used here + R_SetupFrame(viewssnum, false); // This can stay false because it is only used to set viewsky in r_main.c, which isn't used here framecount++; // for timedemo HWR_RenderFrame(viewnumber, player, false); } diff --git a/src/hardware/hw_md2.c b/src/hardware/hw_md2.c index 337bf1d80..774c256b1 100644 --- a/src/hardware/hw_md2.c +++ b/src/hardware/hw_md2.c @@ -794,10 +794,9 @@ static void HWR_CreateBlendedTexture(GLPatch_t *gpatch, GLPatch_t *blendgpatch, } } } - } - if (translen > 0) colorbrightnesses[translen] = colorbrightnesses[translen-1]; + } while (size--) { diff --git a/src/hardware/hw_portal.c b/src/hardware/hw_portal.c index 96a1b300a..d433b78cd 100644 --- a/src/hardware/hw_portal.c +++ b/src/hardware/hw_portal.c @@ -140,13 +140,17 @@ void HWR_PortalFrame(gl_portal_t* portal) static void HWR_RenderPortalSeg(gl_portal_t* portal, SINT8 state) { gl_drawing_stencil = true; // do not draw outside of the stencil buffer, idiot. + // set our portal state and prepare to render the seg HWR_SetPortalState(state); + gl_curline = portal->seg; gl_frontsector = portal->seg->frontsector; gl_backsector = portal->seg->backsector; + HWR_ProcessSeg(); gl_drawing_stencil = false; + // need to work around the r_opengl PF_Invisible bug with this call // similarly as in the linkdraw hack in HWR_DrawSprites HWD.pfnSetBlend(PF_Translucent|PF_Occlude|PF_Masked); @@ -171,7 +175,7 @@ void HWR_RenderPortal(gl_portal_t* portal, gl_portal_t* rootportal, const float HWR_PortalFrame(rootportal); else // current frame is not a portal frame but the main view! { - R_SetupFrame(player, false); + R_SetupFrame(viewssnum, false); portalclipline = NULL; } diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index d918addef..f60fd3a77 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -1010,6 +1010,7 @@ void SetStates(void) pglScalef(1.0f, 1.0f, -1.0f); pglGetFloatv(GL_MODELVIEW_MATRIX, modelMatrix); // added for new coronas' code (without depth buffer) } + // -----------------+ // DeleteTexture : Deletes a texture from the GPU and frees its data // -----------------+ diff --git a/src/hu_stuff.c b/src/hu_stuff.c index e68888c84..9da5f4752 100644 --- a/src/hu_stuff.c +++ b/src/hu_stuff.c @@ -775,10 +775,7 @@ static void Command_Sayteam_f(void) return; } - if (G_GametypeHasTeams()) // revert to normal say if we don't have teams in this gametype. - DoSayCommand(-1, 1, 0); - else - DoSayCommand(0, 1, 0); + DoSayCommand(0, 1, 0); } /** Send a message to everyone, to be displayed by CECHO. Only @@ -1395,7 +1392,7 @@ boolean HU_Responder(event_t *ev) chat_on = true; w_chat_buf[0] = 0; M_TextInputInit(&w_chat, w_chat_buf, sizeof w_chat_buf); - teamtalk = G_GametypeHasTeams(); // Don't teamtalk if we don't have teams. + teamtalk = false; chat_scrollmedown = true; typelines = 1; return true; @@ -2611,7 +2608,6 @@ static inline void HU_DrawSpectatorTicker(void) // static void HU_DrawRankings(void) { - patch_t *p; playersort_t tab[MAXPLAYERS]; INT32 i, j, scorelines, hilicol, numplayersingame = 0; boolean completed[MAXPLAYERS]; @@ -2643,25 +2639,6 @@ static void HU_DrawRankings(void) Z_Free(maptitle); } - if (G_GametypeHasTeams()) - { - if (gametype == GT_CTF) - p = bflagico; - else - p = bmatcico; - - V_DrawSmallScaledPatch(128 - SHORT(p->width)/4, 4, 0, p); - V_DrawCenteredString(128, 16, 0, va("%u", bluescore)); - - if (gametype == GT_CTF) - p = rflagico; - else - p = rmatcico; - - V_DrawSmallScaledPatch(192 - SHORT(p->width)/4, 4, 0, p); - V_DrawCenteredString(192, 16, 0, va("%u", redscore)); - } - if (!G_RaceGametype()) { if (cv_timelimit.value && timelimitintics > 0) diff --git a/src/i_joy.h b/src/i_joy.h index f780d8018..01f29c2cd 100644 --- a/src/i_joy.h +++ b/src/i_joy.h @@ -53,6 +53,6 @@ typedef struct JoyType_s JoyType_t; for palyer[sic] 1-4's joystick/gamepad */ -extern JoyType_t Joystick, Joystick2, Joystick3, Joystick4; +extern JoyType_t Joystick[MAXSPLITSCREENPLAYERS]; #endif // __I_JOY_H__ diff --git a/src/i_net.h b/src/i_net.h index 11dbc6341..504936a3b 100644 --- a/src/i_net.h +++ b/src/i_net.h @@ -82,18 +82,10 @@ extern holepunch_t *holepunchpacket; */ extern boolean (*I_NetGet)(void); -/** \brief ask to driver if there is data waiting -*/ -extern boolean (*I_NetCanGet)(void); - /** \brief send packet within doomcom struct */ extern void (*I_NetSend)(void); -/** \brief ask to driver if all is ok to send data now -*/ -extern boolean (*I_NetCanSend)(void); - /** \brief close a connection \param nodenum node to be closed diff --git a/src/i_system.h b/src/i_system.h index f49bca4a1..baaa0d446 100644 --- a/src/i_system.h +++ b/src/i_system.h @@ -202,9 +202,13 @@ void I_JoyScale4(void); // Called by D_SRB2Main. +/** \brief to startup joystick + */ +void I_InitJoystick(UINT8 index); + /** \brief to startup the first joystick */ -void I_InitJoystick(void); +void I_InitJoystick1(void); /** \brief to startup the second joystick */ @@ -307,21 +311,9 @@ INT32 I_mkdir(const char *dirname, INT32 unixright); */ const char *I_LocateWad(void); -/** \brief First Joystick's events +/** \brief Joystick events */ -void I_GetJoystickEvents(void); - -/** \brief Second Joystick's events -*/ -void I_GetJoystick2Events(void); - -/** \brief Third Joystick's events -*/ -void I_GetJoystick3Events(void); - -/** \brief Fourth Joystick's events -*/ -void I_GetJoystick4Events(void); +void I_GetJoystickEvents(UINT8 index); /** \brief Mouses events */ diff --git a/src/i_tcp.c b/src/i_tcp.c index d7b0d3374..14dd8b5ed 100644 --- a/src/i_tcp.c +++ b/src/i_tcp.c @@ -168,7 +168,6 @@ static UINT8 UPNP_support = TRUE; #endif #include "i_addrinfo.h" -#define SELECTTEST #define DEFAULTPORT "5029" @@ -750,59 +749,6 @@ static boolean SOCK_Get(void) } #endif -// check if we can send (do not go over the buffer) -#ifndef NONET - -static fd_set masterset; - -#ifdef SELECTTEST -static boolean FD_CPY(fd_set *src, fd_set *dst, SOCKET_TYPE *fd, size_t len) -{ - size_t i; - boolean testset = false; - FD_ZERO(dst); - for (i = 0; i < len;i++) - { - if(fd[i] != (SOCKET_TYPE)ERRSOCKET && - FD_ISSET(fd[i], src) && !FD_ISSET(fd[i], dst)) // no checking for dups - { - FD_SET(fd[i], dst); - testset = true; - } - } - return testset; -} - -static boolean SOCK_CanSend(void) -{ - struct timeval timeval_for_select = {0, 0}; - fd_set tset; - int wselect; - - if(!FD_CPY(&masterset, &tset, mysockets, mysocketses)) - return false; - wselect = select(255, NULL, &tset, NULL, &timeval_for_select); - if (wselect >= 1) - return true; - return false; -} - -static boolean SOCK_CanGet(void) -{ - struct timeval timeval_for_select = {0, 0}; - fd_set tset; - int rselect; - - if(!FD_CPY(&masterset, &tset, mysockets, mysocketses)) - return false; - rselect = select(255, &tset, NULL, NULL, &timeval_for_select); - if (rselect >= 1) - return true; - return false; -} -#endif -#endif - #ifndef NONET static inline ssize_t SOCK_SendToAddr(SOCKET_TYPE socket, mysockaddr_t *sockaddr) { @@ -877,7 +823,7 @@ static void SOCK_Send(void) } } #undef ALLOWEDERROR -#endif +#endif //NONET #ifndef NONET static void SOCK_FreeNodenum(INT32 numnode) @@ -1029,7 +975,6 @@ static boolean UDP_Socket(void) mysockets[s] = ERRSOCKET; for (s = 0; s < MAXNETNODES+1; s++) nodesocket[s] = ERRSOCKET; - FD_ZERO(&masterset); s = 0; memset(&hints, 0x00, sizeof (hints)); @@ -1056,7 +1001,6 @@ static boolean UDP_Socket(void) mysockets[s] = UDP_Bind(runp->ai_family, runp->ai_addr, (socklen_t)runp->ai_addrlen); if (mysockets[s] != (SOCKET_TYPE)ERRSOCKET) { - FD_SET(mysockets[s], &masterset); myfamily[s] = hints.ai_family; s++; } @@ -1077,7 +1021,6 @@ static boolean UDP_Socket(void) mysockets[s] = UDP_Bind(runp->ai_family, runp->ai_addr, (socklen_t)runp->ai_addrlen); if (mysockets[s] != (SOCKET_TYPE)ERRSOCKET) { - FD_SET(mysockets[s], &masterset); myfamily[s] = hints.ai_family; s++; #ifdef HAVE_MINIUPNPC @@ -1110,7 +1053,6 @@ static boolean UDP_Socket(void) mysockets[s] = UDP_Bind(runp->ai_family, runp->ai_addr, (socklen_t)runp->ai_addrlen); if (mysockets[s] != (SOCKET_TYPE)ERRSOCKET) { - FD_SET(mysockets[s], &masterset); myfamily[s] = hints.ai_family; s++; } @@ -1131,7 +1073,6 @@ static boolean UDP_Socket(void) mysockets[s] = UDP_Bind(runp->ai_family, runp->ai_addr, (socklen_t)runp->ai_addrlen); if (mysockets[s] != (SOCKET_TYPE)ERRSOCKET) { - FD_SET(mysockets[s], &masterset); myfamily[s] = hints.ai_family; s++; } @@ -1298,16 +1239,15 @@ boolean I_InitTcpDriver(void) static void SOCK_CloseSocket(void) { size_t i; - for (i=0; i < MAXNETNODES+1; i++) + + for (i = 0; i < mysocketses; i++) { - if (mysockets[i] != (SOCKET_TYPE)ERRSOCKET - && FD_ISSET(mysockets[i], &masterset)) - { - FD_CLR(mysockets[i], &masterset); + if (mysockets[i] != (SOCKET_TYPE)ERRSOCKET) close(mysockets[i]); - } mysockets[i] = ERRSOCKET; } + + mysocketses = 0; } #endif @@ -1417,9 +1357,7 @@ static void rendezvous(int size) if (tic == refreshtic) { - #ifdef HOLEPUNCH holepunchpacket->magic = hole_punch_magic; - #endif sendto(mysockets[0], doomcom->data, size, 0, &rzv.any, sizeof rzv.ip4); } @@ -1444,7 +1382,6 @@ static void SOCK_RegisterHolePunch(void) rendezvous(4); } #endif - #endif static boolean SOCK_OpenSocket(void) @@ -1464,13 +1401,7 @@ static boolean SOCK_OpenSocket(void) I_NetFreeNodenum = SOCK_FreeNodenum; I_NetMakeNodewPort = SOCK_NetMakeNodewPort; -#ifdef SELECTTEST - // seem like not work with libsocket : ( - I_NetCanSend = SOCK_CanSend; - I_NetCanGet = SOCK_CanGet; -#endif #ifdef HOLEPUNCH - I_NetRequestHolePunch = SOCK_RequestHolePunch; I_NetRegisterHolePunch = SOCK_RegisterHolePunch; #endif diff --git a/src/info.c b/src/info.c index f8cb9a6f1..91fb99b5a 100644 --- a/src/info.c +++ b/src/info.c @@ -66,7 +66,7 @@ char sprnames[NUMSPRITES + 1][5] = "CNDL","DOCH","DUCK","GTRE","CHES","CHIM","DRGN","LZMN","PGSS","ZTCH", "MKMA","MKMP","RTCH","BOWL","BOWH","BRRL","BRRR","HRSE","TOAH","BFRT", "OFRT","RFRT","PFRT","ASPK","HBST","HBSO","HBSF","WBLZ","WBLN","OPUL", - "TGEM","TCOI","FWRK","XMS4","XMS5","VIEW" + "TGEM","TCOI","FWRK","XMS4","XMS5","VIEW", }; // Doesn't work with g++, needs actionf_p1 (don't modify this comment) diff --git a/src/k_kart.c b/src/k_kart.c index 1956dfb12..9ec6f6c7b 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -497,10 +497,9 @@ UINT8 colortranslations[MAXTRANSLATIONS][16] = { */ void K_RainbowColormap(UINT8 *dest_colormap, UINT8 skincolor) { - INT32 i; + INT32 i, j; RGBA_t color; UINT8 brightness; - INT32 j; UINT8 colorbrightnesses[16]; UINT16 brightdif; INT32 temp; @@ -523,6 +522,7 @@ void K_RainbowColormap(UINT8 *dest_colormap, UINT8 skincolor) color = V_GetColor(i); SETBRIGHTNESS(brightness, color.s.red, color.s.green, color.s.blue); brightdif = 256; + for (j = 0; j < 16; j++) { temp = abs((INT16)brightness - (INT16)colorbrightnesses[j]); @@ -2060,6 +2060,38 @@ void K_MomentumToFacing(player_t *player) player->mo->momy = FixedMul(player->mo->momy - player->cmomy, player->mo->friction) + player->cmomy; } +static inline fixed_t K_GetProjectileSpeed(void) +{ + switch (gamespeed) + { + case 0: + return 68*mapobjectscale; // Avg Speed is 34 + break; + case 2: + return 96*mapobjectscale; // Avg Speed is 48 + break; + default: + return 82*mapobjectscale; // Avg Speed is 41 + break; + } +} + +static inline fixed_t K_GetSneakerBoostSpeed(void) +{ + switch (gamespeed) + { + case 0: + return 53740+768; + break; + case 2: + return 17294+768; + break; + default: + return 32768; + break; + } +} + // sets k_boostpower, k_speedboost, and k_accelboost to whatever we need it to be static void K_GetKartBoostPower(player_t *player) { @@ -2093,18 +2125,7 @@ static void K_GetKartBoostPower(player_t *player) if (player->kartstuff[k_sneakertimer]) // Sneaker { - switch (gamespeed) - { - case 0: - speedboost = max(speedboost, 53740+768); - break; - case 2: - speedboost = max(speedboost, 17294+768); - break; - default: - speedboost = max(speedboost, 32768); - break; - } + speedboost = max(speedboost, K_GetSneakerBoostSpeed()); accelboost = max(accelboost, 8*FRACUNIT); // + 800% } @@ -3595,18 +3616,7 @@ static mobj_t *K_ThrowKartItem(player_t *player, boolean missile, mobjtype_t map } else { - switch (gamespeed) - { - case 0: - PROJSPEED = 68*mapobjectscale; // Avg Speed is 34 - break; - case 2: - PROJSPEED = 96*mapobjectscale; // Avg Speed is 48 - break; - default: - PROJSPEED = 82*mapobjectscale; // Avg Speed is 41 - break; - } + PROJSPEED = K_GetProjectileSpeed(); } if (altthrow) @@ -3834,18 +3844,7 @@ void K_PuntMine(mobj_t *thismine, mobj_t *punter) if (!mine || P_MobjWasRemoved(mine)) return; - switch (gamespeed) - { - case 0: - spd = 68*mapobjectscale; // Avg Speed is 34 - break; - case 2: - spd = 96*mapobjectscale; // Avg Speed is 48 - break; - default: - spd = 82*mapobjectscale; // Avg Speed is 41 - break; - } + spd = K_GetProjectileSpeed(); mine->flags |= MF_NOCLIPTHING; @@ -3992,20 +3991,7 @@ static void K_DoHyudoroSteal(player_t *player) void K_DoSneaker(player_t *player, INT32 type) { - fixed_t intendedboost; - - switch (gamespeed) - { - case 0: - intendedboost = 53740+768; - break; - case 2: - intendedboost = 17294+768; - break; - default: - intendedboost = 32768; - break; - } + const fixed_t intendedboost = K_GetSneakerBoostSpeed(); if (!player->kartstuff[k_floorboost] || player->kartstuff[k_floorboost] == 3) { @@ -4786,10 +4772,6 @@ player_t *K_FindJawzTarget(mobj_t *actor, player_t *source) if (player == source) continue; - // Don't home in on teammates. - if (G_GametypeHasTeams() && source->ctfteam == player->ctfteam) - continue; - // Invisible, don't bother if (player->kartstuff[k_hyudorotimer]) continue; diff --git a/src/lua_baselib.c b/src/lua_baselib.c index 1e60863ef..13e578d5c 100644 --- a/src/lua_baselib.c +++ b/src/lua_baselib.c @@ -455,14 +455,7 @@ static int lib_pSpawnAlteredDirectionMissile(lua_State *L) static int lib_pColorTeamMissile(lua_State *L) { - mobj_t *missile = *((mobj_t **)luaL_checkudata(L, 1, META_MOBJ)); - player_t *source = *((player_t **)luaL_checkudata(L, 2, META_PLAYER)); - NOHUD - if (!missile) - return LUA_ErrInvalid(L, "mobj_t"); - if (!source) - return LUA_ErrInvalid(L, "player_t"); - P_ColorTeamMissile(missile, source); + (void)L; return 0; } @@ -1246,12 +1239,7 @@ static int lib_pPlayerEmeraldBurst(lua_State *L) static int lib_pPlayerFlagBurst(lua_State *L) { - player_t *player = *((player_t **)luaL_checkudata(L, 1, META_PLAYER)); - boolean toss = lua_optboolean(L, 2); - NOHUD - if (!player) - return LUA_ErrInvalid(L, "player_t"); - P_PlayerFlagBurst(player, toss); + (void)L; return 0; } @@ -1817,7 +1805,7 @@ static int lib_sStartSoundAtVolume(lua_State *L) return LUA_ErrInvalid(L, "player_t"); } if (!player || P_IsLocalPlayer(player)) - S_StartSoundAtVolume(origin, sound_id, volume); + S_StartSoundAtVolume(origin, sound_id, volume); return 0; } @@ -1919,7 +1907,7 @@ static int lib_sChangeMusic(lua_State *L) music_flags = (UINT16)((music_num & 0x7FFF0000) >> 16); else #endif - music_flags = (UINT16)luaL_optinteger(L, 4, 0); + music_flags = (UINT16)luaL_optinteger(L, 4, 0); position = (UINT32)luaL_optinteger(L, 5, 0); prefadems = (UINT32)luaL_optinteger(L, 6, 0); @@ -2446,14 +2434,14 @@ static int lib_gIsSpecialStage(lua_State *L) static int lib_gGametypeUsesLives(lua_State *L) { //HUDSAFE - lua_pushboolean(L, G_GametypeUsesLives()); + lua_pushboolean(L, false); return 1; } static int lib_gGametypeHasTeams(lua_State *L) { //HUDSAFE - lua_pushboolean(L, G_GametypeHasTeams()); + lua_pushboolean(L, false); return 1; } @@ -2481,7 +2469,7 @@ static int lib_gRaceGametype(lua_State *L) static int lib_gTagGametype(lua_State *L) { //HUDSAFE - lua_pushboolean(L, G_TagGametype()); + lua_pushboolean(L, false); return 1; } @@ -3154,7 +3142,6 @@ static luaL_Reg lib[] = { {"P_LookForEnemies",lib_pLookForEnemies}, {"P_NukeEnemies",lib_pNukeEnemies}, {"P_HomingAttack",lib_pHomingAttack}, - //{"P_SuperReady",lib_pSuperReady}, {"P_Telekinesis",lib_pTelekinesis}, // p_map diff --git a/src/lua_consolelib.c b/src/lua_consolelib.c index f2fb03dc6..4c29ee317 100644 --- a/src/lua_consolelib.c +++ b/src/lua_consolelib.c @@ -169,7 +169,7 @@ void COM_Lua_f(void) for (i = 0; i < argc; i++) WRITESTRINGN(p, COM_Argv(i), 255); if (flags & 2) - SendNetXCmd2(XD_LUACMD, buf, p-buf); + SendNetXCmdForPlayer(1, XD_LUACMD, buf, p-buf); else SendNetXCmd(XD_LUACMD, buf, p-buf); free(buf); diff --git a/src/m_cheat.c b/src/m_cheat.c index abada4be5..9d0ea6a26 100644 --- a/src/m_cheat.c +++ b/src/m_cheat.c @@ -945,9 +945,6 @@ boolean OP_FreezeObjectplace(void) if (!objectplacing) return false; - if ((maptol & TOL_NIGHTS) && (players[consoleplayer].pflags & PF_NIGHTSMODE)) - return false; - return true; } @@ -1091,7 +1088,7 @@ void OP_ObjectplaceMovement(player_t *player) { ticcmd_t *cmd = &player->cmd; - if (!player->climbing && (netgame || !cv_analog.value || (player->pflags & PF_SPINNING))) + if (!player->climbing && (netgame || (player->pflags & PF_SPINNING))) player->mo->angle = (cmd->angleturn<<16 /* not FRACBITS */); ticruned++; diff --git a/src/m_menu.c b/src/m_menu.c index 530cb98fb..41285f2a9 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -1224,19 +1224,19 @@ static menuitem_t OP_AllControlsMenu[] = static menuitem_t OP_Joystick1Menu[] = { {IT_STRING | IT_CALL, NULL, "Select Gamepad..." , M_Setup1PJoystickMenu, 10}, - {IT_STRING | IT_CVAR, NULL, "Aim Forward/Back" , &cv_aimaxis , 20}, - {IT_STRING | IT_CVAR, NULL, "Turn Left/Right" , &cv_turnaxis , 25}, - {IT_STRING | IT_CVAR, NULL, "Accelerate" , &cv_moveaxis , 30}, - {IT_STRING | IT_CVAR, NULL, "Brake" , &cv_brakeaxis , 35}, - {IT_STRING | IT_CVAR, NULL, "Drift" , &cv_driftaxis , 40}, - {IT_STRING | IT_CVAR, NULL, "Use Item" , &cv_fireaxis , 45}, - {IT_STRING | IT_CVAR, NULL, "Look Backward" , &cv_lookbackaxis , 50}, - {IT_STRING | IT_CVAR, NULL, "Spec. Look Up/Down" , &cv_lookaxis , 55}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 1" , &cv_custom1axis , 60}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 2" , &cv_custom2axis , 65}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 3" , &cv_custom3axis , 70}, - {IT_STRING | IT_CVAR, NULL, "X deadzone" , &cv_xdeadzone , 75}, - {IT_STRING | IT_CVAR, NULL, "Y deadzone" , &cv_ydeadzone , 80}, + {IT_STRING | IT_CVAR, NULL, "Aim Forward/Back" , &cv_aimaxis[0] , 20}, + {IT_STRING | IT_CVAR, NULL, "Turn Left/Right" , &cv_turnaxis[0] , 25}, + {IT_STRING | IT_CVAR, NULL, "Accelerate" , &cv_moveaxis[0] , 30}, + {IT_STRING | IT_CVAR, NULL, "Brake" , &cv_brakeaxis[0] , 35}, + {IT_STRING | IT_CVAR, NULL, "Drift" , &cv_driftaxis[0] , 40}, + {IT_STRING | IT_CVAR, NULL, "Use Item" , &cv_fireaxis[0] , 45}, + {IT_STRING | IT_CVAR, NULL, "Look Backward" , &cv_lookbackaxis[0] , 50}, + {IT_STRING | IT_CVAR, NULL, "Spec. Look Up/Down" , &cv_lookaxis[0] , 55}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 1" , &cv_custom1axis[0] , 60}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 2" , &cv_custom2axis[0] , 65}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 3" , &cv_custom3axis[0] , 70}, + {IT_STRING | IT_CVAR, NULL, "X deadzone" , &cv_xdeadzone[0] , 75}, + {IT_STRING | IT_CVAR, NULL, "Y deadzone" , &cv_ydeadzone[0] , 80}, {IT_STRING | IT_CVAR, NULL, "Controller Rumble" , &cv_rumble[0] , 90}, {IT_STRING | IT_CVAR, NULL, "Set LED to skin color" , &cv_gamepadled[0] , 95}, @@ -1246,19 +1246,19 @@ static menuitem_t OP_Joystick1Menu[] = static menuitem_t OP_Joystick2Menu[] = { {IT_STRING | IT_CALL, NULL, "Select Gamepad..." , M_Setup2PJoystickMenu, 10}, - {IT_STRING | IT_CVAR, NULL, "Aim Forward/Back" , &cv_aimaxis2 , 20}, - {IT_STRING | IT_CVAR, NULL, "Turn Left/Right" , &cv_turnaxis2 , 25}, - {IT_STRING | IT_CVAR, NULL, "Accelerate" , &cv_moveaxis2 , 30}, - {IT_STRING | IT_CVAR, NULL, "Brake" , &cv_brakeaxis2 , 35}, - {IT_STRING | IT_CVAR, NULL, "Drift" , &cv_driftaxis2 , 40}, - {IT_STRING | IT_CVAR, NULL, "Use Item" , &cv_fireaxis2 , 45}, - {IT_STRING | IT_CVAR, NULL, "Look Backward" , &cv_lookbackaxis2 , 50}, - {IT_STRING | IT_CVAR, NULL, "Spec. Look Up/Down" , &cv_lookaxis2 , 55}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 1" , &cv_custom1axis2 , 60}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 2" , &cv_custom2axis2 , 65}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 3" , &cv_custom3axis2 , 70}, - {IT_STRING | IT_CVAR, NULL, "X deadzone" , &cv_xdeadzone2 , 75}, - {IT_STRING | IT_CVAR, NULL, "Y deadzone" , &cv_ydeadzone2 , 80}, + {IT_STRING | IT_CVAR, NULL, "Aim Forward/Back" , &cv_aimaxis[1] , 20}, + {IT_STRING | IT_CVAR, NULL, "Turn Left/Right" , &cv_turnaxis[1] , 25}, + {IT_STRING | IT_CVAR, NULL, "Accelerate" , &cv_moveaxis[1] , 30}, + {IT_STRING | IT_CVAR, NULL, "Brake" , &cv_brakeaxis[1] , 35}, + {IT_STRING | IT_CVAR, NULL, "Drift" , &cv_driftaxis[1] , 40}, + {IT_STRING | IT_CVAR, NULL, "Use Item" , &cv_fireaxis[1] , 45}, + {IT_STRING | IT_CVAR, NULL, "Look Backward" , &cv_lookbackaxis[1] , 50}, + {IT_STRING | IT_CVAR, NULL, "Spec. Look Up/Down" , &cv_lookaxis[1] , 55}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 1" , &cv_custom1axis[1] , 60}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 2" , &cv_custom2axis[1] , 65}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 3" , &cv_custom3axis[1] , 70}, + {IT_STRING | IT_CVAR, NULL, "X deadzone" , &cv_xdeadzone[1] , 75}, + {IT_STRING | IT_CVAR, NULL, "Y deadzone" , &cv_ydeadzone[1] , 80}, {IT_STRING | IT_CVAR, NULL, "Controller Rumble" , &cv_rumble[1] , 90}, {IT_STRING | IT_CVAR, NULL, "Set LED to skin color" , &cv_gamepadled[1] , 95}, @@ -1268,19 +1268,19 @@ static menuitem_t OP_Joystick2Menu[] = static menuitem_t OP_Joystick3Menu[] = { {IT_STRING | IT_CALL, NULL, "Select Gamepad..." , M_Setup3PJoystickMenu, 10}, - {IT_STRING | IT_CVAR, NULL, "Aim Forward/Back" , &cv_aimaxis3 , 20}, - {IT_STRING | IT_CVAR, NULL, "Turn Left/Right" , &cv_turnaxis3 , 25}, - {IT_STRING | IT_CVAR, NULL, "Accelerate" , &cv_moveaxis3 , 30}, - {IT_STRING | IT_CVAR, NULL, "Brake" , &cv_brakeaxis3 , 35}, - {IT_STRING | IT_CVAR, NULL, "Drift" , &cv_driftaxis3 , 40}, - {IT_STRING | IT_CVAR, NULL, "Use Item" , &cv_fireaxis3 , 45}, - {IT_STRING | IT_CVAR, NULL, "Look Backward" , &cv_lookbackaxis3 , 50}, - {IT_STRING | IT_CVAR, NULL, "Spec. Look Up/Down" , &cv_lookaxis3 , 55}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 1" , &cv_custom1axis3 , 60}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 2" , &cv_custom2axis3 , 65}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 3" , &cv_custom3axis3 , 70}, - {IT_STRING | IT_CVAR, NULL, "X deadzone" , &cv_xdeadzone3 , 75}, - {IT_STRING | IT_CVAR, NULL, "Y deadzone" , &cv_ydeadzone3 , 80}, + {IT_STRING | IT_CVAR, NULL, "Aim Forward/Back" , &cv_aimaxis[2] , 20}, + {IT_STRING | IT_CVAR, NULL, "Turn Left/Right" , &cv_turnaxis[2] , 25}, + {IT_STRING | IT_CVAR, NULL, "Accelerate" , &cv_moveaxis[2] , 30}, + {IT_STRING | IT_CVAR, NULL, "Brake" , &cv_brakeaxis[2] , 35}, + {IT_STRING | IT_CVAR, NULL, "Drift" , &cv_driftaxis[2] , 40}, + {IT_STRING | IT_CVAR, NULL, "Use Item" , &cv_fireaxis[2] , 45}, + {IT_STRING | IT_CVAR, NULL, "Look Backward" , &cv_lookbackaxis[2] , 50}, + {IT_STRING | IT_CVAR, NULL, "Spec. Look Up/Down" , &cv_lookaxis[2] , 55}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 1" , &cv_custom1axis[2] , 60}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 2" , &cv_custom2axis[2] , 65}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 3" , &cv_custom3axis[2] , 70}, + {IT_STRING | IT_CVAR, NULL, "X deadzone" , &cv_xdeadzone[2] , 75}, + {IT_STRING | IT_CVAR, NULL, "Y deadzone" , &cv_ydeadzone[2] , 80}, {IT_STRING | IT_CVAR, NULL, "Controller Rumble" , &cv_rumble[2] , 90}, {IT_STRING | IT_CVAR, NULL, "Set LED to skin color" , &cv_gamepadled[2] , 95}, @@ -1290,19 +1290,19 @@ static menuitem_t OP_Joystick3Menu[] = static menuitem_t OP_Joystick4Menu[] = { {IT_STRING | IT_CALL, NULL, "Select Gamepad..." , M_Setup4PJoystickMenu, 10}, - {IT_STRING | IT_CVAR, NULL, "Aim Forward/Back" , &cv_aimaxis4 , 20}, - {IT_STRING | IT_CVAR, NULL, "Turn Left/Right" , &cv_turnaxis4 , 25}, - {IT_STRING | IT_CVAR, NULL, "Accelerate" , &cv_moveaxis4 , 30}, - {IT_STRING | IT_CVAR, NULL, "Brake" , &cv_brakeaxis4 , 35}, - {IT_STRING | IT_CVAR, NULL, "Drift" , &cv_driftaxis4 , 40}, - {IT_STRING | IT_CVAR, NULL, "Use Item" , &cv_fireaxis4 , 45}, - {IT_STRING | IT_CVAR, NULL, "Look Backward" , &cv_lookbackaxis4 , 50}, - {IT_STRING | IT_CVAR, NULL, "Spec. Look Up/Down" , &cv_lookaxis4 , 55}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 1" , &cv_custom1axis4 , 60}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 2" , &cv_custom2axis4 , 65}, - {IT_STRING | IT_CVAR, NULL, "Custom Button 3" , &cv_custom3axis4 , 70}, - {IT_STRING | IT_CVAR, NULL, "X deadzone" , &cv_xdeadzone4 , 75}, - {IT_STRING | IT_CVAR, NULL, "Y deadzone" , &cv_ydeadzone4 , 80}, + {IT_STRING | IT_CVAR, NULL, "Aim Forward/Back" , &cv_aimaxis[3] , 20}, + {IT_STRING | IT_CVAR, NULL, "Turn Left/Right" , &cv_turnaxis[3] , 25}, + {IT_STRING | IT_CVAR, NULL, "Accelerate" , &cv_moveaxis[3] , 30}, + {IT_STRING | IT_CVAR, NULL, "Brake" , &cv_brakeaxis[3] , 35}, + {IT_STRING | IT_CVAR, NULL, "Drift" , &cv_driftaxis[3] , 40}, + {IT_STRING | IT_CVAR, NULL, "Use Item" , &cv_fireaxis[3] , 45}, + {IT_STRING | IT_CVAR, NULL, "Look Backward" , &cv_lookbackaxis[3] , 50}, + {IT_STRING | IT_CVAR, NULL, "Spec. Look Up/Down" , &cv_lookaxis[3] , 55}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 1" , &cv_custom1axis[3] , 60}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 2" , &cv_custom2axis[3] , 65}, + {IT_STRING | IT_CVAR, NULL, "Custom Button 3" , &cv_custom3axis[3] , 70}, + {IT_STRING | IT_CVAR, NULL, "X deadzone" , &cv_xdeadzone[3] , 75}, + {IT_STRING | IT_CVAR, NULL, "Y deadzone" , &cv_ydeadzone[3] , 80}, {IT_STRING | IT_CVAR, NULL, "Controller Rumble" , &cv_rumble[3] , 90}, {IT_STRING | IT_CVAR, NULL, "Set LED to skin color" , &cv_gamepadled[3] , 95}, @@ -1872,52 +1872,52 @@ static menuitem_t OP_Player1CamOptionsMenu[] = { {IT_HEADER, NULL, "Player 1 Camera Options", NULL, 0}, - {IT_STRING | IT_CVAR, NULL, "Flipcam", &cv_flipcam, 30}, - {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Distance", &cv_cam_dist, 40}, - {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Height", &cv_cam_height, 50}, - {IT_STRING | IT_CVAR, NULL, "Camera Speed", &cv_cam_speed, 60}, - {IT_STRING | IT_CVAR, NULL, "Camera Rotation Speed", &cv_cam_rotspeed, 70}, + {IT_STRING | IT_CVAR, NULL, "Flipcam", &cv_flipcam[0], 30}, + {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Distance", &cv_cam_dist[0], 40}, + {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Height", &cv_cam_height[0], 50}, + {IT_STRING | IT_CVAR, NULL, "Camera Speed", &cv_cam_speed[0], 60}, + {IT_STRING | IT_CVAR, NULL, "Camera Rotation Speed", &cv_cam_rotspeed[0], 70}, - {IT_STRING | IT_CVAR, NULL, "Third Person Camera", &cv_chasecam, 85}, + {IT_STRING | IT_CVAR, NULL, "Third Person Camera", &cv_chasecam[0], 85}, }; static menuitem_t OP_Player2CamOptionsMenu[] = { {IT_HEADER, NULL, "Player 2 Camera Options", NULL, 0}, - {IT_STRING | IT_CVAR, NULL, "Flipcam", &cv_flipcam2, 30}, - {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Distance", &cv_cam2_dist, 40}, - {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Height", &cv_cam2_height, 50}, - {IT_STRING | IT_CVAR, NULL, "Camera Speed", &cv_cam2_speed, 60}, - {IT_STRING | IT_CVAR, NULL, "Camera Rotation Speed", &cv_cam2_rotspeed, 70}, + {IT_STRING | IT_CVAR, NULL, "Flipcam", &cv_flipcam[1], 30}, + {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Distance", &cv_cam_dist[1], 40}, + {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Height", &cv_cam_height[1], 50}, + {IT_STRING | IT_CVAR, NULL, "Camera Speed", &cv_cam_speed[1], 60}, + {IT_STRING | IT_CVAR, NULL, "Camera Rotation Speed", &cv_cam_rotspeed[1], 70}, - {IT_STRING | IT_CVAR, NULL, "Third Person Camera", &cv_chasecam2, 85}, + {IT_STRING | IT_CVAR, NULL, "Third Person Camera", &cv_chasecam[1], 85}, }; static menuitem_t OP_Player3CamOptionsMenu[] = { {IT_HEADER, NULL, "Player 3 Camera Options", NULL, 0}, - {IT_STRING | IT_CVAR, NULL, "Flipcam", &cv_flipcam3, 30}, - {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Distance", &cv_cam3_dist, 40}, - {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Height", &cv_cam3_height, 50}, - {IT_STRING | IT_CVAR, NULL, "Camera Speed", &cv_cam3_speed, 60}, - {IT_STRING | IT_CVAR, NULL, "Camera Rotation Speed", &cv_cam3_rotspeed, 70}, + {IT_STRING | IT_CVAR, NULL, "Flipcam", &cv_flipcam[2], 30}, + {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Distance", &cv_cam_dist[2], 40}, + {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Height", &cv_cam_height[2], 50}, + {IT_STRING | IT_CVAR, NULL, "Camera Speed", &cv_cam_speed[2], 60}, + {IT_STRING | IT_CVAR, NULL, "Camera Rotation Speed", &cv_cam_rotspeed[2], 70}, - {IT_STRING | IT_CVAR, NULL, "Third Person Camera", &cv_chasecam3, 85}, + {IT_STRING | IT_CVAR, NULL, "Third Person Camera", &cv_chasecam[2], 85}, }; static menuitem_t OP_Player4CamOptionsMenu[] = { {IT_HEADER, NULL, "Player 4 Camera Options", NULL, 0}, - {IT_STRING | IT_CVAR, NULL, "Flipcam", &cv_flipcam4, 30}, - {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Distance", &cv_cam4_dist, 40}, - {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Height", &cv_cam4_height, 50}, - {IT_STRING | IT_CVAR, NULL, "Camera Speed", &cv_cam4_speed, 60}, - {IT_STRING | IT_CVAR, NULL, "Camera Rotation Speed", &cv_cam4_rotspeed, 70}, + {IT_STRING | IT_CVAR, NULL, "Flipcam", &cv_flipcam[3], 30}, + {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Distance", &cv_cam_dist[3], 40}, + {IT_STRING | IT_CVAR | IT_CV_BIGFLOAT, NULL, "Camera Height", &cv_cam_height[3], 50}, + {IT_STRING | IT_CVAR, NULL, "Camera Speed", &cv_cam_speed[3], 60}, + {IT_STRING | IT_CVAR, NULL, "Camera Rotation Speed", &cv_cam_rotspeed[3], 70}, - {IT_STRING | IT_CVAR, NULL, "Third Person Camera", &cv_chasecam4, 85}, + {IT_STRING | IT_CVAR, NULL, "Third Person Camera", &cv_chasecam[3], 85}, }; static const char* OP_PlayerCamOptionsTooltips[] = @@ -3324,34 +3324,19 @@ static void Newgametype_OnChange(void) P_AllocMapHeader((INT16)(cv_nextmap.value-1)); if ((cv_newgametype.value == GT_RACE && !(mapheaderinfo[cv_nextmap.value-1]->typeoflevel & TOL_RACE)) || // SRB2kart - ((cv_newgametype.value == GT_MATCH || cv_newgametype.value == GT_TEAMMATCH) && !(mapheaderinfo[cv_nextmap.value-1]->typeoflevel & TOL_MATCH))) + (cv_newgametype.value == GT_MATCH && !(mapheaderinfo[cv_nextmap.value-1]->typeoflevel & TOL_MATCH))) { INT32 value = 0; switch (cv_newgametype.value) { - case GT_COOP: - value = TOL_RACE; // SRB2kart - break; - case GT_COMPETITION: - value = TOL_COMPETITION; - break; case GT_RACE: value = TOL_RACE; break; case GT_MATCH: - case GT_TEAMMATCH: value = TOL_MATCH; break; - case GT_TAG: - case GT_HIDEANDSEEK: - value = TOL_TAG; - break; - case GT_CTF: - value = TOL_CTF; - break; } - CV_SetValue(&cv_nextmap, M_FindFirstMap(value)); } } @@ -3740,14 +3725,14 @@ boolean M_Responder(event_t *ev) tic_t thistime = I_GetTime(); if (ev->type == ev_joystick) { - const INT32 jxdeadzone = ((JOYAXISRANGE-1) * max(cv_xdeadzone.value, FRACUNIT/2)) >> FRACBITS; - const INT32 jydeadzone = ((JOYAXISRANGE-1) * max(cv_ydeadzone.value, FRACUNIT/2)) >> FRACBITS; - INT32 accelaxis = abs(cv_moveaxis.value); + const INT32 jxdeadzone = ((JOYAXISRANGE-1) * max(cv_xdeadzone[0].value, FRACUNIT/2)) >> FRACBITS; + const INT32 jydeadzone = ((JOYAXISRANGE-1) * max(cv_ydeadzone[0].value, FRACUNIT/2)) >> FRACBITS; + INT32 accelaxis = abs(cv_moveaxis[0].value); if (ev->data1 == 0) { if (ev->data3 != INT32_MAX) { - if (Joystick.bGamepadStyle || abs(ev->data3) > jydeadzone) + if (Joystick[0].bGamepadStyle || abs(ev->data3) > jydeadzone) { if (joywaity < thistime && (pjoyy == 0 || (ev->data3 < 0) != (pjoyy < 0))) // no previous direction OR change direction @@ -3763,7 +3748,7 @@ boolean M_Responder(event_t *ev) if (ev->data2 != INT32_MAX && joywaitx < thistime) { - if (Joystick.bGamepadStyle || abs(ev->data2) > jxdeadzone) + if (Joystick[0].bGamepadStyle || abs(ev->data2) > jxdeadzone) { if (joywaitx < thistime && (pjoyx == 0 || (ev->data2 < 0) != (pjoyx < 0))) // no previous direction OR change direction @@ -3791,10 +3776,10 @@ boolean M_Responder(event_t *ev) retaxis = xmode ? ev->data2 : ev->data3; if (retaxis != INT32_MAX) { - if (cv_moveaxis.value < 0) + if (cv_moveaxis[0].value < 0) retaxis = -retaxis; - if (Joystick.bGamepadStyle || retaxis > jacceldeadzone) + if (Joystick[0].bGamepadStyle || retaxis > jacceldeadzone) { if (joywaitaccel < thistime && retaxis > pjoyaccel) // only on upwards event { @@ -4472,9 +4457,6 @@ void M_StartControlPanel(void) { MPauseMenu[mpause_switchmap].status = IT_STRING | IT_CALL; MPauseMenu[mpause_addons].status = IT_STRING | IT_CALL; - - if (G_GametypeHasTeams()) - MPauseMenu[mpause_scramble].status = IT_STRING | IT_SUBMENU; } if (server || (!cv_showlocalskinmenus.value)) @@ -4495,16 +4477,7 @@ void M_StartControlPanel(void) if (netgame) { - if (G_GametypeHasTeams()) - { - MPauseMenu[mpause_switchteam].status = IT_STRING | IT_SUBMENU; - MPauseMenu[mpause_switchteam].alphaKey += ((splitscreen+1) * 8); - MPauseMenu[mpause_localskin].alphaKey += 8; - MPauseMenu[mpause_options].alphaKey += 8; - MPauseMenu[mpause_title].alphaKey += 8; - MPauseMenu[mpause_quit].alphaKey += 8; - } - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) { MPauseMenu[mpause_switchspectate].status = IT_STRING | IT_SUBMENU; MPauseMenu[mpause_switchspectate].alphaKey += ((splitscreen+1) * 8); @@ -4538,9 +4511,7 @@ void M_StartControlPanel(void) { MPauseMenu[mpause_psetup].status = IT_STRING | IT_CALL; - if (G_GametypeHasTeams()) - MPauseMenu[mpause_switchteam].status = IT_STRING | IT_SUBMENU; - else if (G_GametypeHasSpectators()) + if (G_GametypeHasSpectators()) { if (!players[consoleplayer].spectator) MPauseMenu[mpause_spectate].status = IT_STRING | IT_CALL; @@ -5683,7 +5654,7 @@ boolean M_CanShowLevelInList(INT32 mapnum, INT32 gt) if (M_MapLocked(mapnum+1)) // not unlocked return cv_showallmaps.value; - if ((gt == GT_MATCH || gt == GT_TEAMMATCH) && (mapheaderinfo[mapnum]->typeoflevel & TOL_MATCH)) + if (gt == GT_MATCH && (mapheaderinfo[mapnum]->typeoflevel & TOL_MATCH)) return true; if (gt == GT_RACE && (mapheaderinfo[mapnum]->typeoflevel & TOL_RACE)) @@ -11836,30 +11807,30 @@ static void M_DrawJoystick(void) //M_DrawSaveLoadBorder(OP_JoystickSetDef.x, OP_JoystickSetDef.y+LINEHEIGHT*i); #ifdef JOYSTICK_HOTPLUG - if (atoi(cv_usejoystick4.string) > I_NumJoys()) - compareval4 = atoi(cv_usejoystick4.string); + if (atoi(cv_usejoystick[3].string) > I_NumJoys()) + compareval4 = atoi(cv_usejoystick[3].string); else - compareval4 = cv_usejoystick4.value; + compareval4 = cv_usejoystick[3].value; - if (atoi(cv_usejoystick3.string) > I_NumJoys()) - compareval3 = atoi(cv_usejoystick3.string); + if (atoi(cv_usejoystick[2].string) > I_NumJoys()) + compareval3 = atoi(cv_usejoystick[2].string); else - compareval3 = cv_usejoystick3.value; + compareval3 = cv_usejoystick[2].value; - if (atoi(cv_usejoystick2.string) > I_NumJoys()) - compareval2 = atoi(cv_usejoystick2.string); + if (atoi(cv_usejoystick[1].string) > I_NumJoys()) + compareval2 = atoi(cv_usejoystick[1].string); else - compareval2 = cv_usejoystick2.value; + compareval2 = cv_usejoystick[1].value; - if (atoi(cv_usejoystick.string) > I_NumJoys()) - compareval = atoi(cv_usejoystick.string); + if (atoi(cv_usejoystick[0].string) > I_NumJoys()) + compareval = atoi(cv_usejoystick[0].string); else - compareval = cv_usejoystick.value; + compareval = cv_usejoystick[0].value; #else - compareval4 = cv_usejoystick4.value; - compareval3 = cv_usejoystick3.value; - compareval2 = cv_usejoystick2.value; - compareval = cv_usejoystick.value; + compareval4 = cv_usejoystick[3].value; + compareval3 = cv_usejoystick[2].value; + compareval2 = cv_usejoystick[1].value; + compareval = cv_usejoystick[0].value; #endif if ((setupcontrolplayer == 4 && (i == compareval4)) @@ -11897,14 +11868,14 @@ void M_SetupJoystickMenu(INT32 choice) // // Update cv_usejoystick.string here so that the user can // properly change this value. - if (i == cv_usejoystick.value) - CV_SetValue(&cv_usejoystick, i); - if (i == cv_usejoystick2.value) - CV_SetValue(&cv_usejoystick2, i); - if (i == cv_usejoystick3.value) - CV_SetValue(&cv_usejoystick3, i); - if (i == cv_usejoystick4.value) - CV_SetValue(&cv_usejoystick4, i); + if (i == cv_usejoystick[0].value) + CV_SetValue(&cv_usejoystick[0], i); + if (i == cv_usejoystick[1].value) + CV_SetValue(&cv_usejoystick[1], i); + if (i == cv_usejoystick[2].value) + CV_SetValue(&cv_usejoystick[2], i); + if (i == cv_usejoystick[3].value) + CV_SetValue(&cv_usejoystick[3], i); #endif } @@ -11947,27 +11918,27 @@ static void M_AssignJoystick(INT32 choice) if (setupcontrolplayer == 4) { - oldchoice = oldstringchoice = atoi(cv_usejoystick4.string) > numjoys ? atoi(cv_usejoystick4.string) : cv_usejoystick4.value; - CV_SetValue(&cv_usejoystick4, choice); + oldchoice = oldstringchoice = atoi(cv_usejoystick[3].string) > numjoys ? atoi(cv_usejoystick[3].string) : cv_usejoystick[3].value; + CV_SetValue(&cv_usejoystick[3], choice); // Just in case last-minute changes were made to cv_usejoystick.value, // update the string too // But don't do this if we're intentionally setting higher than numjoys if (choice <= numjoys) { - CV_SetValue(&cv_usejoystick4, cv_usejoystick4.value); + CV_SetValue(&cv_usejoystick[3], cv_usejoystick[3].value); // reset this so the comparison is valid if (oldchoice > numjoys) - oldchoice = cv_usejoystick4.value; + oldchoice = cv_usejoystick[3].value; if (oldchoice != choice) { if (choice && oldstringchoice > numjoys) // if we did not select "None", we likely selected a used device - CV_SetValue(&cv_usejoystick4, (oldstringchoice > numjoys ? oldstringchoice : oldchoice)); + CV_SetValue(&cv_usejoystick[3], (oldstringchoice > numjoys ? oldstringchoice : oldchoice)); if (oldstringchoice == - (atoi(cv_usejoystick4.string) > numjoys ? atoi(cv_usejoystick4.string) : cv_usejoystick4.value)) + (atoi(cv_usejoystick[3].string) > numjoys ? atoi(cv_usejoystick[3].string) : cv_usejoystick[3].value)) M_StartMessage("This joystick is used by another\n" "player. Reset the joystick\n" "for that player first.\n\n" @@ -11977,27 +11948,27 @@ static void M_AssignJoystick(INT32 choice) } else if (setupcontrolplayer == 3) { - oldchoice = oldstringchoice = atoi(cv_usejoystick3.string) > numjoys ? atoi(cv_usejoystick3.string) : cv_usejoystick3.value; - CV_SetValue(&cv_usejoystick3, choice); + oldchoice = oldstringchoice = atoi(cv_usejoystick[2].string) > numjoys ? atoi(cv_usejoystick[2].string) : cv_usejoystick[2].value; + CV_SetValue(&cv_usejoystick[2], choice); // Just in case last-minute changes were made to cv_usejoystick.value, // update the string too // But don't do this if we're intentionally setting higher than numjoys if (choice <= numjoys) { - CV_SetValue(&cv_usejoystick3, cv_usejoystick3.value); + CV_SetValue(&cv_usejoystick[2], cv_usejoystick[2].value); // reset this so the comparison is valid if (oldchoice > numjoys) - oldchoice = cv_usejoystick3.value; + oldchoice = cv_usejoystick[2].value; if (oldchoice != choice) { if (choice && oldstringchoice > numjoys) // if we did not select "None", we likely selected a used device - CV_SetValue(&cv_usejoystick3, (oldstringchoice > numjoys ? oldstringchoice : oldchoice)); + CV_SetValue(&cv_usejoystick[2], (oldstringchoice > numjoys ? oldstringchoice : oldchoice)); if (oldstringchoice == - (atoi(cv_usejoystick3.string) > numjoys ? atoi(cv_usejoystick3.string) : cv_usejoystick3.value)) + (atoi(cv_usejoystick[2].string) > numjoys ? atoi(cv_usejoystick[2].string) : cv_usejoystick[2].value)) M_StartMessage("This joystick is used by another\n" "player. Reset the joystick\n" "for that player first.\n\n" @@ -12007,27 +11978,27 @@ static void M_AssignJoystick(INT32 choice) } else if (setupcontrolplayer == 2) { - oldchoice = oldstringchoice = atoi(cv_usejoystick2.string) > numjoys ? atoi(cv_usejoystick2.string) : cv_usejoystick2.value; - CV_SetValue(&cv_usejoystick2, choice); + oldchoice = oldstringchoice = atoi(cv_usejoystick[1].string) > numjoys ? atoi(cv_usejoystick[1].string) : cv_usejoystick[1].value; + CV_SetValue(&cv_usejoystick[1], choice); // Just in case last-minute changes were made to cv_usejoystick.value, // update the string too // But don't do this if we're intentionally setting higher than numjoys if (choice <= numjoys) { - CV_SetValue(&cv_usejoystick2, cv_usejoystick2.value); + CV_SetValue(&cv_usejoystick[1], cv_usejoystick[1].value); // reset this so the comparison is valid if (oldchoice > numjoys) - oldchoice = cv_usejoystick2.value; + oldchoice = cv_usejoystick[1].value; if (oldchoice != choice) { if (choice && oldstringchoice > numjoys) // if we did not select "None", we likely selected a used device - CV_SetValue(&cv_usejoystick2, (oldstringchoice > numjoys ? oldstringchoice : oldchoice)); + CV_SetValue(&cv_usejoystick[1], (oldstringchoice > numjoys ? oldstringchoice : oldchoice)); if (oldstringchoice == - (atoi(cv_usejoystick2.string) > numjoys ? atoi(cv_usejoystick2.string) : cv_usejoystick2.value)) + (atoi(cv_usejoystick[1].string) > numjoys ? atoi(cv_usejoystick[1].string) : cv_usejoystick[1].value)) M_StartMessage("This joystick is used by another\n" "player. Reset the joystick\n" "for that player first.\n\n" @@ -12037,27 +12008,27 @@ static void M_AssignJoystick(INT32 choice) } else if (setupcontrolplayer == 1) { - oldchoice = oldstringchoice = atoi(cv_usejoystick.string) > numjoys ? atoi(cv_usejoystick.string) : cv_usejoystick.value; - CV_SetValue(&cv_usejoystick, choice); + oldchoice = oldstringchoice = atoi(cv_usejoystick[0].string) > numjoys ? atoi(cv_usejoystick[0].string) : cv_usejoystick[0].value; + CV_SetValue(&cv_usejoystick[0], choice); // Just in case last-minute changes were made to cv_usejoystick.value, // update the string too // But don't do this if we're intentionally setting higher than numjoys if (choice <= numjoys) { - CV_SetValue(&cv_usejoystick, cv_usejoystick.value); + CV_SetValue(&cv_usejoystick[0], cv_usejoystick[0].value); // reset this so the comparison is valid if (oldchoice > numjoys) - oldchoice = cv_usejoystick.value; + oldchoice = cv_usejoystick[0].value; if (oldchoice != choice) { if (choice && oldstringchoice > numjoys) // if we did not select "None", we likely selected a used device - CV_SetValue(&cv_usejoystick, (oldstringchoice > numjoys ? oldstringchoice : oldchoice)); + CV_SetValue(&cv_usejoystick[0], (oldstringchoice > numjoys ? oldstringchoice : oldchoice)); if (oldstringchoice == - (atoi(cv_usejoystick.string) > numjoys ? atoi(cv_usejoystick.string) : cv_usejoystick.value)) + (atoi(cv_usejoystick[0].string) > numjoys ? atoi(cv_usejoystick[0].string) : cv_usejoystick[0].value)) M_StartMessage("This joystick is used by another\n" "player. Reset the joystick\n" "for that player first.\n\n" @@ -12067,13 +12038,13 @@ static void M_AssignJoystick(INT32 choice) } #else if (setupcontrolplayer == 4) - CV_SetValue(&cv_usejoystick4, choice); + CV_SetValue(&cv_usejoystick[3], choice); else if (setupcontrolplayer == 3) - CV_SetValue(&cv_usejoystick3, choice); + CV_SetValue(&cv_usejoystick[2], choice); else if (setupcontrolplayer == 2) - CV_SetValue(&cv_usejoystick2, choice); + CV_SetValue(&cv_usejoystick[1], choice); else if (setupcontrolplayer == 1) - CV_SetValue(&cv_usejoystick, choice); + CV_SetValue(&cv_usejoystick[0], choice); #endif } @@ -12427,49 +12398,49 @@ static void M_ResetControlsResponse(INT32 ch) switch (setupcontrolplayer) { case 4: - CV_StealthSet(&cv_usejoystick4, cv_usejoystick4.defaultvalue); - CV_StealthSet(&cv_turnaxis4, cv_turnaxis4.defaultvalue); - CV_StealthSet(&cv_moveaxis4, cv_moveaxis4.defaultvalue); - CV_StealthSet(&cv_brakeaxis4, cv_brakeaxis4.defaultvalue); - CV_StealthSet(&cv_aimaxis4, cv_aimaxis4.defaultvalue); - CV_StealthSet(&cv_lookaxis4, cv_lookaxis4.defaultvalue); - CV_StealthSet(&cv_fireaxis4, cv_fireaxis4.defaultvalue); - CV_StealthSet(&cv_driftaxis4, cv_driftaxis4.defaultvalue); - CV_StealthSet(&cv_lookbackaxis4, cv_lookbackaxis4.defaultvalue); + CV_StealthSet(&cv_usejoystick[3], cv_usejoystick[3].defaultvalue); + CV_StealthSet(&cv_turnaxis[3], cv_turnaxis[3].defaultvalue); + CV_StealthSet(&cv_moveaxis[3], cv_moveaxis[3].defaultvalue); + CV_StealthSet(&cv_brakeaxis[3], cv_brakeaxis[3].defaultvalue); + CV_StealthSet(&cv_aimaxis[3], cv_aimaxis[3].defaultvalue); + CV_StealthSet(&cv_lookaxis[3], cv_lookaxis[3].defaultvalue); + CV_StealthSet(&cv_fireaxis[3], cv_fireaxis[3].defaultvalue); + CV_StealthSet(&cv_driftaxis[3], cv_driftaxis[3].defaultvalue); + CV_StealthSet(&cv_lookbackaxis[3], cv_lookbackaxis[3].defaultvalue); break; case 3: - CV_StealthSet(&cv_usejoystick3, cv_usejoystick3.defaultvalue); - CV_StealthSet(&cv_turnaxis3, cv_turnaxis3.defaultvalue); - CV_StealthSet(&cv_moveaxis3, cv_moveaxis3.defaultvalue); - CV_StealthSet(&cv_brakeaxis3, cv_brakeaxis3.defaultvalue); - CV_StealthSet(&cv_aimaxis3, cv_aimaxis3.defaultvalue); - CV_StealthSet(&cv_lookaxis3, cv_lookaxis3.defaultvalue); - CV_StealthSet(&cv_fireaxis3, cv_fireaxis3.defaultvalue); - CV_StealthSet(&cv_driftaxis3, cv_driftaxis3.defaultvalue); - CV_StealthSet(&cv_lookbackaxis3, cv_lookbackaxis3.defaultvalue); + CV_StealthSet(&cv_usejoystick[2], cv_usejoystick[2].defaultvalue); + CV_StealthSet(&cv_turnaxis[2], cv_turnaxis[2].defaultvalue); + CV_StealthSet(&cv_moveaxis[2], cv_moveaxis[2].defaultvalue); + CV_StealthSet(&cv_brakeaxis[2], cv_brakeaxis[2].defaultvalue); + CV_StealthSet(&cv_aimaxis[2], cv_aimaxis[2].defaultvalue); + CV_StealthSet(&cv_lookaxis[2], cv_lookaxis[2].defaultvalue); + CV_StealthSet(&cv_fireaxis[2], cv_fireaxis[2].defaultvalue); + CV_StealthSet(&cv_driftaxis[2], cv_driftaxis[2].defaultvalue); + CV_StealthSet(&cv_lookbackaxis[2], cv_lookbackaxis[2].defaultvalue); break; case 2: - CV_StealthSet(&cv_usejoystick2, cv_usejoystick2.defaultvalue); - CV_StealthSet(&cv_turnaxis2, cv_turnaxis2.defaultvalue); - CV_StealthSet(&cv_moveaxis2, cv_moveaxis2.defaultvalue); - CV_StealthSet(&cv_brakeaxis2, cv_brakeaxis2.defaultvalue); - CV_StealthSet(&cv_aimaxis2, cv_aimaxis2.defaultvalue); - CV_StealthSet(&cv_lookaxis2, cv_lookaxis2.defaultvalue); - CV_StealthSet(&cv_fireaxis2, cv_fireaxis2.defaultvalue); - CV_StealthSet(&cv_driftaxis2, cv_driftaxis2.defaultvalue); - CV_StealthSet(&cv_lookbackaxis2, cv_lookbackaxis2.defaultvalue); + CV_StealthSet(&cv_usejoystick[1], cv_usejoystick[1].defaultvalue); + CV_StealthSet(&cv_turnaxis[1], cv_turnaxis[1].defaultvalue); + CV_StealthSet(&cv_moveaxis[1], cv_moveaxis[1].defaultvalue); + CV_StealthSet(&cv_brakeaxis[1], cv_brakeaxis[1].defaultvalue); + CV_StealthSet(&cv_aimaxis[1], cv_aimaxis[1].defaultvalue); + CV_StealthSet(&cv_lookaxis[1], cv_lookaxis[1].defaultvalue); + CV_StealthSet(&cv_fireaxis[1], cv_fireaxis[1].defaultvalue); + CV_StealthSet(&cv_driftaxis[1], cv_driftaxis[1].defaultvalue); + CV_StealthSet(&cv_lookbackaxis[1], cv_lookbackaxis[1].defaultvalue); break; case 1: default: - CV_StealthSet(&cv_usejoystick, cv_usejoystick.defaultvalue); - CV_StealthSet(&cv_turnaxis, cv_turnaxis.defaultvalue); - CV_StealthSet(&cv_moveaxis, cv_moveaxis.defaultvalue); - CV_StealthSet(&cv_brakeaxis, cv_brakeaxis.defaultvalue); - CV_StealthSet(&cv_aimaxis, cv_aimaxis.defaultvalue); - CV_StealthSet(&cv_lookaxis, cv_lookaxis.defaultvalue); - CV_StealthSet(&cv_fireaxis, cv_fireaxis.defaultvalue); - CV_StealthSet(&cv_driftaxis, cv_driftaxis.defaultvalue); - CV_StealthSet(&cv_lookbackaxis, cv_lookbackaxis.defaultvalue); + CV_StealthSet(&cv_usejoystick[0], cv_usejoystick[0].defaultvalue); + CV_StealthSet(&cv_turnaxis[0], cv_turnaxis[0].defaultvalue); + CV_StealthSet(&cv_moveaxis[0], cv_moveaxis[0].defaultvalue); + CV_StealthSet(&cv_brakeaxis[0], cv_brakeaxis[0].defaultvalue); + CV_StealthSet(&cv_aimaxis[0], cv_aimaxis[0].defaultvalue); + CV_StealthSet(&cv_lookaxis[0], cv_lookaxis[0].defaultvalue); + CV_StealthSet(&cv_fireaxis[0], cv_fireaxis[0].defaultvalue); + CV_StealthSet(&cv_driftaxis[0], cv_driftaxis[0].defaultvalue); + CV_StealthSet(&cv_lookbackaxis[0], cv_lookbackaxis[0].defaultvalue); break; } diff --git a/src/m_misc.c b/src/m_misc.c index 8bb82cdd7..aec2aad1d 100644 --- a/src/m_misc.c +++ b/src/m_misc.c @@ -1573,6 +1573,84 @@ boolean M_ScreenshotResponder(event_t *ev) return true; } +void M_MinimapGenerate(void) +{ +#ifdef USE_PNG + char *filepath; + boolean ret = false; + minigen_t *minigen = NULL; + size_t option_scale; + INT32 mul = 1; + + if (gamestate != GS_LEVEL) + { + CONS_Alert(CONS_ERROR, "You must be in a level to generate a preliminary minimap!\n"); + return; + } + + if (automapactive) + { + CONS_Alert(CONS_ERROR, "The automap is active! Please deactivate it and try again.\n"); + return; + } + + option_scale = COM_CheckPartialParm("-m"); + + if (option_scale) + { + if (COM_Argc() < option_scale + 2)/* no argument after? */ + { + CONS_Alert(CONS_ERROR, + "No multiplier follows parameter '%s'.\n", + COM_Argv(option_scale)); + return; + } + + mul = atoi(COM_Argv(option_scale + 1)); + + if (mul < 1 || mul > 10) + { + CONS_Alert(CONS_ERROR, + "Multiplier %d must be within range 1-10.\n", + mul); + return; + } + + filepath = va("%s" PATHSEP "%s-MINIMAP-%d.png", srb2home, G_BuildMapName(gamemap), mul); + } + else + { + filepath = va("%s" PATHSEP "%s-MINIMAP.png", srb2home, G_BuildMapName(gamemap)); + } + + minigen = AM_MinimapGenerate(mul); + + if (minigen == NULL || minigen->buf == NULL) + goto failure; + + M_CreateScreenShotPalette(); + ret = M_SavePNG(filepath, minigen->buf, minigen->w, minigen->h, screenshot_palette); + +failure: + if (minigen->buf != NULL) + free(minigen->buf); + + if (ret) + { + CONS_Printf(M_GetText("%s saved.\nRemember that this is not a complete minimap,\nand must be edited before putting in-game.\n"), filepath); + if (mul != 1) + { + CONS_Printf("You should divide its size by %d!\n", mul); + } + } + else + { + CONS_Alert(CONS_ERROR, M_GetText("Couldn't create %s\n"), filepath); + } +#endif //#ifdef USE_PNG +} + + // ========================================================================== // TRANSLATION FUNCTIONS // ========================================================================== diff --git a/src/m_misc.h b/src/m_misc.h index 333398161..c858ae128 100644 --- a/src/m_misc.h +++ b/src/m_misc.h @@ -69,6 +69,8 @@ void M_ScreenShot(void); void M_DoScreenShot(void); boolean M_ScreenshotResponder(event_t *ev); +void M_MinimapGenerate(void); + void Command_SaveConfig_f(void); void Command_LoadConfig_f(void); void Command_ChangeConfig_f(void); diff --git a/src/p_enemy.c b/src/p_enemy.c index 567342df9..9196afbc1 100644 --- a/src/p_enemy.c +++ b/src/p_enemy.c @@ -456,10 +456,7 @@ boolean P_Move(mobj_t *actor, fixed_t speed) I_Assert(movedir < NUMDIRS); tryx = actor->x + FixedMul(speed*xspeed[movedir], actor->scale); - if (twodlevel || actor->flags2 & MF2_TWOD) - tryy = actor->y; - else - tryy = actor->y + FixedMul(speed*yspeed[movedir], actor->scale); + tryy = actor->y + FixedMul(speed*yspeed[movedir], actor->scale); if (actor->type == MT_SKIM && !P_WaterInSector(actor, tryx, tryy)) // bail out if sector lacks water return false; @@ -533,8 +530,6 @@ void P_NewChaseDir(mobj_t *actor) else d[1] = DI_NODIR; - if (twodlevel || actor->flags2 & MF2_TWOD) - d[2] = DI_NODIR; if (deltay < -FixedMul(10*FRACUNIT, actor->scale)) d[2] = DI_SOUTH; else if (deltay > FixedMul(10*FRACUNIT, actor->scale)) @@ -2952,9 +2947,7 @@ void A_Invincibility(mobj_t *actor) if (P_IsLocalPlayer(player) && !player->powers[pw_super]) { S_StopMusic(); - if (mariomode) - G_GhostAddColor((INT32) (player - players), GHC_INVINCIBLE); - S_ChangeMusicInternal((mariomode) ? "minvnc" : "invinc", false); + S_ChangeMusicInternal("invinc", false); } } @@ -3052,11 +3045,7 @@ void A_ExtraLife(mobj_t *actor) return; } - // In shooter gametypes, give the player 100 rings instead of an extra life. - if (gametype != GT_COOP && gametype != GT_COMPETITION) - P_GivePlayerRings(player, 100); - else - P_GivePlayerLives(player, 1); + P_GivePlayerRings(player, 100); P_PlayLivesJingle(player); } @@ -3738,11 +3727,6 @@ void A_ThrownRing(mobj_t *actor) if (player->mo == actor->target) continue; - // Don't home in on teammates. - if (gametype == GT_CTF - && actor->target->player->ctfteam == player->ctfteam) - continue; - if (actor->target->player->kartstuff[k_position] < player->kartstuff[k_position]) // SRB2kart - Jawz only go after people ahead of you continue; @@ -3803,11 +3787,6 @@ static inline boolean PIT_GrenadeRing(mobj_t *thing) || (G_BattleGametype() && thing->player && thing->player->kartstuff[k_bumper] <= 0 && thing->player->kartstuff[k_comebacktimer]))) return true; - if ((gametype == GT_CTF || gametype == GT_TEAMMATCH) - && !cv_friendlyfire.value && grenade->target->player && thing->player - && grenade->target->player->ctfteam == thing->player->ctfteam) // Don't blow up at your teammates, unless friendlyfire is on - return true; - // see if it went over / under if (grenade->z - explodedist > thing->z + thing->height) return true; // overhead @@ -4509,12 +4488,7 @@ void A_MouseThink(mobj_t *actor) || (actor->eflags & MFE_VERTICALFLIP && actor->z + actor->height == actor->ceilingz)) && !actor->reactiontime) { - if (twodlevel || actor->flags2 & MF2_TWOD) - { - if (P_RandomChance(FRACUNIT/2)) - actor->angle += ANGLE_180; - } - else if (P_RandomChance(FRACUNIT/2)) + if (P_RandomChance(FRACUNIT/2)) actor->angle += ANGLE_90; else actor->angle -= ANGLE_90; @@ -5321,7 +5295,8 @@ void A_RingExplode(mobj_t *actor) // var1 = object # to explode as debris // var2 = unused // -void A_OldRingExplode(mobj_t *actor) { +void A_OldRingExplode(mobj_t *actor) +{ UINT8 i; mobj_t *mo; const fixed_t ns = FixedMul(20 * FRACUNIT, actor->scale); @@ -5355,10 +5330,10 @@ void A_OldRingExplode(mobj_t *actor) { if (changecolor) { - if (gametype != GT_CTF) - mo->color = actor->target->color; //copy color - else if (actor->target->player->ctfteam == 2) + if (actor->target->player->ctfteam == 2) mo->color = skincolor_bluering; + else + mo->color = actor->target->color; //copy color } } @@ -5371,10 +5346,10 @@ void A_OldRingExplode(mobj_t *actor) { if (changecolor) { - if (gametype != GT_CTF) - mo->color = actor->target->color; //copy color - else if (actor->target->player->ctfteam == 2) + if (actor->target->player->ctfteam == 2) mo->color = skincolor_bluering; + else + mo->color = actor->target->color; //copy color } mo = P_SpawnMobj(actor->x, actor->y, actor->z, locvar1); @@ -5386,10 +5361,10 @@ void A_OldRingExplode(mobj_t *actor) { if (changecolor) { - if (gametype != GT_CTF) - mo->color = actor->target->color; //copy color - else if (actor->target->player->ctfteam == 2) + if (actor->target->player->ctfteam == 2) mo->color = skincolor_bluering; + else + mo->color = actor->target->color; //copy color } } @@ -5413,7 +5388,7 @@ void A_MixUp(mobj_t *actor) // No mix-up monitors in hide and seek or time only race. // The random factor is okay for other game modes, but in these, it is cripplingly unfair. - if (gametype == GT_HIDEANDSEEK || gametype == GT_RACE) + if (gametype == GT_RACE) return; numplayers = 0; diff --git a/src/p_floor.c b/src/p_floor.c index bebc9a272..738524b02 100644 --- a/src/p_floor.c +++ b/src/p_floor.c @@ -2119,10 +2119,11 @@ void T_EachTimeThinker(levelspecthink_t *eachtime) sec = §ors[secnum]; FOFsector = false; + INT32 special = GETSECSPECIAL(sec->special, 2); - if (GETSECSPECIAL(sec->special, 2) == 3 || GETSECSPECIAL(sec->special, 2) == 5) + if (special == 3 || special == 5) floortouch = true; - else if (GETSECSPECIAL(sec->special, 2) >= 1 && GETSECSPECIAL(sec->special, 2) <= 8) + else if (special >= 1 && special <= 8) floortouch = false; else continue; @@ -2254,7 +2255,7 @@ void T_EachTimeThinker(levelspecthink_t *eachtime) continue; if (!(players[i].mo->subsector->sector == sec - || P_PlayerTouchingSectorSpecial(&players[i], 2, (GETSECSPECIAL(sec->special, 2))) == sec)) + || P_PlayerTouchingSectorSpecial(&players[i], 2, special) == sec)) continue; if (floortouch == true && P_IsObjectOnRealGround(players[i].mo, sec)) @@ -2298,7 +2299,9 @@ void T_EachTimeThinker(levelspecthink_t *eachtime) while ((affectPlayer = P_HavePlayersEnteredArea(playersArea, oldPlayersArea, inAndOut)) != -1) { - if (GETSECSPECIAL(sec->special, 2) == 2 || GETSECSPECIAL(sec->special, 2) == 3) + INT32 special = GETSECSPECIAL(sec->special, 2); + + if (special == 2 || special == 3) { for (i = 0; i < MAXPLAYERS; i++) { @@ -2507,123 +2510,44 @@ void T_CameraScanner(elevator_t *elevator) { // leveltime is compared to make multiple scanners in one map function correctly. static tic_t lastleveltime = 32000; // any number other than 0 should do here - static boolean camerascanned, camerascanned2, camerascanned3, camerascanned4; + static boolean camerascanned[MAXSPLITSCREENPLAYERS]; + static fixed_t t_cam_dist[MAXSPLITSCREENPLAYERS] = {-42, -42, -42, -42}; + static fixed_t t_cam_height[MAXSPLITSCREENPLAYERS] = {-42, -42, -42, -42}; if (leveltime != lastleveltime) // Back on the first camera scanner { - camerascanned = camerascanned2 = camerascanned3 = camerascanned4 = false; + memset(camerascanned, false, sizeof (camerascanned)); lastleveltime = leveltime; } - if (players[displayplayers[0]].mo) + for (UINT8 i = 0; i <= splitscreen; i++) { - if (players[displayplayers[0]].mo->subsector->sector == elevator->actionsector) - { - if (t_cam_dist == -42) - t_cam_dist = cv_cam_dist.value; - if (t_cam_height == -42) - t_cam_height = cv_cam_height.value; - if (t_cam_rotate == -42) - t_cam_rotate = cv_cam_rotate.value; - CV_SetValue(&cv_cam_height, FixedInt(elevator->sector->floorheight)); - CV_SetValue(&cv_cam_dist, FixedInt(elevator->sector->ceilingheight)); - CV_SetValue(&cv_cam_rotate, elevator->distance); - camerascanned = true; - } - else if (!camerascanned) - { - if (t_cam_height != -42 && cv_cam_height.value != t_cam_height) - CV_Set(&cv_cam_height, va("%f", (double)FIXED_TO_FLOAT(t_cam_height))); - if (t_cam_dist != -42 && cv_cam_dist.value != t_cam_dist) - CV_Set(&cv_cam_dist, va("%f", (double)FIXED_TO_FLOAT(t_cam_dist))); - if (t_cam_rotate != -42 && cv_cam_rotate.value != t_cam_rotate) - CV_Set(&cv_cam_rotate, va("%f", (double)t_cam_rotate)); + if (!players[displayplayers[i]].mo || P_MobjWasRemoved(players[displayplayers[i]].mo)) + continue; - t_cam_dist = t_cam_height = t_cam_rotate = -42; - } - } - - if (splitscreen && players[displayplayers[1]].mo) - { - if (players[displayplayers[1]].mo->subsector->sector == elevator->actionsector) + if (players[displayplayers[i]].mo->subsector->sector == elevator->actionsector) { - if (t_cam2_rotate == -42) - t_cam2_dist = cv_cam2_dist.value; - if (t_cam2_rotate == -42) - t_cam2_height = cv_cam2_height.value; - if (t_cam2_rotate == -42) - t_cam2_rotate = cv_cam2_rotate.value; - CV_SetValue(&cv_cam2_height, FixedInt(elevator->sector->floorheight)); - CV_SetValue(&cv_cam2_dist, FixedInt(elevator->sector->ceilingheight)); - CV_SetValue(&cv_cam2_rotate, elevator->distance); - camerascanned2 = true; + if (t_cam_dist[i] == -42) + t_cam_dist[i] = cv_cam_dist[i].value; + if (t_cam_height[i] == -42) + t_cam_height[i] = cv_cam_height[i].value; + if (t_cam_rotate[i] == -42) + t_cam_rotate[i] = cv_cam_rotate[i].value; + CV_SetValue(&cv_cam_height[i], FixedInt(elevator->sector->floorheight)); + CV_SetValue(&cv_cam_dist[i], FixedInt(elevator->sector->ceilingheight)); + CV_SetValue(&cv_cam_rotate[i], elevator->distance); + camerascanned[i] = true; } - else if (!camerascanned2) + else if (!camerascanned[i]) { - if (t_cam2_height != -42 && cv_cam2_height.value != t_cam2_height) - CV_Set(&cv_cam2_height, va("%f", (double)FIXED_TO_FLOAT(t_cam2_height))); - if (t_cam2_dist != -42 && cv_cam2_dist.value != t_cam2_dist) - CV_Set(&cv_cam2_dist, va("%f", (double)FIXED_TO_FLOAT(t_cam2_dist))); - if (t_cam2_rotate != -42 && cv_cam2_rotate.value != t_cam2_rotate) - CV_Set(&cv_cam2_rotate, va("%f", (double)t_cam2_rotate)); + if (t_cam_height[i] != -42 && cv_cam_height[i].value != t_cam_height[i]) + CV_Set(&cv_cam_height[i], va("%f", (double)FIXED_TO_FLOAT(t_cam_height[i]))); + if (t_cam_dist[i] != -42 && cv_cam_dist[i].value != t_cam_dist[i]) + CV_Set(&cv_cam_dist[i], va("%f", (double)FIXED_TO_FLOAT(t_cam_dist[i]))); + if (t_cam_rotate[i] != -42 && cv_cam_rotate[i].value != t_cam_rotate[i]) + CV_Set(&cv_cam_rotate[i], va("%f", (double)t_cam_rotate[i])); - t_cam2_dist = t_cam2_height = t_cam2_rotate = -42; - } - } - - if (splitscreen > 1 && players[displayplayers[2]].mo) - { - if (players[displayplayers[2]].mo->subsector->sector == elevator->actionsector) - { - if (t_cam3_rotate == -42) - t_cam3_dist = cv_cam3_dist.value; - if (t_cam3_rotate == -42) - t_cam3_height = cv_cam3_height.value; - if (t_cam3_rotate == -42) - t_cam3_rotate = cv_cam3_rotate.value; - CV_SetValue(&cv_cam3_height, FixedInt(elevator->sector->floorheight)); - CV_SetValue(&cv_cam3_dist, FixedInt(elevator->sector->ceilingheight)); - CV_SetValue(&cv_cam3_rotate, elevator->distance); - camerascanned3 = true; - } - else if (!camerascanned3) - { - if (t_cam3_height != -42 && cv_cam3_height.value != t_cam3_height) - CV_Set(&cv_cam3_height, va("%f", (double)FIXED_TO_FLOAT(t_cam3_height))); - if (t_cam3_dist != -42 && cv_cam3_dist.value != t_cam3_dist) - CV_Set(&cv_cam3_dist, va("%f", (double)FIXED_TO_FLOAT(t_cam3_dist))); - if (t_cam3_rotate != -42 && cv_cam3_rotate.value != t_cam3_rotate) - CV_Set(&cv_cam3_rotate, va("%f", (double)t_cam3_rotate)); - - t_cam3_dist = t_cam3_height = t_cam3_rotate = -42; - } - } - - if (splitscreen > 2 && players[displayplayers[3]].mo) - { - if (players[displayplayers[3]].mo->subsector->sector == elevator->actionsector) - { - if (t_cam4_rotate == -42) - t_cam4_dist = cv_cam4_dist.value; - if (t_cam4_rotate == -42) - t_cam4_height = cv_cam4_height.value; - if (t_cam4_rotate == -42) - t_cam4_rotate = cv_cam4_rotate.value; - CV_SetValue(&cv_cam4_height, FixedInt(elevator->sector->floorheight)); - CV_SetValue(&cv_cam4_dist, FixedInt(elevator->sector->ceilingheight)); - CV_SetValue(&cv_cam4_rotate, elevator->distance); - camerascanned4 = true; - } - else if (!camerascanned4) - { - if (t_cam4_height != -42 && cv_cam4_height.value != t_cam4_height) - CV_Set(&cv_cam4_height, va("%f", (double)FIXED_TO_FLOAT(t_cam4_height))); - if (t_cam4_dist != -42 && cv_cam4_dist.value != t_cam4_dist) - CV_Set(&cv_cam4_dist, va("%f", (double)FIXED_TO_FLOAT(t_cam4_dist))); - if (t_cam4_rotate != -42 && cv_cam4_rotate.value != t_cam4_rotate) - CV_Set(&cv_cam4_rotate, va("%f", (double)t_cam4_rotate)); - - t_cam4_dist = t_cam4_height = t_cam4_rotate = -42; + t_cam_dist[i] = t_cam_height[i] = t_cam_rotate[i] = -42; } } } @@ -2996,14 +2920,14 @@ void EV_CrumbleChain(sector_t *sec, ffloor_t *rover) fixed_t a, b, c; mobjtype_t type = MT_ROCKCRUMBLE1; const fixed_t spacing = 48*mapobjectscale; + INT32 special = GETSECSPECIAL(rover->master->frontsector->special, 3); // If the control sector has a special // of Section3:7-15, use the custom debris. - if (GETSECSPECIAL(rover->master->frontsector->special, 3) >= 8) - type = MT_ROCKCRUMBLE1+(GETSECSPECIAL(rover->master->frontsector->special, 3)-7); + if (special >= 8) + type = MT_ROCKCRUMBLE1+(special-7); - // soundorg z height never gets set normally, so MEH. - sec->soundorg.z = sec->floorheight; + sec->soundorg.z = (rover->master->frontsector->floorheight + rover->master->frontsector->ceilingheight)/2; S_StartSound(&sec->soundorg, sfx_crumbl); // Find the outermost vertexes in the subsector diff --git a/src/p_inter.c b/src/p_inter.c index 378cec557..c111bf71a 100644 --- a/src/p_inter.c +++ b/src/p_inter.c @@ -662,9 +662,6 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) special->momx = special->momy = special->momz = 0; P_GivePlayerRings(player, 1); - - if ((maptol & TOL_NIGHTS) && special->type != MT_FLINGRING) - P_DoNightsScore(player); break; case MT_COIN: @@ -674,9 +671,6 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) special->momx = special->momy = 0; P_GivePlayerRings(player, 1); - - if ((maptol & TOL_NIGHTS) && special->type != MT_FLINGCOIN) - P_DoNightsScore(player); break; case MT_BLUEBALL: if (!(P_CanPickupItem(player, 0))) @@ -690,9 +684,6 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) special->scalespeed = FixedDiv(FixedDiv(special->destscale, special->scale), states[special->info->deathstate].tics<scalespeed = 4*FRACUNIT/5; - - if (maptol & TOL_NIGHTS) - P_DoNightsScore(player); break; case MT_AUTOPICKUP: case MT_BOUNCEPICKUP: @@ -842,8 +833,6 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) return; if (special->fuse == 1) return; -// if (special->momz > 0) -// return; { UINT8 flagteam = (special->type == MT_REDFLAG) ? 1 : 2; const char *flagtext; @@ -1341,10 +1330,6 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) return; // SRB2kart - don't need bubbles mucking with the player if ((player->powers[pw_shield] & SH_NOSTACK) == SH_ELEMENTAL) return; - if (maptol & TOL_NIGHTS) - return; - if (mariomode) - return; else if (toucher->eflags & MFE_VERTICALFLIP) { if (special->z+special->height < toucher->z + toucher->height / 3 @@ -1433,46 +1418,36 @@ void P_CheckTimeLimit(void) if (gamestate == GS_LEVEL && (leveltime == (timelimitintics + TICRATE))) S_StartSound(NULL, sfx_strpst); - // Normal Match - if (!G_GametypeHasTeams()) + //Store the nodes of participating players in an array. + for (i = 0; i < MAXPLAYERS; i++) { - //Store the nodes of participating players in an array. - for (i = 0; i < MAXPLAYERS; i++) + if (playeringame[i] && !players[i].spectator) { - if (playeringame[i] && !players[i].spectator) + playerarray[playercount] = i; + playercount++; + } + } + + if (playercount > MAXPLAYERS) + playercount = MAXPLAYERS; + + //Sort 'em. + for (i = 1; i < playercount; i++) + { + for (k = i; k < playercount; k++) + { + if (players[playerarray[i-1]].marescore < players[playerarray[k]].marescore) { - playerarray[playercount] = i; - playercount++; + tempplayer = playerarray[i-1]; + playerarray[i-1] = playerarray[k]; + playerarray[k] = tempplayer; } } - - if (playercount > MAXPLAYERS) - playercount = MAXPLAYERS; - - //Sort 'em. - for (i = 1; i < playercount; i++) - { - for (k = i; k < playercount; k++) - { - if (players[playerarray[i-1]].marescore < players[playerarray[k]].marescore) - { - tempplayer = playerarray[i-1]; - playerarray[i-1] = playerarray[k]; - playerarray[k] = tempplayer; - } - } - } - - //End the round if the top players aren't tied. - if (players[playerarray[0]].marescore == players[playerarray[1]].marescore) - return; - } - else - { - //In team match and CTF, determining a tie is much simpler. =P - if (redscore == bluescore) - return; } + + //End the round if the top players aren't tied. + if (players[playerarray[0]].marescore == players[playerarray[1]].marescore) + return; } } @@ -1719,21 +1694,6 @@ void P_KillMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source) P_UnsetThingPosition(target); target->flags |= MF_NOBLOCKMAP|MF_NOCLIPHEIGHT; P_SetThingPosition(target); - - if (!target->player->bot && !G_IsSpecialStage(gamemap) - && G_GametypeUsesLives()) - { - target->player->lives -= 1; // Lose a life Tails 03-11-2000 - - if (target->player->lives <= 0) // Tails 03-14-2000 - { - if (P_IsLocalPlayer(target->player)/* && target->player == &players[consoleplayer] */) - { - S_StopMusic(); // Stop the Music! Tails 03-14-2000 - S_ChangeMusicInternal("gmover", false); // Yousa dead now, Okieday? Tails 03-14-2000 - } - } - } target->player->playerstate = PST_DEAD; if (cv_birdmusic.value && cv_fading.value && P_IsLocalPlayer(target->player)) @@ -1785,8 +1745,7 @@ void P_KillMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source) // Drop stuff. // This determines the kind of object spawned // during the death frame of a thing. - if (!mariomode // Don't show birds, etc. in Mario Mode Tails 12-23-2001 - && target->flags & MF_ENEMY) + if (target->flags & MF_ENEMY) { if (cv_soniccd.value) item = MT_SEED; @@ -2159,90 +2118,9 @@ static inline void P_NiGHTSDamage(mobj_t *target, mobj_t *source) } } -static inline boolean P_TagDamage(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage) +static inline boolean P_PlayerHitsPlayer(mobj_t *target, mobj_t *source) { player_t *player = target->player; - (void)damage; //unused parm - - // If flashing or invulnerable, ignore the tag, - if (player->powers[pw_flashing] || player->powers[pw_invulnerability]) - return false; - - // Ignore IT players shooting each other, unless friendlyfire is on. - if ((player->pflags & PF_TAGIT && !(cv_friendlyfire.value && - source && source->player && source->player->pflags & PF_TAGIT))) - return false; - - // Don't allow any damage before the round starts. - if (leveltime <= hidetime * TICRATE) - return false; - - // Don't allow players on the same team to hurt one another, - // unless cv_friendlyfire is on. - if (!cv_friendlyfire.value && (player->pflags & PF_TAGIT) == (source->player->pflags & PF_TAGIT)) - { - if (!(inflictor->flags & MF_FIRE)) - P_GivePlayerRings(player, 1); - if (inflictor->flags2 & MF2_BOUNCERING) - inflictor->fuse = 0; // bounce ring disappears at -1 not 0 - return false; - } - - P_DoPlayerPain(player, source, inflictor); - - // Check for a shield - if (player->powers[pw_shield]) - { - P_RemoveShield(player); - S_StartSound(target, sfx_shldls); - return true; - } - - if (target->health <= 1) // Death - { - P_PlayDeathSound(target); - P_PlayVictorySound(source); // Killer laughs at you! LAUGHS! BWAHAHAHHAHAA!! - } - else if (target->health > 1) // Ring loss - { - P_PlayRinglossSound(target, source); - P_PlayerRingBurst(player, player->mo->health - 1); - } - - if (inflictor && ((inflictor->flags & MF_MISSILE) || inflictor->player) && player->powers[pw_super] && ALL7EMERALDS(player->powers[pw_emeralds])) - { - player->health -= 10; - if (player->health < 2) - player->health = 2; - target->health = player->health; - } - else - player->health = target->health = 1; - - return true; -} - -static inline boolean P_PlayerHitsPlayer(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage) -{ - player_t *player = target->player; - - // Tag handling - if (G_TagGametype()) - return P_TagDamage(target, inflictor, source, damage); - else if (G_GametypeHasTeams()) // CTF + Team Match - { - // Don't allow players on the same team to hurt one another, - // unless cv_friendlyfire is on. - if (!cv_friendlyfire.value && target->player->ctfteam == source->player->ctfteam) - { - if (!(inflictor->flags & MF_FIRE)) - P_GivePlayerRings(target->player, 1); - if (inflictor->flags2 & MF2_BOUNCERING) - inflictor->fuse = 0; // bounce ring disappears at -1 not 0 - - return false; - } - } // Add pity. if (!player->powers[pw_flashing] && !player->powers[pw_invulnerability] && !player->powers[pw_super] @@ -2483,9 +2361,6 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da { if (player->exiting) return false; - - if (!(target->player->pflags & (PF_NIGHTSMODE|PF_NIGHTSFALL)) && (maptol & TOL_NIGHTS)) - return false; } if (player->pflags & PF_NIGHTSMODE) // NiGHTS damage handling @@ -2494,10 +2369,6 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da { if (source == target) return false; // Don't hit yourself with your own paraloop, baka - if (source && source->player && !cv_friendlyfire.value - && (gametype == GT_COOP - || (G_GametypeHasTeams() && target->player->ctfteam == source->player->ctfteam))) - return false; // Don't run eachother over in special stages and team games and such } if (LUAh_MobjDamage(target, inflictor, source, damage)) @@ -2530,7 +2401,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da // Player hits another player if (!force && source && source->player) { - if (!P_PlayerHitsPlayer(target, inflictor, source, damage)) + if (!P_PlayerHitsPlayer(target, source)) return false; } @@ -2584,9 +2455,6 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da if (player->health < 2) player->health = 2; } - - if (gametype == GT_CTF && (player->gotflag & (GF_REDFLAG|GF_BLUEFLAG))) - P_PlayerFlagBurst(player, false); } else { @@ -2738,9 +2606,7 @@ void P_PlayerRingBurst(player_t *player, INT32 num_rings) { ns = FixedMul(((i*FRACUNIT)/16)+2*FRACUNIT, mo->scale); mo->momx = FixedMul(FINECOSINE(fa),ns); - - if (!(twodlevel || (player->mo->flags2 & MF2_TWOD))) - mo->momy = FixedMul(FINESINE(fa),ns); + mo->momy = FixedMul(FINESINE(fa),ns); P_SetObjectMomZ(mo, 8*FRACUNIT, false); mo->fuse = 20*TICRATE; // Adjust fuse for NiGHTS @@ -2762,9 +2628,7 @@ void P_PlayerRingBurst(player_t *player, INT32 num_rings) ns = FixedMul(momxy, mo->scale); mo->momx = FixedMul(FINECOSINE(fa),ns); - - if (!(twodlevel || (player->mo->flags2 & MF2_TWOD))) - mo->momy = FixedMul(FINESINE(fa),ns); + mo->momy = FixedMul(FINESINE(fa),ns); ns = momz; P_SetObjectMomZ(mo, ns, false); @@ -2869,9 +2733,7 @@ void P_PlayerWeaponPanelBurst(player_t *player) // >16 ring type spillout ns = FixedMul(3*FRACUNIT, mo->scale); mo->momx = FixedMul(FINECOSINE(fa),ns); - - if (!(twodlevel || (player->mo->flags2 & MF2_TWOD))) - mo->momy = FixedMul(FINESINE(fa),ns); + mo->momy = FixedMul(FINESINE(fa),ns); P_SetObjectMomZ(mo, 4*FRACUNIT, false); @@ -2953,9 +2815,7 @@ void P_PlayerWeaponAmmoBurst(player_t *player) // Spill them! ns = FixedMul(2*FRACUNIT, mo->scale); mo->momx = FixedMul(FINECOSINE(fa), ns); - - if (!(twodlevel || (player->mo->flags2 & MF2_TWOD))) - mo->momy = FixedMul(FINESINE(fa),ns); + mo->momy = FixedMul(FINESINE(fa),ns); P_SetObjectMomZ(mo, 3*FRACUNIT, false); @@ -3069,11 +2929,7 @@ void P_PlayerEmeraldBurst(player_t *player, boolean toss) } momx = FixedMul(FINECOSINE(fa), ns); - - if (!(twodlevel || (player->mo->flags2 & MF2_TWOD))) - momy = FixedMul(FINESINE(fa),ns); - else - momy = 0; + momy = FixedMul(FINESINE(fa),ns); mo = P_SpawnMobj(player->mo->x, player->mo->y, z, MT_FLINGEMERALD); mo->health = 1; @@ -3097,88 +2953,3 @@ void P_PlayerEmeraldBurst(player_t *player, boolean toss) } } } - -/** Makes an injured or dead player lose possession of the flag. - * - * \param player The player with the flag, about to lose it. - * \sa P_PlayerRingBurst - */ -void P_PlayerFlagBurst(player_t *player, boolean toss) -{ - mobj_t *flag; - mobjtype_t type; - - if (!(player->gotflag & (GF_REDFLAG|GF_BLUEFLAG))) - return; - - if (player->gotflag & GF_REDFLAG) - type = MT_REDFLAG; - else - type = MT_BLUEFLAG; - - flag = P_SpawnMobj(player->mo->x, player->mo->y, player->mo->z, type); - - if (player->mo->eflags & MFE_VERTICALFLIP) - flag->z += player->mo->height - flag->height; - - if (toss) - P_InstaThrust(flag, player->mo->angle, FixedMul(6*FRACUNIT, player->mo->scale)); - else - { - angle_t fa = P_RandomByte()*FINEANGLES/256; - flag->momx = FixedMul(FINECOSINE(fa), FixedMul(6*FRACUNIT, player->mo->scale)); - if (!(twodlevel || (player->mo->flags2 & MF2_TWOD))) - flag->momy = FixedMul(FINESINE(fa), FixedMul(6*FRACUNIT, player->mo->scale)); - } - - flag->momz = FixedMul(8*FRACUNIT, player->mo->scale); - if (player->mo->eflags & MFE_VERTICALFLIP) - flag->momz = -flag->momz; - - if (type == MT_REDFLAG) - flag->spawnpoint = rflagpoint; - else - flag->spawnpoint = bflagpoint; - - flag->fuse = cv_flagtime.value * TICRATE; - P_SetTarget(&flag->target, player->mo); - - // Flag text - char plname[MAXPLAYERNAME+4]; - const char *flagtext; - char flagcolor; - - snprintf(plname, sizeof(plname), "%s%s%s", - CTFTEAMCODE(player), - player_names[player - players], - CTFTEAMENDCODE(player)); - - if (type == MT_REDFLAG) - { - flagtext = M_GetText("Red flag"); - flagcolor = '\x85'; - } - else - { - flagtext = M_GetText("Blue flag"); - flagcolor = '\x84'; - } - - if (toss) - CONS_Printf(M_GetText("%s tossed the %c%s%c.\n"), plname, flagcolor, flagtext, 0x80); - else - CONS_Printf(M_GetText("%s dropped the %c%s%c.\n"), plname, flagcolor, flagtext, 0x80); - - player->gotflag = 0; - - // Pointers set for displaying time value and for consistency restoration. - if (type == MT_REDFLAG) - redflag = flag; - else - blueflag = flag; - - if (toss) - player->tossdelay = 2*TICRATE; - - return; -} diff --git a/src/p_local.h b/src/p_local.h index 7bc343775..4a7da680f 100644 --- a/src/p_local.h +++ b/src/p_local.h @@ -57,9 +57,6 @@ #define AIMINGTOSLOPE(aiming) FINESINE((aiming>>ANGLETOFINESHIFT) & FINEMASK) -#define mariomode (maptol & TOL_MARIO) -#define twodlevel (maptol & TOL_2D) - // // P_TICK // @@ -116,7 +113,7 @@ struct demofreecam_s { camera_t *cam; // this is useful when the game is paused, notably mobj_t *soundmobj; // mobj to play sound from, used in s_sound - + angle_t localangle; // keeps track of the cam angle for cmds angle_t localaiming; // ditto with aiming boolean turnheld; // holding turn button for gradual turn speed @@ -126,17 +123,12 @@ struct demofreecam_s { extern struct demofreecam_s democam; extern camera_t camera[MAXSPLITSCREENPLAYERS]; -extern consvar_t cv_cam_dist, cv_cam_still, cv_cam_height; -extern consvar_t cv_cam_speed, cv_cam_rotate, cv_cam_rotspeed; - -extern consvar_t cv_cam2_dist, cv_cam2_still, cv_cam2_height; -extern consvar_t cv_cam2_speed, cv_cam2_rotate, cv_cam2_rotspeed; - -extern consvar_t cv_cam3_dist, cv_cam3_still, cv_cam3_height; -extern consvar_t cv_cam3_speed, cv_cam3_rotate, cv_cam3_rotspeed; - -extern consvar_t cv_cam4_dist, cv_cam4_still, cv_cam4_height; -extern consvar_t cv_cam4_speed, cv_cam4_rotate, cv_cam4_rotspeed; +extern consvar_t cv_cam_dist[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_cam_still[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_cam_height[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_cam_speed[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_cam_rotate[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_cam_rotspeed[MAXSPLITSCREENPLAYERS]; extern consvar_t cv_tilting; extern consvar_t cv_quaketilt; @@ -146,10 +138,7 @@ extern consvar_t cv_actionmovie; extern consvar_t cv_lookbackmom; -extern fixed_t t_cam_dist, t_cam_height, t_cam_rotate; -extern fixed_t t_cam2_dist, t_cam2_height, t_cam2_rotate; -extern fixed_t t_cam3_dist, t_cam3_height, t_cam3_rotate; -extern fixed_t t_cam4_dist, t_cam4_height, t_cam4_rotate; +extern fixed_t t_cam_rotate[MAXSPLITSCREENPLAYERS]; fixed_t P_GetPlayerHeight(player_t *player); fixed_t P_GetPlayerSpinHeight(player_t *player); @@ -297,7 +286,6 @@ mobj_t *P_SPMAngle(mobj_t *source, mobjtype_t type, angle_t angle, UINT8 aimtype #ifdef SEENAMES #define P_SpawnNameFinder(s,t) P_SPMAngle(s,t,s->angle,true,0) #endif -void P_ColorTeamMissile(mobj_t *missile, player_t *source); // P_MobjFlip // Special utility to return +1 or -1 depending on mobj's gravity @@ -445,10 +433,8 @@ void P_PlayerWeaponAmmoBurst(player_t *player); void P_PlayerEmeraldBurst(player_t *player, boolean toss); void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck); -void P_PlayerFlagBurst(player_t *player, boolean toss); void P_CheckTimeLimit(void); void P_CheckPointLimit(void); -//void P_CheckSurvivors(void); boolean P_CheckRacers(void); boolean P_CanPickupItem(player_t *player, UINT8 weapon); diff --git a/src/p_map.c b/src/p_map.c index bd551829d..3034f2a06 100644 --- a/src/p_map.c +++ b/src/p_map.c @@ -371,11 +371,6 @@ static boolean PIT_CheckThing(mobj_t *thing) if (!(thing->flags & (MF_SOLID|MF_SPECIAL|MF_PAIN|MF_SHOOTABLE)) || (thing->flags & MF_NOCLIPTHING)) return true; - // Don't collide with your buddies while NiGHTS-flying. - if (tmthing->player && thing->player && (maptol & TOL_NIGHTS) - && ((tmthing->player->pflags & PF_NIGHTSMODE) || (thing->player->pflags & PF_NIGHTSMODE))) - return true; - blockdist = thing->radius + tmthing->radius; if (abs(thing->x - tmx) >= blockdist || abs(thing->y - tmy) >= blockdist) @@ -1727,6 +1722,7 @@ boolean P_CheckPosition(mobj_t *thing, fixed_t x, fixed_t y) tmbbox[BOXLEFT] = x - tmthing->radius; newsubsec = R_PointInSubsector(x, y); + ceilingline = blockingline = NULL; // The base floor / ceiling is from the subsector @@ -2165,7 +2161,6 @@ boolean P_TryCameraMove(fixed_t x, fixed_t y, camera_t *thiscam) { subsector_t *s = R_PointInSubsector(x, y); boolean retval = true; - boolean itsatwodlevel = false; UINT8 i; floatok = false; @@ -2173,22 +2168,7 @@ boolean P_TryCameraMove(fixed_t x, fixed_t y, camera_t *thiscam) if (dedicated) // this crashes so don't even try it return false; - if (twodlevel) - itsatwodlevel = true; - else - { - for (i = 0; i <= splitscreen; i++) - { - if (thiscam == &camera[i] && players[displayplayers[i]].mo - && (players[displayplayers[i]].mo->flags2 & MF2_TWOD)) - { - itsatwodlevel = true; - break; - } - } - } - - if (!itsatwodlevel && players[displayplayers[0]].mo) + if (players[displayplayers[0]].mo) { fixed_t tryx = thiscam->x; fixed_t tryy = thiscam->y; @@ -2391,16 +2371,19 @@ boolean P_TryMove(mobj_t *thing, fixed_t x, fixed_t y, boolean allowdropoff) { //All things are affected by their scale. fixed_t maxstep = FixedMul(MAXSTEPMOVE, mapobjectscale); + INT32 special = 0; if (thing->player) { + special = GETSECSPECIAL(R_PointInSubsector(x, y)->sector->special, 1); + // If using type Section1:13, double the maxstep. if (P_PlayerTouchingSectorSpecial(thing->player, 1, 13) - || GETSECSPECIAL(R_PointInSubsector(x, y)->sector->special, 1) == 13) + || special == 13) maxstep <<= 1; // If using type Section1:12, no maxstep. For ledges you don't want the player to climb! (see: Egg Zeppelin & SMK port walls) else if (P_PlayerTouchingSectorSpecial(thing->player, 1, 12) - || GETSECSPECIAL(R_PointInSubsector(x, y)->sector->special, 1) == 12) + || special == 12) maxstep = 0; } @@ -2446,7 +2429,7 @@ boolean P_TryMove(mobj_t *thing, fixed_t x, fixed_t y, boolean allowdropoff) else if (maxstep > 0 && !( thing->player && ( P_PlayerTouchingSectorSpecial(thing->player, 1, 14) - || GETSECSPECIAL(R_PointInSubsector(x, y)->sector->special, 1) == 14) + || special == 14) )) // Step down { // If the floor difference is MAXSTEPMOVE or less, and the sector isn't Section1:14, ALWAYS @@ -3179,16 +3162,8 @@ stairstep: P_HitSlideLine(bestslideline); // clip the moves - if ((twodlevel || (mo->flags2 & MF2_TWOD)) && mo->player) - { - mo->momx = tmxmove; - tmymove = 0; - } - else - { - mo->momx = tmxmove; - mo->momy = tmymove; - } + mo->momx = tmxmove; + mo->momy = tmymove; do { if (tmxmove > mo->radius) { diff --git a/src/p_mobj.c b/src/p_mobj.c index c1b8b4a6f..2420d2a50 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -1174,7 +1174,7 @@ static void P_XYFriction(mobj_t *mo, fixed_t oldx, fixed_t oldy) } else if (abs(player->rmomx) < FixedMul(STOPSPEED, mo->scale) && abs(player->rmomy) < FixedMul(STOPSPEED, mo->scale) - && (!(player->cmd.forwardmove && !(twodlevel || mo->flags2 & MF2_TWOD)) && !player->cmd.sidemove && !(player->pflags & PF_SPINNING)) + && (!player->cmd.forwardmove && !player->cmd.sidemove && !(player->pflags & PF_SPINNING)) && !(player->mo->standingslope && (!(player->mo->standingslope->flags & SL_NOPHYSICS)) && (abs(player->mo->standingslope->zdelta) >= FRACUNIT/2)) ) { @@ -1881,12 +1881,13 @@ boolean P_CheckDeathPitCollide(mobj_t *mo) I_Assert(mo != NULL); I_Assert(!P_MobjWasRemoved(mo)); + INT32 special = GETSECSPECIAL(mo->subsector->sector->special, 1); + if (((mo->z <= mo->subsector->sector->floorheight && !(mo->eflags & MFE_VERTICALFLIP) && (mo->subsector->sector->flags & SF_FLIPSPECIAL_FLOOR)) || (mo->z + mo->height >= mo->subsector->sector->ceilingheight && (mo->eflags & MFE_VERTICALFLIP) && (mo->subsector->sector->flags & SF_FLIPSPECIAL_CEILING))) - && (GETSECSPECIAL(mo->subsector->sector->special, 1) == 6 - || GETSECSPECIAL(mo->subsector->sector->special, 1) == 7)) + && (special == 6 || special == 7)) return true; return false; @@ -1897,16 +1898,14 @@ boolean P_CheckSolidLava(mobj_t *mo, ffloor_t *rover) I_Assert(mo != NULL); I_Assert(!P_MobjWasRemoved(mo)); - { - fixed_t topheight = - *rover->t_slope ? P_GetZAt(*rover->t_slope, mo->x, mo->y) : - *rover->topheight; + fixed_t topheight = + *rover->t_slope ? P_GetZAt(*rover->t_slope, mo->x, mo->y) : + *rover->topheight; - if (rover->flags & FF_SWIMMABLE && GETSECSPECIAL(rover->master->frontsector->special, 1) == 3 - && !(rover->master->flags & ML_BLOCKMONSTERS) - && ((rover->master->flags & ML_EFFECT3) || mo->z-mo->momz > topheight - FixedMul(16*FRACUNIT, mo->scale))) - return true; - } + if (rover->flags & FF_SWIMMABLE && GETSECSPECIAL(rover->master->frontsector->special, 1) == 3 + && !(rover->master->flags & ML_BLOCKMONSTERS) + && ((rover->master->flags & ML_EFFECT3) || mo->z-mo->momz > topheight - FixedMul(16*FRACUNIT, mo->scale))) + return true; return false; } @@ -2218,10 +2217,7 @@ static boolean P_ZMovement(mobj_t *mo) || mo->type == MT_CANNONBALLDECOR || mo->type == MT_FALLINGROCK) { - if (maptol & TOL_NIGHTS) - mom.z = -FixedDiv(mom.z, 10*FRACUNIT); - else - mom.z = -FixedMul(mom.z, FixedDiv(17*FRACUNIT,20*FRACUNIT)); + mom.z = -FixedMul(mom.z, FixedDiv(17*FRACUNIT,20*FRACUNIT)); if (mo->type == MT_BIGTUMBLEWEED || mo->type == MT_LITTLETUMBLEWEED) { @@ -2359,12 +2355,7 @@ static boolean P_ZMovement(mobj_t *mo) else // Flags bounce if (mo->type == MT_REDFLAG || mo->type == MT_BLUEFLAG) - { - if (maptol & TOL_NIGHTS) - mo->momz = -FixedDiv(mo->momz, 10*FRACUNIT); - else - mo->momz = -FixedMul(mo->momz, FixedDiv(17*FRACUNIT,20*FRACUNIT)); - } + mo->momz = -FixedMul(mo->momz, FixedDiv(17*FRACUNIT,20*FRACUNIT)); else mo->momz = 0; } @@ -2667,10 +2658,6 @@ nightsdone: } // Ugly ugly billions of braces! Argh! } - // hit the ceiling - if (mariomode) - S_StartSound(mo, sfx_mario1); - if (!mo->player->climbing) mo->momz = 0; } @@ -3316,7 +3303,9 @@ boolean P_CameraThinker(player_t *player, camera_t *thiscam, boolean resetcalled } } +#ifndef NOCLIPCAM P_CheckCameraPosition(thiscam->x, thiscam->y, thiscam); +#endif thiscam->subsector = R_PointInSubsector(thiscam->x, thiscam->y); thiscam->floorz = tmfloorz; @@ -9209,7 +9198,6 @@ void P_PushableThinker(mobj_t *mobj) if (GETSECSPECIAL(sec->special, 2) == 1 && mobj->z == sec->floorheight) P_LinedefExecute(sec->tag, mobj, sec); -// else if (GETSECSPECIAL(sec->special, 2) == 8) { sector_t *sec2; @@ -10500,11 +10488,8 @@ void P_RespawnSpecials(void) } //CTF rings should continue to respawn as normal rings outside of CTF. - if (gametype != GT_CTF) - { - if (i == MT_REDTEAMRING || i == MT_BLUETEAMRING) - i = MT_RING; - } + if (i == MT_REDTEAMRING || i == MT_BLUETEAMRING) + i = MT_RING; if (mthing->options & MTF_OBJECTFLIP) { @@ -10577,48 +10562,7 @@ void P_SpawnPlayer(INT32 playernum) } else if (multiplayer && !netgame) { - // If you're in a team game and you don't have a team assigned yet... - if (G_GametypeHasTeams() && p->ctfteam == 0) - { - changeteam_union NetPacket; - UINT16 usvalue; - NetPacket.value.l = NetPacket.value.b = 0; - - // Spawn as a spectator, - // yes even in splitscreen mode - p->spectator = true; - p->spectatorreentry = 0; //(cv_spectatorreentry.value * TICRATE); - - if (playernum&1) p->skincolor = skincolor_redteam; - else p->skincolor = skincolor_blueteam; - - // but immediately send a team change packet. - NetPacket.packet.playernum = playernum; - NetPacket.packet.verification = true; - NetPacket.packet.newteam = !(playernum&1) + 1; - - usvalue = SHORT(NetPacket.value.l|NetPacket.value.b); - SendNetXCmd(XD_TEAMCHANGE, &usvalue, sizeof(usvalue)); - } - else // Otherwise, never spectator. - p->spectator = false; - } - - if (G_GametypeHasTeams()) - { - // Fix stupid non spectator spectators. - if (!p->spectator && !p->ctfteam) - { - p->spectator = true; - p->spectatorreentry = 0; //(cv_spectatorreentry.value * TICRATE); - } - - // Fix team colors. - // This code isn't being done right somewhere else. Oh well. - if (p->ctfteam == 1) - p->skincolor = skincolor_redteam; - else if (p->ctfteam == 2) - p->skincolor = skincolor_blueteam; + p->spectator = false; } mobj = P_SpawnMobj(0, 0, 0, MT_PLAYER); @@ -11019,36 +10963,14 @@ void P_SpawnMapThing(mapthing_t *mthing) return; if (i >= MT_EMERALD1 && i <= MT_EMERALD7) // Pickupable Emeralds - { - if (gametype != GT_COOP) // Don't place emeralds in non-coop modes - return; - - if (metalrecording) - return; // Metal Sonic isn't for collecting emeralds. - - if (emeralds & mobjinfo[i].speed) // You already have this emerald! - return; - } + return; if (!G_BattleGametype() || !cv_specialrings.value) if (P_WeaponOrPanel(i)) return; // Don't place weapons/panels in non-ringslinger modes if (i == MT_EMERHUNT) - { - // Emerald Hunt is Coop only. - if (gametype != GT_COOP) - return; - - ss = R_PointInSubsector(mthing->x << FRACBITS, mthing->y << FRACBITS); - mthing->z = (INT16)((( - ss->sector->f_slope ? P_GetZAt(ss->sector->f_slope, mthing->x << FRACBITS, mthing->y << FRACBITS) : - ss->sector->floorheight)>>FRACBITS) + (mthing->options >> ZSHIFT)); - - if (numhuntemeralds < MAXHUNTEMERALDS) - huntemeralds[numhuntemeralds++] = mthing; return; - } if (i == MT_EMERALDSPAWN) { @@ -11065,57 +10987,29 @@ void P_SpawnMapThing(mapthing_t *mthing) if ((mobjinfo[i].flags & MF_ENEMY) || (mobjinfo[i].flags & MF_BOSS)) return; - // Set powerup boxes to user settings for competition. - if (gametype == GT_COMPETITION) - { - if ((mobjinfo[i].flags & MF_MONITOR) && cv_competitionboxes.value) // not Normal - { - if (cv_competitionboxes.value == 1) // Random - i = MT_QUESTIONBOX; - else if (cv_competitionboxes.value == 2) // Teleports - i = MT_MIXUPBOX; - else if (cv_competitionboxes.value == 3) // None - return; // Don't spawn! - } - } - // Set powerup boxes to user settings for other netplay modes - else if (gametype != GT_COOP) + if ((mobjinfo[i].flags & MF_MONITOR) && cv_matchboxes.value) // not Normal { - if ((mobjinfo[i].flags & MF_MONITOR) && cv_matchboxes.value) // not Normal - { - if (cv_matchboxes.value == 1) // Random - i = MT_QUESTIONBOX; - else if (cv_matchboxes.value == 3) // Don't spawn - return; - else // cv_matchboxes.value == 2, Non-Random - { - if (i == MT_QUESTIONBOX) - return; // don't spawn in Non-Random - - mthing->options &= ~(MTF_AMBUSH|MTF_OBJECTSPECIAL); // no random respawning! - } - } - } - - if (gametype != GT_CTF) // CTF specific things - { - if (i == MT_BLUETEAMRING || i == MT_REDTEAMRING) - i = MT_RING; - else if (i == MT_BLUERINGBOX || i == MT_REDRINGBOX) - i = MT_SUPERRINGBOX; - else if (i == MT_BLUEFLAG || i == MT_REDFLAG) - return; // No flags in non-CTF modes! - } - else - { - if ((i == MT_BLUEFLAG && blueflag) || (i == MT_REDFLAG && redflag)) - { - CONS_Alert(CONS_ERROR, M_GetText("Only one flag per team allowed in CTF!\n")); + if (cv_matchboxes.value == 1) // Random + i = MT_QUESTIONBOX; + else if (cv_matchboxes.value == 3) // Don't spawn return; + else // cv_matchboxes.value == 2, Non-Random + { + if (i == MT_QUESTIONBOX) + return; // don't spawn in Non-Random + + mthing->options &= ~(MTF_AMBUSH|MTF_OBJECTSPECIAL); // no random respawning! } } + if (i == MT_BLUETEAMRING || i == MT_REDTEAMRING) + i = MT_RING; + else if (i == MT_BLUERINGBOX || i == MT_REDRINGBOX) + i = MT_SUPERRINGBOX; + else if (i == MT_BLUEFLAG || i == MT_REDFLAG) + return; // No flags in non-CTF modes! + if (!G_RaceGametype() && (i == MT_SIGN || i == MT_STARPOST)) return; // Don't spawn exit signs or starposts in wrong game modes @@ -11145,7 +11039,7 @@ void P_SpawnMapThing(mapthing_t *mthing) return; // No rings in Ultimate mode (except special stages) } - if (i == MT_EMMY && (gametype != GT_COOP || ultimatemode || tokenbits == 30 || tokenlist & (1 << tokenbits++))) + if (i == MT_EMMY && (ultimatemode || tokenbits == 30 || tokenlist & (1 << tokenbits++))) return; // you already got this token, or there are too many, or the gametype's not right // Objectplace landing point @@ -12320,25 +12214,6 @@ mobj_t *P_SpawnMissile(mobj_t *source, mobj_t *dest, mobjtype_t type) return dist ? th : NULL; } -// -// P_ColorTeamMissile -// Colors a player's ring based on their team -// -void P_ColorTeamMissile(mobj_t *missile, player_t *source) -{ - if (G_GametypeHasTeams()) - { - if (source->ctfteam == 2) - missile->color = skincolor_bluering; - else if (source->ctfteam == 1) - missile->color = skincolor_redring; - } - /* - else - missile->color = player->mo->color; //copy color - */ -} - // // P_SPMAngle // Fires missile at angle from what is presumably a player diff --git a/src/p_setup.c b/src/p_setup.c index 93207a3c1..4f2518b88 100644 --- a/src/p_setup.c +++ b/src/p_setup.c @@ -319,8 +319,6 @@ static void P_ClearSingleMapHeaderInfo(INT16 i) mapheaderinfo[num]->saveoverride = SAVE_DEFAULT; mapheaderinfo[num]->levelflags = 0; mapheaderinfo[num]->menuflags = (mainwads ? 0 : LF2_EXISTSHACK); // see p_setup.c - prevents replacing maps in addons with easier versions - // TODO grades support for delfile (pfft yeah right) - P_DeleteGrades(num); // SRB2Kart //mapheaderinfo[num]->automap = false; mapheaderinfo[num]->mobj_scale = FRACUNIT; @@ -343,103 +341,6 @@ void P_AllocMapHeader(INT16 i) P_ClearSingleMapHeaderInfo(i + 1); } -/** NiGHTS Grades are a special structure, - * we initialize them here. - * - * \param i Index of header to allocate grades for - * \param mare The mare we're adding grades for - * \param grades the string from DeHackEd, we work with it ourselves - */ -void P_AddGradesForMare(INT16 i, UINT8 mare, char *gtext) -{ - INT32 g; - char *spos = gtext; - - CONS_Debug(DBG_SETUP, "Map %d Mare %d: ", i+1, (UINT16)mare+1); - - if (mapheaderinfo[i]->numGradedMares < mare+1) - { - mapheaderinfo[i]->numGradedMares = mare+1; - mapheaderinfo[i]->grades = Z_Realloc(mapheaderinfo[i]->grades, sizeof(nightsgrades_t) * mapheaderinfo[i]->numGradedMares, PU_STATIC, NULL); - } - - for (g = 0; g < 6; ++g) - { - // Allow "partial" grading systems - if (spos != NULL) - { - mapheaderinfo[i]->grades[mare].grade[g] = atoi(spos); - CONS_Debug(DBG_SETUP, "%u ", atoi(spos)); - // Grab next comma - spos = strchr(spos, ','); - if (spos) - ++spos; - } - else - { - // Grade not reachable - mapheaderinfo[i]->grades[mare].grade[g] = UINT32_MAX; - } - } - - CONS_Debug(DBG_SETUP, "\n"); -} - -/** And this removes the grades safely. - * - * \param i The header to remove grades from - */ -void P_DeleteGrades(INT16 i) -{ - if (mapheaderinfo[i]->grades) - Z_Free(mapheaderinfo[i]->grades); - - mapheaderinfo[i]->grades = NULL; - mapheaderinfo[i]->numGradedMares = 0; -} - -/** And this fetches the grades - * - * \param pscore The player's score. - * \param map The game map. - * \param mare The mare to test. - */ -UINT8 P_GetGrade(UINT32 pscore, INT16 map, UINT8 mare) -{ - INT32 i; - - // Determining the grade - if (mapheaderinfo[map-1] && mapheaderinfo[map-1]->grades && mapheaderinfo[map-1]->numGradedMares >= mare + 1) - { - INT32 pgrade = 0; - for (i = 0; i < 6; ++i) - { - if (pscore >= mapheaderinfo[map-1]->grades[mare].grade[i]) - ++pgrade; - } - return (UINT8)pgrade; - } - return 0; -} - -UINT8 P_HasGrades(INT16 map, UINT8 mare) -{ - // Determining the grade - // Mare 0 is treated as overall and is true if ANY grades exist - if (mapheaderinfo[map-1] && mapheaderinfo[map-1]->grades - && (mare == 0 || mapheaderinfo[map-1]->numGradedMares >= mare)) - return true; - return false; -} - -UINT32 P_GetScoreForGrade(INT16 map, UINT8 mare, UINT8 grade) -{ - // Get the score for the grade... if it exists - if (grade == GRADE_F || grade > GRADE_S || !P_HasGrades(map, mare)) return 0; - - return mapheaderinfo[map-1]->grades[mare].grade[grade-1]; -} - // Loads the vertexes for a level. FUNCINLINE static ATTRINLINE void P_LoadRawVertexes(UINT8 *data) { @@ -1546,16 +1447,23 @@ static void P_CreateBlockMap(void) // First find limits of map for (i = 0; i < numvertexes; i++) { - if (vertexes[i].x>>FRACBITS < minx) - minx = vertexes[i].x>>FRACBITS; - else if (vertexes[i].x>>FRACBITS > maxx) - maxx = vertexes[i].x>>FRACBITS; - if (vertexes[i].y>>FRACBITS < miny) - miny = vertexes[i].y>>FRACBITS; - else if (vertexes[i].y>>FRACBITS > maxy) - maxy = vertexes[i].y>>FRACBITS; + fixed_t t; + + if ((t = vertexes[i].x) < minx) + minx = t; + else if (t > maxx) + maxx = t; + if ((t = vertexes[i].y) < miny) + miny = t; + else if (t > maxy) + maxy = t; } + minx >>= FRACBITS; + maxx >>= FRACBITS; + miny >>= FRACBITS; + maxy >>= FRACBITS; + // Save blockmap parameters bmaporgx = minx << FRACBITS; bmaporgy = miny << FRACBITS; @@ -2439,7 +2347,6 @@ static void P_SetupCamera(UINT8 pnum, camera_t *cam) switch (gametype) { case GT_MATCH: - case GT_TAG: thing = deathmatchstarts[0]; break; @@ -2470,17 +2377,11 @@ static void P_InitCamera(void) P_SetupCamera(displayplayers[i], &camera[i]); // Though, I don't think anyone would care about cam_rotate being reset back to the only value that makes sense :P - if (!cv_cam_rotate.changed) - CV_Set(&cv_cam_rotate, cv_cam_rotate.defaultvalue); - - if (!cv_cam2_rotate.changed) - CV_Set(&cv_cam2_rotate, cv_cam2_rotate.defaultvalue); - - if (!cv_cam3_rotate.changed) - CV_Set(&cv_cam3_rotate, cv_cam3_rotate.defaultvalue); - - if (!cv_cam4_rotate.changed) - CV_Set(&cv_cam4_rotate, cv_cam4_rotate.defaultvalue); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + if (!cv_cam_rotate[i].changed) + CV_Set(&cv_cam_rotate[i], cv_cam_rotate[i].defaultvalue); + } displayplayers[0] = consoleplayer; // Start with your OWN view, please! } @@ -2611,18 +2512,11 @@ boolean P_SetupLevel(boolean skipprecip, boolean reloadinggamestate) if (!dedicated) { - if (!cv_chasecam.changed) - CV_SetValue(&cv_chasecam, chase); - - // same for second player - if (!cv_chasecam2.changed) - CV_SetValue(&cv_chasecam2, chase); - - if (!cv_chasecam3.changed) - CV_SetValue(&cv_chasecam3, chase); - - if (!cv_chasecam4.changed) - CV_SetValue(&cv_chasecam4, chase); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + if (!cv_chasecam[i].changed) + CV_SetValue(&cv_chasecam[i], chase); + } } // Initial height of PointOfView @@ -2866,44 +2760,7 @@ boolean P_SetupLevel(boolean skipprecip, boolean reloadinggamestate) if (modeattacking == ATTACKING_RECORD && !demo.playback) P_LoadRecordGhosts(); - if (G_TagGametype()) - { - INT32 realnumplayers = 0; - INT32 playersactive[MAXPLAYERS]; - - //I just realized how problematic this code can be. - //D_NumPlayers() will not always cover the scope of the netgame. - //What if one player is node 0 and the other node 31? - //The solution? Make a temp array of all players that are currently playing and pick from them. - //Future todo? When a player leaves, shift all nodes down so D_NumPlayers() can be used as intended? - //Also, you'd never have to loop through all 32 players slots to find anything ever again. - for (i = 0; i < MAXPLAYERS; i++) - { - if (playeringame[i] && !players[i].spectator) - { - playersactive[realnumplayers] = i; //stores the player's node in the array. - realnumplayers++; - } - } - - if (realnumplayers) //this should also fix the dedicated crash bug. You only pick a player if one exists to be picked. - { - i = P_RandomKey(realnumplayers); - players[playersactive[i]].pflags |= PF_TAGIT; //choose our initial tagger before map starts. - - // Taken and modified from G_DoReborn() - // Remove the player so he can respawn elsewhere. - // first dissasociate the corpse - if (players[playersactive[i]].mo) - P_RemoveMobj(players[playersactive[i]].mo); - - G_SpawnPlayer(playersactive[i], false); //respawn the lucky player in his dedicated spawn location. - } - else - CONS_Printf(M_GetText("No player currently available to become IT. Awaiting available players.\n")); - - } - else if (G_RaceGametype() && server) + if (G_RaceGametype() && server) CV_StealthSetValue(&cv_numlaps, ((netgame || multiplayer) && cv_basenumlaps.value && (!(mapheaderinfo[gamemap - 1]->levelflags & LF_SECTIONRACE) diff --git a/src/p_setup.h b/src/p_setup.h index 7f90564e0..295258fd8 100644 --- a/src/p_setup.h +++ b/src/p_setup.h @@ -97,11 +97,4 @@ void P_UpdateSegLightOffset(seg_t *li); size_t P_PrecacheLevelFlats(void); void P_AllocMapHeader(INT16 i); -// Needed for NiGHTS -void P_DeleteGrades(INT16 i); -void P_AddGradesForMare(INT16 i, UINT8 mare, char *gtext); -UINT8 P_GetGrade(UINT32 pscore, INT16 map, UINT8 mare); -UINT8 P_HasGrades(INT16 map, UINT8 mare); -UINT32 P_GetScoreForGrade(INT16 map, UINT8 mare, UINT8 grade); - #endif diff --git a/src/p_spec.c b/src/p_spec.c index 5f9ef78a6..2ff1b78b4 100644 --- a/src/p_spec.c +++ b/src/p_spec.c @@ -1431,12 +1431,14 @@ boolean P_RunTriggerLinedef(line_t *triggerline, mobj_t *actor, sector_t *caller } else if (caller) { - if (GETSECSPECIAL(caller->special, 2) == 6) + INT32 special = GETSECSPECIAL(caller->special, 2); + + if (special == 6) { if (!(ALL7EMERALDS(emeralds))) return false; } - else if (GETSECSPECIAL(caller->special, 2) == 7) // SRB2Kart: reusing for Race Lap executor + else if (special == 7) // SRB2Kart: reusing for Race Lap executor { UINT8 lap; @@ -1470,7 +1472,7 @@ boolean P_RunTriggerLinedef(line_t *triggerline, mobj_t *actor, sector_t *caller // If we were not triggered by a sector type especially for the purpose, // a Linedef Executor linedef trigger is not handling sector triggers properly, return. - else if ((!GETSECSPECIAL(caller->special, 2) || GETSECSPECIAL(caller->special, 2) > 7) && (specialtype > 322)) + else if ((!special || special > 7) && (specialtype > 322)) { CONS_Alert(CONS_WARNING, M_GetText("Linedef executor trigger isn't handling sector triggers properly!\nspecialtype = %d, if you are not a dev, report this warning instance\nalong with the wad that caused it!\n"), @@ -2630,14 +2632,6 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) mo->flags2 &= ~MF2_TWOD; else mo->flags2 |= MF2_TWOD; - - // Copy effect to bot if necessary - // (Teleport them to you so they don't break it.) - if (bot && (bot->flags2 & MF2_TWOD) != (mo->flags2 & MF2_TWOD)) - { - bot->flags2 = (bot->flags2 & ~MF2_TWOD) | (mo->flags2 & MF2_TWOD); - P_SetOrigin(bot, mo->x, mo->y, mo->z); - } } break; @@ -3401,9 +3395,6 @@ void P_ProcessSpecialSector(player_t *player, sector_t *sector, sector_t *rovers } P_DoPlayerPain(player, NULL, NULL); // this does basically everything that was here before - - if (gametype == GT_CTF && player->gotflag & (GF_REDFLAG|GF_BLUEFLAG)) - P_PlayerFlagBurst(player, false); break; case 12: // Wall Sector (Don't step-up/down) case 13: // Ramp Sector (Increase step-up/down) @@ -3423,7 +3414,7 @@ void P_ProcessSpecialSector(player_t *player, sector_t *sector, sector_t *rovers case 3: // Linedef executor requires all players present // Trigger Linedef Exec (Floor Touch, All Players) /// \todo check continues for proper splitscreen support? for (i = 0; i < MAXPLAYERS; i++) - if (playeringame[i] && !players[i].bot && players[i].mo && (gametype != GT_COOP || players[i].lives > 0)) + if (playeringame[i] && !players[i].bot && players[i].mo && players[i].lives > 0) { if (roversector) { @@ -3693,95 +3684,12 @@ DoneSection2: sstimer = 6; // Just let P_Ticker take care of the rest. // Exit (for FOF exits; others are handled in P_PlayerThink in p_user.c) - { - INT32 lineindex; - - P_DoPlayerExit(player); - - P_SetupSignExit(player); - // important: use sector->tag on next line instead of player->mo->subsector->tag - // this part is different from in P_PlayerThink, this is what was causing - // FOF custom exits not to work. - lineindex = P_FindSpecialLineFromTag(2, sector->tag, -1); - - if (gametype == GT_COOP && lineindex != -1) // Custom exit! - { - // Special goodies with the block monsters flag depending on emeralds collected - if ((lines[lineindex].flags & ML_BLOCKMONSTERS) && ALL7EMERALDS(emeralds)) - nextmapoverride = (INT16)(lines[lineindex].frontsector->ceilingheight>>FRACBITS); - else - nextmapoverride = (INT16)(lines[lineindex].frontsector->floorheight>>FRACBITS); - - if (lines[lineindex].flags & ML_NOCLIMB) - skipstats = true; - } - } + P_DoPlayerExit(player); + P_SetupSignExit(player); break; case 3: // Red Team's Base - if (gametype == GT_CTF && P_IsObjectOnGround(player->mo)) - { - if (player->ctfteam == 1 && (player->gotflag & GF_BLUEFLAG)) - { - mobj_t *mo; - - // Make sure the red team still has their own - // flag at their base so they can score. - if (!P_IsFlagAtBase(MT_REDFLAG)) - break; - - HU_SetCEchoFlags(0); - HU_SetCEchoDuration(5); - HU_DoCEcho(va(M_GetText("%s\\captured the blue flag.\\\\\\\\"), player_names[player-players])); - - if (splitscreen || players[consoleplayer].ctfteam == 1) - S_StartSound(NULL, sfx_flgcap); - else if (players[consoleplayer].ctfteam == 2) - S_StartSound(NULL, sfx_lose); - - mo = P_SpawnMobj(player->mo->x,player->mo->y,player->mo->z,MT_BLUEFLAG); - player->gotflag &= ~GF_BLUEFLAG; - mo->flags &= ~MF_SPECIAL; - mo->fuse = TICRATE; - mo->spawnpoint = bflagpoint; - mo->flags2 |= MF2_JUSTATTACKED; - redscore += 1; - P_AddPlayerScore(player, 5); - } - } - break; - case 4: // Blue Team's Base - if (gametype == GT_CTF && P_IsObjectOnGround(player->mo)) - { - if (player->ctfteam == 2 && (player->gotflag & GF_REDFLAG)) - { - mobj_t *mo; - - // Make sure the blue team still has their own - // flag at their base so they can score. - if (!P_IsFlagAtBase(MT_BLUEFLAG)) - break; - - HU_SetCEchoFlags(0); - HU_SetCEchoDuration(5); - HU_DoCEcho(va(M_GetText("%s\\captured the red flag.\\\\\\\\"), player_names[player-players])); - - if (splitscreen || players[consoleplayer].ctfteam == 2) - S_StartSound(NULL, sfx_flgcap); - else if (players[consoleplayer].ctfteam == 1) - S_StartSound(NULL, sfx_lose); - - mo = P_SpawnMobj(player->mo->x,player->mo->y,player->mo->z,MT_REDFLAG); - player->gotflag &= ~GF_REDFLAG; - mo->flags &= ~MF_SPECIAL; - mo->fuse = TICRATE; - mo->spawnpoint = rflagpoint; - mo->flags2 |= MF2_JUSTATTACKED; - bluescore += 1; - P_AddPlayerScore(player, 5); - } - } break; case 5: // Fan sector @@ -6081,8 +5989,7 @@ void P_SpawnSpecials(INT32 fromnetsave, boolean reloadinggamestate) // Linedef executor triggers for CTF teams. case 309: case 311: - if (gametype != GT_CTF) - lines[i].special = 0; + lines[i].special = 0; break; // Each time executors diff --git a/src/p_tick.c b/src/p_tick.c index 700424b17..f4d75683b 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -345,7 +345,7 @@ static void P_DeviceRumbleTick(void) if (!P_IsLocalPlayer(player)) continue; - if (G_GetDeviceForPlayer(i) == 0) + if (cv_usejoystick[i].value == 0) continue; if (!playeringame[displayplayers[i]] || player->spectator) @@ -641,7 +641,7 @@ void P_Ticker(boolean run) G_WriteAllGhostTics(); if (cv_recordmultiplayerdemos.value && (demo.savemode == DSM_NOTSAVING || demo.savemode == DSM_WILLAUTOSAVE)) - if (demo.savebutton && demo.savebutton + 3*TICRATE < leveltime && (InputDown(gc_lookback, 1) || (cv_usejoystick.value && axis > 0))) + if (demo.savebutton && demo.savebutton + 3*TICRATE < leveltime && (InputDown(gc_lookback, 1) || (cv_usejoystick[0].value && axis > 0))) demo.savemode = DSM_TITLEENTRY; //if there are no players left at all, stop demo recording @@ -689,16 +689,18 @@ void P_Ticker(boolean run) for (i = 0; i <= splitscreen; i++) { player_t *player = &players[displayplayers[i]]; - boolean isSkyVisibleForPlayer = skyVisiblePerPlayer[i]; if (!player->mo) continue; - if (isSkyVisibleForPlayer && skyboxmo[0] && cv_skybox.value) + const boolean skybox = (skyboxmo[0] && cv_skybox.value); + boolean isSkyVisibleForPlayer = skyVisiblePerPlayer[i]; + + if (isSkyVisibleForPlayer && skybox) { - R_SkyboxFrame(player); + R_SkyboxFrame(i); } - R_SetupFrame(player, (skyboxmo[0] && cv_skybox.value)); + R_SetupFrame(i, skybox); } } } diff --git a/src/p_user.c b/src/p_user.c index f8e4de294..fbcc0387b 100644 --- a/src/p_user.c +++ b/src/p_user.c @@ -76,9 +76,7 @@ void P_Thrust(mobj_t *mo, angle_t angle, fixed_t move) angle >>= ANGLETOFINESHIFT; mo->momx += FixedMul(move, FINECOSINE(angle)); - - if (!(twodlevel || (mo->flags2 & MF2_TWOD))) - mo->momy += FixedMul(move, FINESINE(angle)); + mo->momy += FixedMul(move, FINESINE(angle)); } @@ -93,9 +91,7 @@ void P_InstaThrust(mobj_t *mo, angle_t angle, fixed_t move) angle >>= ANGLETOFINESHIFT; mo->momx = FixedMul(move, FINECOSINE(angle)); - - if (!(twodlevel || (mo->flags2 & MF2_TWOD))) - mo->momy = FixedMul(move,FINESINE(angle)); + mo->momy = FixedMul(move,FINESINE(angle)); } void P_InstaThrustEvenIn2D(mobj_t *mo, angle_t angle, fixed_t move) @@ -427,8 +423,6 @@ void P_ResetPlayer(player_t *player) player->powers[pw_tailsfly] = 0; player->onconveyor = 0; player->skidtime = 0; - /*if (player-players == consoleplayer && botingame) - CV_SetValue(&cv_analog2, true);*/ } // @@ -457,24 +451,6 @@ void P_GivePlayerRings(player_t *player, INT32 num_rings) player->health = 1; } //} - - // Now extra life bonuses are handled here instead of in P_MovePlayer, since why not? - if (!ultimatemode && !modeattacking && !G_IsSpecialStage(gamemap) && G_GametypeUsesLives()) - { - INT32 gainlives = 0; - - while (player->xtralife < maxXtraLife && player->health > 100 * (player->xtralife+1)) - { - ++gainlives; - ++player->xtralife; - } - - if (gainlives) - { - P_GivePlayerLives(player, gainlives); - P_PlayLivesJingle(player); - } - } } // @@ -508,8 +484,6 @@ void P_DoSuperTransformation(player_t *player, boolean giverings) // Adds to the player's score void P_AddPlayerScore(player_t *player, UINT32 amount) { - //UINT32 oldscore; - if (!(G_BattleGametype())) return; @@ -519,22 +493,11 @@ void P_AddPlayerScore(player_t *player, UINT32 amount) if (player->exiting) // srb2kart return; - //oldscore = player->score; - // Don't go above MAXSCORE. if (player->marescore + amount < MAXSCORE) player->marescore += amount; else player->marescore = MAXSCORE; - - // In team match, all awarded points are incremented to the team's running score. - if (gametype == GT_TEAMMATCH) - { - if (player->ctfteam == 1) - redscore += amount; - else if (player->ctfteam == 2) - bluescore += amount; - } } // @@ -547,8 +510,6 @@ void P_PlayLivesJingle(player_t *player) if (use1upSound) S_StartSound(NULL, sfx_oneup); - else if (mariomode) - S_StartSound(NULL, sfx_marioa); else { if (player) @@ -580,7 +541,7 @@ void P_PlayRinglossSound(mobj_t *source, mobj_t *damager) S_StartSound(NULL, sfx); } else - S_StartSound(source, (mariomode) ? sfx_mario8 : sfx_khurt1 + key); + S_StartSound(source, sfx_khurt1 + key); } else S_StartSound(source, sfx_slip); @@ -1754,58 +1715,6 @@ static void P_DoBubbleBreath(player_t *player) return; } -// -// P_DoPlayerHeadSigns -// -// Spawns "IT" and "GOT FLAG" signs for Tag and CTF respectively -// -static void P_DoPlayerHeadSigns(player_t *player) -{ - if (G_TagGametype()) - { - // If you're "IT", show a big "IT" over your head for others to see. - if (player->pflags & PF_TAGIT) - { - if (!P_IsDisplayPlayer(player)) // Don't display it on your own view. - { - if (!(player->mo->eflags & MFE_VERTICALFLIP)) - P_SpawnMobj(player->mo->x, player->mo->y, player->mo->z + player->mo->height, MT_TAG); - else - P_SpawnMobj(player->mo->x, player->mo->y, player->mo->z - mobjinfo[MT_TAG].height, MT_TAG)->eflags |= MFE_VERTICALFLIP; - } - } - } - else if (gametype == GT_CTF) - { - if (player->gotflag & (GF_REDFLAG|GF_BLUEFLAG)) // If you have the flag (duh). - { - // Spawn a got-flag message over the head of the player that - // has it (but not on your own screen if you have the flag). - if (splitscreen || player != &players[consoleplayer]) - { - if (player->gotflag & GF_REDFLAG) - { - if (!(player->mo->eflags & MFE_VERTICALFLIP)) - P_SpawnMobj(player->mo->x+player->mo->momx, player->mo->y+player->mo->momy, - player->mo->z+P_GetPlayerHeight(player)+FixedMul(16*FRACUNIT, player->mo->scale)+player->mo->momz, MT_GOTFLAG); - else - P_SpawnMobj(player->mo->x+player->mo->momx, player->mo->y+player->mo->momy, - player->mo->z+player->mo->height-P_GetPlayerHeight(player)-mobjinfo[MT_GOTFLAG].height-FixedMul(16*FRACUNIT, player->mo->scale)+player->mo->momz, MT_GOTFLAG)->eflags |= MFE_VERTICALFLIP; - } - if (player->gotflag & GF_BLUEFLAG) - { - if (!(player->mo->eflags & MFE_VERTICALFLIP)) - P_SpawnMobj(player->mo->x+player->mo->momx, player->mo->y+player->mo->momy, - player->mo->z+P_GetPlayerHeight(player)+FixedMul(16*FRACUNIT, player->mo->scale)+player->mo->momz, MT_GOTFLAG2); - else - P_SpawnMobj(player->mo->x+player->mo->momx, player->mo->y+player->mo->momy, - player->mo->z+player->mo->height-P_GetPlayerHeight(player)-mobjinfo[MT_GOTFLAG2].height-FixedMul(16*FRACUNIT, player->mo->scale)+player->mo->momz, MT_GOTFLAG2)->eflags |= MFE_VERTICALFLIP; - } - } - } - } -} - // // P_DoJumpShield // @@ -2240,38 +2149,6 @@ static void P_MovePlayer(player_t *player) } // note: don't unset stasis here - if (!player->spectator && G_TagGametype()) - { - // If we have stasis already here, it's because it's forced on us - // by a linedef executor or what have you - boolean forcestasis = false; - - //During hide time, taggers cannot move. - if (leveltime < hidetime * TICRATE) - { - if (player->pflags & PF_TAGIT) - forcestasis = true; - } - else if (gametype == GT_HIDEANDSEEK) - { - if (!(player->pflags & PF_TAGIT)) - { - forcestasis = true; - if (player->pflags & PF_TAGGED) // Already hit. - player->powers[pw_flashing] = 5; - } - } - - if (forcestasis) - { - player->pflags |= PF_FULLSTASIS; - // If you're in stasis in tag, you don't drown. - /*if (player->powers[pw_underwater] <= 12*TICRATE + 1) - P_RestoreMusic(player);*/ - player->powers[pw_underwater] = player->powers[pw_spacetime] = 0; - } - } - if (player->spectator) { P_SpectatorMovement(player); @@ -2338,11 +2215,6 @@ static void P_MovePlayer(player_t *player) P_3dMovement(player); } - if (maptol & TOL_2D) - runspd = FixedMul(runspd, 2*FRACUNIT/3); - - //P_SkidStuff(player); - ///////////////////////// // MOVEMENT ANIMATIONS // ///////////////////////// @@ -2776,10 +2648,6 @@ boolean P_LookForEnemies(player_t *player) player->mo->z-mo->z) > FixedMul(RING_DIST, player->mo->scale)) continue; // out of range - if ((twodlevel || player->mo->flags2 & MF2_TWOD) - && abs(player->mo->y-mo->y) > player->mo->radius) - continue; // not in your 2d plane - if (mo->type == MT_PLAYER) // Don't chase after other players! continue; @@ -2976,34 +2844,34 @@ camera_t camera[MAXSPLITSCREENPLAYERS]; // Four cameras, three for splitscreen static void CV_CamRotate_OnChange(void) { - if (cv_cam_rotate.value < 0) - CV_SetValue(&cv_cam_rotate, cv_cam_rotate.value + 360); - else if (cv_cam_rotate.value > 359) - CV_SetValue(&cv_cam_rotate, cv_cam_rotate.value % 360); + if (cv_cam_rotate[0].value < 0) + CV_SetValue(&cv_cam_rotate[0], cv_cam_rotate[0].value + 360); + else if (cv_cam_rotate[0].value > 359) + CV_SetValue(&cv_cam_rotate[0], cv_cam_rotate[0].value % 360); } static void CV_CamRotate2_OnChange(void) { - if (cv_cam2_rotate.value < 0) - CV_SetValue(&cv_cam2_rotate, cv_cam2_rotate.value + 360); - else if (cv_cam2_rotate.value > 359) - CV_SetValue(&cv_cam2_rotate, cv_cam2_rotate.value % 360); + if (cv_cam_rotate[1].value < 0) + CV_SetValue(&cv_cam_rotate[1], cv_cam_rotate[1].value + 360); + else if (cv_cam_rotate[1].value > 359) + CV_SetValue(&cv_cam_rotate[1], cv_cam_rotate[1].value % 360); } static void CV_CamRotate3_OnChange(void) { - if (cv_cam3_rotate.value < 0) - CV_SetValue(&cv_cam3_rotate, cv_cam3_rotate.value + 360); - else if (cv_cam3_rotate.value > 359) - CV_SetValue(&cv_cam3_rotate, cv_cam3_rotate.value % 360); + if (cv_cam_rotate[2].value < 0) + CV_SetValue(&cv_cam_rotate[2], cv_cam_rotate[2].value + 360); + else if (cv_cam_rotate[2].value > 359) + CV_SetValue(&cv_cam_rotate[2], cv_cam_rotate[2].value % 360); } static void CV_CamRotate4_OnChange(void) { - if (cv_cam4_rotate.value < 0) - CV_SetValue(&cv_cam4_rotate, cv_cam4_rotate.value + 360); - else if (cv_cam4_rotate.value > 359) - CV_SetValue(&cv_cam4_rotate, cv_cam4_rotate.value % 360); + if (cv_cam_rotate[3].value < 0) + CV_SetValue(&cv_cam_rotate[3], cv_cam_rotate[3].value + 360); + else if (cv_cam_rotate[3].value > 359) + CV_SetValue(&cv_cam_rotate[3], cv_cam_rotate[3].value % 360); } static CV_PossibleValue_t CV_CamSpeed[] = {{0, "MIN"}, {1*FRACUNIT, "MAX"}, {0, NULL}}; @@ -3074,33 +2942,47 @@ static void CV_PlayerCam4_OnChange(void) P_ResetCamera(&players[displayplayers[3]], &camera[3]); } -consvar_t cv_cam_dist = {"cam_dist", "160", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam1_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam_height = {"cam_height", "50", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam1_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam_still = {"cam_still", "Off", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam_speed = {"cam_speed", "0.4", CV_FLOAT|CV_SAVE, CV_CamSpeed, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam_rotate = {"cam_rotate", "0", CV_CALL|CV_NOINIT, CV_CamRotate, CV_CamRotate_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam_rotspeed = {"cam_rotspeed", "10", CV_SAVE, rotation_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_cam_dist[MAXSPLITSCREENPLAYERS] = { + {"cam_dist", "160", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam1_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"cam2_dist", "160", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam2_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"cam3_dist", "160", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam3_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"cam4_dist", "160", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam4_OnChange, 0, NULL, NULL, 0, 0, NULL} +}; -consvar_t cv_cam2_dist = {"cam2_dist", "160", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam2_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam2_height = {"cam2_height", "50", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam2_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam2_still = {"cam2_still", "Off", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam2_speed = {"cam2_speed", "0.4", CV_FLOAT|CV_SAVE, CV_CamSpeed, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam2_rotate = {"cam2_rotate", "0", CV_CALL|CV_NOINIT, CV_CamRotate, CV_CamRotate2_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam2_rotspeed = {"cam2_rotspeed", "10", CV_SAVE, rotation_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_cam_height[MAXSPLITSCREENPLAYERS] = { + {"cam_height", "50", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam1_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"cam2_height", "50", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam2_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"cam3_height", "50", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam3_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"cam4_height", "50", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam4_OnChange, 0, NULL, NULL, 0, 0, NULL}, +}; -consvar_t cv_cam3_dist = {"cam3_dist", "160", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam3_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam3_height = {"cam3_height", "50", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam3_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam3_still = {"cam3_still", "Off", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam3_speed = {"cam3_speed", "0.4", CV_FLOAT|CV_SAVE, CV_CamSpeed, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam3_rotate = {"cam3_rotate", "0", CV_CALL|CV_NOINIT, CV_CamRotate, CV_CamRotate3_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam3_rotspeed = {"cam3_rotspeed", "10", CV_SAVE, rotation_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_cam_still[MAXSPLITSCREENPLAYERS] = { + {"cam_still", "Off", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"cam2_still", "Off", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"cam3_still", "Off", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"cam4_still", "Off", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL} +}; -consvar_t cv_cam4_dist = {"cam4_dist", "160", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam4_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam4_height = {"cam4_height", "50", CV_FLOAT|CV_SAVE|CV_CALL|CV_NOINIT, NULL, CV_PlayerCam4_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam4_still = {"cam4_still", "Off", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam4_speed = {"cam4_speed", "0.4", CV_FLOAT|CV_SAVE, CV_CamSpeed, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam4_rotate = {"cam4_rotate", "0", CV_CALL|CV_NOINIT, CV_CamRotate, CV_CamRotate4_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_cam4_rotspeed = {"cam4_rotspeed", "10", CV_SAVE, rotation_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_cam_speed[MAXSPLITSCREENPLAYERS] = { + {"cam_speed", "0.4", CV_FLOAT|CV_SAVE, CV_CamSpeed, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"cam2_speed", "0.4", CV_FLOAT|CV_SAVE, CV_CamSpeed, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"cam3_speed", "0.4", CV_FLOAT|CV_SAVE, CV_CamSpeed, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"cam4_speed", "0.4", CV_FLOAT|CV_SAVE, CV_CamSpeed, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_cam_rotate[MAXSPLITSCREENPLAYERS] = { + {"cam_rotate", "0", CV_CALL|CV_NOINIT, CV_CamRotate, CV_CamRotate_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"cam2_rotate", "0", CV_CALL|CV_NOINIT, CV_CamRotate, CV_CamRotate2_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"cam3_rotate", "0", CV_CALL|CV_NOINIT, CV_CamRotate, CV_CamRotate3_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"cam4_rotate", "0", CV_CALL|CV_NOINIT, CV_CamRotate, CV_CamRotate4_OnChange, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_cam_rotspeed[MAXSPLITSCREENPLAYERS] = { + {"cam_rotspeed", "10", CV_SAVE, rotation_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"cam2_rotspeed", "10", CV_SAVE, rotation_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"cam3_rotspeed", "10", CV_SAVE, rotation_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"cam4_rotspeed", "10", CV_SAVE, rotation_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL} +}; consvar_t cv_tilting = {"tilting", "Off", CV_SAVE|CV_CALL, CV_OnOff, Bird_menu_Onchange, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_quaketilt = {"quaketilt", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; @@ -3111,18 +2993,7 @@ consvar_t cv_actionmovie = {"actionmovie", "Off", CV_SAVE, CV_OnOff, NULL, 0, NU static CV_PossibleValue_t lookbackmom_cons_t[] = {{0, "Off"}, {1, "On"}, {2, "Double"}, {0, NULL}}; consvar_t cv_lookbackmom = {"cameralookbackmom", "Off", CV_SAVE, lookbackmom_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; -fixed_t t_cam_dist = -42; -fixed_t t_cam_height = -42; -fixed_t t_cam_rotate = -42; -fixed_t t_cam2_dist = -42; -fixed_t t_cam2_height = -42; -fixed_t t_cam2_rotate = -42; -fixed_t t_cam3_dist = -42; -fixed_t t_cam3_height = -42; -fixed_t t_cam3_rotate = -42; -fixed_t t_cam4_dist = -42; -fixed_t t_cam4_height = -42; -fixed_t t_cam4_rotate = -42; +fixed_t t_cam_rotate[MAXSPLITSCREENPLAYERS] = {-42, -42, -42, -42}; #define MAXCAMERADIST 140*FRACUNIT // Max distance the camera can be in front of the player (2D mode) @@ -3174,7 +3045,7 @@ static ticcmd_t *P_CameraCmd(camera_t *cam) mouseaiming = true; invertmouse = cv_invertmouse.value; - lookaxis = cv_lookaxis.value; + lookaxis = cv_lookaxis[0].value; usejoystick = true; turnright = InputDown(gc_turnright, 1); @@ -3388,14 +3259,8 @@ void P_ResetCamera(player_t *player, camera_t *thiscam) thiscam->z = z; thiscam->reset = true; - if (!(thiscam == &camera[0] && (cv_cam_still.value || cv_analog.value)) - && !(thiscam == &camera[1] && (cv_cam2_still.value || cv_analog2.value)) - && !(thiscam == &camera[2] && (cv_cam3_still.value || cv_analog3.value)) - && !(thiscam == &camera[3] && (cv_cam4_still.value || cv_analog4.value))) - { - thiscam->angle = player->mo->angle; - thiscam->aiming = 0; - } + thiscam->angle = player->mo->angle; + thiscam->aiming = 0; thiscam->relativex = 0; thiscam->subsector = R_PointInSubsector(thiscam->x,thiscam->y); @@ -3410,7 +3275,7 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall { static boolean lookbackactive[MAXSPLITSCREENPLAYERS]; static UINT8 lookbackdelay[MAXSPLITSCREENPLAYERS]; - UINT8 num; + UINT8 num, plyrnum; angle_t angle = 0, focusangle = 0, focusaiming = 0; fixed_t x, y, z, dist, viewpointx, viewpointy, camspeed, camdist, camheight, pviewheight; fixed_t pan, xpan, ypan; @@ -3440,6 +3305,44 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall return true; } + if (thiscam == &camera[1]) // Camera 2 + { + num = 1; + } + else if (thiscam == &camera[2]) // Camera 3 + { + num = 2; + } + else if (thiscam == &camera[3]) // Camera 4 + { + num = 3; + } + else // Camera 1 + { + num = 0; + } + + if (player == &players[consoleplayer]) + { + plyrnum = 0; + } + else if (player == &players[displayplayers[1]]) + { + plyrnum = 1; + } + else if (player == &players[displayplayers[2]]) + { + plyrnum = 2; + } + else if (player == &players[displayplayers[3]]) + { + plyrnum = 3; + } + else + { + plyrnum = 255; + } + mo = player->mo; #ifndef NOCLIPCAM @@ -3458,42 +3361,22 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall if (player->spectator) // force cam off for spectators return true; - if (!cv_chasecam.value && thiscam == &camera[0]) - return true; - - if (!cv_chasecam2.value && thiscam == &camera[1]) - return true; - - if (!cv_chasecam3.value && thiscam == &camera[2]) - return true; - - if (!cv_chasecam4.value && thiscam == &camera[3]) + if (!cv_chasecam[num].value && thiscam == &camera[num]) return true; } if (!thiscam->chase && !resetcalled) { - if (player == &players[consoleplayer]) - focusangle = localangle[0]; - else if (player == &players[displayplayers[1]]) - focusangle = localangle[1]; - else if (player == &players[displayplayers[2]]) - focusangle = localangle[2]; - else if (player == &players[displayplayers[3]]) - focusangle = localangle[3]; + if (plyrnum != 255) + { + focusangle = localangle[plyrnum]; + } else + { focusangle = mo->angle; + } - if (thiscam == &camera[0]) - camrotate = cv_cam_rotate.value; - else if (thiscam == &camera[1]) - camrotate = cv_cam2_rotate.value; - else if (thiscam == &camera[2]) - camrotate = cv_cam3_rotate.value; - else if (thiscam == &camera[3]) - camrotate = cv_cam4_rotate.value; - else - camrotate = 0; + camrotate = cv_cam_rotate[num].value; if (leveltime < introtime) // Whoooshy camera! { @@ -3509,35 +3392,15 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall thiscam->radius = 20*mapobjectscale; thiscam->height = 16*mapobjectscale; - // Don't run while respawning from a starpost - // Inu 4/8/13 Why not?! -// if (leveltime > 0 && timeinmap <= 0) -// return true; - if (demo.playback) { focusangle = mo->angle; focusaiming = 0; } - else if (player == &players[consoleplayer]) + else if (plyrnum != 255) { - focusangle = localangle[0]; - focusaiming = localaiming[0]; - } - else if (player == &players[displayplayers[1]]) - { - focusangle = localangle[1]; - focusaiming = localaiming[1]; - } - else if (player == &players[displayplayers[2]]) - { - focusangle = localangle[2]; - focusaiming = localaiming[2]; - } - else if (player == &players[displayplayers[3]]) - { - focusangle = localangle[3]; - focusaiming = localaiming[3]; + focusangle = localangle[plyrnum]; + focusaiming = localaiming[plyrnum]; } else { @@ -3548,46 +3411,12 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall if (P_CameraThinker(player, thiscam, resetcalled)) return true; - if (thiscam == &camera[1]) // Camera 2 - { - num = 1; - camspeed = cv_cam2_speed.value; - camstill = cv_cam2_still.value; - camrotate = cv_cam2_rotate.value; - camdist = FixedMul(cv_cam2_dist.value, mapobjectscale); - camheight = FixedMul(cv_cam2_height.value, mapobjectscale); - lookback = camspin[1]; - } - else if (thiscam == &camera[2]) // Camera 3 - { - num = 2; - camspeed = cv_cam3_speed.value; - camstill = cv_cam3_still.value; - camrotate = cv_cam3_rotate.value; - camdist = FixedMul(cv_cam3_dist.value, mapobjectscale); - camheight = FixedMul(cv_cam3_height.value, mapobjectscale); - lookback = camspin[2]; - } - else if (thiscam == &camera[3]) // Camera 4 - { - num = 3; - camspeed = cv_cam4_speed.value; - camstill = cv_cam4_still.value; - camrotate = cv_cam4_rotate.value; - camdist = FixedMul(cv_cam4_dist.value, mapobjectscale); - camheight = FixedMul(cv_cam4_height.value, mapobjectscale); - lookback = camspin[3]; - } - else // Camera 1 - { - num = 0; - camspeed = cv_cam_speed.value; - camstill = cv_cam_still.value; - camrotate = cv_cam_rotate.value; - camdist = FixedMul(cv_cam_dist.value, mapobjectscale); - camheight = FixedMul(cv_cam_height.value, mapobjectscale); - lookback = camspin[0]; - } + camspeed = cv_cam_speed[num].value; + camstill = cv_cam_still[num].value; + camrotate = cv_cam_rotate[num].value; + camdist = FixedMul(cv_cam_dist[num].value, mapobjectscale); + camheight = FixedMul(cv_cam_height[num].value, mapobjectscale); + lookback = camspin[num]; if (timeover) { @@ -3651,10 +3480,7 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall } if (!resetcalled && (leveltime > starttime && timeover != 2) - && ((thiscam == &camera[0] && t_cam_rotate != -42) - || (thiscam == &camera[1] && t_cam2_rotate != -42) - || (thiscam == &camera[2] && t_cam3_rotate != -42) - || (thiscam == &camera[3] && t_cam4_rotate != -42))) + && (t_cam_rotate[num] != -42)) { angle = FixedAngle(camrotate*FRACUNIT); thiscam->angle = angle; @@ -3954,7 +3780,7 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall if (player->playerstate != PST_DEAD && !((player->pflags & PF_NIGHTSMODE) && player->exiting)) angle += (focusaiming < ANGLE_180 ? focusaiming/2 : InvAngle(InvAngle(focusaiming)/2)); // overcomplicated version of '((signed)focusaiming)/2;' - if (twodlevel || (mo->flags2 & MF2_TWOD) || (!camstill && !timeover)) // Keep the view still... + if (!camstill && !timeover) // Keep the view still... { G_ClipAimingPitch((INT32 *)&angle); @@ -4019,65 +3845,8 @@ boolean P_SpectatorJoinGame(player_t *player) { if (P_IsLocalPlayer(player)) CONS_Printf(M_GetText("Server does not allow team change.\n")); - //player->powers[pw_flashing] = TICRATE + 1; //to prevent message spam. } - // Team changing in Team Match and CTF - // Pressing fire assigns you to a team that needs players if allowed. - // Partial code reproduction from p_tick.c autobalance code. - else if (G_GametypeHasTeams()) - { - INT32 changeto = 0; - INT32 z, numplayersred = 0, numplayersblue = 0; - - //find a team by num players, score, or random if all else fails. - for (z = 0; z < MAXPLAYERS; ++z) - if (playeringame[z]) - { - if (players[z].ctfteam == 1) - ++numplayersred; - else if (players[z].ctfteam == 2) - ++numplayersblue; - } - // for z - - if (numplayersblue > numplayersred) - changeto = 1; - else if (numplayersred > numplayersblue) - changeto = 2; - else if (bluescore > redscore) - changeto = 1; - else if (redscore > bluescore) - changeto = 2; - else - changeto = (P_RandomFixed() & 1) + 1; - - if (player->mo) - { - P_RemoveMobj(player->mo); - player->mo = NULL; - } - player->spectator = false; - player->pflags &= ~PF_WANTSTOJOIN; - player->kartstuff[k_spectatewait] = 0; - player->ctfteam = changeto; - player->playerstate = PST_REBORN; - - //center camera - P_ResetLocalCamAiming(player); - - //Reset away view - if (P_IsLocalPlayer(player) && displayplayers[0] != consoleplayer) - displayplayers[0] = consoleplayer; - - if (changeto == 1) - CONS_Printf(M_GetText("%s switched to the %c%s%c.\n"), player_names[player-players], '\x85', M_GetText("Red team"), '\x80'); - else if (changeto == 2) - CONS_Printf(M_GetText("%s switched to the %c%s%c.\n"), player_names[player-players], '\x84', M_GetText("Blue team"), '\x80'); - - return true; // no more player->mo, cannot continue. - } - // Joining in game from firing. - else + else // Joining in game from firing. { if (player->mo) { @@ -4654,39 +4423,6 @@ void P_PlayerThink(player_t *player) { player->pflags ^= PF_WANTSTOJOIN; player->powers[pw_flashing] = TICRATE/2 + 1; - /*if (P_SpectatorJoinGame(player)) - return; // player->mo was removed.*/ - } - - // Even if not NiGHTS, pull in nearby objects when walking around as John Q. Elliot. - if (!objectplacing && !((netgame || multiplayer) && player->spectator) - && maptol & TOL_NIGHTS && (!(player->pflags & PF_NIGHTSMODE) || player->powers[pw_nights_helper])) - { - thinker_t *th; - mobj_t *mo2; - fixed_t x = player->mo->x; - fixed_t y = player->mo->y; - fixed_t z = player->mo->z; - - for (th = thinkercap.next; th != &thinkercap; th = th->next) - { - if (th->function.acp1 != (actionf_p1)P_MobjThinker) - continue; - - mo2 = (mobj_t *)th; - - if (!(mo2->type == MT_NIGHTSWING || mo2->type == MT_RING || mo2->type == MT_COIN - || mo2->type == MT_BLUEBALL)) - continue; - - if (P_AproxDistance(P_AproxDistance(mo2->x - x, mo2->y - y), mo2->z - z) > FixedMul(128*FRACUNIT, player->mo->scale)) - continue; - - // Yay! The thing's in reach! Pull it in! - mo2->flags |= MF_NOCLIP|MF_NOCLIPHEIGHT; - mo2->flags2 |= MF2_NIGHTSPULL; - P_SetTarget(&mo2->tracer, player->mo); - } } if (player->linktimer && !player->powers[pw_nights_linkfreeze]) @@ -4725,14 +4461,9 @@ void P_PlayerThink(player_t *player) if (player->onconveyor == 1) player->cmomy = player->cmomx = 0; - //P_DoSuperStuff(player); - //P_CheckSneakerAndLivesTimer(player); P_DoBubbleBreath(player); // Spawn Sonic's bubbles - //P_CheckUnderwaterAndSpaceTimer(player); // Display the countdown drown numbers! P_CheckInvincibilityTimer(player); // Spawn Invincibility Sparkles - P_DoPlayerHeadSigns(player); // Spawn Tag/CTF signs over player's head -#if 1 // "Blur" a bit when you have speed shoes and are going fast enough if ((player->powers[pw_super] || player->powers[pw_sneakers] || player->kartstuff[k_driftboost] || player->kartstuff[k_sneakertimer] || player->kartstuff[k_startboost]) && !player->kartstuff[k_invincibilitytimer] // SRB2kart @@ -4760,7 +4491,6 @@ void P_PlayerThink(player_t *player) } } } -#endif // check for use if (!(player->pflags & PF_NIGHTSMODE)) @@ -4947,7 +4677,6 @@ void P_PlayerAfterThink(player_t *player) if (player->pflags & PF_NIGHTSMODE) { player->powers[pw_gravityboots] = 0; - //player->mo->eflags &= ~MFE_VERTICALFLIP; } if (player->pflags & PF_SLIDING) @@ -4970,8 +4699,7 @@ void P_PlayerAfterThink(player_t *player) else if (cmd->forwardmove < 0 && player->mo->tracer->target->lastlook > player->mo->tracer->target->movecount) player->mo->tracer->target->lastlook -= 2; - if (!(player->mo->tracer->target->flags & MF_SLIDEME) // Noclimb on chain parameters gives this - && !(twodlevel || player->mo->flags2 & MF2_TWOD)) // why on earth would you want to turn them in 2D mode? + if (!(player->mo->tracer->target->flags & MF_SLIDEME)) // Noclimb on chain parameters gives this { player->mo->tracer->target->health += cmd->sidemove; player->mo->angle += cmd->sidemove< ANGLE_MAX diff --git a/src/r_bsp.c b/src/r_bsp.c index 500a58035..989939860 100644 --- a/src/r_bsp.c +++ b/src/r_bsp.c @@ -627,7 +627,21 @@ static boolean R_CheckBBox(const fixed_t *bspcoord) cliprange_t *start; // Find the corners of the box that define the edges from current viewpoint. - if ((boxpos = (viewx <= bspcoord[BOXLEFT] ? 0 : viewx < bspcoord[BOXRIGHT] ? 1 : 2) + (viewy >= bspcoord[BOXTOP] ? 0 : viewy > bspcoord[BOXBOTTOM] ? 4 : 8)) == 5) + if (viewx <= bspcoord[BOXLEFT]) + boxpos = 0; + else if (viewx < bspcoord[BOXRIGHT]) + boxpos = 1; + else + boxpos = 2; + + if (viewy >= bspcoord[BOXTOP]) + boxpos |= 0; + else if (viewy > bspcoord[BOXBOTTOM]) + boxpos |= 1<<2; + else + boxpos |= 2<<2; + + if (boxpos == 5) return true; check = checkcoord[boxpos]; @@ -656,7 +670,8 @@ static boolean R_CheckBBox(const fixed_t *bspcoord) sx2 = viewangletox[angle2]; // Does not cross a pixel. - if (sx1 >= sx2) return false; + if (sx1 >= sx2) + return false; start = solidsegs; while (start->last < sx2) diff --git a/src/r_main.c b/src/r_main.c index c2c7210e2..59e5c5e90 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -161,14 +161,20 @@ void SendWeaponPref4(void); static void Precipstuff_OnChange(void); consvar_t cv_tailspickup = {"tailspickup", "On", CV_NETVAR|CV_NOSHOWHELP, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_chasecam = {"chasecam", "On", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_chasecam2 = {"chasecam2", "On", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_chasecam3 = {"chasecam3", "On", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_chasecam4 = {"chasecam4", "On", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_flipcam = {"flipcam", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, FlipCam_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_flipcam2 = {"flipcam2", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, FlipCam2_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_flipcam3 = {"flipcam3", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, FlipCam3_OnChange, 0, NULL, NULL, 0, 0, NULL}; -consvar_t cv_flipcam4 = {"flipcam4", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, FlipCam4_OnChange, 0, NULL, NULL, 0, 0, NULL}; + +consvar_t cv_chasecam[MAXSPLITSCREENPLAYERS] = { + {"chasecam", "On", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"chasecam2", "On", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"chasecam3", "On", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}, + {"chasecam4", "On", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL} +}; + +consvar_t cv_flipcam[MAXSPLITSCREENPLAYERS] = { + {"flipcam", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, FlipCam_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"flipcam2", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, FlipCam2_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"flipcam3", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, FlipCam3_OnChange, 0, NULL, NULL, 0, 0, NULL}, + {"flipcam4", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, FlipCam4_OnChange, 0, NULL, NULL, 0, 0, NULL} +}; consvar_t cv_shadow = {"shadow", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_shadowoffs = {"offsetshadows", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; @@ -1069,10 +1075,6 @@ subsector_t *R_IsPointInSubsector(fixed_t x, fixed_t y) size_t nodenum; subsector_t *ret; - // single subsector is a special case - //if (numnodes == 0) - //return subsectors; - nodenum = numnodes - 1; while (!(nodenum & NF_SUBSECTOR)) @@ -1096,38 +1098,29 @@ subsector_t *R_IsPointInSubsector(fixed_t x, fixed_t y) mobj_t *viewmobj; -void R_SkyboxFrame(player_t *player) +static void +R_SetupCommonFrame +( player_t * player, + subsector_t * subsector) { - camera_t *thiscam = &camera[0]; - UINT8 i; + newview->player = player; - if (splitscreen) - { - for (i = 0; i <= splitscreen; i++) - { - if (player == &players[displayplayers[i]]) - { - thiscam = &camera[i]; - R_SetViewContext(VIEWCONTEXT_SKY1 + i); - break; - } - } - } + newview->x += quake.x; + newview->y += quake.y; + newview->z += quake.z; + + newview->roll = R_ViewRollAngle(player); + + if (subsector) + newview->sector = subsector->sector; else - { - R_SetViewContext(VIEWCONTEXT_SKY1); - } + newview->sector = R_PointInSubsector(newview->x, newview->y)->sector; - // cut-away view stuff - newview->sky = true; - viewmobj = skyboxmo[0]; -#ifdef PARANOIA - if (!viewmobj) - { - const size_t playeri = (size_t)(player - players); - I_Error("R_SkyboxFrame: viewmobj null (player %s)", sizeu1(playeri)); - } -#endif + R_InterpolateView(R_UsingFrameInterpolation() ? (demo.playback && demo.freecam) ? rendertimefrac_unpaused : rendertimefrac : FRACUNIT, false); +} + +static void R_SetupAimingFrame(player_t *player, camera_t *thiscam) +{ if (player->awayviewtics) { newview->aim = player->awayviewaiming; @@ -1142,31 +1135,42 @@ void R_SkyboxFrame(player_t *player) { newview->aim = player->aiming; newview->angle = player->mo->angle; + if (!demo.playback && player->playerstate != PST_DEAD) { - if (player == &players[consoleplayer]) + for (UINT8 i = 0; i <= splitscreen; i++) { - newview->angle = localangle[0]; // WARNING: camera uses this - newview->aim = localaiming[0]; - } - else if (splitscreen) - { - for (i = 1; i <= splitscreen; i++) + if (player == (i == 0 ? &players[consoleplayer] : &players[displayplayers[i]])) { - if (player == &players[displayplayers[i]]) - { - newview->angle = localangle[i]; - newview->aim = localaiming[i]; - break; - } + newview->angle = localangle[i]; + newview->aim = localaiming[i]; + break; } } } } - newview->angle += viewmobj->angle; - newview->roll = R_ViewRollAngle(player); +} - newview->player = player; +void R_SkyboxFrame(int s) +{ + player_t *player = &players[displayplayers[s]]; + camera_t *thiscam = &camera[s]; + + R_SetViewContext(VIEWCONTEXT_SKY1 + s); + + // cut-away view stuff + newview->sky = true; + viewmobj = skyboxmo[0]; +#ifdef PARANOIA + if (!viewmobj) + { + const size_t playeri = (size_t)(player - players); + I_Error("R_SkyboxFrame: viewmobj null (player %s)", sizeu1(playeri)); + } +#endif + R_SetupAimingFrame(player, thiscam); + + newview->angle += viewmobj->angle; newview->x = viewmobj->x; newview->y = viewmobj->y; @@ -1174,211 +1178,83 @@ void R_SkyboxFrame(player_t *player) if (viewmobj->spawnpoint) newview->z = ((fixed_t)viewmobj->spawnpoint->angle)<x += quake.x; - newview->y += quake.y; - newview->z += quake.z; +#define SETUPSKYVIEW(viewmo, zscale)\ + if (skyboxmo[1])\ + {\ + fixed_t x = 0, y = 0;\ + if (mh->skybox_scalex > 0)\ + x = (viewmo->x - skyboxmo[1]->x) / mh->skybox_scalex;\ + else if (mh->skybox_scalex < 0)\ + x = (viewmo->x - skyboxmo[1]->x) * -mh->skybox_scalex;\ + if (mh->skybox_scaley > 0)\ + y = (viewmo->y - skyboxmo[1]->y) / mh->skybox_scaley;\ + else if (mh->skybox_scaley < 0)\ + y = (viewmo->y - skyboxmo[1]->y) * -mh->skybox_scaley;\ + if (viewmobj->angle == 0)\ + {\ + newview->x += x;\ + newview->y += y;\ + }\ + else if (viewmobj->angle == ANGLE_90)\ + {\ + newview->x -= y;\ + newview->y += x;\ + }\ + else if (viewmobj->angle == ANGLE_180)\ + {\ + newview->x -= x;\ + newview->y -= y;\ + }\ + else if (viewmobj->angle == ANGLE_270)\ + {\ + newview->x += y;\ + newview->y -= x;\ + }\ + else\ + {\ + angle_t ang = viewmobj->angle>>ANGLETOFINESHIFT;\ + newview->x += FixedMul(x,FINECOSINE(ang)) - FixedMul(y, FINESINE(ang));\ + newview->y += FixedMul(x, FINESINE(ang)) + FixedMul(y,FINECOSINE(ang));\ + }\ + }\ + if (mh->skybox_scalez > 0)\ + newview->z += zscale / mh->skybox_scalez;\ + else if (mh->skybox_scalez < 0)\ + newview->z += zscale * -mh->skybox_scalez; if (mapheaderinfo[gamemap-1]) { mapheader_t *mh = mapheaderinfo[gamemap-1]; + if (player->awayviewtics) { - if (skyboxmo[1]) - { - fixed_t x = 0, y = 0; - if (mh->skybox_scalex > 0) - x = (player->awayviewmobj->x - skyboxmo[1]->x) / mh->skybox_scalex; - else if (mh->skybox_scalex < 0) - x = (player->awayviewmobj->x - skyboxmo[1]->x) * -mh->skybox_scalex; - - if (mh->skybox_scaley > 0) - y = (player->awayviewmobj->y - skyboxmo[1]->y) / mh->skybox_scaley; - else if (mh->skybox_scaley < 0) - y = (player->awayviewmobj->y - skyboxmo[1]->y) * -mh->skybox_scaley; - - if (viewmobj->angle == 0) - { - newview->x += x; - newview->y += y; - } - else if (viewmobj->angle == ANGLE_90) - { - newview->x -= y; - newview->y += x; - } - else if (viewmobj->angle == ANGLE_180) - { - newview->x -= x; - newview->y -= y; - } - else if (viewmobj->angle == ANGLE_270) - { - newview->x += y; - newview->y -= x; - } - else - { - angle_t ang = viewmobj->angle>>ANGLETOFINESHIFT; - newview->x += FixedMul(x,FINECOSINE(ang)) - FixedMul(y, FINESINE(ang)); - newview->y += FixedMul(x, FINESINE(ang)) + FixedMul(y,FINECOSINE(ang)); - } - } - if (mh->skybox_scalez > 0) - newview->z += (player->awayviewmobj->z + 20*FRACUNIT) / mh->skybox_scalez; - else if (mh->skybox_scalez < 0) - newview->z += (player->awayviewmobj->z + 20*FRACUNIT) * -mh->skybox_scalez; + SETUPSKYVIEW(player->awayviewmobj, (player->awayviewmobj->z + 20*FRACUNIT)); } else if (thiscam->chase) { - if (skyboxmo[1]) - { - fixed_t x = 0, y = 0; - if (mh->skybox_scalex > 0) - x = (thiscam->x - skyboxmo[1]->x) / mh->skybox_scalex; - else if (mh->skybox_scalex < 0) - x = (thiscam->x - skyboxmo[1]->x) * -mh->skybox_scalex; - - if (mh->skybox_scaley > 0) - y = (thiscam->y - skyboxmo[1]->y) / mh->skybox_scaley; - else if (mh->skybox_scaley < 0) - y = (thiscam->y - skyboxmo[1]->y) * -mh->skybox_scaley; - - if (viewmobj->angle == 0) - { - newview->x += x; - newview->y += y; - } - else if (viewmobj->angle == ANGLE_90) - { - newview->x -= y; - newview->y += x; - } - else if (viewmobj->angle == ANGLE_180) - { - newview->x -= x; - newview->y -= y; - } - else if (viewmobj->angle == ANGLE_270) - { - newview->x += y; - newview->y -= x; - } - else - { - angle_t ang = viewmobj->angle>>ANGLETOFINESHIFT; - newview->x += FixedMul(x,FINECOSINE(ang)) - FixedMul(y, FINESINE(ang)); - newview->y += FixedMul(x, FINESINE(ang)) + FixedMul(y,FINECOSINE(ang)); - } - } - if (mh->skybox_scalez > 0) - newview->z += (thiscam->z + (thiscam->height>>1)) / mh->skybox_scalez; - else if (mh->skybox_scalez < 0) - newview->z += (thiscam->z + (thiscam->height>>1)) * -mh->skybox_scalez; + SETUPSKYVIEW(thiscam, (thiscam->z + (thiscam->height>>1))); } else { - if (skyboxmo[1]) - { - fixed_t x = 0, y = 0; - if (mh->skybox_scalex > 0) - x = (player->mo->x - skyboxmo[1]->x) / mh->skybox_scalex; - else if (mh->skybox_scalex < 0) - x = (player->mo->x - skyboxmo[1]->x) * -mh->skybox_scalex; - if (mh->skybox_scaley > 0) - y = (player->mo->y - skyboxmo[1]->y) / mh->skybox_scaley; - else if (mh->skybox_scaley < 0) - y = (player->mo->y - skyboxmo[1]->y) * -mh->skybox_scaley; - - if (viewmobj->angle == 0) - { - newview->x += x; - newview->y += y; - } - else if (viewmobj->angle == ANGLE_90) - { - newview->x -= y; - newview->y += x; - } - else if (viewmobj->angle == ANGLE_180) - { - newview->x -= x; - newview->y -= y; - } - else if (viewmobj->angle == ANGLE_270) - { - newview->x += y; - newview->y -= x; - } - else - { - angle_t ang = viewmobj->angle>>ANGLETOFINESHIFT; - newview->x += FixedMul(x,FINECOSINE(ang)) - FixedMul(y, FINESINE(ang)); - newview->y += FixedMul(x, FINESINE(ang)) + FixedMul(y,FINECOSINE(ang)); - } - } - if (mh->skybox_scalez > 0) - newview->z += player->viewz / mh->skybox_scalez; - else if (mh->skybox_scalez < 0) - newview->z += player->viewz * -mh->skybox_scalez; + SETUPSKYVIEW(player->mo, player->viewz); } } +#undef SETUPSKYVIEW - if (viewmobj->subsector) - newview->sector = viewmobj->subsector->sector; - else - newview->sector = R_PointInSubsector(newview->x, newview->y)->sector; - - R_InterpolateView(R_UsingFrameInterpolation() ? (demo.playback && demo.freecam) ? rendertimefrac_unpaused : rendertimefrac : FRACUNIT, false); + R_SetupCommonFrame(player, viewmobj->subsector); } -void R_SetupFrame(player_t *player, boolean skybox) +void R_SetupFrame(int s, boolean skybox) { - camera_t *thiscam; - boolean chasecam = false; + player_t *player = &players[displayplayers[s]]; + camera_t *thiscam = &camera[s]; + boolean chasecam = (cv_chasecam[s].value != 0); - if (splitscreen > 2 && player == &players[displayplayers[3]]) + R_SetViewContext(VIEWCONTEXT_PLAYER1 + s); + if (thiscam->reset) { - thiscam = &camera[3]; - chasecam = (cv_chasecam4.value != 0); - R_SetViewContext(VIEWCONTEXT_PLAYER4); - if (thiscam->reset) - { - R_ResetViewInterpolation(4); - thiscam->reset = false; - } - } - else if (splitscreen > 1 && player == &players[displayplayers[2]]) - { - thiscam = &camera[2]; - chasecam = (cv_chasecam3.value != 0); - R_SetViewContext(VIEWCONTEXT_PLAYER3); - if (thiscam->reset) - { - R_ResetViewInterpolation(3); - thiscam->reset = false; - } - } - else if (splitscreen && player == &players[displayplayers[1]]) - { - thiscam = &camera[1]; - chasecam = (cv_chasecam2.value != 0); - R_SetViewContext(VIEWCONTEXT_PLAYER2); - if (thiscam->reset) - { - R_ResetViewInterpolation(2); - thiscam->reset = false; - } - } - else - { - thiscam = &camera[0]; - chasecam = (cv_chasecam.value != 0); - R_SetViewContext(VIEWCONTEXT_PLAYER1); - if (thiscam->reset) - { - R_ResetViewInterpolation(1); - thiscam->reset = false; - } + R_ResetViewInterpolation(s); + thiscam->reset = false; } if (player->spectator) // no spectator chasecam @@ -1396,84 +1272,40 @@ void R_SetupFrame(player_t *player, boolean skybox) newview->sky = !skybox; + R_SetupAimingFrame(player, thiscam); + if (player->awayviewtics) // cut-away view stuff { viewmobj = player->awayviewmobj; // should be a MT_ALTVIEWMAN I_Assert(viewmobj != NULL); + + newview->x = viewmobj->x; + newview->y = viewmobj->y; newview->z = viewmobj->z + 20*FRACUNIT; - newview->aim = player->awayviewaiming; - newview->angle = viewmobj->angle; + + R_SetupCommonFrame(player, viewmobj->subsector); } else if (!player->spectator && (thiscam && chasecam)) // use outside cam view { viewmobj = NULL; + + newview->x = thiscam->x; + newview->y = thiscam->y; newview->z = thiscam->z + (thiscam->height>>1); - newview->aim = thiscam->aiming; - newview->angle = thiscam->angle; + + R_SetupCommonFrame(player, thiscam->subsector); } else // use the player's eyes view { - newview->z = player->viewz; - viewmobj = player->mo; I_Assert(viewmobj != NULL); - newview->aim = player->aiming; - newview->angle = viewmobj->angle; - - if (!demo.playback && player->playerstate != PST_DEAD) - { - if (player == &players[consoleplayer]) - { - newview->angle = localangle[0]; // WARNING: camera uses this - newview->aim = localaiming[0]; - } - else if (splitscreen) - { - UINT8 i; - for (i = 1; i <= splitscreen; i++) - { - if (player == &players[displayplayers[i]]) - { - newview->angle = localangle[i]; - newview->aim = localaiming[i]; - break; - } - } - } - } - } - newview->roll = R_ViewRollAngle(player); - newview->z += quake.z; - - newview->player = player; - - if ((thiscam && chasecam) && !player->awayviewtics && !player->spectator) - { - newview->x = thiscam->x; - newview->y = thiscam->y; - newview->x += quake.x; - newview->y += quake.y; - - if (thiscam->subsector && thiscam->subsector->sector) - newview->sector = thiscam->subsector->sector; - else - newview->sector = R_PointInSubsector(newview->x, newview->y)->sector; - } - else - { newview->x = viewmobj->x; newview->y = viewmobj->y; - newview->x += quake.x; - newview->y += quake.y; + newview->z = player->viewz; - if (!P_MobjWasRemoved(viewmobj) && viewmobj->subsector && thiscam && thiscam->subsector->sector) - newview->sector = viewmobj->subsector->sector; - else - newview->sector = R_PointInSubsector(newview->x, newview->y)->sector; + R_SetupCommonFrame(player, viewmobj->subsector); } - - R_InterpolateView(R_UsingFrameInterpolation() ? (demo.playback && demo.freecam) ? rendertimefrac_unpaused : rendertimefrac : FRACUNIT, false); } static void R_PortalFrame(portal_t *portal) @@ -1556,7 +1388,7 @@ void R_RenderPlayerView(player_t *player) PS_START_TIMING(ps_skyboxtime); if (skybox && skyVisible) { - R_SkyboxFrame(player); + R_SkyboxFrame(viewssnum); R_ClearClipSegs(); R_ClearDrawSegs(); @@ -1576,7 +1408,7 @@ void R_RenderPlayerView(player_t *player) } PS_STOP_TIMING(ps_skyboxtime); - R_SetupFrame(player, skybox); + R_SetupFrame(viewssnum, skybox); skyVisible = false; framecount++; validcount++; @@ -1682,15 +1514,18 @@ void R_RenderPlayerView(player_t *player) void R_RegisterEngineStuff(void) { + INT32 i; + CV_RegisterVar(&cv_gravity); CV_RegisterVar(&cv_tailspickup); CV_RegisterVar(&cv_soniccd); CV_RegisterVar(&cv_allowmlook); CV_RegisterVar(&cv_homremoval); - CV_RegisterVar(&cv_flipcam); - CV_RegisterVar(&cv_flipcam2); - CV_RegisterVar(&cv_flipcam3); - CV_RegisterVar(&cv_flipcam4); + + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + CV_RegisterVar(&cv_flipcam[i]); + } // Enough for dedicated server if (dedicated) @@ -1703,43 +1538,25 @@ void R_RegisterEngineStuff(void) CV_RegisterVar(&cv_mobjscaleprecip); CV_RegisterVar(&cv_fov); - CV_RegisterVar(&cv_chasecam); - CV_RegisterVar(&cv_chasecam2); - CV_RegisterVar(&cv_chasecam3); - CV_RegisterVar(&cv_chasecam4); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + CV_RegisterVar(&cv_chasecam[i]); + } CV_RegisterVar(&cv_shadow); CV_RegisterVar(&cv_shadowoffs); CV_RegisterVar(&cv_skybox); CV_RegisterVar(&cv_ffloorclip); CV_RegisterVar(&cv_spriteclip); - CV_RegisterVar(&cv_cam_dist); - CV_RegisterVar(&cv_cam_still); - CV_RegisterVar(&cv_cam_height); - CV_RegisterVar(&cv_cam_speed); - CV_RegisterVar(&cv_cam_rotate); - CV_RegisterVar(&cv_cam_rotspeed); - - CV_RegisterVar(&cv_cam2_dist); - CV_RegisterVar(&cv_cam2_still); - CV_RegisterVar(&cv_cam2_height); - CV_RegisterVar(&cv_cam2_speed); - CV_RegisterVar(&cv_cam2_rotate); - CV_RegisterVar(&cv_cam2_rotspeed); - - CV_RegisterVar(&cv_cam3_dist); - CV_RegisterVar(&cv_cam3_still); - CV_RegisterVar(&cv_cam3_height); - CV_RegisterVar(&cv_cam3_speed); - CV_RegisterVar(&cv_cam3_rotate); - CV_RegisterVar(&cv_cam3_rotspeed); - - CV_RegisterVar(&cv_cam4_dist); - CV_RegisterVar(&cv_cam4_still); - CV_RegisterVar(&cv_cam4_height); - CV_RegisterVar(&cv_cam4_speed); - CV_RegisterVar(&cv_cam4_rotate); - CV_RegisterVar(&cv_cam4_rotspeed); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + CV_RegisterVar(&cv_cam_dist[i]); + CV_RegisterVar(&cv_cam_still[i]); + CV_RegisterVar(&cv_cam_height[i]); + CV_RegisterVar(&cv_cam_speed[i]); + CV_RegisterVar(&cv_cam_rotate[i]); + CV_RegisterVar(&cv_cam_rotspeed[i]); + } CV_RegisterVar(&cv_tilting); CV_RegisterVar(&cv_quaketilt); diff --git a/src/r_main.h b/src/r_main.h index cfca7e1a4..804dd543c 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -82,7 +82,7 @@ FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSegSide(fixed_t x, fixed_t fixed_t ldy = line->v2->y - ly; // use cross product to determine side quickly - return (INT64)(y - ly) * ldx - (INT64)(x - lx) * ldy > 0; + return ((INT64)y - ly) * ldx - ((INT64)x - lx) * ldy > 0; } angle_t R_PointToAngle(fixed_t x, fixed_t y); @@ -97,7 +97,6 @@ subsector_t *R_IsPointInSubsector(fixed_t x, fixed_t y); #define R_PointToDist(x, y) R_PointToDist2(viewx, viewy, x, y) #define R_PointToDist2(px2, py2, px1, py1) FixedHypot((px1) - (px2), (py1) - (py2)) - boolean R_DoCulling(line_t *cullheight, line_t *viewcullheight, fixed_t vz, fixed_t bottomh, fixed_t toph); void R_GetRenderBlockMapDimensions(fixed_t drawdist, INT32 *xl, INT32 *xh, INT32 *yl, INT32 *yh); @@ -127,8 +126,8 @@ extern ps_metric_t ps_numpolyobjects; extern consvar_t cv_showhud, cv_translucenthud, cv_uncappedhud; extern consvar_t cv_homremoval; -extern consvar_t cv_chasecam, cv_chasecam2, cv_chasecam3, cv_chasecam4; -extern consvar_t cv_flipcam, cv_flipcam2, cv_flipcam3, cv_flipcam4; +extern consvar_t cv_chasecam[MAXSPLITSCREENPLAYERS]; +extern consvar_t cv_flipcam[MAXSPLITSCREENPLAYERS]; extern consvar_t cv_shadow, cv_shadowoffs; extern consvar_t cv_ffloorclip, cv_spriteclip; extern consvar_t cv_translucency; @@ -153,9 +152,9 @@ void R_SetViewSize(void); // do it (sometimes explicitly called) void R_ExecuteSetViewSize(void); -void R_SkyboxFrame(player_t *player); +void R_SkyboxFrame(int s); +void R_SetupFrame(int s, boolean skybox); -void R_SetupFrame(player_t *player, boolean skybox); // Called by G_Drawer. void R_RenderPlayerView(player_t *player); diff --git a/src/r_patch.c b/src/r_patch.c index ae8ec4f5e..50dda0c5f 100644 --- a/src/r_patch.c +++ b/src/r_patch.c @@ -14,6 +14,7 @@ #include "byteptr.h" #include "dehacked.h" +#include "doomdef.h" #include "i_video.h" #include "r_data.h" #include "r_draw.h" diff --git a/src/r_segs.c b/src/r_segs.c index 3b2c7d512..d6f7c9d2a 100644 --- a/src/r_segs.c +++ b/src/r_segs.c @@ -661,13 +661,13 @@ static boolean R_IsFFloorTranslucent(visffloor_t *pfloor) // Renders all the thick sides in the given range. void R_RenderThickSideRange(drawseg_t *ds, INT32 x1, INT32 x2, ffloor_t *pfloor) { - size_t pindex; + size_t pindex = 0; column_t * col; - INT32 lightnum; - INT32 texnum; + INT32 lightnum; + INT32 texnum; sector_t tempsec; - INT32 templight; - INT32 i, p; + INT32 templight; + INT32 i, p; fixed_t bottombounds = viewheight << FRACBITS; fixed_t topbounds = (con_clipviewtop - 1) << FRACBITS; fixed_t offsetvalue = 0; @@ -1036,6 +1036,7 @@ void R_RenderThickSideRange(drawseg_t *ds, INT32 x1, INT32 x2, ffloor_t *pfloor) // Check if the current light effects the colormap/lightlevel rlight = &dc_lightlist[i]; lighteffect = !(dc_lightlist[i].flags & FF_NOSHADE); + if (lighteffect) { lightnum = rlight->lightnum; @@ -1233,7 +1234,6 @@ static void R_RenderSegLoop (void) } } - yh = bottomfrac>>HEIGHTBITS; bottom = floorclip[rw_x]-1; @@ -1244,13 +1244,14 @@ static void R_RenderSegLoop (void) if (markfloor) { top = yh < ceilingclip[rw_x] ? ceilingclip[rw_x] : yh; + if (++top <= bottom && floorplane) { floorplane->top[rw_x] = (INT16)top; floorplane->bottom[rw_x] = (INT16)bottom; } } - + rw_floormarked = false; rw_ceilingmarked = false; @@ -1591,6 +1592,8 @@ static void R_RenderSegLoop (void) topfrac += topstep; bottomfrac += bottomstep; } + + //colfunc = wallcolfunc; } // Uses precalculated seg->length @@ -1853,21 +1856,19 @@ void R_StoreWallRange(INT32 start, INT32 stop) rw_toptextureslide = rw_midtextureslide = rw_bottomtextureslide = 0; ceilingfrontslide = floorfrontslide = ceilingbackslide = floorbackslide = 0; - { - angle_t lineangle = R_PointToAngle2(curline->v1->x, curline->v1->y, curline->v2->x, curline->v2->y); + angle_t lineangle = R_PointToAngle2(curline->v1->x, curline->v1->y, curline->v2->x, curline->v2->y); - if (frontsector->f_slope) - floorfrontslide = FixedMul(frontsector->f_slope->zdelta, FINECOSINE((lineangle-frontsector->f_slope->xydirection)>>ANGLETOFINESHIFT)); + if (frontsector->f_slope) + floorfrontslide = FixedMul(frontsector->f_slope->zdelta, FINECOSINE((lineangle-frontsector->f_slope->xydirection)>>ANGLETOFINESHIFT)); - if (frontsector->c_slope) - ceilingfrontslide = FixedMul(frontsector->c_slope->zdelta, FINECOSINE((lineangle-frontsector->c_slope->xydirection)>>ANGLETOFINESHIFT)); + if (frontsector->c_slope) + ceilingfrontslide = FixedMul(frontsector->c_slope->zdelta, FINECOSINE((lineangle-frontsector->c_slope->xydirection)>>ANGLETOFINESHIFT)); - if (backsector && backsector->f_slope) - floorbackslide = FixedMul(backsector->f_slope->zdelta, FINECOSINE((lineangle-backsector->f_slope->xydirection)>>ANGLETOFINESHIFT)); + if (backsector && backsector->f_slope) + floorbackslide = FixedMul(backsector->f_slope->zdelta, FINECOSINE((lineangle-backsector->f_slope->xydirection)>>ANGLETOFINESHIFT)); - if (backsector && backsector->c_slope) - ceilingbackslide = FixedMul(backsector->c_slope->zdelta, FINECOSINE((lineangle-backsector->c_slope->xydirection)>>ANGLETOFINESHIFT)); - } + if (backsector && backsector->c_slope) + ceilingbackslide = FixedMul(backsector->c_slope->zdelta, FINECOSINE((lineangle-backsector->c_slope->xydirection)>>ANGLETOFINESHIFT)); if (!backsector) { @@ -1936,9 +1937,7 @@ void R_StoreWallRange(INT32 start, INT32 stop) ds_p->sprtopclip = ds_p->sprbottomclip = NULL; ds_p->silhouette = 0; - if ( - worldbottomslope > worldlowslope || - worldbottom > worldlow) + if (worldbottomslope > worldlowslope || worldbottom > worldlow) { ds_p->silhouette = SIL_BOTTOM; if ((backsector->f_slope ? P_GetZAt(backsector->f_slope, viewx, viewy) : backsector->floorheight) > viewz) @@ -1953,9 +1952,7 @@ void R_StoreWallRange(INT32 start, INT32 stop) // ds_p->sprbottomclip = negonearray; } - if ( - worldtopslope < worldhighslope || - worldtop < worldhigh) + if (worldtopslope < worldhighslope || worldtop < worldhigh) { ds_p->silhouette |= SIL_TOP; if ((backsector->c_slope ? P_GetZAt(backsector->c_slope, viewx, viewy) : backsector->ceilingheight) < viewz) @@ -2029,7 +2026,7 @@ void R_StoreWallRange(INT32 start, INT32 stop) || frontsector->extra_colormap != backsector->extra_colormap || (frontsector->ffloors != backsector->ffloors && frontsector->tag != backsector->tag)) { - markceiling = true; + markceiling = true; } else { @@ -2045,9 +2042,7 @@ void R_StoreWallRange(INT32 start, INT32 stop) } // check TOP TEXTURE - if (worldhigh < worldtop - || worldhighslope < worldtopslope - ) + if (worldhigh < worldtop || worldhighslope < worldtopslope) { fixed_t texheight; // top texture @@ -2124,7 +2119,6 @@ void R_StoreWallRange(INT32 start, INT32 stop) // Used for height comparisons and etc across FOFs and slopes fixed_t high1, highslope1, low1, lowslope1, high2, highslope2, low2, lowslope2; - //markceiling = markfloor = true; maskedtexture = true; ds_p->thicksidecol = maskedtexturecol = lastopening - rw_x; diff --git a/src/r_things.c b/src/r_things.c index 6813955e2..71096a05c 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -965,7 +965,8 @@ static void R_DrawPrecipitationVisSprite(vissprite_t *vis) // // R_SplitSprite -// runs through a sector's lightlist and +// runs through a sector's lightlist and splits the sprite according to the heights +// static void R_SplitSprite(vissprite_t *sprite, mobj_t *thing) { INT32 i, lightnum, lindex; @@ -1207,7 +1208,7 @@ static void R_ProjectSprite(mobj_t *thing) tx = -(gyt + gxt); // too far off the side? - if (!papersprite && abs(tx) > tz<<2) // papersprite clipping is handled later + if (!papersprite && abs(tx) > (INT64)tz<<2) // papersprite clipping is handled later return; // aspect ratio stuff diff --git a/src/s_sound.c b/src/s_sound.c index 0a6a5ba0c..1bbe154e3 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -652,58 +652,6 @@ void S_StartSound(const void *origin, sfxenum_t sfx_id) if (S_SoundDisabled()) return; - if (mariomode) // Sounds change in Mario mode! - { - switch (sfx_id) - { -// case sfx_altow1: -// case sfx_altow2: -// case sfx_altow3: -// case sfx_altow4: -// sfx_id = sfx_mario8; -// break; - case sfx_thok: - sfx_id = sfx_mario7; - break; - case sfx_pop: - sfx_id = sfx_mario5; - break; - case sfx_jump: - sfx_id = sfx_mario6; - break; - case sfx_shield: - sfx_id = sfx_mario3; - break; - case sfx_itemup: - sfx_id = sfx_mario4; - break; -// case sfx_tink: -// sfx_id = sfx_mario1; -// break; -// case sfx_cgot: -// sfx_id = sfx_mario9; -// break; -// case sfx_lose: -// sfx_id = sfx_mario2; -// break; - default: - break; - } - } - if (maptol & TOL_XMAS) // Some sounds change for xmas - { - switch (sfx_id) - { - case sfx_ideya: - case sfx_nbmper: - case sfx_ncitem: - case sfx_ngdone: - ++sfx_id; - default: - break; - } - } - // the volume is handled 8 bits #ifdef HW3SOUND if (hws_mode != HWS_DEFAULT_MODE) @@ -950,7 +898,6 @@ void S_ClearSfx(void) static void S_StopChannel(INT32 cnum) { - INT32 i; channel_t *c = &channels[cnum]; if (c->sfxinfo) @@ -959,12 +906,6 @@ static void S_StopChannel(INT32 cnum) if (I_SoundIsPlaying(c->handle)) I_StopSound(c->handle); - // check to see - // if other channels are playing the sound - for (i = 0; i < numofchannels; i++) - if (cnum != i && c->sfxinfo == channels[i].sfxinfo) - break; - // degrade usefulness of sound data c->sfxinfo->usefulness--; c->sfxinfo = 0; diff --git a/src/screen.c b/src/screen.c index e1f6fe93e..249c7225c 100644 --- a/src/screen.c +++ b/src/screen.c @@ -273,10 +273,13 @@ void SCR_Recalc(void) vid.fsmalldupy = vid.smalldupy*FRACUNIT; #endif - // toggle off automap because some screensize-dependent values will + // toggle off (then back on) the automap because some screensize-dependent values will // be calculated next time the automap is activated. if (automapactive) - AM_Stop(); + { + am_recalc = true; + AM_Start(); + } // set the screen[x] ptrs on the new vidbuffers V_Init(); diff --git a/src/sdl/i_system.c b/src/sdl/i_system.c index f999d8684..882535203 100644 --- a/src/sdl/i_system.c +++ b/src/sdl/i_system.c @@ -401,39 +401,15 @@ static void JoyReset(SDLJoyInfo_t *JoySet) //JoySet->scale } -/** \brief First joystick up and running +/** \brief joystick up and running */ -static INT32 joystick_started = 0; +static INT32 joystick_started[MAXSPLITSCREENPLAYERS] = {0, 0, 0, 0}; -/** \brief SDL info about joystick 1 +/** \brief SDL info about joystick */ -SDLJoyInfo_t JoyInfo; +SDLJoyInfo_t JoyInfo[MAXSPLITSCREENPLAYERS]; -/** \brief Second joystick up and running -*/ -static INT32 joystick2_started = 0; - -/** \brief SDL info about joystick 2 -*/ -SDLJoyInfo_t JoyInfo2; - -/** \brief Third joystick up and running -*/ -static INT32 joystick3_started = 0; - -/** \brief SDL info about joystick 3 -*/ -SDLJoyInfo_t JoyInfo3; - -/** \brief Fourth joystick up and running -*/ -static INT32 joystick4_started = 0; - -/** \brief SDL info about joystick 4 -*/ -SDLJoyInfo_t JoyInfo4; - #ifdef HAVE_TERMIOS static INT32 fdmouse2 = -1; static INT32 mouse2_started = 0; @@ -1079,26 +1055,26 @@ INT32 I_GetKey (void) // void I_JoyScale(void) { - Joystick.bGamepadStyle = cv_joyscale.value==0; - JoyInfo.scale = Joystick.bGamepadStyle?1:cv_joyscale.value; + Joystick[0].bGamepadStyle = cv_joyscale[0].value==0; + JoyInfo[0].scale = Joystick[0].bGamepadStyle?1:cv_joyscale[0].value; } void I_JoyScale2(void) { - Joystick2.bGamepadStyle = cv_joyscale2.value==0; - JoyInfo2.scale = Joystick2.bGamepadStyle?1:cv_joyscale2.value; + Joystick[1].bGamepadStyle = cv_joyscale[1].value==0; + JoyInfo[1].scale = Joystick[1].bGamepadStyle?1:cv_joyscale[1].value; } void I_JoyScale3(void) { - Joystick3.bGamepadStyle = cv_joyscale3.value==0; - JoyInfo3.scale = Joystick3.bGamepadStyle?1:cv_joyscale3.value; + Joystick[2].bGamepadStyle = cv_joyscale[2].value==0; + JoyInfo[2].scale = Joystick[2].bGamepadStyle?1:cv_joyscale[2].value; } void I_JoyScale4(void) { - Joystick4.bGamepadStyle = cv_joyscale4.value==0; - JoyInfo4.scale = Joystick4.bGamepadStyle?1:cv_joyscale4.value; + Joystick[3].bGamepadStyle = cv_joyscale[3].value==0; + JoyInfo[3].scale = Joystick[3].bGamepadStyle?1:cv_joyscale[3].value; } // Cheat to get the device index for a joystick handle @@ -1116,219 +1092,70 @@ INT32 I_GetJoystickDeviceIndex(SDL_GameController *dev) return -1; } -// Misleading function: updates device indices for all players BUT the one specified. -// Necessary for SDL_JOYDEVICEADDED events -void I_UpdateJoystickDeviceIndices(INT32 player) +void I_UpdateJoystickDeviceIndex(UINT8 player) { - if (player != 1) // This is a fucking mess. + /////////////////////////////////////////////// + // update this joystick's device index (wow) // + /////////////////////////////////////////////// + if (JoyInfo[player].dev) { - ////////////////////////////// - // update joystick 1's device index - ////////////////////////////// - - if (JoyInfo.dev) - cv_usejoystick.value = I_GetJoystickDeviceIndex(JoyInfo.dev) + 1; - // is cv_usejoystick used? - else if (// don't check JoyInfo or cv_usejoystick; we're currently operating on those - atoi(cv_usejoystick.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick2.value - && atoi(cv_usejoystick.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick3.value - && atoi(cv_usejoystick.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick4.value) - cv_usejoystick.value = atoi(cv_usejoystick.string); - // is cv_usejoystick2 used? - else if ( // don't check JoyInfo or cv_usejoystick; we're currently operating on those - atoi(cv_usejoystick2.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick2.value - && atoi(cv_usejoystick2.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick3.value - && atoi(cv_usejoystick2.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick4.value) - cv_usejoystick.value = atoi(cv_usejoystick2.string); - // is cv_usejoystick3 used? - else if (// don't check JoyInfo or cv_usejoystick; we're currently operating on those - atoi(cv_usejoystick3.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick2.value - && atoi(cv_usejoystick3.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick3.value - && atoi(cv_usejoystick3.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick4.value) - cv_usejoystick.value = atoi(cv_usejoystick3.string); - // is cv_usejoystick4 used? - else if (// don't check JoyInfo or cv_usejoystick; we're currently operating on those - atoi(cv_usejoystick4.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick2.value - && atoi(cv_usejoystick4.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick3.value - && atoi(cv_usejoystick4.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick4.value) - cv_usejoystick.value = atoi(cv_usejoystick4.string); - else // we tried... - cv_usejoystick.value = 0; + cv_usejoystick[player].value = I_GetJoystickDeviceIndex(JoyInfo[player].dev) + 1; } - - if (player != 2) + else { - ////////////////////////////// - // update joystick 2's device index - ////////////////////////////// - - if (JoyInfo2.dev) - cv_usejoystick2.value = I_GetJoystickDeviceIndex(JoyInfo2.dev) + 1; - // is cv_usejoystick2 used? - else if (atoi(cv_usejoystick2.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick.value - // don't check JoyInfo2 or cv_usejoystick2; we're currently operating on those - && atoi(cv_usejoystick2.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick3.value - && atoi(cv_usejoystick2.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick4.value) - cv_usejoystick2.value = atoi(cv_usejoystick2.string); - // is cv_usejoystick used? - else if (atoi(cv_usejoystick.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick.value - // don't check JoyInfo2 or cv_usejoystick2; we're currently operating on those - && atoi(cv_usejoystick.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick3.value - && atoi(cv_usejoystick.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick4.value) - cv_usejoystick2.value = atoi(cv_usejoystick.string); - // is cv_usejoystick3 used? - else if (atoi(cv_usejoystick3.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick.value - // don't check JoyInfo2 or cv_usejoystick2; we're currently operating on those - && atoi(cv_usejoystick3.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick3.value - && atoi(cv_usejoystick3.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick4.value) - cv_usejoystick2.value = atoi(cv_usejoystick3.string); - // is cv_usejoystick4 used? - else if (atoi(cv_usejoystick4.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick.value - // don't check JoyInfo2 or cv_usejoystick2; we're currently operating on those - && atoi(cv_usejoystick4.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick3.value - && atoi(cv_usejoystick4.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick4.value) - cv_usejoystick2.value = atoi(cv_usejoystick4.string); - else // we tried... - cv_usejoystick2.value = 0; - } - - if (player != 3) - { - ////////////////////////////// - // update joystick 3's device index - ////////////////////////////// - - if (JoyInfo3.dev) - cv_usejoystick3.value = I_GetJoystickDeviceIndex(JoyInfo3.dev) + 1; - // is cv_usejoystick3 used? - else if (atoi(cv_usejoystick3.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick.value - && atoi(cv_usejoystick3.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick2.value - // don't check JoyInfo3 or cv_usejoystick3; we're currently operating on those - && atoi(cv_usejoystick3.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick4.value) - cv_usejoystick3.value = atoi(cv_usejoystick3.string); - // is cv_usejoystick used? - else if (atoi(cv_usejoystick.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick.value - && atoi(cv_usejoystick.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick2.value - // don't check JoyInfo3 or cv_usejoystick3; we're currently operating on those - && atoi(cv_usejoystick.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick4.value) - cv_usejoystick3.value = atoi(cv_usejoystick.string); - // is cv_usejoystick2 used? - else if (atoi(cv_usejoystick2.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick.value - && atoi(cv_usejoystick2.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick2.value - // don't check JoyInfo3 or cv_usejoystick3; we're currently operating on those - && atoi(cv_usejoystick2.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick4.value) - cv_usejoystick3.value = atoi(cv_usejoystick2.string); - // is cv_usejoystick4 used? - else if (atoi(cv_usejoystick4.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick.value - && atoi(cv_usejoystick4.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick2.value - // don't check JoyInfo3 or cv_usejoystick3; we're currently operating on those - && atoi(cv_usejoystick4.string) != JoyInfo4.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick4.value) - cv_usejoystick3.value = atoi(cv_usejoystick4.string); - else // we tried... - cv_usejoystick3.value = 0; - } - - if (player != 4) - { - ////////////////////////////// - // update joystick 4's device index - ////////////////////////////// - - if (JoyInfo4.dev) - cv_usejoystick4.value = I_GetJoystickDeviceIndex(JoyInfo4.dev) + 1; - // is cv_usejoystick4 used? - else if (atoi(cv_usejoystick4.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick.value - && atoi(cv_usejoystick4.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick2.value - && atoi(cv_usejoystick4.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick4.string) != cv_usejoystick3.value) - // don't check JoyInfo4 or cv_usejoystick4; we're currently operating on those - cv_usejoystick4.value = atoi(cv_usejoystick4.string); - // is cv_usejoystick used? - else if (atoi(cv_usejoystick.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick.value - && atoi(cv_usejoystick.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick2.value - && atoi(cv_usejoystick.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick.string) != cv_usejoystick3.value) - // don't check JoyInfo4 or cv_usejoystick4; we're currently operating on those - cv_usejoystick4.value = atoi(cv_usejoystick.string); - // is cv_usejoystick2 used? - else if (atoi(cv_usejoystick2.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick.value - && atoi(cv_usejoystick2.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick2.value - && atoi(cv_usejoystick2.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick2.string) != cv_usejoystick3.value) - // don't check JoyInfo4 or cv_usejoystick4; we're currently operating on those - cv_usejoystick4.value = atoi(cv_usejoystick2.string); - // is cv_usejoystick3 used? - else if (atoi(cv_usejoystick3.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick.value - && atoi(cv_usejoystick3.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick2.value - && atoi(cv_usejoystick3.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick3.string) != cv_usejoystick3.value) - // don't check JoyInfo4 or cv_usejoystick4; we're currently operating on those - cv_usejoystick4.value = atoi(cv_usejoystick3.string); - else // we tried... - cv_usejoystick4.value = 0; + UINT8 joystickID, compareJoystick; + for (joystickID = 0; joystickID < MAXSPLITSCREENPLAYERS; joystickID++) + { + // is this cv_usejoystick used? + const INT32 value = atoi(cv_usejoystick[joystickID].string); + for (compareJoystick = 0; compareJoystick < MAXSPLITSCREENPLAYERS; compareJoystick++) + { + if (compareJoystick == player) + continue; + if (value == JoyInfo[compareJoystick].oldjoy || value == cv_usejoystick[compareJoystick].value) + break; + } + if (compareJoystick == MAXSPLITSCREENPLAYERS) + { + // We DID make it through the whole loop, so we can use this one! + cv_usejoystick[player].value = value; + break; + } + } + if (joystickID == MAXSPLITSCREENPLAYERS) + { + // We DID NOT make it through the whole loop, so we can't assign this joystick to anything. + // When you try your best, but you don't succeed... + cv_usejoystick[player].value = 0; + } } } -/** \brief Joystick 1 buttons states +void I_UpdateJoystickDeviceIndices(UINT8 excludePlayer) +{ + UINT8 player; + + for (player = 0; player < MAXSPLITSCREENPLAYERS; player++) + { + if (player == excludePlayer) + continue; + + I_UpdateJoystickDeviceIndex(player); + } +} + +/** \brief Joystick buttons states */ -static UINT64 lastjoybuttons = 0; +static UINT64 lastjoybuttons[MAXSPLITSCREENPLAYERS] = {0,0,0,0}; -/** \brief Joystick 1 hats state +/** \brief Joystick hats state */ -static UINT64 lastjoyhats = 0; - -/** \brief Shuts down joystick 1 - +static UINT64 lastjoyhats[MAXSPLITSCREENPLAYERS] = {0,0,0,0}; +/** \brief Shuts down joystick \return void - - */ -void I_ShutdownJoystick(void) +void I_ShutdownJoystick(UINT8 index) { INT32 i; event_t event; @@ -1336,7 +1163,7 @@ void I_ShutdownJoystick(void) event.data2 = 0; event.data3 = 0; - lastjoybuttons = lastjoyhats = 0; + lastjoybuttons[index] = lastjoyhats[index] = 0; // emulate the up of all joystick buttons for (i=0;i= 0; i--) - { - joybuttons <<= 1; - if (SDL_JoystickGetButton(JoyInfo.dev,i)) - joybuttons |= 1; - } + joyhats |= SDL_GameControllerGetButton(JoyInfo[index].dev, SDL_CONTROLLER_BUTTON_DPAD_UP); + joyhats |= SDL_GameControllerGetButton(JoyInfo[index].dev, SDL_CONTROLLER_BUTTON_DPAD_DOWN) << 1; + joyhats |= SDL_GameControllerGetButton(JoyInfo[index].dev, SDL_CONTROLLER_BUTTON_DPAD_LEFT) << 2; + joyhats |= SDL_GameControllerGetButton(JoyInfo[index].dev, SDL_CONTROLLER_BUTTON_DPAD_RIGHT) << 3; - if (joybuttons != lastjoybuttons) + if (joyhats != lastjoyhats[index]) { INT64 j = 1; // keep only bits that changed since last time - INT64 newbuttons = joybuttons ^ lastjoybuttons; - lastjoybuttons = joybuttons; - - for (i = 0; i < JOYBUTTONS; i++, j <<= 1) - { - if (newbuttons & j) // button changed state? - { - if (joybuttons & j) - event.type = ev_keydown; - else - event.type = ev_keyup; - event.data1 = KEY_JOY1 + i; - D_PostEvent(&event); - } - } - } -#endif - - joyhats |= SDL_GameControllerGetButton(JoyInfo.dev, SDL_CONTROLLER_BUTTON_DPAD_UP); - joyhats |= SDL_GameControllerGetButton(JoyInfo.dev, SDL_CONTROLLER_BUTTON_DPAD_DOWN) << 1; - joyhats |= SDL_GameControllerGetButton(JoyInfo.dev, SDL_CONTROLLER_BUTTON_DPAD_LEFT) << 2; - joyhats |= SDL_GameControllerGetButton(JoyInfo.dev, SDL_CONTROLLER_BUTTON_DPAD_RIGHT) << 3; - - if (joyhats != lastjoyhats) - { - INT64 j = 1; // keep only bits that changed since last time - INT64 newhats = joyhats ^ lastjoyhats; - lastjoyhats = joyhats; + INT64 newhats = joyhats ^ lastjoyhats[index]; + lastjoyhats[index] = joyhats; for (i = 0; i < JOYHATS*4; i++, j <<= 1) { @@ -1437,59 +1229,6 @@ void I_GetJoystickEvents(void) } } } - -#if 0 - // send joystick axis positions - event.type = ev_joystick; - - for (i = JOYAXISSET - 1; i >= 0; i--) - { - event.data1 = i; - if (i*2 + 1 <= JoyInfo.axises) - axisx = SDL_JoystickGetAxis(JoyInfo.dev, i*2 + 0); - else axisx = 0; - if (i*2 + 2 <= JoyInfo.axises) - axisy = SDL_JoystickGetAxis(JoyInfo.dev, i*2 + 1); - else axisy = 0; - - // -32768 to 32767 - axisx = axisx/32; - axisy = axisy/32; - - if (Joystick.bGamepadStyle) - { - // gamepad control type, on or off, live or die - if (axisx < -(JOYAXISRANGE/2)) - event.data2 = -1; - else if (axisx > (JOYAXISRANGE/2)) - event.data2 = 1; - else - event.data2 = 0; - if (axisy < -(JOYAXISRANGE/2)) - event.data3 = -1; - else if (axisy > (JOYAXISRANGE/2)) - event.data3 = 1; - else - event.data3 = 0; - } - else - { - - axisx = JoyInfo.scale?((axisx/JoyInfo.scale)*JoyInfo.scale):axisx; - axisy = JoyInfo.scale?((axisy/JoyInfo.scale)*JoyInfo.scale):axisy; - -#ifdef SDL_JDEADZONE - if (-SDL_JDEADZONE <= axisx && axisx <= SDL_JDEADZONE) axisx = 0; - if (-SDL_JDEADZONE <= axisy && axisy <= SDL_JDEADZONE) axisy = 0; -#endif - - // analog control style , just send the raw data - event.data2 = axisx; // x axis - event.data3 = axisy; // y axis - } - D_PostEvent(&event); - } -#endif } /** \brief Open joystick handle @@ -1500,7 +1239,7 @@ void I_GetJoystickEvents(void) */ -static int joy_open(int joyindex) +static int joy_open(int playerIndex, int joyIndex) { SDL_GameController *newdev = NULL; int num_joy = 0; @@ -1516,7 +1255,7 @@ static int joy_open(int joyindex) return -1; } - if (joyindex <= 0) + if (joyIndex <= 0) return -1; num_joy = SDL_NumJoysticks(); @@ -1527,7 +1266,7 @@ static int joy_open(int joyindex) return -1; } - newdev = SDL_GameControllerOpen(joyindex-1); + newdev = SDL_GameControllerOpen(joyIndex-1); // Handle the edge case where the device <-> joystick index assignment can change due to hotplugging // This indexing is SDL's responsibility and there's not much we can do about it. @@ -1539,869 +1278,51 @@ static int joy_open(int joyindex) // 4. Unplug Controller B -> Index 0 inactive, Index 1 closed // 5. Plug Controller B -> Index 0 opened // 6. Plug Controller A -> Index 0 REPLACED, opened as Controller A; Index 1 is now Controller B - if (JoyInfo.dev) + if (JoyInfo[playerIndex].dev) { - if (JoyInfo.dev == newdev // same device, nothing to do - || (newdev == NULL && SDL_GameControllerGetAttached(JoyInfo.dev))) // we failed, but already have a working device + if (JoyInfo[playerIndex].dev == newdev // same device, nothing to do + || (newdev == NULL && SDL_GameControllerGetAttached(JoyInfo[playerIndex].dev))) // we failed, but already have a working device return SDL_CONTROLLER_AXIS_MAX; // Else, we're changing devices, so send neutral joy events CONS_Debug(DBG_GAMELOGIC, "Joystick1 device is changing; resetting events...\n"); - I_ShutdownJoystick(); + I_ShutdownJoystick(playerIndex); } - JoyInfo.dev = newdev; + JoyInfo[playerIndex].dev = newdev; - if (JoyInfo.dev == NULL) + if (JoyInfo[playerIndex].dev == NULL) { CONS_Debug(DBG_GAMELOGIC, M_GetText("Joystick1: Couldn't open device - %s\n"), SDL_GetError()); return -1; } else { - CONS_Debug(DBG_GAMELOGIC, M_GetText("Joystick1: %s\n"), SDL_GameControllerName(JoyInfo.dev)); - JoyInfo.axises = SDL_CONTROLLER_AXIS_MAX; - if (JoyInfo.axises > JOYAXISSET*2) - JoyInfo.axises = JOYAXISSET*2; - /* if (joyaxes<2) - { - I_OutputMsg("Not enought axes?\n"); - return 0; - }*/ + CONS_Debug(DBG_GAMELOGIC, M_GetText("Joystick1: %s\n"), SDL_GameControllerName(JoyInfo[playerIndex].dev)); + JoyInfo[playerIndex].axises = SDL_CONTROLLER_AXIS_MAX; - JoyInfo.buttons = SDL_CONTROLLER_BUTTON_MAX ; // dpad is 4 buttons - if (JoyInfo.buttons > JOYBUTTONS) - JoyInfo.buttons = JOYBUTTONS; + if (JoyInfo[playerIndex].axises > JOYAXISSET*2) + JoyInfo[playerIndex].axises = JOYAXISSET*2; - JoyInfo.hats = 4; - if (JoyInfo.hats > JOYHATS) - JoyInfo.hats = JOYHATS; + JoyInfo[playerIndex].buttons = SDL_CONTROLLER_BUTTON_MAX ; // dpad is 4 buttons + if (JoyInfo[playerIndex].buttons > JOYBUTTONS) + JoyInfo[playerIndex].buttons = JOYBUTTONS; - JoyInfo.balls = 0; + JoyInfo[playerIndex].hats = 4; + if (JoyInfo[playerIndex].hats > JOYHATS) + JoyInfo[playerIndex].hats = JOYHATS; - //Joystick.bGamepadStyle = !stricmp(SDL_JoystickName(JoyInfo.dev), "pad"); + JoyInfo[playerIndex].balls = 0; - return JoyInfo.axises; - } -} - -//Joystick2 - -/** \brief Joystick 2 buttons states -*/ -static UINT64 lastjoy2buttons = 0; - -/** \brief Joystick 2 hats state -*/ -static UINT64 lastjoy2hats = 0; - -/** \brief Shuts down joystick 2 - - - \return void -*/ -void I_ShutdownJoystick2(void) -{ - INT32 i; - event_t event; - event.type = ev_keyup; - event.data2 = 0; - event.data3 = 0; - - lastjoy2buttons = lastjoy2hats = 0; - - // emulate the up of all joystick buttons - for (i = 0; i < JOYBUTTONS; i++) - { - event.data1 = KEY_2JOY1 + i; - D_PostEvent(&event); - } - - // emulate the up of all joystick hats - for (i = 0; i < JOYHATS*4; i++) - { - event.data1 = KEY_2HAT1 + i; - D_PostEvent(&event); - } - - // reset joystick position - event.type = ev_joystick2; - for (i = 0; i < JOYAXISSET; i++) - { - event.data1 = i; - D_PostEvent(&event); - } - - joystick2_started = 0; - JoyReset(&JoyInfo2); - - // don't shut down the subsystem here, because hotplugging -} - -void I_GetJoystick2Events(void) -{ - static event_t event = {0,0,0,0}; - INT32 i = 0; - UINT64 joyhats = 0; -#if 0 - UINT64 joybuttons = 0; - UINT32 axisx, axisy; -#endif - - if (!joystick2_started) - return; - - if (!JoyInfo2.dev) //I_ShutdownJoystick2(); - return; - -#if 0 - //faB: look for as much buttons as g_input code supports, - // we don't use the others - for (i = JoyInfo2.buttons - 1; i >= 0; i--) - { - joybuttons <<= 1; - if (SDL_JoystickGetButton(JoyInfo2.dev,i)) - joybuttons |= 1; - } - - if (joybuttons != lastjoy2buttons) - { - INT64 j = 1; // keep only bits that changed since last time - INT64 newbuttons = joybuttons ^ lastjoy2buttons; - lastjoy2buttons = joybuttons; - - for (i = 0; i < JOYBUTTONS; i++, j <<= 1) - { - if (newbuttons & j) // button changed state? - { - if (joybuttons & j) - event.type = ev_keydown; - else - event.type = ev_keyup; - event.data1 = KEY_2JOY1 + i; - D_PostEvent(&event); - } - } - } -#endif - - joyhats |= SDL_GameControllerGetButton(JoyInfo2.dev, SDL_CONTROLLER_BUTTON_DPAD_UP); - joyhats |= SDL_GameControllerGetButton(JoyInfo2.dev, SDL_CONTROLLER_BUTTON_DPAD_DOWN) << 1; - joyhats |= SDL_GameControllerGetButton(JoyInfo2.dev, SDL_CONTROLLER_BUTTON_DPAD_LEFT) << 2; - joyhats |= SDL_GameControllerGetButton(JoyInfo2.dev, SDL_CONTROLLER_BUTTON_DPAD_RIGHT) << 3; - - if (joyhats != lastjoy2hats) - { - INT64 j = 1; // keep only bits that changed since last time - INT64 newhats = joyhats ^ lastjoy2hats; - lastjoy2hats = joyhats; - - for (i = 0; i < JOYHATS*4; i++, j <<= 1) - { - if (newhats & j) // hat changed state? - { - if (joyhats & j) - event.type = ev_keydown; - else - event.type = ev_keyup; - event.data1 = KEY_2HAT1 + i; - D_PostEvent(&event); - } - } - } - -#if 0 - // send joystick axis positions - event.type = ev_joystick2; - - for (i = JOYAXISSET - 1; i >= 0; i--) - { - event.data1 = i; - if (i*2 + 1 <= JoyInfo2.axises) - axisx = SDL_JoystickGetAxis(JoyInfo2.dev, i*2 + 0); - else axisx = 0; - if (i*2 + 2 <= JoyInfo2.axises) - axisy = SDL_JoystickGetAxis(JoyInfo2.dev, i*2 + 1); - else axisy = 0; - - // -32768 to 32767 - axisx = axisx/32; - axisy = axisy/32; - - if (Joystick2.bGamepadStyle) - { - // gamepad control type, on or off, live or die - if (axisx < -(JOYAXISRANGE/2)) - event.data2 = -1; - else if (axisx > (JOYAXISRANGE/2)) - event.data2 = 1; - else - event.data2 = 0; - if (axisy < -(JOYAXISRANGE/2)) - event.data3 = -1; - else if (axisy > (JOYAXISRANGE/2)) - event.data3 = 1; - else - event.data3 = 0; - } - else - { - - axisx = JoyInfo2.scale?((axisx/JoyInfo2.scale)*JoyInfo2.scale):axisx; - axisy = JoyInfo2.scale?((axisy/JoyInfo2.scale)*JoyInfo2.scale):axisy; - -#ifdef SDL_JDEADZONE - if (-SDL_JDEADZONE <= axisx && axisx <= SDL_JDEADZONE) axisx = 0; - if (-SDL_JDEADZONE <= axisy && axisy <= SDL_JDEADZONE) axisy = 0; -#endif - - // analog control style , just send the raw data - event.data2 = axisx; // x axis - event.data3 = axisy; // y axis - } - D_PostEvent(&event); - } -#endif -} - -/** \brief Open joystick handle - - \param fname name of joystick - - \return axises - - -*/ -static int joy_open2(int joyindex) -{ - SDL_GameController *newdev = NULL; - int num_joy = 0; - - if (SDL_WasInit(SDL_INIT_JOYSTICK) == 0) - { - CONS_Printf(M_GetText("Joystick subsystem not started\n")); - return -1; - } - if (SDL_WasInit(SDL_INIT_GAMECONTROLLER) == 0) - { - CONS_Printf(M_GetText("Game Controller subsystem not started\n")); - return -1; - } - - if (joyindex <= 0) - return -1; - - num_joy = SDL_NumJoysticks(); - - if (num_joy == 0) - { - CONS_Printf("%s", M_GetText("Found no joysticks on this system\n")); - return -1; - } - - newdev = SDL_GameControllerOpen(joyindex-1); - - // Handle the edge case where the device <-> joystick index assignment can change due to hotplugging - // This indexing is SDL's responsibility and there's not much we can do about it. - // - // Example: - // 1. Plug Controller A -> Index 0 opened - // 2. Plug Controller B -> Index 1 opened - // 3. Unplug Controller A -> Index 0 closed, Index 1 active - // 4. Unplug Controller B -> Index 0 inactive, Index 1 closed - // 5. Plug Controller B -> Index 0 opened - // 6. Plug Controller A -> Index 0 REPLACED, opened as Controller A; Index 1 is now Controller B - if (JoyInfo2.dev) - { - if (JoyInfo2.dev == newdev // same device, nothing to do - || (newdev == NULL && SDL_GameControllerGetAttached(JoyInfo2.dev))) // we failed, but already have a working device - return SDL_CONTROLLER_AXIS_MAX; - // Else, we're changing devices, so send neutral joy events - CONS_Debug(DBG_GAMELOGIC, "Joystick2 device is changing; resetting events...\n"); - I_ShutdownJoystick2(); - } - - JoyInfo2.dev = newdev; - - if (JoyInfo2.dev == NULL) - { - CONS_Debug(DBG_GAMELOGIC, M_GetText("Joystick2: couldn't open device - %s\n"), SDL_GetError()); - return -1; - } - else - { - CONS_Debug(DBG_GAMELOGIC, M_GetText("Joystick2: %s\n"), SDL_GameControllerName(JoyInfo2.dev)); - JoyInfo2.axises = SDL_CONTROLLER_AXIS_MAX; - if (JoyInfo2.axises > JOYAXISSET*2) - JoyInfo2.axises = JOYAXISSET*2; -/* if (joyaxes<2) - { - I_OutputMsg("Not enought axes?\n"); - return 0; - }*/ - - JoyInfo2.buttons = SDL_CONTROLLER_BUTTON_MAX ; // dpad is 4 buttons - if (JoyInfo2.buttons > JOYBUTTONS) - JoyInfo2.buttons = JOYBUTTONS; - - JoyInfo2.hats = 4; - if (JoyInfo2.hats > JOYHATS) - JoyInfo2.hats = JOYHATS; - - JoyInfo2.balls = 0; - - //Joystick.bGamepadStyle = !stricmp(SDL_JoystickName(JoyInfo2.dev), "pad"); - - return JoyInfo2.axises; - } -} - -//Joystick3 - -/** \brief Joystick 3 buttons states -*/ -static UINT64 lastjoy3buttons = 0; - -/** \brief Joystick 3 hats state -*/ -static UINT64 lastjoy3hats = 0; - -/** \brief Shuts down joystick 3 - - -\return void -*/ -void I_ShutdownJoystick3(void) -{ - INT32 i; - event_t event; - event.type = ev_keyup; - event.data2 = 0; - event.data3 = 0; - - lastjoy3buttons = lastjoy3hats = 0; - - // emulate the up of all joystick buttons - for (i = 0; i < JOYBUTTONS; i++) - { - event.data1 = KEY_3JOY1 + i; - D_PostEvent(&event); - } - - // emulate the up of all joystick hats - for (i = 0; i < JOYHATS*4; i++) - { - event.data1 = KEY_3HAT1 + i; - D_PostEvent(&event); - } - - // reset joystick position - event.type = ev_joystick3; - for (i = 0; i < JOYAXISSET; i++) - { - event.data1 = i; - D_PostEvent(&event); - } - - joystick3_started = 0; - JoyReset(&JoyInfo3); - - // don't shutdown the subsystem here, because hotplugging -} - -void I_GetJoystick3Events(void) -{ - static event_t event = {0,0,0,0}; - INT32 i = 0; - UINT64 joyhats = 0; -#if 0 - UINT64 joybuttons = 0; - UINT32 axisx, axisy; -#endif - - if (!joystick3_started) - return; - - if (!JoyInfo3.dev) //I_ShutdownJoystick3(); - return; - -#if 0 - //faB: look for as much buttons as g_input code supports, - // we don't use the others - for (i = JoyInfo3.buttons - 1; i >= 0; i--) - { - joybuttons <<= 1; - if (SDL_JoystickGetButton(JoyInfo3.dev,i)) - joybuttons |= 1; - } - - if (joybuttons != lastjoy3buttons) - { - INT64 j = 1; // keep only bits that changed since last time - INT64 newbuttons = joybuttons ^ lastjoy3buttons; - lastjoy3buttons = joybuttons; - - for (i = 0; i < JOYBUTTONS; i++, j <<= 1) - { - if (newbuttons & j) // button changed state? - { - if (joybuttons & j) - event.type = ev_keydown; - else - event.type = ev_keyup; - event.data1 = KEY_3JOY1 + i; - D_PostEvent(&event); - } - } - } -#endif - - joyhats |= SDL_GameControllerGetButton(JoyInfo3.dev, SDL_CONTROLLER_BUTTON_DPAD_UP); - joyhats |= SDL_GameControllerGetButton(JoyInfo3.dev, SDL_CONTROLLER_BUTTON_DPAD_DOWN) << 1; - joyhats |= SDL_GameControllerGetButton(JoyInfo3.dev, SDL_CONTROLLER_BUTTON_DPAD_LEFT) << 2; - joyhats |= SDL_GameControllerGetButton(JoyInfo3.dev, SDL_CONTROLLER_BUTTON_DPAD_RIGHT) << 3; - - if (joyhats != lastjoy3hats) - { - INT64 j = 1; // keep only bits that changed since last time - INT64 newhats = joyhats ^ lastjoy3hats; - lastjoy3hats = joyhats; - - for (i = 0; i < JOYHATS*4; i++, j <<= 1) - { - if (newhats & j) // hat changed state? - { - if (joyhats & j) - event.type = ev_keydown; - else - event.type = ev_keyup; - event.data1 = KEY_3HAT1 + i; - D_PostEvent(&event); - } - } - } - -#if 0 - // send joystick axis positions - event.type = ev_joystick3; - - for (i = JOYAXISSET - 1; i >= 0; i--) - { - event.data1 = i; - if (i*2 + 1 <= JoyInfo3.axises) - axisx = SDL_JoystickGetAxis(JoyInfo3.dev, i*2 + 0); - else axisx = 0; - if (i*2 + 2 <= JoyInfo3.axises) - axisy = SDL_JoystickGetAxis(JoyInfo3.dev, i*2 + 1); - else axisy = 0; - - // -32768 to 32767 - axisx = axisx/32; - axisy = axisy/32; - - if (Joystick3.bGamepadStyle) - { - // gamepad control type, on or off, live or die - if (axisx < -(JOYAXISRANGE/2)) - event.data2 = -1; - else if (axisx > (JOYAXISRANGE/2)) - event.data2 = 1; - else - event.data2 = 0; - if (axisy < -(JOYAXISRANGE/2)) - event.data3 = -1; - else if (axisy > (JOYAXISRANGE/2)) - event.data3 = 1; - else - event.data3 = 0; - } - else - { - - axisx = JoyInfo3.scale?((axisx/JoyInfo3.scale)*JoyInfo3.scale):axisx; - axisy = JoyInfo3.scale?((axisy/JoyInfo3.scale)*JoyInfo3.scale):axisy; - -#ifdef SDL_JDEADZONE - if (-SDL_JDEADZONE <= axisx && axisx <= SDL_JDEADZONE) axisx = 0; - if (-SDL_JDEADZONE <= axisy && axisy <= SDL_JDEADZONE) axisy = 0; -#endif - - // analog control style , just send the raw data - event.data2 = axisx; // x axis - event.data3 = axisy; // y axis - } - D_PostEvent(&event); - } -#endif -} - -/** \brief Open joystick handle - - \param fname name of joystick - - \return axises - - -*/ -static int joy_open3(int joyindex) -{ - SDL_GameController *newdev = NULL; - int num_joy = 0; - - if (SDL_WasInit(SDL_INIT_JOYSTICK) == 0) - { - CONS_Printf(M_GetText("Joystick subsystem not started\n")); - return -1; - } - if (SDL_WasInit(SDL_INIT_GAMECONTROLLER) == 0) - { - CONS_Printf(M_GetText("Game Controller subsystem not started\n")); - return -1; - } - - if (joyindex <= 0) - return -1; - - num_joy = SDL_NumJoysticks(); - - if (num_joy == 0) - { - CONS_Printf("%s", M_GetText("Found no joysticks on this system\n")); - return -1; - } - - newdev = SDL_GameControllerOpen(joyindex - 1); - - // Handle the edge case where the device <-> joystick index assignment can change due to hotplugging - // This indexing is SDL's responsibility and there's not much we can do about it. - // - // Example: - // 1. Plug Controller A -> Index 0 opened - // 2. Plug Controller B -> Index 1 opened - // 3. Unplug Controller A -> Index 0 closed, Index 1 active - // 4. Unplug Controller B -> Index 0 inactive, Index 1 closed - // 5. Plug Controller B -> Index 0 opened - // 6. Plug Controller A -> Index 0 REPLACED, opened as Controller A; Index 1 is now Controller B - if (JoyInfo3.dev) - { - if (JoyInfo3.dev == newdev // same device, nothing to do - || (newdev == NULL && SDL_GameControllerGetAttached(JoyInfo3.dev))) // we failed, but already have a working device - return SDL_CONTROLLER_AXIS_MAX; - // Else, we're changing devices, so send neutral joy events - CONS_Debug(DBG_GAMELOGIC, "Joystick3 device is changing; resetting events...\n"); - I_ShutdownJoystick3(); - } - - JoyInfo3.dev = newdev; - - if (JoyInfo3.dev == NULL) - { - CONS_Debug(DBG_GAMELOGIC, M_GetText("Joystick3: couldn't open device - %s\n"), SDL_GetError()); - return -1; - } - else - { - CONS_Debug(DBG_GAMELOGIC, M_GetText("Joystick3: %s\n"), SDL_GameControllerName(JoyInfo3.dev)); - JoyInfo3.axises = SDL_CONTROLLER_AXIS_MAX; - if (JoyInfo3.axises > JOYAXISSET * 2) - JoyInfo3.axises = JOYAXISSET * 2; - /* if (joyaxes<2) - { - I_OutputMsg("Not enought axes?\n"); - return 0; - }*/ - - JoyInfo3.buttons = SDL_CONTROLLER_BUTTON_MAX ; // dpad is 4 buttons - if (JoyInfo3.buttons > JOYBUTTONS) - JoyInfo3.buttons = JOYBUTTONS; - - JoyInfo3.hats = 4; - if (JoyInfo3.hats > JOYHATS) - JoyInfo3.hats = JOYHATS; - - JoyInfo3.balls = 0; - - //Joystick.bGamepadStyle = !stricmp(SDL_JoystickName(JoyInfo3.dev), "pad"); - - return JoyInfo3.axises; - } -} - -//Joystick4 - -/** \brief Joystick 4 buttons states -*/ -static UINT64 lastjoy4buttons = 0; - -/** \brief Joystick 4 hats state -*/ -static UINT64 lastjoy4hats = 0; - -/** \brief Shuts down joystick 4 - - -\return void -*/ -void I_ShutdownJoystick4(void) -{ - INT32 i; - event_t event; - event.type = ev_keyup; - event.data2 = 0; - event.data3 = 0; - - lastjoy4buttons = lastjoy4hats = 0; - - // emulate the up of all joystick buttons - for (i = 0; i < JOYBUTTONS; i++) - { - event.data1 = KEY_4JOY1 + i; - D_PostEvent(&event); - } - - // emulate the up of all joystick hats - for (i = 0; i < JOYHATS*4; i++) - { - event.data1 = KEY_4HAT1 + i; - D_PostEvent(&event); - } - - // reset joystick position - event.type = ev_joystick4; - for (i = 0; i < JOYAXISSET; i++) - { - event.data1 = i; - D_PostEvent(&event); - } - - joystick4_started = 0; - JoyReset(&JoyInfo4); - - // don't shutdown the subsystem here, because hotplugging -} - -void I_GetJoystick4Events(void) -{ - static event_t event = {0,0,0,0}; - INT32 i = 0; - UINT64 joyhats = 0; -#if 0 - UINT64 joybuttons = 0; - UINT32 axisx, axisy; -#endif - - if (!joystick4_started) - return; - - if (!JoyInfo4.dev) //I_ShutdownJoystick4(); - return; - -#if 0 - //faB: look for as much buttons as g_input code supports, - // we don't use the others - for (i = JoyInfo4.buttons - 1; i >= 0; i--) - { - joybuttons <<= 1; - if (SDL_JoystickGetButton(JoyInfo4.dev,i)) - joybuttons |= 1; - } - - if (joybuttons != lastjoy4buttons) - { - INT64 j = 1; // keep only bits that changed since last time - INT64 newbuttons = joybuttons ^ lastjoy4buttons; - lastjoy4buttons = joybuttons; - - for (i = 0; i < JOYBUTTONS; i++, j <<= 1) - { - if (newbuttons & j) // button changed state? - { - if (joybuttons & j) - event.type = ev_keydown; - else - event.type = ev_keyup; - event.data1 = KEY_4JOY1 + i; - D_PostEvent(&event); - } - } - } -#endif - - joyhats |= SDL_GameControllerGetButton(JoyInfo4.dev, SDL_CONTROLLER_BUTTON_DPAD_UP); - joyhats |= SDL_GameControllerGetButton(JoyInfo4.dev, SDL_CONTROLLER_BUTTON_DPAD_DOWN) << 1; - joyhats |= SDL_GameControllerGetButton(JoyInfo4.dev, SDL_CONTROLLER_BUTTON_DPAD_LEFT) << 2; - joyhats |= SDL_GameControllerGetButton(JoyInfo4.dev, SDL_CONTROLLER_BUTTON_DPAD_RIGHT) << 3; - - if (joyhats != lastjoy4hats) - { - INT64 j = 1; // keep only bits that changed since last time - INT64 newhats = joyhats ^ lastjoy4hats; - lastjoy4hats = joyhats; - - for (i = 0; i < JOYHATS*4; i++, j <<= 1) - { - if (newhats & j) // hat changed state? - { - if (joyhats & j) - event.type = ev_keydown; - else - event.type = ev_keyup; - event.data1 = KEY_4HAT1 + i; - D_PostEvent(&event); - } - } - } - -#if 0 - // send joystick axis positions - event.type = ev_joystick4; - - for (i = JOYAXISSET - 1; i >= 0; i--) - { - event.data1 = i; - if (i*2 + 1 <= JoyInfo4.axises) - axisx = SDL_JoystickGetAxis(JoyInfo4.dev, i*2 + 0); - else axisx = 0; - if (i*2 + 2 <= JoyInfo4.axises) - axisy = SDL_JoystickGetAxis(JoyInfo4.dev, i*2 + 1); - else axisy = 0; - - // -32768 to 32767 - axisx = axisx/32; - axisy = axisy/32; - - if (Joystick4.bGamepadStyle) - { - // gamepad control type, on or off, live or die - if (axisx < -(JOYAXISRANGE/2)) - event.data2 = -1; - else if (axisx > (JOYAXISRANGE/2)) - event.data2 = 1; - else - event.data2 = 0; - if (axisy < -(JOYAXISRANGE/2)) - event.data3 = -1; - else if (axisy > (JOYAXISRANGE/2)) - event.data3 = 1; - else - event.data3 = 0; - } - else - { - - axisx = JoyInfo4.scale?((axisx/JoyInfo4.scale)*JoyInfo4.scale):axisx; - axisy = JoyInfo4.scale?((axisy/JoyInfo4.scale)*JoyInfo4.scale):axisy; - -#ifdef SDL_JDEADZONE - if (-SDL_JDEADZONE <= axisx && axisx <= SDL_JDEADZONE) axisx = 0; - if (-SDL_JDEADZONE <= axisy && axisy <= SDL_JDEADZONE) axisy = 0; -#endif - - // analog control style , just send the raw data - event.data2 = axisx; // x axis - event.data3 = axisy; // y axis - } - D_PostEvent(&event); - } -#endif -} - -/** \brief Open joystick handle - - \param fname name of joystick - - \return axises - - -*/ -static int joy_open4(int joyindex) -{ - SDL_GameController *newdev = NULL; - int num_joy = 0; - - if (SDL_WasInit(SDL_INIT_JOYSTICK) == 0) - { - CONS_Printf(M_GetText("Joystick subsystem not started\n")); - return -1; - } - if (SDL_WasInit(SDL_INIT_GAMECONTROLLER) == 0) - { - CONS_Printf(M_GetText("Game Controller subsystem not started\n")); - return -1; - } - - if (joyindex <= 0) - return -1; - - num_joy = SDL_NumJoysticks(); - - if (num_joy == 0) - { - CONS_Printf("%s", M_GetText("Found no joysticks on this system\n")); - return -1; - } - - newdev = SDL_GameControllerOpen(joyindex - 1); - - // Handle the edge case where the device <-> joystick index assignment can change due to hotplugging - // This indexing is SDL's responsibility and there's not much we can do about it. - // - // Example: - // 1. Plug Controller A -> Index 0 opened - // 2. Plug Controller B -> Index 1 opened - // 3. Unplug Controller A -> Index 0 closed, Index 1 active - // 4. Unplug Controller B -> Index 0 inactive, Index 1 closed - // 5. Plug Controller B -> Index 0 opened - // 6. Plug Controller A -> Index 0 REPLACED, opened as Controller A; Index 1 is now Controller B - if (JoyInfo4.dev) - { - if (JoyInfo4.dev == newdev // same device, nothing to do - || (newdev == NULL && SDL_GameControllerGetAttached(JoyInfo4.dev))) // we failed, but already have a working device - return SDL_CONTROLLER_AXIS_MAX; - // Else, we're changing devices, so send neutral joy events - CONS_Debug(DBG_GAMELOGIC, "Joystick4 device is changing; resetting events...\n"); - I_ShutdownJoystick4(); - } - - JoyInfo4.dev = newdev; - - if (JoyInfo4.dev == NULL) - { - CONS_Debug(DBG_GAMELOGIC, M_GetText("Joystick4: couldn't open device - %s\n"), SDL_GetError()); - return -1; - } - else - { - CONS_Debug(DBG_GAMELOGIC, M_GetText("Joystick4: %s\n"), SDL_GameControllerName(JoyInfo4.dev)); - JoyInfo4.axises = SDL_CONTROLLER_AXIS_MAX; - if (JoyInfo4.axises > JOYAXISSET * 2) - JoyInfo4.axises = JOYAXISSET * 2; - /* if (joyaxes<2) - { - I_OutputMsg("Not enought axes?\n"); - return 0; - }*/ - - JoyInfo4.buttons = SDL_CONTROLLER_BUTTON_MAX ; // dpad is 4 buttons - if (JoyInfo4.buttons > JOYBUTTONS) - JoyInfo4.buttons = JOYBUTTONS; - - JoyInfo4.hats = 4; - if (JoyInfo4.hats > JOYHATS) - JoyInfo4.hats = JOYHATS; - - JoyInfo4.balls = 0; - - //Joystick.bGamepadStyle = !stricmp(SDL_JoystickName(JoyInfo4.dev), "pad"); - - return JoyInfo4.axises; + return JoyInfo[playerIndex].axises; } } // // I_InitJoystick // -void I_InitJoystick(void) +void I_InitJoystick(UINT8 index) { + UINT8 i; SDL_GameController *newcontroller = NULL; //I_ShutdownJoystick(); @@ -2434,192 +1355,80 @@ void I_InitJoystick(void) } } - if (cv_usejoystick.value) - newcontroller = SDL_GameControllerOpen(cv_usejoystick.value-1); + if (cv_usejoystick[index].value) + newcontroller = SDL_GameControllerOpen(cv_usejoystick[index].value-1); - if (newcontroller && (JoyInfo2.dev == newcontroller || JoyInfo3.dev == newcontroller || JoyInfo4.dev == newcontroller)) // don't override an active device - cv_usejoystick.value = I_GetJoystickDeviceIndex(JoyInfo.dev) + 1; - else if (newcontroller && joy_open(cv_usejoystick.value) != -1) + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + if (i == index) + continue; + + if (JoyInfo[i].dev == newcontroller) + break; + } + + if (newcontroller && i < MAXSPLITSCREENPLAYERS) // don't override an active device + { + cv_usejoystick[index].value = I_GetJoystickDeviceIndex(JoyInfo[index].dev) + 1; + } + else if (newcontroller && joy_open(index, cv_usejoystick[index].value) != -1) { // SDL's device indexes are unstable, so cv_usejoystick may not match // the actual device index. So let's cheat a bit and find the device's current index. - JoyInfo.oldjoy = I_GetJoystickDeviceIndex(JoyInfo.dev) + 1; - joystick_started = 1; + JoyInfo[index].oldjoy = I_GetJoystickDeviceIndex(JoyInfo[index].dev) + 1; + joystick_started[index] = 1; } else { - if (JoyInfo.oldjoy) - I_ShutdownJoystick(); - cv_usejoystick.value = 0; - joystick_started = 0; + if (JoyInfo[index].oldjoy) + I_ShutdownJoystick(index); + cv_usejoystick[index].value = 0; + joystick_started[index] = 0; } - if (JoyInfo.dev != newcontroller && JoyInfo2.dev != newcontroller && JoyInfo3.dev != newcontroller && JoyInfo4.dev != newcontroller) + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + if (JoyInfo[i].dev == newcontroller) + break; + } + + if (i == MAXSPLITSCREENPLAYERS) + { + // Joystick didn't end up being used SDL_GameControllerClose(newcontroller); + } +} + +void I_InitJoystick1(void) +{ + I_InitJoystick(0); } void I_InitJoystick2(void) { - SDL_GameController *newcontroller = NULL; - - //I_ShutdownJoystick2(); - //SDL_SetHintWithPriority("SDL_XINPUT_ENABLED", "0", SDL_HINT_OVERRIDE); - if (M_CheckParm("-nojoy")) - return; - - if (SDL_WasInit(SDL_INIT_JOYSTICK) == 0) - { - CONS_Printf("I_InitJoystick2()...\n"); - if (SDL_InitSubSystem(SDL_INIT_JOYSTICK) == -1) - { - CONS_Printf(M_GetText("Couldn't initialize joystick: %s\n"), SDL_GetError()); - return; - } - } - if (SDL_WasInit(SDL_INIT_GAMECONTROLLER) == 0) - { - if (SDL_InitSubSystem(SDL_INIT_GAMECONTROLLER) == -1) - { - CONS_Printf(M_GetText("Couldn't initialize gamepads: %s\n"), SDL_GetError()); - return; - } - } - - if (cv_usejoystick2.value) - newcontroller = SDL_GameControllerOpen(cv_usejoystick2.value-1); - - if (newcontroller && (JoyInfo.dev == newcontroller || JoyInfo3.dev == newcontroller || JoyInfo4.dev == newcontroller)) // don't override an active device - cv_usejoystick2.value = I_GetJoystickDeviceIndex(JoyInfo2.dev) + 1; - else if (newcontroller && joy_open2(cv_usejoystick2.value) != -1) - { - // SDL's device indexes are unstable, so cv_usejoystick may not match - // the actual device index. So let's cheat a bit and find the device's current index. - JoyInfo2.oldjoy = I_GetJoystickDeviceIndex(JoyInfo2.dev) + 1; - joystick2_started = 1; - } - else - { - if (JoyInfo2.oldjoy) - I_ShutdownJoystick2(); - cv_usejoystick2.value = 0; - joystick2_started = 0; - } - - if (JoyInfo.dev != newcontroller && JoyInfo2.dev != newcontroller && JoyInfo3.dev != newcontroller && JoyInfo4.dev != newcontroller) - SDL_GameControllerClose(newcontroller); + I_InitJoystick(1); } void I_InitJoystick3(void) { - SDL_GameController *newcontroller = NULL; - - //I_ShutdownJoystick3(); - //SDL_SetHintWithPriority("SDL_XINPUT_ENABLED", "0", SDL_HINT_OVERRIDE); - if (M_CheckParm("-nojoy")) - return; - - if (SDL_WasInit(SDL_INIT_JOYSTICK) == 0) - { - CONS_Printf("I_InitJoystick3()...\n"); - if (SDL_InitSubSystem(SDL_INIT_JOYSTICK) == -1) - { - CONS_Printf(M_GetText("Couldn't initialize joystick: %s\n"), SDL_GetError()); - return; - } - } - if (SDL_WasInit(SDL_INIT_GAMECONTROLLER) == 0) - { - if (SDL_InitSubSystem(SDL_INIT_GAMECONTROLLER) == -1) - { - CONS_Printf(M_GetText("Couldn't initialize gamepads: %s\n"), SDL_GetError()); - return; - } - } - - if (cv_usejoystick3.value) - newcontroller = SDL_GameControllerOpen(cv_usejoystick3.value - 1); - - if (newcontroller && (JoyInfo.dev == newcontroller || JoyInfo2.dev == newcontroller || JoyInfo4.dev == newcontroller)) // don't override an active device - cv_usejoystick3.value = I_GetJoystickDeviceIndex(JoyInfo3.dev) + 1; - else if (newcontroller && joy_open3(cv_usejoystick3.value) != -1) - { - // SDL's device indexes are unstable, so cv_usejoystick may not match - // the actual device index. So let's cheat a bit and find the device's current index. - JoyInfo3.oldjoy = I_GetJoystickDeviceIndex(JoyInfo3.dev) + 1; - joystick3_started = 1; - } - else - { - if (JoyInfo3.oldjoy) - I_ShutdownJoystick3(); - cv_usejoystick3.value = 0; - joystick3_started = 0; - } - - if (JoyInfo.dev != newcontroller && JoyInfo2.dev != newcontroller && JoyInfo3.dev != newcontroller && JoyInfo4.dev != newcontroller) - SDL_GameControllerClose(newcontroller); + I_InitJoystick(2); } void I_InitJoystick4(void) { - SDL_GameController *newcontroller = NULL; - - //I_ShutdownJoystick4(); - //SDL_SetHintWithPriority("SDL_XINPUT_ENABLED", "0", SDL_HINT_OVERRIDE); - if (M_CheckParm("-nojoy")) - return; - - if (SDL_WasInit(SDL_INIT_JOYSTICK) == 0) - { - CONS_Printf("I_InitJoystick4()...\n"); - if (SDL_InitSubSystem(SDL_INIT_JOYSTICK) == -1) - { - CONS_Printf(M_GetText("Couldn't initialize joystick: %s\n"), SDL_GetError()); - return; - } - } - if (SDL_WasInit(SDL_INIT_GAMECONTROLLER) == 0) - { - if (SDL_InitSubSystem(SDL_INIT_GAMECONTROLLER) == -1) - { - CONS_Printf(M_GetText("Couldn't initialize gamepads: %s\n"), SDL_GetError()); - return; - } - } - - if (cv_usejoystick4.value) - newcontroller = SDL_GameControllerOpen(cv_usejoystick4.value - 1); - - if (newcontroller && (JoyInfo.dev == newcontroller || JoyInfo2.dev == newcontroller || JoyInfo4.dev == newcontroller)) // don't override an active device - cv_usejoystick4.value = I_GetJoystickDeviceIndex(JoyInfo4.dev) + 1; - else if (newcontroller && joy_open4(cv_usejoystick4.value) != -1) - { - // SDL's device indexes are unstable, so cv_usejoystick may not match - // the actual device index. So let's cheat a bit and find the device's current index. - JoyInfo4.oldjoy = I_GetJoystickDeviceIndex(JoyInfo4.dev) + 1; - joystick4_started = 1; - } - else - { - if (JoyInfo4.oldjoy) - I_ShutdownJoystick4(); - cv_usejoystick4.value = 0; - joystick4_started = 0; - } - - if (JoyInfo.dev != newcontroller && JoyInfo2.dev != newcontroller && JoyInfo3.dev != newcontroller && JoyInfo4.dev != newcontroller) - SDL_GameControllerClose(newcontroller); + I_InitJoystick(3); } static void I_ShutdownInput(void) { + UINT8 i; + // Yes, the name is misleading: these send neutral events to // clean up the unplugged joystick's input // Note these methods are internal to this file, not called elsewhere. - I_ShutdownJoystick(); - I_ShutdownJoystick2(); - I_ShutdownJoystick3(); - I_ShutdownJoystick4(); + + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + I_ShutdownJoystick(i); if (SDL_WasInit(SDL_INIT_GAMECONTROLLER) == SDL_INIT_GAMECONTROLLER) { diff --git a/src/sdl/i_video.c b/src/sdl/i_video.c index 1dcfe57a7..aaea21f48 100644 --- a/src/sdl/i_video.c +++ b/src/sdl/i_video.c @@ -667,90 +667,37 @@ static INT32 SDLJoyAxis(const Sint16 axis, evtype_t which) { // -32768 to 32767 INT32 raxis = axis/32; + UINT8 pid; + if (which == ev_joystick) - { - if (Joystick.bGamepadStyle) - { - // gamepad control type, on or off, live or die - if (raxis < -(JOYAXISRANGE/2)) - raxis = -1; - else if (raxis > (JOYAXISRANGE/2)) - raxis = 1; - else - raxis = 0; - } - else - { - raxis = JoyInfo.scale!=1?((raxis/JoyInfo.scale)*JoyInfo.scale):raxis; - -#ifdef SDL_JDEADZONE - if (-SDL_JDEADZONE <= raxis && raxis <= SDL_JDEADZONE) - raxis = 0; -#endif - } - } + pid = 0; else if (which == ev_joystick2) - { - if (Joystick2.bGamepadStyle) - { - // gamepad control type, on or off, live or die - if (raxis < -(JOYAXISRANGE/2)) - raxis = -1; - else if (raxis > (JOYAXISRANGE/2)) - raxis = 1; - else raxis = 0; - } - else - { - raxis = JoyInfo2.scale!=1?((raxis/JoyInfo2.scale)*JoyInfo2.scale):raxis; - -#ifdef SDL_JDEADZONE - if (-SDL_JDEADZONE <= raxis && raxis <= SDL_JDEADZONE) - raxis = 0; -#endif - } - } + pid = 1; else if (which == ev_joystick3) - { - if (Joystick3.bGamepadStyle) - { - // gamepad control type, on or off, live or die - if (raxis < -(JOYAXISRANGE/2)) - raxis = -1; - else if (raxis > (JOYAXISRANGE/2)) - raxis = 1; - else raxis = 0; - } - else - { - raxis = JoyInfo3.scale!=1?((raxis/JoyInfo3.scale)*JoyInfo3.scale):raxis; - -#ifdef SDL_JDEADZONE - if (-SDL_JDEADZONE <= raxis && raxis <= SDL_JDEADZONE) - raxis = 0; -#endif - } - } + pid = 2; else if (which == ev_joystick4) + pid = 3; + else + return 0; + + if (Joystick[pid].bGamepadStyle) { - if (Joystick4.bGamepadStyle) - { - // gamepad control type, on or off, live or die - if (raxis < -(JOYAXISRANGE/2)) - raxis = -1; - else if (raxis > (JOYAXISRANGE/2)) - raxis = 1; - else raxis = 0; - } + // gamepad control type, on or off, live or die + if (raxis < -(JOYAXISRANGE/2)) + raxis = -1; + else if (raxis > (JOYAXISRANGE/2)) + raxis = 1; else - { - raxis = JoyInfo4.scale!=1?((raxis/JoyInfo4.scale)*JoyInfo4.scale):raxis; + raxis = 0; + } + else + { + raxis = JoyInfo[pid].scale!=1?((raxis/JoyInfo[pid].scale)*JoyInfo[pid].scale):raxis; #ifdef SDL_JDEADZONE - if (-SDL_JDEADZONE <= raxis && raxis <= SDL_JDEADZONE) - raxis = 0; + if (-SDL_JDEADZONE <= raxis && raxis <= SDL_JDEADZONE) + raxis = 0; #endif - } } return raxis; } @@ -834,7 +781,7 @@ static void I_FixXwaylandNvidia(void) //dumbass crap, fix ur shit nvidia static void Impl_HandleWindowEvent(SDL_WindowEvent evt) { -#define FOCUSUNION (mousefocus | (kbfocus << 1)) +#define FOCUSUNION (mousefocus | (kbfocus << 1) | (windowmoved << 2)) static SDL_bool firsttimeonmouse = SDL_TRUE; static SDL_bool mousefocus = SDL_TRUE; static SDL_bool kbfocus = SDL_TRUE; @@ -1062,12 +1009,13 @@ static void Impl_HandleControllerAxisEvent(SDL_ControllerAxisEvent evt) event_t event; SDL_JoystickID joyid[4]; INT32 value; + UINT8 i; // Determine the Joystick IDs for each current open joystick - joyid[0] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo.dev)); - joyid[1] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo2.dev)); - joyid[2] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo3.dev)); - joyid[3] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo4.dev)); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + joyid[i] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo[i].dev)); + } event.data1 = event.data2 = event.data3 = INT32_MAX; @@ -1088,9 +1036,11 @@ static void Impl_HandleControllerAxisEvent(SDL_ControllerAxisEvent evt) event.type = ev_joystick4; } else return; + //axis if (evt.axis > JOYAXISSET*2) return; + //vaule value = SDLJoyAxis(evt.value, event.type); switch (evt.axis) @@ -1125,43 +1075,17 @@ static void Impl_HandleControllerAxisEvent(SDL_ControllerAxisEvent evt) D_PostEvent(&event); } -#if 0 -static void Impl_HandleJoystickHatEvent(SDL_JoyHatEvent evt) -{ - event_t event; - SDL_JoystickID joyid[2]; - - // Determine the Joystick IDs for each current open joystick - joyid[0] = SDL_JoystickInstanceID(JoyInfo.dev); - joyid[1] = SDL_JoystickInstanceID(JoyInfo2.dev); - - if (evt.hat >= JOYHATS) - return; // ignore hats with too high an index - - if (evt.which == joyid[0]) - { - event.data1 = KEY_HAT1 + (evt.hat*4); - } - else if (evt.which == joyid[1]) - { - event.data1 = KEY_2HAT1 + (evt.hat*4); - } - else return; - - // NOTE: UNFINISHED -} -#endif - static void Impl_HandleControllerButtonEvent(SDL_ControllerButtonEvent evt, Uint32 type) { event_t event; SDL_JoystickID joyid[4]; + UINT8 i; // Determine the Joystick IDs for each current open joystick - joyid[0] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo.dev)); - joyid[1] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo2.dev)); - joyid[2] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo3.dev)); - joyid[3] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo4.dev)); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + joyid[i] = SDL_JoystickInstanceID(SDL_GameControllerGetJoystick(JoyInfo[i].dev)); + } if (evt.button == SDL_CONTROLLER_BUTTON_DPAD_UP || evt.button == SDL_CONTROLLER_BUTTON_DPAD_DOWN @@ -1208,8 +1132,6 @@ static void Impl_HandleControllerButtonEvent(SDL_ControllerButtonEvent evt, Uint if (event.type != ev_console) D_PostEvent(&event); } - - void I_GetEvent(void) { SDL_Event evt; @@ -1217,6 +1139,7 @@ void I_GetEvent(void) // We only want the first motion event, // otherwise we'll end up catching the warp back to center. //int mouseMotionOnce = 0; + INT32 i; if (!graphics_started) { @@ -1282,77 +1205,42 @@ void I_GetEvent(void) // * BUT: If that default index is being occupied, use ANOTHER cv_usejoystick's default value! //////////////////////////////////////////////////////////// - ////////////////////////////// - // PLAYER 1 - ////////////////////////////// - - if (newcontroller && (!JoyInfo.dev || !SDL_GameControllerGetAttached(JoyInfo.dev)) - && JoyInfo2.dev != newcontroller && JoyInfo3.dev != newcontroller && JoyInfo4.dev != newcontroller) // don't override a currently active device + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) { - cv_usejoystick.value = evt.cdevice.which + 1; - I_UpdateJoystickDeviceIndices(1); - } + if (newcontroller && (!JoyInfo[i].dev || !SDL_GameControllerGetAttached(JoyInfo[i].dev))) + { + UINT8 j; - ////////////////////////////// - // PLAYER 2 - ////////////////////////////// + for (j = 0; j < MAXSPLITSCREENPLAYERS; j++) + { + if (i == j) + continue; - else if (newcontroller && (!JoyInfo2.dev || !SDL_GameControllerGetAttached(JoyInfo2.dev)) - && JoyInfo.dev != newcontroller && JoyInfo3.dev != newcontroller && JoyInfo4.dev != newcontroller) // don't override a currently active device - { - cv_usejoystick2.value = evt.cdevice.which + 1; - I_UpdateJoystickDeviceIndices(2); - } + if (JoyInfo[j].dev == newcontroller) + break; + } - ////////////////////////////// - // PLAYER 3 - ////////////////////////////// - - else if (newcontroller && (!JoyInfo3.dev || !SDL_GameControllerGetAttached(JoyInfo3.dev)) - && JoyInfo.dev != newcontroller && JoyInfo2.dev != newcontroller && JoyInfo4.dev != newcontroller) // don't override a currently active device - { - cv_usejoystick3.value = evt.cdevice.which + 1; - I_UpdateJoystickDeviceIndices(3); - } - - ////////////////////////////// - // PLAYER 4 - ////////////////////////////// - - else if (newcontroller && (!JoyInfo4.dev || !SDL_GameControllerGetAttached(JoyInfo4.dev)) - && JoyInfo.dev != newcontroller && JoyInfo2.dev != newcontroller && JoyInfo3.dev != newcontroller) // don't override a currently active device - { - cv_usejoystick4.value = evt.cdevice.which + 1; - I_UpdateJoystickDeviceIndices(4); + if (j == MAXSPLITSCREENPLAYERS) + { + // ensures we aren't overriding a currently active device + cv_usejoystick[i].value = evt.jdevice.which + 1; + I_UpdateJoystickDeviceIndices(0); + } + } } //////////////////////////////////////////////////////////// // Was cv_usejoystick disabled in settings? //////////////////////////////////////////////////////////// - if (!strcmp(cv_usejoystick.string, "0") || !cv_usejoystick.value) - cv_usejoystick.value = 0; - else if (atoi(cv_usejoystick.string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys - && cv_usejoystick.value) // update the cvar ONLY if a device exists - CV_SetValue(&cv_usejoystick, cv_usejoystick.value); - - if (!strcmp(cv_usejoystick2.string, "0") || !cv_usejoystick2.value) - cv_usejoystick2.value = 0; - else if (atoi(cv_usejoystick2.string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys - && cv_usejoystick2.value) // update the cvar ONLY if a device exists - CV_SetValue(&cv_usejoystick2, cv_usejoystick2.value); - - if (!strcmp(cv_usejoystick3.string, "0") || !cv_usejoystick3.value) - cv_usejoystick3.value = 0; - else if (atoi(cv_usejoystick3.string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys - && cv_usejoystick3.value) // update the cvar ONLY if a device exists - CV_SetValue(&cv_usejoystick3, cv_usejoystick3.value); - - if (!strcmp(cv_usejoystick4.string, "0") || !cv_usejoystick4.value) - cv_usejoystick4.value = 0; - else if (atoi(cv_usejoystick4.string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys - && cv_usejoystick4.value) // update the cvar ONLY if a device exists - CV_SetValue(&cv_usejoystick4, cv_usejoystick4.value); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + if (!strcmp(cv_usejoystick[i].string, "0") || !cv_usejoystick[i].value) + cv_usejoystick[i].value = 0; + else if (atoi(cv_usejoystick[i].string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys + && cv_usejoystick[i].value) // update the cvar ONLY if a device exists + CV_SetValue(&cv_usejoystick[i], cv_usejoystick[i].value); + } //////////////////////////////////////////////////////////// // Update all joysticks' init states @@ -1361,23 +1249,25 @@ void I_GetEvent(void) // if the device is already active, this should do nothing, effectively. //////////////////////////////////////////////////////////// - I_InitJoystick(); - I_InitJoystick2(); - I_InitJoystick3(); - I_InitJoystick4(); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + I_InitJoystick(i); //////////////////////////////////////////////////////////// - CONS_Debug(DBG_GAMELOGIC, "Joystick1 device index: %d\n", JoyInfo.oldjoy); - CONS_Debug(DBG_GAMELOGIC, "Joystick2 device index: %d\n", JoyInfo2.oldjoy); - CONS_Debug(DBG_GAMELOGIC, "Joystick3 device index: %d\n", JoyInfo3.oldjoy); - CONS_Debug(DBG_GAMELOGIC, "Joystick4 device index: %d\n", JoyInfo4.oldjoy); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + CONS_Debug(DBG_GAMELOGIC, "Joystick%d device index: %d\n", i+1, JoyInfo[i].oldjoy); // update the menu if (currentMenu == &OP_JoystickSetDef) M_SetupJoystickMenu(0); - if (JoyInfo.dev != newcontroller && JoyInfo2.dev != newcontroller && JoyInfo3.dev != newcontroller && JoyInfo4.dev != newcontroller) + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + if (JoyInfo[i].dev == newcontroller) + break; + } + + if (i == MAXSPLITSCREENPLAYERS) SDL_GameControllerClose(newcontroller); } break; @@ -1385,28 +1275,13 @@ void I_GetEvent(void) //////////////////////////////////////////////////////////// case SDL_CONTROLLERDEVICEREMOVED: - if (JoyInfo.dev && !SDL_GameControllerGetAttached(JoyInfo.dev)) + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) { - CONS_Debug(DBG_GAMELOGIC, "Joystick1 removed, device index: %d\n", JoyInfo.oldjoy); - I_ShutdownJoystick(); - } - - if (JoyInfo2.dev && !SDL_GameControllerGetAttached(JoyInfo2.dev)) - { - CONS_Debug(DBG_GAMELOGIC, "Joystick2 removed, device index: %d\n", JoyInfo2.oldjoy); - I_ShutdownJoystick2(); - } - - if (JoyInfo3.dev && !SDL_GameControllerGetAttached(JoyInfo3.dev)) - { - CONS_Debug(DBG_GAMELOGIC, "Joystick3 removed, device index: %d\n", JoyInfo3.oldjoy); - I_ShutdownJoystick3(); - } - - if (JoyInfo4.dev && !SDL_GameControllerGetAttached(JoyInfo4.dev)) - { - CONS_Debug(DBG_GAMELOGIC, "Joystick4 removed, device index: %d\n", JoyInfo4.oldjoy); - I_ShutdownJoystick4(); + if (JoyInfo[i].dev && !SDL_GameControllerGetAttached(JoyInfo[i].dev)) + { + CONS_Debug(DBG_GAMELOGIC, "Joystick%d removed, device index: %d\n", i+1, JoyInfo[i].oldjoy); + I_ShutdownJoystick(i); + } } //////////////////////////////////////////////////////////// @@ -1415,124 +1290,32 @@ void I_GetEvent(void) // * BUT: If that default index is being occupied, use ANOTHER cv_usejoystick's default value! //////////////////////////////////////////////////////////// - if (JoyInfo.dev) - cv_usejoystick.value = JoyInfo.oldjoy = I_GetJoystickDeviceIndex(JoyInfo.dev) + 1; - else if (atoi(cv_usejoystick.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick.string) != JoyInfo4.oldjoy) - cv_usejoystick.value = atoi(cv_usejoystick.string); - else if (atoi(cv_usejoystick2.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick2.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick2.string) != JoyInfo4.oldjoy) - cv_usejoystick.value = atoi(cv_usejoystick2.string); - else if (atoi(cv_usejoystick3.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick3.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick3.string) != JoyInfo4.oldjoy) - cv_usejoystick.value = atoi(cv_usejoystick3.string); - else if (atoi(cv_usejoystick4.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick4.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick4.string) != JoyInfo4.oldjoy) - cv_usejoystick.value = atoi(cv_usejoystick4.string); - else // we tried... - cv_usejoystick.value = 0; - - if (JoyInfo2.dev) - cv_usejoystick2.value = JoyInfo2.oldjoy = I_GetJoystickDeviceIndex(JoyInfo2.dev) + 1; - else if (atoi(cv_usejoystick.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick.string) != JoyInfo4.oldjoy) - cv_usejoystick2.value = atoi(cv_usejoystick.string); - else if (atoi(cv_usejoystick2.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick2.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick2.string) != JoyInfo4.oldjoy) - cv_usejoystick2.value = atoi(cv_usejoystick2.string); - else if (atoi(cv_usejoystick3.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick3.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick3.string) != JoyInfo4.oldjoy) - cv_usejoystick2.value = atoi(cv_usejoystick3.string); - else if (atoi(cv_usejoystick4.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick4.string) != JoyInfo3.oldjoy - && atoi(cv_usejoystick4.string) != JoyInfo4.oldjoy) - cv_usejoystick2.value = atoi(cv_usejoystick4.string); - else // we tried... - cv_usejoystick2.value = 0; - - if (JoyInfo3.dev) - cv_usejoystick3.value = JoyInfo3.oldjoy = I_GetJoystickDeviceIndex(JoyInfo3.dev) + 1; - else if (atoi(cv_usejoystick.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick.string) != JoyInfo4.oldjoy) - cv_usejoystick3.value = atoi(cv_usejoystick.string); - else if (atoi(cv_usejoystick2.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick2.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick2.string) != JoyInfo4.oldjoy) - cv_usejoystick3.value = atoi(cv_usejoystick2.string); - else if (atoi(cv_usejoystick3.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick3.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick3.string) != JoyInfo4.oldjoy) - cv_usejoystick3.value = atoi(cv_usejoystick3.string); - else if (atoi(cv_usejoystick4.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick4.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick4.string) != JoyInfo4.oldjoy) - cv_usejoystick3.value = atoi(cv_usejoystick4.string); - else // we tried... - cv_usejoystick3.value = 0; - - if (JoyInfo4.dev) - cv_usejoystick4.value = JoyInfo4.oldjoy = I_GetJoystickDeviceIndex(JoyInfo4.dev) + 1; - else if (atoi(cv_usejoystick.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick.string) != JoyInfo3.oldjoy) - cv_usejoystick4.value = atoi(cv_usejoystick.string); - else if (atoi(cv_usejoystick2.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick2.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick2.string) != JoyInfo3.oldjoy) - cv_usejoystick4.value = atoi(cv_usejoystick2.string); - else if (atoi(cv_usejoystick3.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick3.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick3.string) != JoyInfo3.oldjoy) - cv_usejoystick4.value = atoi(cv_usejoystick3.string); - else if (atoi(cv_usejoystick4.string) != JoyInfo.oldjoy - && atoi(cv_usejoystick4.string) != JoyInfo2.oldjoy - && atoi(cv_usejoystick4.string) != JoyInfo3.oldjoy) - cv_usejoystick4.value = atoi(cv_usejoystick4.string); - else // we tried... - cv_usejoystick4.value = 0; + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + I_UpdateJoystickDeviceIndex(i); + } //////////////////////////////////////////////////////////// // Was cv_usejoystick disabled in settings? //////////////////////////////////////////////////////////// - if (!strcmp(cv_usejoystick.string, "0")) - cv_usejoystick.value = 0; - else if (atoi(cv_usejoystick.string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys - && cv_usejoystick.value) // update the cvar ONLY if a device exists - CV_SetValue(&cv_usejoystick, cv_usejoystick.value); - - if (!strcmp(cv_usejoystick2.string, "0")) - cv_usejoystick2.value = 0; - else if (atoi(cv_usejoystick2.string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys - && cv_usejoystick2.value) // update the cvar ONLY if a device exists - CV_SetValue(&cv_usejoystick2, cv_usejoystick2.value); - - if (!strcmp(cv_usejoystick3.string, "0")) - cv_usejoystick3.value = 0; - else if (atoi(cv_usejoystick3.string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys - && cv_usejoystick3.value) // update the cvar ONLY if a device exists - CV_SetValue(&cv_usejoystick3, cv_usejoystick3.value); - - if (!strcmp(cv_usejoystick4.string, "0")) - cv_usejoystick4.value = 0; - else if (atoi(cv_usejoystick4.string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys - && cv_usejoystick4.value) // update the cvar ONLY if a device exists - CV_SetValue(&cv_usejoystick4, cv_usejoystick4.value); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + { + if (!strcmp(cv_usejoystick[i].string, "0")) + { + cv_usejoystick[i].value = 0; + } + else if (atoi(cv_usejoystick[i].string) <= I_NumJoys() // don't mess if we intentionally set higher than NumJoys + && cv_usejoystick[i].value) // update the cvar ONLY if a device exists + { + CV_SetValue(&cv_usejoystick[i], cv_usejoystick[i].value); + } + } //////////////////////////////////////////////////////////// - CONS_Debug(DBG_GAMELOGIC, "Joystick1 device index: %d\n", JoyInfo.oldjoy); - CONS_Debug(DBG_GAMELOGIC, "Joystick2 device index: %d\n", JoyInfo2.oldjoy); - CONS_Debug(DBG_GAMELOGIC, "Joystick3 device index: %d\n", JoyInfo3.oldjoy); - CONS_Debug(DBG_GAMELOGIC, "Joystick4 device index: %d\n", JoyInfo4.oldjoy); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + CONS_Debug(DBG_GAMELOGIC, "Joystick%d device index: %d\n", i+1, JoyInfo[i].oldjoy); // update the menu if (currentMenu == &OP_JoystickSetDef) @@ -1594,16 +1377,15 @@ void I_StartupMouse(void) void I_OsPolling(void) { SDL_Keymod mod; + INT32 i; if (consolevent) I_GetConsoleEvents(); if (SDL_WasInit(SDL_INIT_JOYSTICK | SDL_INIT_GAMECONTROLLER) == (SDL_INIT_JOYSTICK | SDL_INIT_GAMECONTROLLER)) { SDL_GameControllerUpdate(); - I_GetJoystickEvents(); - I_GetJoystick2Events(); - I_GetJoystick3Events(); - I_GetJoystick4Events(); + for (i = 0; i < MAXSPLITSCREENPLAYERS; i++) + I_GetJoystickEvents(i); } I_GetMouseEvents(); @@ -2242,27 +2024,27 @@ void I_StartupGraphics(void) else if (M_CheckParm("-opengl")) rendermode = render_opengl; - msaa = 0; boolean msaa_set = false; - a2c = false; boolean a2c_set = false; + msaa = 0; boolean msaa_set = false; + a2c = false; boolean a2c_set = false; - if (M_CheckParm("-msaa") && M_IsNextParm()) - { - const char* str = M_GetNextParm(); - if (sscanf(str, "%u", &msaa)) - { - msaa_set = true; - } - } + if (M_CheckParm("-msaa") && M_IsNextParm()) + { + const char* str = M_GetNextParm(); + if (sscanf(str, "%u", &msaa)) + { + msaa_set = true; + } + } - if (M_CheckParm("-a2c")) - { - a2c = true; - a2c_set = true; - } - else if (M_CheckParm("-noa2c")) - { - a2c_set = true; - } + if (M_CheckParm("-a2c")) + { + a2c = true; + a2c_set = true; + } + else if (M_CheckParm("-noa2c")) + { + a2c_set = true; + } { char line[16]; @@ -2272,52 +2054,52 @@ void I_StartupGraphics(void) { while (fgets(line, sizeof line, file) != NULL) { - word = strtok(line, " \n"); + word = strtok(line, " \n"); - if (rendermode == render_none) - { - if (strcasecmp(word, "software") == 0) - { - rendermode = render_soft; - } - else if (strcasecmp(word, "opengl") == 0) - { - rendermode = render_opengl; - } + if (rendermode == render_none) + { + if (strcasecmp(word, "software") == 0) + { + rendermode = render_soft; + } + else if (strcasecmp(word, "opengl") == 0) + { + rendermode = render_opengl; + } - if (rendermode != render_none) - { - CONS_Printf("Using last known renderer: %s\n", line); - } + if (rendermode != render_none) + { + CONS_Printf("Using last known renderer: %s\n", line); + } } - if (!msaa_set) - { - if (strcasecmp(word, "msaa") == 0) - { - const char *nextword = strtok(NULL, " \n"); + if (!msaa_set) + { + if (strcasecmp(word, "msaa") == 0) + { + const char *nextword = strtok(NULL, " \n"); - if (!nextword || !sscanf(nextword, "%u", &msaa)) - { - CONS_Alert(CONS_ERROR, "Malformed MSAA entry in renderer.txt\n"); - } - else - { - CONS_Printf("Using last know MSAA value: %u\n", msaa); - } - } - } + if (!nextword || !sscanf(nextword, "%u", &msaa)) + { + CONS_Alert(CONS_ERROR, "Malformed MSAA entry in renderer.txt\n"); + } + else + { + CONS_Printf("Using last know MSAA value: %u\n", msaa); + } + } + } - if (!a2c_set) - { - if (strcasecmp(word, "a2c") == 0) - { - a2c = true; + if (!a2c_set) + { + if (strcasecmp(word, "a2c") == 0) + { + a2c = true; - CONS_Printf("Using a2c because it was specified to be used earlier\n"); - } - } - } + CONS_Printf("Using a2c because it was specified to be used earlier\n"); + } + } + } fclose(file); } @@ -2349,13 +2131,13 @@ void I_StartupGraphics(void) } #ifdef HWRENDER - fprintf(file, "msaa %u\n", msaa); + fprintf(file, "msaa %u\n", msaa); - if (a2c) - fputs("a2c\n", file); + if (a2c) + fputs("a2c\n", file); #endif - fclose(file); + fclose(file); } else { @@ -2366,8 +2148,8 @@ void I_StartupGraphics(void) usesdl2soft = M_CheckParm("-softblit"); borderlesswindow = M_CheckParm("-borderless"); - //SDL_EnableKeyRepeat(SDL_DEFAULT_REPEAT_DELAY>>1,SDL_DEFAULT_REPEAT_INTERVAL<<2); VID_Command_ModeList_f(); + #ifdef HWRENDER if (rendermode == render_opengl) { @@ -2540,4 +2322,5 @@ static void Impl_SetVsync(void) } #endif } + #endif diff --git a/src/sdl/sdlmain.h b/src/sdl/sdlmain.h index 01edd866a..0ba8da762 100644 --- a/src/sdl/sdlmain.h +++ b/src/sdl/sdlmain.h @@ -59,38 +59,24 @@ typedef struct SDLJoyInfo_s /** \brief SDL info about controller 1 */ -extern SDLJoyInfo_t JoyInfo; +extern SDLJoyInfo_t JoyInfo[4]; //MAXSPLITSCREENPLAYERS /** \brief joystick axis deadzone */ #define SDL_JDEADZONE 153 #undef SDL_JDEADZONE -/** \brief SDL inof about controller 2 -*/ -extern SDLJoyInfo_t JoyInfo2; - -/** \brief SDL inof about controller 3 -*/ -extern SDLJoyInfo_t JoyInfo3; - -/** \brief SDL inof about controller 4 -*/ -extern SDLJoyInfo_t JoyInfo4; - void I_GetConsoleEvents(void); // So we can call this from i_video event loop -void I_ShutdownJoystick(void); -void I_ShutdownJoystick2(void); -void I_ShutdownJoystick3(void); -void I_ShutdownJoystick4(void); +void I_ShutdownJoystick(UINT8 index); // Cheat to get the device index for a game controller handle INT32 I_GetJoystickDeviceIndex(SDL_GameController *dev); // Quick thing to make SDL_JOYDEVICEADDED events less of an abomination -void I_UpdateJoystickDeviceIndices(INT32 player); +void I_UpdateJoystickDeviceIndex(UINT8 player); +void I_UpdateJoystickDeviceIndices(UINT8 excludePlayer); void I_GetConsoleEvents(void); diff --git a/src/st_stuff.c b/src/st_stuff.c index de89fa6e3..6967b2aaf 100644 --- a/src/st_stuff.c +++ b/src/st_stuff.c @@ -220,13 +220,6 @@ boolean ST_SameTeam(player_t *a, player_t *b) if (a->spectator && b->spectator) return true; - // Team chat. - if (G_GametypeHasTeams()) - return a->ctfteam == b->ctfteam; - - if (G_TagGametype()) - return ((a->pflags & PF_TAGIT) == (b->pflags & PF_TAGIT)); - return false; } @@ -750,8 +743,6 @@ static void ST_overlayDrawer(void) itemtxt = M_GetText("Item - . . ."); else if (stplyr->pflags & PF_WANTSTOJOIN) itemtxt = M_GetText("Item - Cancel Join"); - else if (G_GametypeHasTeams()) - itemtxt = M_GetText("Item - Join Team"); if (cv_ingamecap.value) { @@ -961,18 +952,14 @@ void ST_Drawer(void) V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT/2 + 15, V_HUDTRANSHALF, player_names[seenplayer-players]); else if (cv_seenames.value == 2) V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT/2 + 15, V_HUDTRANSHALF, - va("%s%s", G_GametypeHasTeams() ? ((seenplayer->ctfteam == 1) ? "\x85" : "\x84") : "", player_names[seenplayer-players])); + va("%s%s", "", player_names[seenplayer-players])); else //if (cv_seenames.value == 3) V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT/2 + 15, V_HUDTRANSHALF, - va("%s%s", !G_BattleGametype() || (G_GametypeHasTeams() && players[consoleplayer].ctfteam == seenplayer->ctfteam) + va("%s%s", !G_BattleGametype() ? "\x83" : "\x85", player_names[seenplayer-players])); } #endif - // Doom's status bar only updated if necessary. - // However, ours updates every frame regardless, so the "refresh" param was removed - //(void)refresh; - // force a set of the palette by using doPaletteStuff() if (vid.recalc) st_palette = -1; diff --git a/src/y_inter.c b/src/y_inter.c index 12fc705ad..e3abb111b 100644 --- a/src/y_inter.c +++ b/src/y_inter.c @@ -57,26 +57,6 @@ typedef struct typedef union { - /*struct - { - char passed1[21]; // KNUCKLES GOT / CRAWLA HONCHO - char passed2[16]; // THROUGH THE ACT / PASSED THE ACT - INT32 passedx1; - INT32 passedx2; - - y_bonus_t bonuses[4]; - patch_t *bonuspatches[4]; - - SINT8 gotperfbonus; // Used for visitation flags. - - UINT32 score, total; // fake score, total - UINT32 tics; // time - - patch_t *ttlnum; // act number being displayed - patch_t *ptotal; // TOTAL - UINT8 gotlife; // Number of extra lives obtained - } coop;*/ - struct { UINT8 *color[MAXPLAYERS]; // Winner's color # @@ -631,7 +611,7 @@ void Y_Ticker(void) { INT32 axis = JoyAxis(AXISLOOKBACK, 1); - if (demo.savemode == DSM_NOTSAVING && (InputDown(gc_lookback, 1) || (cv_usejoystick.value && axis > 0))) + if (demo.savemode == DSM_NOTSAVING && (InputDown(gc_lookback, 1) || (cv_usejoystick[0].value && axis > 0))) demo.savemode = DSM_TITLEENTRY; if (demo.savemode == DSM_WILLSAVE || demo.savemode == DSM_WILLAUTOSAVE) @@ -828,9 +808,7 @@ void Y_StartIntermission(void) } else { - if (cv_inttime.value == 0 && gametype == GT_COOP) - timer = 0; - else if (demo.playback) // Override inttime (which is pulled from the replay anyway + if (demo.playback) // Override inttime (which is pulled from the replay anyway timer = 10*TICRATE; else { -- 2.54.0 From 6afcb06e088ec9d899267054af4a807214885efe Mon Sep 17 00:00:00 2001 From: Alug Date: Mon, 2 Dec 2024 20:56:21 +0100 Subject: [PATCH 099/143] forgor - refactored musicdef handling - other things --- src/hardware/hw_batching.c | 1 - src/hardware/hw_draw.c | 8 +- src/k_kart.c | 2 +- src/p_setup.c | 5 - src/p_user.c | 3 +- src/s_sound.c | 458 +++++++++++++------------------------ src/s_sound.h | 1 + 7 files changed, 164 insertions(+), 314 deletions(-) diff --git a/src/hardware/hw_batching.c b/src/hardware/hw_batching.c index 138c35a5d..e32a7162a 100644 --- a/src/hardware/hw_batching.c +++ b/src/hardware/hw_batching.c @@ -17,7 +17,6 @@ #include "../qs22j.h" - // The texture for the next polygon given to HWR_ProcessPolygon. // Set with HWR_SetCurrentTexture. GLMipmap_t *current_texture = NULL; diff --git a/src/hardware/hw_draw.c b/src/hardware/hw_draw.c index efb4eeaa3..768e523e0 100644 --- a/src/hardware/hw_draw.c +++ b/src/hardware/hw_draw.c @@ -588,9 +588,9 @@ void HWR_FadeScreenMenuBack(UINT16 color, UINT8 strength) Surf.PolyColor.s.alpha = (strength*8); poly_flags |= PF_Translucent; } - } - else // Do TRANSMAP** fade. - { + } + else // Do TRANSMAP** fade. + { RGBA_t *palette = HWR_GetTexturePalette(); Surf.PolyColor.rgba = palette[color&0xFF].rgba; @@ -600,7 +600,7 @@ void HWR_FadeScreenMenuBack(UINT16 color, UINT8 strength) Surf.PolyColor.s.alpha = (UINT8)(strength*25.5f); poly_flags |= PF_Translucent; - } + } HWD.pfnDrawPolygon(&Surf, v, 4, poly_flags); } diff --git a/src/k_kart.c b/src/k_kart.c index 9ec6f6c7b..e9becb30e 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -8834,7 +8834,7 @@ static void K_drawKartSpeedometer(void) { UINT8 *colormap = R_GetTranslationColormap(TC_DEFAULT, K_GetHudColor(), GTC_CACHE); V_DrawStretchyFixedPatch((SPDM_X-1)<pflags & PF_TAGIT))) + if (cv_seenames.value && cv_allowseenames.value) { mobj_t *mo = P_SpawnNameFinder(player->mo, MT_NAMECHECK); diff --git a/src/s_sound.c b/src/s_sound.c index 1bbe154e3..065d56082 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -1258,175 +1258,191 @@ static UINT32 queue_fadeinms; musicdef_t *musicdefstart = NULL; // First music definition struct cursongcredit cursongcredit; // Currently displayed song credit info -// -// search for music definition in wad -// -static UINT16 W_CheckForMusicDefInPwad(UINT16 wadid) +static boolean +ReadMusicDefFields (UINT16 wadnum, int line, char *stoken, musicdef_t **defp) { - UINT16 i; - lumpinfo_t *lump_p; + musicdef_t *def; - lump_p = wadfiles[wadid]->lumpinfo; - for (i = 0; i < wadfiles[wadid]->numlumps; i++, lump_p++) - if (memcmp(lump_p->name, "MUSICDEF", 8) == 0) - return i; - - return INT16_MAX; // not found -} - -void S_LoadMusicDefs(UINT16 wadnum) -{ - UINT16 lump; - char *buf; - char *buf2; - char *stoken; char *value; - size_t size; - musicdef_t *def, *prev; - UINT16 line = 1; // for better error msgs + char *textline; - lump = W_CheckForMusicDefInPwad(wadnum); - if (lump == INT16_MAX) - return; - - buf = W_CacheLumpNumPwad(wadnum, lump, PU_CACHE); - size = W_LumpLengthPwad(wadnum, lump); - - // for strtok - buf2 = malloc(size+1); - if (!buf2) - I_Error("S_LoadMusicDefs: No more free memory\n"); - M_Memcpy(buf2,buf,size); - buf2[size] = '\0'; - - def = prev = NULL; - - stoken = strtok (buf2, "\r\n "); - // Find music def - while (stoken) + if (!stricmp(stoken, "lump")) { - if (!stricmp(stoken, "lump")) + value = strtok(NULL, " "); + if (!value) { - value = strtok(NULL, "\r\n "); - - if (!value) - { - CONS_Alert(CONS_WARNING, "MUSICDEF: Lump '%s' is missing name. (file %s, line %d)\n", stoken, wadfiles[wadnum]->filename, line); - stoken = strtok(NULL, "\r\n"); // skip end of line - goto skip_lump; - } - - // No existing musicdefs - if (!musicdefstart) - { - musicdefstart = Z_Calloc(sizeof (musicdef_t), PU_STATIC, NULL); - STRBUFCPY(musicdefstart->name, value); - strlwr(musicdefstart->name); - def = musicdefstart; - //CONS_Printf("S_LoadMusicDefs: Initialized musicdef w/ song '%s'\n", def->name); - } - else - { - def = musicdefstart; - - // Search if this is a replacement - //CONS_Printf("S_LoadMusicDefs: Searching for song replacement...\n"); - while (def) - { - if (!stricmp(def->name, value)) - { - //CONS_Printf("S_LoadMusicDefs: Found song replacement '%s'\n", def->name); - break; - } - - prev = def; - def = def->next; - } - - // Nothing found, add to the end. - if (!def) - { - def = Z_Calloc(sizeof (musicdef_t), PU_STATIC, NULL); - STRBUFCPY(def->name, value); - strlwr(def->name); - if (prev != NULL) - prev->next = def; - //CONS_Printf("S_LoadMusicDefs: Added song '%s'\n", def->name); - } - } - - strncpy(def->filename, wadfiles[wadnum]->filename, 256); - def->filename[256] = '\0'; - -skip_lump: - stoken = strtok(NULL, "\r\n "); - line++; + CONS_Alert(CONS_WARNING, + "MUSICDEF: Field '%s' is missing name. (file %s, line %d)\n", + stoken, wadfiles[wadnum]->filename, line); + return false; } else { - value = strtok(NULL, "\r\n= "); + def = S_FindMusicCredit(value); - if (!value) + // Nothing found, add to the end. + if (!def) { - CONS_Alert(CONS_WARNING, "MUSICDEF: Field '%s' is missing value. (file %s, line %d)\n", stoken, wadfiles[wadnum]->filename, line); - stoken = strtok(NULL, "\r\n"); // skip end of line - goto skip_field; + def = Z_Calloc(sizeof (musicdef_t), PU_STATIC, NULL); + + STRBUFCPY(def->name, value); + strlwr(def->name); + def->hash = quickncasehash (def->name, 6); + + def->next = musicdefstart; + musicdefstart = def; } + (*defp) = def; + } + } + else + { + value = strtok(NULL, ""); + + if (value) + { + // Find the equals sign. + value = strchr(value, '='); + } + + if (!value) + { + CONS_Alert(CONS_WARNING, + "MUSICDEF: Field '%s' is missing value. (file %s, line %d)\n", + stoken, wadfiles[wadnum]->filename, line); + return false; + } + else + { + def = (*defp); + if (!def) { - CONS_Alert(CONS_ERROR, "MUSICDEF: No music definition before field '%s'. (file %s, line %d)\n", stoken, wadfiles[wadnum]->filename, line); - free(buf2); - return; + CONS_Alert(CONS_ERROR, + "MUSICDEF: No music definition before field '%s'. (file %s, line %d)\n", + stoken, wadfiles[wadnum]->filename, line); + return false; } - + + // Skip the equals sign. + value++; + + // Now skip funny whitespace. + value += strspn(value, "\t "); + + textline = value; + +// turn _ into spaces. +#define ADDDEF(field)\ + STRBUFCPY(def->field, textline);\ + for (textline = def->field; *textline; textline++)\ + if (*textline == '_') *textline = ' '; + if (!stricmp(stoken, "usage")) { - STRBUFCPY(def->usage, value); - for (value = def->usage; *value; value++) - if (*value == '_') *value = ' '; // turn _ into spaces. - //CONS_Printf("S_LoadMusicDefs: Set usage to '%s'\n", def->usage); + ADDDEF(usage); } else if (!stricmp(stoken, "source")) { - STRBUFCPY(def->source, value); - for (value = def->source; *value; value++) - if (*value == '_') *value = ' '; // turn _ into spaces. - //CONS_Printf("S_LoadMusicDefs: Set source to '%s'\n", def->source); + ADDDEF(source); } else if (!stricmp(stoken, "title")) { def->use_info = true; - STRBUFCPY(def->title, value); - for (value = def->title; *value; value++) - if (*value == '_') *value = ' '; // turn _ into spaces. - //CONS_Printf("S_LoadMusicDefs: Set source to '%s'\n", def->source); + ADDDEF(title); } else if (!stricmp(stoken, "alttitle")) { - STRBUFCPY(def->alttitle, value); - for (value = def->alttitle; *value; value++) - if (*value == '_') *value = ' '; // turn _ into spaces. - //CONS_Printf("S_LoadMusicDefs: Set source to '%s'\n", def->source); + ADDDEF(alttitle); } else if (!stricmp(stoken, "authors")) { - STRBUFCPY(def->authors, value); - for (value = def->authors; *value; value++) - if (*value == '_') *value = ' '; // turn _ into spaces. - //CONS_Printf("S_LoadMusicDefs: Set source to '%s'\n", def->source); + ADDDEF(authors); } else CONS_Alert(CONS_WARNING, "MUSICDEF: Invalid field '%s'. (file %s, line %d)\n", stoken, wadfiles[wadnum]->filename, line); - -skip_field: - stoken = strtok(NULL, "\r\n= "); - line++; +#undef ADDDEF } } - free(buf2); - return; + return true; +} + +void S_LoadMusicDefs(UINT16 wadnum) +{ + UINT16 lumpnum; + char *lump; + char *musdeftext; + size_t size; + + char *lf; + char *stoken; + + size_t nlf; + size_t ncr; + + musicdef_t *def = NULL; + int line = 1; // for better error msgs + + for (int k = 0; k < 2; k++) + { + lumpnum = W_CheckNumForNamePwad((k == 1 ? "MUSCINFO" : "MUSICDEF") , wadnum, 0); //check for MUSCINFO lump on 2nd iteration + + if (lumpnum == INT16_MAX) + continue; + + lump = W_CacheLumpNumPwad(wadnum, lumpnum, PU_CACHE); + size = W_LumpLengthPwad(wadnum, lumpnum); + + // Null-terminated MUSICDEF lump. + musdeftext = malloc(size+1); + if (!musdeftext) + I_Error("S_LoadMusicDefs: No more free memory for the parser\n"); + M_Memcpy(musdeftext, lump, size); + musdeftext[size] = '\0'; + + // Find music def + stoken = musdeftext; + for (;;) + { + lf = strpbrk(stoken, "\r\n"); + if (lf) + { + if (*lf == '\n') + nlf = 1; + else + nlf = 0; + *lf++ = '\0';/* now we can delimit to here */ + } + + stoken = strtok(stoken, " "); + if (stoken) + { + if (! ReadMusicDefFields(wadnum, line, stoken, &def)) + break; + } + + if (lf) + { + do + { + line += nlf; + ncr = strspn(lf, "\r");/* skip CR */ + lf += ncr; + nlf = strspn(lf, "\n"); + lf += nlf; + } + while (nlf || ncr) ; + + stoken = lf;/* now the next nonempty line */ + } + else + break;/* EOF */ + } + + free(musdeftext); + } } // @@ -1441,164 +1457,6 @@ void S_InitMusicDefs(void) S_LoadMusicDefs(i); } -// -// search for music definition in wad -// -static UINT16 W_CheckForMusicInfoInPwad(UINT16 wadid) -{ - UINT16 i; - lumpinfo_t *lump_p; - - lump_p = wadfiles[wadid]->lumpinfo; - for (i = 0; i < wadfiles[wadid]->numlumps; i++, lump_p++) - if (memcmp(lump_p->name, "MUSCINFO", 8) == 0) - return i; - - return INT16_MAX; // not found -} - -void S_LoadMTDefs(UINT16 wadnum) -{ - UINT16 lump; - char *buf; - char *buf2; - char *stoken; - char *value; - size_t size; - musicdef_t *def, *prev; - UINT16 line = 1; // for better error msgs - - lump = W_CheckForMusicInfoInPwad(wadnum); - if (lump == INT16_MAX) - return; - - buf = W_CacheLumpNumPwad(wadnum, lump, PU_CACHE); - size = W_LumpLengthPwad(wadnum, lump); - - // for strtok - buf2 = malloc(size+1); - if (!buf2) - I_Error("S_LoadMTDefs: No more free memory\n"); - M_Memcpy(buf2,buf,size); - buf2[size] = '\0'; - - def = prev = NULL; - - stoken = strtok (buf2, "\r\n "); - // Find music def - while (stoken) - { - if (!stricmp(stoken, "lump")) - { - value = strtok(NULL, "\r\n "); - - if (!value) - { - CONS_Alert(CONS_WARNING, "MUSICDEF: Lump '%s' is missing name. (file %s, line %d)\n", stoken, wadfiles[wadnum]->filename, line); - stoken = strtok(NULL, "\r\n"); // skip end of line - goto skip_lump; - } - - // No existing musicdefs - if (!musicdefstart) - { - musicdefstart = Z_Calloc(sizeof (musicdef_t), PU_STATIC, NULL); - STRBUFCPY(musicdefstart->name, value); - strlwr(musicdefstart->name); - def = musicdefstart; - //CONS_Printf("S_LoadMusicDefs: Initialized musicdef w/ song '%s'\n", def->name); - } - else - { - def = musicdefstart; - - // Search if this is a replacement - //CONS_Printf("S_LoadMusicDefs: Searching for song replacement...\n"); - while (def) - { - if (!stricmp(def->name, value)) - { - //CONS_Printf("S_LoadMusicDefs: Found song replacement '%s'\n", def->name); - break; - } - - prev = def; - def = def->next; - } - - // Nothing found, abort. - if (!def) - { - CONS_Alert(CONS_WARNING, "MUSCINFO: Music def for '%s' does not exist. (file %s, line %d)\n", stoken, wadfiles[wadnum]->filename, line); - free(buf2); - return; - } - } - -skip_lump: - stoken = strtok(NULL, "\r\n "); - line++; - } - else - { - value = strtok(NULL, "\r\n= "); - - if (!value) - { - CONS_Alert(CONS_WARNING, "MUSCINFO: Field '%s' is missing value. (file %s, line %d)\n", stoken, wadfiles[wadnum]->filename, line); - stoken = strtok(NULL, "\r\n"); // skip end of line - goto skip_field; - } - - if (!def) - { - CONS_Alert(CONS_ERROR, "MUSCINFO: No music definition before field '%s'. (file %s, line %d)\n", stoken, wadfiles[wadnum]->filename, line); - free(buf2); - return; - } - - if (!stricmp(stoken, "title")) - { - def->use_info = true; - STRBUFCPY(def->title, value); - for (value = def->title; *value; value++) - if (*value == '_') *value = ' '; // turn _ into spaces. - //CONS_Printf("S_LoadMusicDefs: Set source to '%s'\n", def->source); - } - else if (!stricmp(stoken, "alttitle")) - { - STRBUFCPY(def->alttitle, value); - for (value = def->alttitle; *value; value++) - if (*value == '_') *value = ' '; // turn _ into spaces. - //CONS_Printf("S_LoadMusicDefs: Set source to '%s'\n", def->source); - } - else if (!stricmp(stoken, "authors")) - { - STRBUFCPY(def->authors, value); - for (value = def->authors; *value; value++) - if (*value == '_') *value = ' '; // turn _ into spaces. - //CONS_Printf("S_LoadMusicDefs: Set source to '%s'\n", def->source); - } - else - CONS_Alert(CONS_WARNING, "MUSCINFO: Invalid field '%s'. (file %s, line %d)\n", stoken, wadfiles[wadnum]->filename, line); - -skip_field: - stoken = strtok(NULL, "\r\n= "); - line++; - } - } - - free(buf2); - return; -} - -void S_InitMTDefs(void) -{ - UINT16 i; - for (i = 0; i < numwadfiles; i++) - S_LoadMTDefs(i); -} - // // S_FindMusicCredit // @@ -1606,19 +1464,17 @@ void S_InitMTDefs(void) // musicdef_t *S_FindMusicCredit(const char *musname) { - musicdef_t *def = musicdefstart; + UINT32 hash = quickncasehash (musname, 6); + musicdef_t *def; - if (!def) // No definitions - return NULL; - - while (def) + for (def = musicdefstart; def; def = def->next) { - if (!stricmp(def->name, musname)) - { - return def; - } - else - def = def->next; + if (hash != def->hash) + continue; + if (stricmp(def->name, musname)) + continue; + + return def; } return NULL; diff --git a/src/s_sound.h b/src/s_sound.h index 887cdd878..6008cf0b4 100644 --- a/src/s_sound.h +++ b/src/s_sound.h @@ -168,6 +168,7 @@ boolean S_SpeedMusic(float speed); typedef struct musicdef_s { char name[7]; + UINT32 hash; char usage[256]; char source[256]; char filename[256+1]; -- 2.54.0 From c1765258b2d92409801ed6ecf79dbe5a764cb578 Mon Sep 17 00:00:00 2001 From: Alug Date: Mon, 2 Dec 2024 20:57:08 +0100 Subject: [PATCH 100/143] quickncasehash --- src/doomdef.h | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/src/doomdef.h b/src/doomdef.h index c426e64e1..c8d2a28f7 100644 --- a/src/doomdef.h +++ b/src/doomdef.h @@ -522,6 +522,22 @@ extern boolean capslock; // i_system.c, replace getchar() once the keyboard has been appropriated INT32 I_GetKey(void); +/* http://www.cse.yorku.ca/~oz/hash.html */ +static inline +UINT32 quickncasehash (const char *p, size_t n) +{ + size_t i = 0; + UINT32 x = 5381; + + while (i < n && p[i]) + { + x = (x * 33) ^ tolower(p[i]); + i++; + } + + return x; +} + #ifndef min // Double-Check with WATTCP-32's cdefs.h #define min(x, y) (((x) < (y)) ? (x) : (y)) #endif -- 2.54.0 From 521bb88cda4356d34633ff4ddfbe1074a40ec534 Mon Sep 17 00:00:00 2001 From: Alug Date: Mon, 2 Dec 2024 20:58:01 +0100 Subject: [PATCH 101/143] gah --- src/d_main.c | 1 - 1 file changed, 1 deletion(-) diff --git a/src/d_main.c b/src/d_main.c index a19f581eb..803d24bea 100644 --- a/src/d_main.c +++ b/src/d_main.c @@ -1839,7 +1839,6 @@ void D_SRB2Main(void) } S_InitMusicDefs(); - S_InitMTDefs(); CONS_Printf("ST_Init(): Init status bar.\n"); ST_Init(); -- 2.54.0 From 9401eb15910cce36f6a664db467c8b0051eee5bf Mon Sep 17 00:00:00 2001 From: Alug Date: Mon, 2 Dec 2024 21:09:58 +0100 Subject: [PATCH 102/143] oops revert this just in case --- src/p_floor.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/p_floor.c b/src/p_floor.c index 738524b02..17e32c089 100644 --- a/src/p_floor.c +++ b/src/p_floor.c @@ -2927,7 +2927,8 @@ void EV_CrumbleChain(sector_t *sec, ffloor_t *rover) if (special >= 8) type = MT_ROCKCRUMBLE1+(special-7); - sec->soundorg.z = (rover->master->frontsector->floorheight + rover->master->frontsector->ceilingheight)/2; + // soundorg z height never gets set normally, so MEH. + sec->soundorg.z = sec->floorheight; S_StartSound(&sec->soundorg, sfx_crumbl); // Find the outermost vertexes in the subsector -- 2.54.0 From 208f96535ea2196857ea032904e7b18922ed7bfa Mon Sep 17 00:00:00 2001 From: Indev Date: Tue, 3 Dec 2024 22:06:35 +0300 Subject: [PATCH 103/143] Add MENUCAPS to some menu options --- src/m_menu.c | 62 ++++++++++++++++++++++++++-------------------------- 1 file changed, 31 insertions(+), 31 deletions(-) diff --git a/src/m_menu.c b/src/m_menu.c index 41285f2a9..5f96723a2 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -4986,7 +4986,7 @@ static void M_CentreText(INT32 y, const char *string) INT32 x; //added : 02-02-98 : centre on 320, because V_DrawString centers on vid.width... x = (BASEVIDWIDTH - V_StringWidth(string, V_OLDSPACING))>>1; - V_DrawString(x,y,V_OLDSPACING,string); + V_DrawString(x,y,V_OLDSPACING|MENUCAPS,string); } // @@ -5931,12 +5931,12 @@ static void M_DrawImageDef(void) { INT32 x = BASEVIDWIDTH>>1, y = (BASEVIDHEIGHT>>1) - 4; x += (itemOn ? 1 : -1)*((BASEVIDWIDTH>>2) + 10); - V_DrawCenteredString(x, y-10, highlightflags, "USE ARROW KEYS"); + V_DrawCenteredString(x, y-10, highlightflags|MENUCAPS, "Use arrow keys"); V_DrawCharacter(x - 10 - (skullAnimCounter/5), y, '\x1C' | highlightflags, false); // left arrow V_DrawCharacter(x + 2 + (skullAnimCounter/5), y, '\x1D' | highlightflags, false); // right arrow - V_DrawCenteredString(x, y+10, highlightflags, "TO LEAF THROUGH"); + V_DrawCenteredString(x, y+10, highlightflags|MENUCAPS, "to leaf through"); } } @@ -8110,7 +8110,7 @@ static void M_DrawChecklist(void) ++line; secretname = M_CreateSecretMenuOption(unlockables[i].name); - V_DrawString(8, (line*8), V_RETURN8|(unlockables[i].unlocked ? recommendedflags : warningflags), (secret ? secretname : unlockables[i].name)); + V_DrawString(8, (line*8), V_RETURN8|MENUCAPS|(unlockables[i].unlocked ? recommendedflags : warningflags), (secret ? secretname : unlockables[i].name)); if (conditionSets[unlockables[i].conditionset - 1].numconditions) { @@ -8668,8 +8668,8 @@ static void M_DrawStatsMaps(int location) } else if (dotopname) { - V_DrawString(20, y, highlightflags, "LEVEL NAME"); - V_DrawString(256, y, highlightflags, "MEDALS"); + V_DrawString(20, y, highlightflags|MENUCAPS, "Level name"); + V_DrawString(256, y, highlightflags|MENUCAPS, "Medals"); y += 8; dotopname = false; } @@ -8678,11 +8678,11 @@ static void M_DrawStatsMaps(int location) M_DrawMapEmblems(mnum+1, 295, y); if (mapheaderinfo[mnum]->levelflags & LF_NOZONE) - V_DrawString(20, y, 0, va("%s %s", + V_DrawString(20, y, MENUCAPS, va("%s %s", mapheaderinfo[mnum]->lvlttl, mapheaderinfo[mnum]->actnum)); else - V_DrawString(20, y, 0, va("%s %s %s", + V_DrawString(20, y, MENUCAPS, va("%s %s %s", mapheaderinfo[mnum]->lvlttl, (mapheaderinfo[mnum]->zonttl[0] ? mapheaderinfo[mnum]->zonttl : "Zone"), mapheaderinfo[mnum]->actnum)); @@ -8694,8 +8694,8 @@ static void M_DrawStatsMaps(int location) } if (dotopname && !location) { - V_DrawString(20, y, highlightflags, "LEVEL NAME"); - V_DrawString(256, y, highlightflags, "MEDALS"); + V_DrawString(20, y, highlightflags|MENUCAPS, "Level name"); + V_DrawString(256, y, highlightflags|MENUCAPS, "Medals"); y += 8; } else if (location) @@ -8706,7 +8706,7 @@ static void M_DrawStatsMaps(int location) { if (i == -1) { - V_DrawString(20, y, highlightflags, "EXTRA MEDALS"); + V_DrawString(20, y, highlightflags|MENUCAPS, "Extra medals"); if (location) { y += 8; @@ -8729,7 +8729,7 @@ static void M_DrawStatsMaps(int location) else V_DrawSmallScaledPatch(295, y, 0, W_CachePatchName("NEEDIT", PU_CACHE)); - V_DrawString(20, y, 0, va("%s", exemblem->description)); + V_DrawString(20, y, MENUCAPS, va("%s", exemblem->description)); } y += 8; @@ -8754,13 +8754,13 @@ static void M_DrawLevelStats(void) M_DrawMenuTitle(); - V_DrawString(20, 24, highlightflags, "Total Play Time:"); - V_DrawCenteredString(BASEVIDWIDTH/2, 32, 0, va("%i hours, %i minutes, %i seconds", + V_DrawString(20, 24, highlightflags|MENUCAPS, "Total Play Time:"); + V_DrawCenteredString(BASEVIDWIDTH/2, 32, MENUCAPS, va("%i hours, %i minutes, %i seconds", G_TicsToHours(totalplaytime), G_TicsToMinutes(totalplaytime, false), G_TicsToSeconds(totalplaytime))); - V_DrawString(20, 42, highlightflags, "Total Matches:"); - V_DrawRightAlignedString(BASEVIDWIDTH-16, 42, 0, va("%i played", matchesplayed)); + V_DrawString(20, 42, highlightflags|MENUCAPS, "Total Matches:"); + V_DrawRightAlignedString(BASEVIDWIDTH-16, 42, MENUCAPS, va("%i played", matchesplayed)); for (i = 0; i < NUMMAPS; i++) { @@ -8776,17 +8776,17 @@ static void M_DrawLevelStats(void) besttime += mainrecords[i]->time; } - V_DrawString(20, 62, highlightflags, "Combined time records:"); + V_DrawString(20, 62, highlightflags|MENUCAPS, "Combined time records:"); sprintf(beststr, "%i:%02i:%02i.%02i", G_TicsToHours(besttime), G_TicsToMinutes(besttime, false), G_TicsToSeconds(besttime), G_TicsToCentiseconds(besttime)); V_DrawRightAlignedString(BASEVIDWIDTH-16, 62, (mapsunfinished ? warningflags : 0), beststr); if (mapsunfinished) - V_DrawRightAlignedString(BASEVIDWIDTH-16, 70, warningflags, va("(%d unfinished)", mapsunfinished)); + V_DrawRightAlignedString(BASEVIDWIDTH-16, 70, warningflags|MENUCAPS, va("(%d unfinished)", mapsunfinished)); else - V_DrawRightAlignedString(BASEVIDWIDTH-16, 70, recommendedflags, "(complete)"); + V_DrawRightAlignedString(BASEVIDWIDTH-16, 70, recommendedflags|MENUCAPS, "(complete)"); - V_DrawString(32, 70, 0, va("x %d/%d", M_CountEmblems(), numemblems+numextraemblems)); + V_DrawString(32, 70, MENUCAPS, va("x %d/%d", M_CountEmblems(), numemblems+numextraemblems)); V_DrawSmallScaledPatch(20, 70, 0, W_CachePatchName("GOTITA", PU_STATIC)); M_DrawStatsMaps(statsLocation); @@ -12714,17 +12714,17 @@ static void M_DrawVideoMode(void) M_DrawMenuTitle(); V_DrawCenteredString(BASEVIDWIDTH/2, OP_VideoModeDef.y, - highlightflags, "Choose mode, reselect to change default"); + highlightflags|MENUCAPS, "Choose mode, reselect to change default"); row = 41; col = OP_VideoModeDef.y + 14; for (i = 0; i < vidm_nummodes; i++) { if (i == vidm_selected) - V_DrawString(row, col, highlightflags, modedescs[i].desc); + V_DrawString(row, col, highlightflags|MENUCAPS, modedescs[i].desc); // Show multiples of 320x200 as green. else - V_DrawString(row, col, (modedescs[i].goodratio) ? recommendedflags : 0, modedescs[i].desc); + V_DrawString(row, col, ((modedescs[i].goodratio) ? recommendedflags : 0)|MENUCAPS, modedescs[i].desc); col += 8; if ((i % vidm_column_size) == (vidm_column_size-1)) @@ -12762,11 +12762,11 @@ static void M_DrawVideoMode(void) cv_scr_width.value, cv_scr_height.value)); V_DrawCenteredString(BASEVIDWIDTH/2, OP_VideoModeDef.y + 138, - recommendedflags, "Marked modes are recommended."); + recommendedflags|MENUCAPS, "Marked modes are recommended."); V_DrawCenteredString(BASEVIDWIDTH/2, OP_VideoModeDef.y + 146, - highlightflags, "Other modes may have visual errors."); + highlightflags|MENUCAPS, "Other modes may have visual errors."); V_DrawCenteredString(BASEVIDWIDTH/2, OP_VideoModeDef.y + 158, - highlightflags, "Larger modes may have performance issues."); + highlightflags|MENUCAPS, "Larger modes may have performance issues."); } // Draw the cursor for the VidMode menu @@ -12834,9 +12834,9 @@ static void M_DrawColorMenu(void) case IT_STRING: case IT_WHITESTRING: if (i != itemOn && (currentMenu->menuitems[i].status & IT_DISPLAY)==IT_STRING) - V_DrawString(x, y, 0, currentMenu->menuitems[i].text); + V_DrawString(x, y, MENUCAPS, currentMenu->menuitems[i].text); else - V_DrawString(x, y, V_YELLOWMAP, currentMenu->menuitems[i].text); + V_DrawString(x, y, V_YELLOWMAP|MENUCAPS, currentMenu->menuitems[i].text); // Cvar specific handling switch (currentMenu->menuitems[i].status & IT_TYPE) @@ -12871,13 +12871,13 @@ static void M_DrawColorMenu(void) } break; case IT_TRANSTEXT: - V_DrawString(x, y, V_TRANSLUCENT, currentMenu->menuitems[i].text); + V_DrawString(x, y, V_TRANSLUCENT|MENUCAPS, currentMenu->menuitems[i].text); break; case IT_QUESTIONMARKS: - V_DrawString(x, y, V_TRANSLUCENT|V_OLDSPACING, M_CreateSecretMenuOption(currentMenu->menuitems[i].text)); + V_DrawString(x, y, V_TRANSLUCENT|V_OLDSPACING|MENUCAPS, M_CreateSecretMenuOption(currentMenu->menuitems[i].text)); break; case IT_HEADERTEXT: - V_DrawString(x-16, y, V_YELLOWMAP, currentMenu->menuitems[i].text); + V_DrawString(x-16, y, V_YELLOWMAP|MENUCAPS, currentMenu->menuitems[i].text); //V_DrawFill(19, y, 281, 9, currentMenu->menuitems[i+1].alphaKey); //V_DrawFill(300, y, 1, 9, 26); //M_DrawLevelPlatterHeader(y - (lsheadingheight - 12), currentMenu->menuitems[i].text, false); -- 2.54.0 From 55acbb208eca1739534c47196f56e195cd5416fe Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 3 Dec 2024 20:39:46 +0100 Subject: [PATCH 104/143] try to make demo data handling a bit safer - Use Z_Malloc to allocate demobuffer - Use Z_Free to free demobuffer - Make functions for freeing and resseting demobuffer - Always reset demobuffer when not saving --- src/d_netcmd.c | 11 +++-- src/g_game.c | 120 ++++++++++++++++++++++--------------------------- src/g_game.h | 1 + src/p_tick.c | 19 +++++--- src/y_inter.c | 2 + 5 files changed, 76 insertions(+), 77 deletions(-) diff --git a/src/d_netcmd.c b/src/d_netcmd.c index 174bb4d9f..aeb3e5d90 100644 --- a/src/d_netcmd.c +++ b/src/d_netcmd.c @@ -2878,9 +2878,14 @@ static void Command_Map_f(void) } } - // spend atleast 35 seconds in one map - if (cv_demochangemap.value && demo.recording && demo.savemode != DSM_NOTSAVING && (timeinmap > 1463) && ((cv_demochangemap.value == 2 && newmapnum == gamemap) || newmapnum != gamemap)) - G_SaveDemo(); + if (cv_demochangemap.value && demo.recording) + { + // spend atleast 35 seconds in one map + if (demo.savemode != DSM_NOTSAVING && (timeinmap > 1463) && ((cv_demochangemap.value == 2 && newmapnum == gamemap) || newmapnum != gamemap)) + G_SaveDemo(); + else + G_ResetDemoRecording(); + } fromlevelselect = false; D_MapChange(newmapnum, newgametype, newencoremode, newresetplayers, 0, false, false); diff --git a/src/g_game.c b/src/g_game.c index 279cbdb00..3e4edf231 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -82,6 +82,8 @@ static void G_DoContinued(void); static void G_DoWorldDone(void); static void G_DoStartVote(void); +static void G_ResetDemoPlayback(char *pdemoname); + char mapmusname[7]; // Music name UINT16 mapmusflags; // Track and reset bit UINT32 mapmusposition; // Position to jump to @@ -3214,6 +3216,8 @@ void G_AfterIntermission(void) } else if (demo.recording && (modeattacking || demo.savemode != DSM_NOTSAVING)) G_SaveDemo(); + else if (demo.recording) + G_ResetDemoRecording(); if (modeattacking) // End the run. { @@ -3361,6 +3365,8 @@ void G_EndGame(void) { if (demo.recording && (modeattacking || demo.savemode != DSM_NOTSAVING)) G_SaveDemo(); + else if (demo.recording) + G_ResetDemoRecording(); // 1100 or competitive multiplayer, so go back to title screen. D_StartTitle(); @@ -5887,10 +5893,7 @@ void G_RecordDemo(const char *name) INT32 maxsize; demo_p = NULL; - demo.recording = false; - if (demobuffer) - free(demobuffer); - demobuffer = NULL; + G_ResetDemoRecording(); demoend = NULL; if (cv_recordmultiplayerdemos.value) @@ -5902,7 +5905,7 @@ void G_RecordDemo(const char *name) maxsize = cv_maxdemosize.value*1024*1024; - demobuffer = malloc(maxsize); + demobuffer = Z_Malloc(maxsize, PU_STATIC, NULL); demoend = demobuffer + maxsize; if (demobuffer) @@ -5917,10 +5920,10 @@ void G_RecordMetal(void) INT32 maxsize; maxsize = cv_maxdemosize.value*1024*1024; if (demobuffer) - free(demobuffer); + Z_Free(demobuffer); demo_p = NULL; metalrecording = false; - demobuffer = malloc(maxsize); + demobuffer = Z_Malloc(maxsize, PU_STATIC, NULL); demoend = demobuffer + maxsize; if (demobuffer) @@ -6772,11 +6775,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s is not a SRB2Kart replay file.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } demo_p += 12; // DEMOHEADER @@ -6801,11 +6800,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s is an incompatible replay format and cannot be played.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } demo_p += 16; // demo checksum @@ -6814,11 +6809,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s is the wrong type of recording and cannot be played.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } demo_p += 4; // "PLAY" @@ -6834,11 +6825,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s is an alpha multiplayer replay and cannot be played.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } } @@ -6895,11 +6882,7 @@ void G_DoPlayDemo(char *defdemoname) CONS_Alert(CONS_ERROR, "%s", msg); if (!CON_Ready()) // In the console they'll just see the notice there! No point pulling them out. M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } } @@ -6962,11 +6945,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s features a character that is not currently loaded.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } @@ -6976,11 +6955,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s features a course that is not currently loaded.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } @@ -7001,11 +6976,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s contains no data to be played.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } @@ -7045,11 +7016,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s contains no data to be played.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } @@ -7100,11 +7067,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s is a Record Attack replay with spectators, and is thus invalid.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } } @@ -7115,11 +7078,7 @@ void G_DoPlayDemo(char *defdemoname) snprintf(msg, 1024, M_GetText("%s is a Record Attack replay with multiple players, and is thus invalid.\n"), pdemoname); CONS_Alert(CONS_ERROR, "%s", msg); M_StartMessage(msg, NULL, MM_NOTHING); - Z_Free(pdemoname); - Z_Free(demobuffer); - demobuffer = NULL; - demo.playback = false; - demo.title = false; + G_ResetDemoPlayback(pdemoname); return; } @@ -7762,7 +7721,7 @@ ATTRNORETURN void FUNCNORETURN G_StopMetalRecording(void) #endif saved = FIL_WriteFile(va("%sMS.LMP", G_BuildMapName(gamemap)), demobuffer, demo_p - demobuffer); // finally output the file. } - free(demobuffer); + Z_Free(demobuffer); demobuffer = NULL; metalrecording = false; if (saved) @@ -7872,13 +7831,41 @@ boolean G_CheckDemoStatus(void) G_SaveDemo(); return true; } - demo.recording = false; + else if (demo.recording) + G_ResetDemoRecording(); return false; } +void G_ResetDemoRecording(void) +{ + if (demobuffer) + Z_Free(demobuffer); + demobuffer = NULL; + demo.recording = false; +} + +static void G_ResetDemoPlayback(char *pdemoname) +{ + if (pdemoname) + Z_Free(pdemoname); + if (demobuffer) + Z_Free(demobuffer); + demobuffer = NULL; + demo.playback = false; + demo.title = false; +} + void G_SaveDemo(void) { + if (!demo_p) + { + CONS_Alert(CONS_ERROR, "Failed to save Demo. No Demo pointer exists!\n"); + // reset the demo buffer + G_ResetDemoRecording(); + return; + } + UINT8 *p = demobuffer+16; // after version UINT32 length; #ifdef NOMD5 @@ -7948,9 +7935,8 @@ void G_SaveDemo(void) if (FIL_WriteFile(va(pandf, srb2home, demoname), demobuffer, demo_p - demobuffer)) // finally output the file. demo.savemode = DSM_SAVED; - free(demobuffer); - demobuffer = NULL; - demo.recording = false; + + G_ResetDemoRecording(); if (modeattacking != ATTACKING_RECORD) { diff --git a/src/g_game.h b/src/g_game.h index 09d9bc3d5..40154e65b 100644 --- a/src/g_game.h +++ b/src/g_game.h @@ -364,6 +364,7 @@ extern demoghost *ghosts; #define DFILE_ERROR_CANNOTLOAD 0x04 // Files are missing and cannot be loaded. #define DFILE_ERROR_EXTRAFILES 0x05 // Extra files outside of the replay's file list are loaded. +void G_ResetDemoRecording(void); void G_DoPlayDemo(char *defdemoname); void G_TimeDemo(const char *name); void G_AddGhost(char *defdemoname); diff --git a/src/p_tick.c b/src/p_tick.c index d358353bc..9b9d723eb 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -663,14 +663,19 @@ void P_Ticker(boolean run) G_WriteAllGhostTics(); - if (cv_recordmultiplayerdemos.value && (demo.savemode == DSM_NOTSAVING || demo.savemode == DSM_WILLAUTOSAVE)) - if (demo.savebutton && demo.savebutton + 3*TICRATE < leveltime && (InputDown(gc_lookback, 1) || (cv_usejoystick[0].value && axis > 0))) - demo.savemode = DSM_TITLEENTRY; + if (cv_recordmultiplayerdemos.value) + { + if (demo.savemode == DSM_NOTSAVING || demo.savemode == DSM_WILLAUTOSAVE) + if (demo.savebutton && demo.savebutton + 3*TICRATE < leveltime && (InputDown(gc_lookback, 1) || (cv_usejoystick[0].value && axis > 0))) + demo.savemode = DSM_TITLEENTRY; - //if there are no players left at all, stop demo recording - //Demos that that dont have any players crash during playback, which can happen with dedicated servers - if (cv_recordmultiplayerdemos.value && demo.savemode == DSM_WILLAUTOSAVE && !D_NumPlayers()) - G_SaveDemo(); + // if there are no players left at all, stop demo recording + // Demos that that dont have any players crash during playback, which can happen with dedicated servers + if (demo.savemode == DSM_WILLAUTOSAVE && !D_NumPlayers()) + G_SaveDemo(); + else + G_ResetDemoRecording(); + } } else if (demo.playback) // Use Ghost data for consistency checks. { diff --git a/src/y_inter.c b/src/y_inter.c index 68398e4df..55e092eaa 100644 --- a/src/y_inter.c +++ b/src/y_inter.c @@ -616,6 +616,8 @@ void Y_Ticker(void) if (demo.savemode == DSM_WILLSAVE || demo.savemode == DSM_WILLAUTOSAVE) G_SaveDemo(); + else + G_ResetDemoRecording(); } // Check for pause or menu up in single player -- 2.54.0 From f4e498e55922b594c346a73e2d621e1a0f8dce99 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 3 Dec 2024 19:55:51 +0100 Subject: [PATCH 105/143] this may be used unitialised lul --- src/m_menu.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/m_menu.c b/src/m_menu.c index 5f96723a2..7523c1014 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -7312,7 +7312,7 @@ static void M_DrawReplayHut(void) static void M_DrawReplayStartMenu(void) { - const char *warning; + const char *warning = ""; UINT8 i; M_DrawGenericBackgroundMenu(); @@ -7415,7 +7415,8 @@ static void M_DrawReplayStartMenu(void) return; } - V_DrawSmallString(4, BASEVIDHEIGHT-14, V_SNAPTOBOTTOM|V_SNAPTOLEFT|V_ALLOWLOWERCASE, warning); + if (warning) + V_DrawSmallString(4, BASEVIDHEIGHT-14, V_SNAPTOBOTTOM|V_SNAPTOLEFT|V_ALLOWLOWERCASE, warning); } static boolean M_QuitReplayHut(void) -- 2.54.0 From 00bdd684ed7a35fbefd30dd25fb030c2481ccfd7 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 3 Dec 2024 20:52:02 +0100 Subject: [PATCH 106/143] 1463 lmao change this to be readable also raise to 40 secs --- src/d_netcmd.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/d_netcmd.c b/src/d_netcmd.c index aeb3e5d90..c2ad1be2e 100644 --- a/src/d_netcmd.c +++ b/src/d_netcmd.c @@ -2880,8 +2880,8 @@ static void Command_Map_f(void) if (cv_demochangemap.value && demo.recording) { - // spend atleast 35 seconds in one map - if (demo.savemode != DSM_NOTSAVING && (timeinmap > 1463) && ((cv_demochangemap.value == 2 && newmapnum == gamemap) || newmapnum != gamemap)) + // spend atleast 40 seconds in one map + if (demo.savemode != DSM_NOTSAVING && (timeinmap > (TICRATE * 40)) && ((cv_demochangemap.value == 2 && newmapnum == gamemap) || newmapnum != gamemap)) G_SaveDemo(); else G_ResetDemoRecording(); -- 2.54.0 From 68090a55e12d5ecbbd31aebc12388c43649f3206 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 3 Dec 2024 21:50:45 +0100 Subject: [PATCH 107/143] change this a little --- src/g_game.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/g_game.c b/src/g_game.c index 3e4edf231..8f2546bf1 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -7826,13 +7826,16 @@ boolean G_CheckDemoStatus(void) return true; } - if (demo.recording && (modeattacking || demo.savemode != DSM_NOTSAVING)) + if (!demo.recording) + return false; + + if (modeattacking || demo.savemode != DSM_NOTSAVING) { G_SaveDemo(); return true; } - else if (demo.recording) - G_ResetDemoRecording(); + + G_ResetDemoRecording(); return false; } -- 2.54.0 From e4343f09352a226c75288cb7fa3f67524be5f398 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 4 Dec 2024 01:39:04 +0100 Subject: [PATCH 108/143] only ever call pointtoangle for sprites that really need it --- src/hardware/hw_main.c | 17 ++++++++++++----- 1 file changed, 12 insertions(+), 5 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 06d4e75a6..062f3f303 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4552,16 +4552,23 @@ static void HWR_ProjectSprite(mobj_t *thing) I_Error("sprframes NULL for sprite %d\n", thing->sprite); #endif - ang = R_PointToAngle(interp.x, interp.y); + if (sprframe->rotate != SRF_SINGLE || papersprite || +#ifdef ROTSPRITE + (shouldrotate) +#endif + ) + { + ang = R_PointToAngle(interp.x, interp.y); #ifdef ROTSPRITE - camang = ang; + camang = ang; #endif - ang -= interp.angle; + ang -= interp.angle; - if (mirrored) - ang = InvAngle(ang); + if (mirrored) + ang = InvAngle(ang); + } if (sprframe->rotate == SRF_SINGLE) { -- 2.54.0 From e2a651e5538a89154700a109e203fef030df71d6 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 4 Dec 2024 14:20:15 +0100 Subject: [PATCH 109/143] make those const --- src/hardware/hw_main.c | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 062f3f303..9dbd52696 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4434,15 +4434,11 @@ static void HWR_ProjectSprite(mobj_t *thing) size_t lumpoff; unsigned rot; UINT8 flip; - boolean vflip; - boolean mirrored; - boolean hflip; angle_t ang = 0; #ifdef ROTSPRITE angle_t camang = 0; #endif - boolean papersprite; INT32 heightsec, phs; INT32 dist = -1; @@ -4461,10 +4457,10 @@ static void HWR_ProjectSprite(mobj_t *thing) // uncapped/interpolation interpmobjstate_t interp = {0}; - vflip = (thing->eflags & MFE_VERTICALFLIP); - mirrored = thing->mirrored; - hflip = (!(thing->frame & FF_HORIZONTALFLIP) != !mirrored); - papersprite = (thing->frame & FF_PAPERSPRITE); + const boolean mirrored = thing->mirrored; + const boolean vflip = (thing->eflags & MFE_VERTICALFLIP); + const boolean hflip = (!(thing->frame & FF_HORIZONTALFLIP) != !mirrored); + const boolean papersprite = (thing->frame & FF_PAPERSPRITE); if (cv_maxinterpdist.value) dist = R_QuickCamDist(thing->x, thing->y); -- 2.54.0 From 55d9d64910c260ffb967c4d2f307b879992846a4 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 4 Dec 2024 14:20:49 +0100 Subject: [PATCH 110/143] clean up this mess --- src/hardware/hw_md2.c | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/src/hardware/hw_md2.c b/src/hardware/hw_md2.c index 774c256b1..ab92f6873 100644 --- a/src/hardware/hw_md2.c +++ b/src/hardware/hw_md2.c @@ -1369,18 +1369,15 @@ void HWR_DrawMD2(gl_vissprite_t *spr) p.spritexscale = FIXED_TO_FLOAT(spr->mobj->spritexscale); p.spriteyscale = FIXED_TO_FLOAT(spr->mobj->spriteyscale); - - angle_t sliptideroll = 0; - if (spr->mobj->player) - sliptideroll = ((cv_sloperoll.value && cv_sliptideroll.value) ? spr->mobj->player->sliproll : 0); + angle_t sliptideroll = ((cv_sloperoll.value && cv_sliptideroll.value && spr->mobj->player) ? spr->mobj->player->sliproll : 0); - if ((spr->mobj->rollangle)||(sliptideroll && cv_sliptideroll.value)) + if (spr->mobj->rollangle || sliptideroll) { angle_t rollang = 0; rollfactor = ((spr->mobj->rollmodel == true) ? 1 : 0); - rollang = (spr->mobj->player && sliptideroll && cv_sliptideroll.value) + rollang = sliptideroll ? (spr->mobj->rollangle * rollfactor) + (sliptideroll * spr->mobj->player->sliptidemem) : (spr->mobj->rollangle * rollfactor); -- 2.54.0 From 6265d0e38ea66862da400e463e36f1a1c8e004c4 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 4 Dec 2024 14:22:14 +0100 Subject: [PATCH 111/143] why does this need a variable? it just gets assigned kartstuff[k_aizdriftstrat] anyways? --- src/d_player.h | 1 - src/hardware/hw_main.c | 2 +- src/hardware/hw_md2.c | 2 +- src/k_kart.c | 4 ---- src/r_main.c | 4 ++-- src/r_things.c | 2 +- 6 files changed, 5 insertions(+), 10 deletions(-) diff --git a/src/d_player.h b/src/d_player.h index 09400fa9b..140a4a748 100644 --- a/src/d_player.h +++ b/src/d_player.h @@ -403,7 +403,6 @@ typedef struct player_s angle_t old_frameangle, old_frameangle2; // SRB2Kart CEP: Sliptide rolling - INT32 sliptidemem; angle_t sliproll; INT16 lturn_max[MAXPREDICTTICS]; // What's the expected turn value for full-left for a number of frames back (to account for netgame latency)? diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 9dbd52696..7115ca376 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4622,7 +4622,7 @@ static void HWR_ProjectSprite(mobj_t *thing) { if (sliprollrotate) { - sliptiderollangle = thing->player->sliproll * (thing->player->sliptidemem); + sliptiderollangle = thing->player->sliproll * thing->player->kartstuff[k_aizdriftstrat]; pitchnroll += rollangle + FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), sliptiderollangle); } else diff --git a/src/hardware/hw_md2.c b/src/hardware/hw_md2.c index ab92f6873..3de86bbda 100644 --- a/src/hardware/hw_md2.c +++ b/src/hardware/hw_md2.c @@ -1378,7 +1378,7 @@ void HWR_DrawMD2(gl_vissprite_t *spr) rollfactor = ((spr->mobj->rollmodel == true) ? 1 : 0); rollang = sliptideroll - ? (spr->mobj->rollangle * rollfactor) + (sliptideroll * spr->mobj->player->sliptidemem) + ? (spr->mobj->rollangle * rollfactor) + (sliptideroll * spr->mobj->player->kartstuff[k_aizdriftstrat]) : (spr->mobj->rollangle * rollfactor); fixed_t anglef = AngleFixed(rollang); diff --git a/src/k_kart.c b/src/k_kart.c index 3414b11e8..fe4ba6e0d 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -5662,7 +5662,6 @@ static void K_KartDrift(player_t *player, boolean onground) } } - // Stop drifting if (player->kartstuff[k_spinouttimer] > 0 || player->speed < minspeed) { @@ -5671,7 +5670,6 @@ static void K_KartDrift(player_t *player, boolean onground) if (!player->sliproll) { - player->sliptidemem = 0; player->sliproll = 0; } @@ -5694,8 +5692,6 @@ static void K_KartDrift(player_t *player, boolean onground) if (player->sliproll < (32*ANG1)) player->sliproll += (4*ANG1); - - player->sliptidemem = player->kartstuff[k_aizdriftstrat]; } if (player->kartstuff[k_drift] diff --git a/src/r_main.c b/src/r_main.c index 28b31de5b..b68bde658 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -398,7 +398,7 @@ angle_t R_PlayerSliptideAngle(player_t *player) mo = player->mo; - if (mo->player->sliproll == 0 && mo->player->sliptidemem == 0) + if (mo->player->sliproll == 0 || mo->player->kartstuff[k_aizdriftstrat] == 0) return 0; size_t rot = (mo->frame & FF_FRAMEMASK); @@ -429,7 +429,7 @@ angle_t R_PlayerSliptideAngle(player_t *player) if (sprframe->rotate != SRF_SINGLE || (mo->frame & FF_PAPERSPRITE)) ang = R_PointToAngle(mo->x, mo->y) - mo->angle; - return FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), mo->player->sliproll * mo->player->sliptidemem); + return FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), mo->player->sliproll * mo->player->kartstuff[k_aizdriftstrat]); } INT32 R_GetHudUncap(void) diff --git a/src/r_things.c b/src/r_things.c index 71096a05c..0c3e13a1b 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -1352,7 +1352,7 @@ static void R_ProjectSprite(mobj_t *thing) { if (sliprollrotate) { - sliptiderollangle = thing->player->sliproll * (thing->player->sliptidemem); + sliptiderollangle = thing->player->sliproll * thing->player->kartstuff[k_aizdriftstrat]; pitchnroll += rollangle + FixedMul(FINECOSINE((ang) >> ANGLETOFINESHIFT), sliptiderollangle); } else -- 2.54.0 From d519f9cf0617f8ab132634f0fa449076f5e579b3 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 5 Dec 2024 07:58:11 +0100 Subject: [PATCH 112/143] try fix keepmusic occasionally not working idk but sometimes DoReborn broke it? also this ensures keepmusic and skipintromus flags always get reset --- src/d_main.c | 3 +++ src/g_game.c | 8 +++++--- src/g_game.h | 1 - src/k_kart.c | 2 +- src/p_user.c | 2 +- src/s_sound.c | 24 ++++++++++++++++++++---- src/s_sound.h | 4 +++- 7 files changed, 33 insertions(+), 11 deletions(-) diff --git a/src/d_main.c b/src/d_main.c index 803d24bea..642870a86 100644 --- a/src/d_main.c +++ b/src/d_main.c @@ -964,6 +964,9 @@ void D_StartTitle(void) //demosequence = -1; gametype = GT_RACE; // SRB2kart paused = false; + + S_ResetKeepAndSpecialMus(); // just in case + F_StartTitleScreen(); // Reset the palette -- SRB2Kart: actually never mind let's do this in the middle of every fade diff --git a/src/g_game.c b/src/g_game.c index 8f2546bf1..7e1c0e04c 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -1215,16 +1215,19 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer) if (cv_director.value) CV_SetValue(&cv_director, 0); } - } // // G_DoLoadLevel // -void G_DoLoadLevel(boolean resetplayer) +static void G_DoLoadLevel(boolean resetplayer) { INT32 i; + // Saturn Music Feature stuffs + S_ResetKeepAndSpecialMus(); + S_CheckMap(); + // Make sure objectplace is OFF when you first start the level! OP_ResetObjectplace(); @@ -3962,7 +3965,6 @@ void G_InitNew(UINT8 pencoremode, const char *mapname, boolean resetplayer, bool else { LUA_HookInt(gamemap, HOOK(MapChange)); - S_CheckMap(); G_DoLoadLevel(resetplayer); } diff --git a/src/g_game.h b/src/g_game.h index 40154e65b..d528ace86 100644 --- a/src/g_game.h +++ b/src/g_game.h @@ -274,7 +274,6 @@ void G_SpawnPlayer(INT32 playernum, boolean starpost); // A normal game starts at map 1, but a warp test can start elsewhere void G_DeferedInitNew(boolean pencoremode, const char *mapname, INT32 pickedchar, UINT8 ssplayers, boolean FLS); -void G_DoLoadLevel(boolean resetplayer); void G_LoadDemoInfo(menudemo_t *pdemo); void G_LoadDemoTitle(menudemo_t *pdemo); // For use in replay search feature diff --git a/src/k_kart.c b/src/k_kart.c index fe4ba6e0d..2a348a85b 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -5334,7 +5334,7 @@ void K_KartPlayerThink(player_t *player, ticcmd_t *cmd) // Plays the music during and after the starting countdown. if (P_IsLocalPlayer(player)) - S_StartMapMusic(false); + S_StartMapMusic(); } void K_KartPlayerAfterThink(player_t *player) diff --git a/src/p_user.c b/src/p_user.c index 6c0e629c7..e9942bdf8 100644 --- a/src/p_user.c +++ b/src/p_user.c @@ -704,7 +704,7 @@ void P_RestoreMusic(player_t *player) return; if (leveltime < MUSICSTARTTIME) - S_StartMapMusic(true); + S_StartMapMusic(); else // see also where time overs are handled - search for "lives = 2" in this file { INT32 wantedmus = 0; // 0 is level music, 1 is invincibility, 2 is grow diff --git a/src/s_sound.c b/src/s_sound.c index 12e79aba2..d4d8477bd 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -2004,6 +2004,11 @@ static const char *musicexception_list[17] = { "CHRSHF", "CHRSHP" // no clue what those are tbh }; +void S_ResetKeepAndSpecialMus(void) +{ + keepmusic = skipintromus = false; +} + //checks for any kind of event music like intermission, vote etc. //always runs when musicchange gets invoked static void S_CheckEventMus(const char *newmus) @@ -2020,9 +2025,9 @@ static void S_CheckEventMus(const char *newmus) break; } - //CONS_Printf("musname = %s\n", music_name); + //CONS_Printf("music_name = %s\n", music_name); //CONS_Printf("newmus = %s\n", newmus); - //CONS_Printf("newmus = %d\n", skipmusic); + //CONS_Printf("skipmusic = %d\n", skipmusic); } //this one compares map and encoremode instead of the music itself @@ -2037,6 +2042,8 @@ void S_CheckMap(void) keepmusic = (!skipmusic && gamestate == GS_LEVEL && oldmap == gamemap && oldencore == encoremode); + //CONS_Printf("keepmusic = %s\n", keepmusic); + oldencore = encoremode; oldmap = gamemap; } @@ -2083,13 +2090,13 @@ void S_InitMapMusic(void) //S_ChangeMusicEx((encoremode ? "estart" : "kstart"), 0, false, mapmusposition, 0, 0); } -void S_StartMapMusic(boolean restore) +void S_StartMapMusic(void) { //no need to constantly run this after race has started if (leveltime > MUSICSTARTTIME) return; - if (keepmusic && !restore) // make sure this doesent kill the music when its called from P_RestoreMusic in some cases + if (keepmusic) return; if (skipintromus) @@ -2124,6 +2131,8 @@ void S_RestartMusic(void) S_SetMusicVolume(cv_digmusicvolume.value, cv_midimusicvolume.value); #endif + S_ResetKeepAndSpecialMus(); + if (Playing()) // Gotta make sure the player is in a level P_RestoreMusic(&players[consoleplayer]); else @@ -2228,6 +2237,8 @@ static void Command_RestartAudio_f(void) S_StartSound(NULL, sfx_strpst); + S_ResetKeepAndSpecialMus(); + if (Playing()) // Gotta make sure the player is in a level P_RestoreMusic(&players[consoleplayer]); else @@ -2305,6 +2316,8 @@ static void GameDigiMusic_OnChange(void) I_StartupSound(); // will return early if initialised I_InitMusic(); + S_ResetKeepAndSpecialMus(); + if (Playing()) P_RestoreMusic(&players[consoleplayer]); else @@ -2390,6 +2403,9 @@ static void GameMIDIMusic_OnChange(void) { midi_disabled = false; I_InitMusic(); + + S_ResetKeepAndSpecialMus(); + if (Playing()) P_RestoreMusic(&players[consoleplayer]); else diff --git a/src/s_sound.h b/src/s_sound.h index 9ee63a2b8..be4ed381d 100644 --- a/src/s_sound.h +++ b/src/s_sound.h @@ -109,8 +109,10 @@ void S_InitSfxChannels(INT32 sfxVolume); void S_StopSounds(void); void S_ClearSfx(void); +void S_ResetKeepAndSpecialMus(void); + void S_InitMapMusic(void); -void S_StartMapMusic(boolean restore); +void S_StartMapMusic(void); void S_CheckMap(void); -- 2.54.0 From 9805b03533df1f0bd73800fae8f52f3143a5cafa Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 5 Dec 2024 08:07:52 +0100 Subject: [PATCH 113/143] reduce the scope of those only this function needs those --- src/s_sound.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/s_sound.c b/src/s_sound.c index d4d8477bd..f44231213 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -1992,8 +1992,6 @@ boolean S_FadeOutStopMusic(UINT32 ms) return false; }*/ -static INT16 oldmap = 0; -static boolean oldencore = false; static boolean skipmusic = false; boolean skipintromus = false; @@ -2034,6 +2032,9 @@ static void S_CheckEventMus(const char *newmus) //makes tunes work and stuff void S_CheckMap(void) { + static INT16 oldmap = 0; + static boolean oldencore = false; + if (!cv_keepmusic.value) { keepmusic = false; -- 2.54.0 From 5a206822c5db9cf31ea0d2dde36fe1e4ddbd62bc Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 5 Dec 2024 08:10:05 +0100 Subject: [PATCH 114/143] little extra safety --- src/s_sound.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/s_sound.c b/src/s_sound.c index f44231213..122b07525 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -2078,7 +2078,7 @@ void S_InitMapMusic(void) { char *maptitle = G_BuildMapTitle(gamemap); // for some reason, occasionally the title screen music doesent seem to be reset in time, so skipping the intro may make it just continue playing it instead, weird.. - skipintromus = (stricmp(music_name, "titles") != 0) && (stricmp(maptitle, "Wandering Falls") != 0); // thanks diggle! + skipintromus = (stricmp(music_name, "titles") != 0) && (maptitle && (stricmp(maptitle, "Wandering Falls") != 0)); // thanks diggle! if (maptitle) Z_Free(maptitle); } -- 2.54.0 From 686a9f7237bc7da95f030ec79c0e27ae6f310e12 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 5 Dec 2024 14:30:16 +0100 Subject: [PATCH 115/143] use long M_PI to fix some render issues --- src/hardware/hw_clip.c | 2 +- src/hardware/r_opengl/r_opengl.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/hardware/hw_clip.c b/src/hardware/hw_clip.c index 12d870ea4..e9b1bce98 100644 --- a/src/hardware/hw_clip.c +++ b/src/hardware/hw_clip.c @@ -333,7 +333,7 @@ angle_t gld_FrustumAngle(angle_t tiltangle) // ok, this is a gross hack that barely works... // but at least it doesn't overestimate too much... - clipfov = atan(1 / projMatrix[0]) * 360 / M_PI; + clipfov = atan(1 / projMatrix[0]) * 360 / M_PIl; floatangle = 2.0f + (45.0f + (tilt / 1.9f)) * clipfov / 90.0f; if (floatangle >= 180.0) return 0xffffffff; diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index f60fd3a77..5ae1af77f 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -2983,7 +2983,7 @@ EXPORT void HWRAPI(SetTransform) (FTransform *stransform) if (special_splitscreen) { - used_fov = (float)(atan(tan(used_fov*M_PI/360)*0.8)*360/M_PI); + used_fov = (float)(atan(tan(used_fov * M_PIl / 360) * 0.8) * 360 / M_PIl); GLPerspective((GLfloat)used_fov, 2*ASPECT_RATIO); } else -- 2.54.0 From 216acf083a943b049160230b7a96fd462703156c Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 5 Dec 2024 14:29:48 +0100 Subject: [PATCH 116/143] bruh --- src/p_tick.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/p_tick.c b/src/p_tick.c index 9b9d723eb..266defd74 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -672,8 +672,6 @@ void P_Ticker(boolean run) // if there are no players left at all, stop demo recording // Demos that that dont have any players crash during playback, which can happen with dedicated servers if (demo.savemode == DSM_WILLAUTOSAVE && !D_NumPlayers()) - G_SaveDemo(); - else G_ResetDemoRecording(); } } -- 2.54.0 From 3a5b282b9b45d673bad58f72ee2f4059dc99105d Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 5 Dec 2024 11:36:53 +0100 Subject: [PATCH 117/143] try less maths for projectionmatrix from dsdadoom again lul --- src/hardware/r_opengl/r_opengl.c | 20 ++++++++------------ 1 file changed, 8 insertions(+), 12 deletions(-) diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index 5ae1af77f..7bb6f85f9 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -932,23 +932,19 @@ static void GLPerspective(GLfloat fovy, GLfloat aspect) { 0.0f, 0.0f, 1.0f,-1.0f}, { 0.0f, 0.0f, 0.0f, 0.0f}, }; - const GLfloat zNear = NEAR_CLIPPING_PLANE; - const GLfloat zFar = FAR_CLIPPING_PLANE; - const GLfloat radians = (GLfloat)(fovy / 2.0f * M_PIl / 180.0f); - const GLfloat sine = (GLfloat)sin(radians); - const GLfloat deltaZ = zFar - zNear; - GLfloat cotangent; - if ((fabsf((float)deltaZ) < 1.0E-36f) || fpclassify(sine) == FP_ZERO || fpclassify(aspect) == FP_ZERO) + const GLfloat focallength = (GLfloat)(1.0f / (GLfloat)tan(fovy * (GLfloat)M_PIl / 360.0f)); + const GLfloat deltaZ = FAR_CLIPPING_PLANE - NEAR_CLIPPING_PLANE; + + if ((fabsf((float)deltaZ) < 1.0E-36f) || fpclassify(aspect) == FP_ZERO) { return; } - cotangent = cosf(radians) / sine; - m[0][0] = cotangent / aspect; - m[1][1] = cotangent; - m[2][2] = -(zFar + zNear) / deltaZ; - m[3][2] = -2.0f * zNear * zFar / deltaZ; + m[0][0] = focallength / aspect; + m[1][1] = focallength; + m[2][2] = -(FAR_CLIPPING_PLANE + NEAR_CLIPPING_PLANE) / deltaZ; + m[3][2] = -2.0f * NEAR_CLIPPING_PLANE * FAR_CLIPPING_PLANE / deltaZ; pglMultMatrixf(&m[0][0]); } -- 2.54.0 From 13f6b62dc0d5c87b9e88c2899fd635ada966fc4f Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 7 Dec 2024 12:38:53 +0100 Subject: [PATCH 118/143] port updated skydome code from srb2 seems to actually fix some visual issues on certain maps with it --- src/hardware/hw_defs.h | 36 ++++- src/hardware/hw_drv.h | 2 +- src/hardware/hw_main.c | 165 +++++++++++++++++++++- src/hardware/hw_main.h | 3 + src/hardware/r_opengl/r_opengl.c | 227 +++++-------------------------- 5 files changed, 237 insertions(+), 196 deletions(-) diff --git a/src/hardware/hw_defs.h b/src/hardware/hw_defs.h index f36631690..41d86c89c 100644 --- a/src/hardware/hw_defs.h +++ b/src/hardware/hw_defs.h @@ -164,6 +164,41 @@ typedef struct FLOAT s,t; } FOutVector; +typedef struct vbo_vertex_s +{ + float x, y, z; + float u, v; + unsigned char r, g, b, a; +} gl_skyvertex_t; + +typedef enum gl_skyloopmode_e +{ + HWD_SKYLOOP_FAN, + HWD_SKYLOOP_STRIP +} gl_skyloopmode_t; + +typedef struct +{ + gl_skyloopmode_t mode; + int vertexcount; + int vertexindex; + boolean use_texture; +} gl_skyloopdef_t; + +typedef struct +{ + unsigned int vbo; + int rows, columns; + int loopcount; + + int detail, vertex_count; + int texture, width, height; + boolean rebuild; // VBO needs to be rebuilt + + gl_skyloopdef_t *loops; + gl_skyvertex_t *data; +} gl_sky_t; + // Shader targets used to render specific types of geometry. // A shader target is resolved to an actual shader with HWR_GetShaderFromTarget. // The shader returned may be a base shader or a custom shader. @@ -201,7 +236,6 @@ enum hwdshaderstage typedef enum hwdshaderstage hwdshaderstage_t; - // ========================================================================== // RENDER MODES // ========================================================================== diff --git a/src/hardware/hw_drv.h b/src/hardware/hw_drv.h index 335940142..78fb53d1e 100644 --- a/src/hardware/hw_drv.h +++ b/src/hardware/hw_drv.h @@ -54,7 +54,7 @@ EXPORT void HWRAPI(CreateModelVBOs) (model_t *model); EXPORT void HWRAPI(SetTransform) (FTransform *stransform); EXPORT INT32 HWRAPI(GetTextureUsed) (void); -EXPORT void HWRAPI(RenderSkyDome) (INT32 tex, INT32 texture_width, INT32 texture_height, FTransform transform); +EXPORT void HWRAPI(RenderSkyDome) (gl_sky_t *sky); EXPORT void HWRAPI(FlushScreenTextures) (void); EXPORT void HWRAPI(DoScreenWipe) (int wipeStart, int wipeEnd); diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 7115ca376..204405ae3 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -4916,6 +4916,153 @@ static void HWR_ProjectPrecipitationSprite(precipmobj_t *thing) vis->precip = true; } + +// ========================================================================== +// Sky dome rendering, ported from PrBoom+ +// ========================================================================== + +static gl_sky_t gl_sky; + +static void HWR_SkyDomeVertex(gl_sky_t *sky, gl_skyvertex_t *vbo, int r, int c, signed char yflip, float delta, boolean foglayer) +{ + const float radians = (float)(M_PIl / 180.0f); + const float scale = 10000.0f; + const float maxSideAngle = 60.0f; + + float topAngle = (c / (float)sky->columns * 360.0f); + float sideAngle = (maxSideAngle * (sky->rows - r) / sky->rows); + float height = (float)(sin(sideAngle * radians)); + float realRadius = (float)(scale * cos(sideAngle * radians)); + float x = (float)(realRadius * cos(topAngle * radians)); + float y = (!yflip) ? scale * height : -scale * height; + float z = (float)(realRadius * sin(topAngle * radians)); + float timesRepeat = (4 * (256.0f / sky->width)); + if (fpclassify(timesRepeat) == FP_ZERO) + timesRepeat = 1.0f; + + if (!foglayer) + { + vbo->r = 255; + vbo->g = 255; + vbo->b = 255; + vbo->a = (r == 0 ? 0 : 255); + + // And the texture coordinates. + vbo->u = (-timesRepeat * c / (float)sky->columns); + if (!yflip) // Flipped Y is for the lower hemisphere. + vbo->v = (r / (float)sky->rows) + 0.5f; + else + vbo->v = 1.0f + ((sky->rows - r) / (float)sky->rows) + 0.5f; + } + + if (r != 4) + y += 300.0f; + + // And finally the vertex. + vbo->x = x; + vbo->y = y + delta; + vbo->z = z; +} + +// Clears the sky dome. +void HWR_ClearSkyDome(void) +{ + gl_sky_t *sky = &gl_sky; + + if (sky->loops) + free(sky->loops); + if (sky->data) + free(sky->data); + + sky->loops = NULL; + sky->data = NULL; + + sky->vbo = 0; + sky->rows = sky->columns = 0; + sky->loopcount = 0; + + sky->detail = 0; + sky->texture = -1; + sky->width = sky->height = 0; + + sky->rebuild = true; +} + +void HWR_BuildSkyDome(void) +{ + int c, r; + signed char yflip; + int row_count = 4; + int col_count = 4; + float delta; + + gl_sky_t *sky = &gl_sky; + gl_skyvertex_t *vertex_p; + texture_t *texture = textures[texturetranslation[skytexture]]; + + sky->detail = 16; + col_count *= sky->detail; + + if ((sky->columns != col_count) || (sky->rows != row_count)) + HWR_ClearSkyDome(); + + sky->columns = col_count; + sky->rows = row_count; + sky->vertex_count = 2 * sky->rows * (sky->columns * 2 + 2) + sky->columns * 2; + + if (!sky->loops) + sky->loops = malloc((sky->rows * 2 + 2) * sizeof(sky->loops[0])); + + // create vertex array + if (!sky->data) + sky->data = malloc(sky->vertex_count * sizeof(sky->data[0])); + + sky->texture = texturetranslation[skytexture]; + sky->width = texture->width; + sky->height = texture->height; + + vertex_p = &sky->data[0]; + sky->loopcount = 0; + + for (yflip = 0; yflip < 2; yflip++) + { + sky->loops[sky->loopcount].mode = HWD_SKYLOOP_FAN; + sky->loops[sky->loopcount].vertexindex = vertex_p - &sky->data[0]; + sky->loops[sky->loopcount].vertexcount = col_count; + sky->loops[sky->loopcount].use_texture = false; + sky->loopcount++; + + delta = 0.0f; + + for (c = 0; c < col_count; c++) + { + HWR_SkyDomeVertex(sky, vertex_p, 1, c, yflip, 0.0f, true); + vertex_p->r = 255; + vertex_p->g = 255; + vertex_p->b = 255; + vertex_p->a = 255; + vertex_p++; + } + + delta = (yflip ? 5.0f : -5.0f) / 128.0f; + + for (r = 0; r < row_count; r++) + { + sky->loops[sky->loopcount].mode = HWD_SKYLOOP_STRIP; + sky->loops[sky->loopcount].vertexindex = vertex_p - &sky->data[0]; + sky->loops[sky->loopcount].vertexcount = 2 * col_count + 2; + sky->loops[sky->loopcount].use_texture = true; + sky->loopcount++; + + for (c = 0; c <= col_count; c++) + { + HWR_SkyDomeVertex(sky, vertex_p++, r + (yflip ? 1 : 0), (c ? c : 0), yflip, delta, false); + HWR_SkyDomeVertex(sky, vertex_p++, r + (yflip ? 0 : 1), (c ? c : 0), yflip, delta, false); + } + } + } +} + static boolean drewsky = false; static void HWR_DrawSkyBackground(float fpov) @@ -4925,6 +5072,8 @@ static void HWR_DrawSkyBackground(float fpov) if (drewsky) return; + HWD.pfnSetBlend(PF_Translucent|PF_NoDepthTest|PF_Modulated); + memset(&dometransform, 0x00, sizeof(FTransform)); //04/01/2000: Hurdler: added for T&L @@ -4945,9 +5094,17 @@ static void HWR_DrawSkyBackground(float fpov) dometransform.splitscreen = splitscreen; HWR_GetTexture(texturetranslation[skytexture], false); + + if (gl_sky.texture != texturetranslation[skytexture]) + { + HWR_ClearSkyDome(); + HWR_BuildSkyDome(); + } + if (HWR_UseShader()) - HWD.pfnSetShader(HWR_GetShaderFromTarget(SHADER_SKY));// sky shader - HWD.pfnRenderSkyDome(skytexture, textures[skytexture]->width, textures[skytexture]->height, dometransform); + HWD.pfnSetShader(HWR_GetShaderFromTarget(SHADER_SKY)); + HWD.pfnSetTransform(&dometransform); + HWD.pfnRenderSkyDome(&gl_sky); } @@ -5327,6 +5484,10 @@ void HWR_LoadLevel(void) HWR_CreatePlanePolygons((INT32)numnodes - 1); + // Build the sky dome + HWR_ClearSkyDome(); + HWR_BuildSkyDome(); + if (HWR_ShouldUsePaletteRendering()) HWR_SetMapPalette(); } diff --git a/src/hardware/hw_main.h b/src/hardware/hw_main.h index 8d4228a26..52616b7e4 100644 --- a/src/hardware/hw_main.h +++ b/src/hardware/hw_main.h @@ -105,6 +105,9 @@ void HWR_AddCommands(void); void HWR_RenderPlayerView(INT32 viewnumber, player_t *player); void HWR_RenderViewpoint(gl_portal_t *rootportal, const float fpov, player_t *player, int stencil_level, boolean allow_portals); +void HWR_ClearSkyDome(void); +void HWR_BuildSkyDome(void); + void HWR_SetTransform(float fpov, player_t *player); void HWR_ClearClipper(void); void HWR_SetStencilState(int state, int level); diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index 7bb6f85f9..92fb78d35 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -2090,230 +2090,83 @@ EXPORT void HWRAPI(DrawIndexedTriangles) (FSurfaceInfo *pSurf, FOutVector *pOutV // the DrawPolygon variant of this has some code about polyflags and wrapping here but havent noticed any problems from omitting it? } -// Sky dome code, taken/backported from SRB2 - -typedef struct vbo_vertex_s -{ - float x, y, z; - float u, v; - unsigned char r, g, b, a; -} vbo_vertex_t; - -typedef struct -{ - int mode; - int vertexcount; - int vertexindex; - int use_texture; -} GLSkyLoopDef; - -typedef struct -{ - unsigned int id; - int rows, columns; - int loopcount; - GLSkyLoopDef *loops; - vbo_vertex_t *data; -} GLSkyVBO; - static const boolean gl_ext_arb_vertex_buffer_object = true; -#define NULL_VBO_VERTEX ((vbo_vertex_t*)NULL) -#define sky_vbo_x (gl_ext_arb_vertex_buffer_object ? &NULL_VBO_VERTEX->x : &vbo->data[0].x) -#define sky_vbo_u (gl_ext_arb_vertex_buffer_object ? &NULL_VBO_VERTEX->u : &vbo->data[0].u) -#define sky_vbo_r (gl_ext_arb_vertex_buffer_object ? &NULL_VBO_VERTEX->r : &vbo->data[0].r) +#define NULL_VBO_VERTEX ((gl_skyvertex_t*)NULL) +#define sky_vbo_x (gl_ext_arb_vertex_buffer_object ? &NULL_VBO_VERTEX->x : &sky->data[0].x) +#define sky_vbo_u (gl_ext_arb_vertex_buffer_object ? &NULL_VBO_VERTEX->u : &sky->data[0].u) +#define sky_vbo_r (gl_ext_arb_vertex_buffer_object ? &NULL_VBO_VERTEX->r : &sky->data[0].r) -// The texture offset to be applied to the texture coordinates in SkyVertex(). -static int rows, columns; -static signed char yflip; -static int texw, texh; -static boolean foglayer; -static float delta = 0.0f; - -static int gl_sky_detail = 16; - -static INT32 lasttex = -1; - -#define MAP_COEFF 128.0f - -static void SkyVertex(vbo_vertex_t *vbo, int r, int c) -{ - const float radians = (float)(M_PIl / 180.0f); - const float scale = 10000.0f; - const float maxSideAngle = 60.0f; - - float topAngle = (c / (float)columns * 360.0f); - float sideAngle = (maxSideAngle * (rows - r) / rows); - float height = (float)(sin(sideAngle * radians)); - float realRadius = (float)(scale * cos(sideAngle * radians)); - float x = (float)(realRadius * cos(topAngle * radians)); - float y = (!yflip) ? scale * height : -scale * height; - float z = (float)(realRadius * sin(topAngle * radians)); - float timesRepeat = (4 * (256.0f / texw)); - if (fpclassify(timesRepeat) == FP_ZERO) - timesRepeat = 1.0f; - - if (!foglayer) - { - vbo->r = 255; - vbo->g = 255; - vbo->b = 255; - vbo->a = (r == 0 ? 0 : 255); - - // And the texture coordinates. - //vbo->u = (-timesRepeat * c / (float)columns); - vbo->u = (timesRepeat * c / (float)columns);// TEST - if (!yflip) // Flipped Y is for the lower hemisphere. - vbo->v = (r / (float)rows) + 0.5f; - else - vbo->v = 1.0f + ((rows - r) / (float)rows) + 0.5f; - } - - if (r != 4) - { - y += 300.0f; - } - - // And finally the vertex. - vbo->x = x; - vbo->y = y + delta; - vbo->z = z; -} - -static GLSkyVBO sky_vbo; - -static void gld_BuildSky(int row_count, int col_count) -{ - int c, r; - vbo_vertex_t *vertex_p; - int vertex_count = 2 * row_count * (col_count * 2 + 2) + col_count * 2; - - GLSkyVBO *vbo = &sky_vbo; - - if ((vbo->columns != col_count) || (vbo->rows != row_count)) - { - free(vbo->loops); - free(vbo->data); - memset(vbo, 0, sizeof(&vbo)); - } - - if (!vbo->data) - { - memset(vbo, 0, sizeof(&vbo)); - vbo->loops = malloc((row_count * 2 + 2) * sizeof(vbo->loops[0])); - // create vertex array - vbo->data = malloc(vertex_count * sizeof(vbo->data[0])); - } - - vbo->columns = col_count; - vbo->rows = row_count; - - vertex_p = &vbo->data[0]; - vbo->loopcount = 0; - - for (yflip = 0; yflip < 2; yflip++) - { - vbo->loops[vbo->loopcount].mode = GL_TRIANGLE_FAN; - vbo->loops[vbo->loopcount].vertexindex = vertex_p - &vbo->data[0]; - vbo->loops[vbo->loopcount].vertexcount = col_count; - vbo->loops[vbo->loopcount].use_texture = false; - vbo->loopcount++; - - delta = 0.0f; - foglayer = true; - for (c = 0; c < col_count; c++) - { - SkyVertex(vertex_p, 1, c); - vertex_p->r = 255; - vertex_p->g = 255; - vertex_p->b = 255; - vertex_p->a = 255; - vertex_p++; - } - foglayer = false; - - delta = (yflip ? 5.0f : -5.0f) / MAP_COEFF; - - for (r = 0; r < row_count; r++) - { - vbo->loops[vbo->loopcount].mode = GL_TRIANGLE_STRIP; - vbo->loops[vbo->loopcount].vertexindex = vertex_p - &vbo->data[0]; - vbo->loops[vbo->loopcount].vertexcount = 2 * col_count + 2; - vbo->loops[vbo->loopcount].use_texture = true; - vbo->loopcount++; - - for (c = 0; c <= col_count; c++) - { - SkyVertex(vertex_p++, r + (yflip ? 1 : 0), (c ? c : 0)); - SkyVertex(vertex_p++, r + (yflip ? 0 : 1), (c ? c : 0)); - } - } - } -} - -static void RenderDome(INT32 skytexnum) +EXPORT void HWRAPI(RenderSkyDome) (gl_sky_t *sky) { int i, j; - int vbosize; - GLSkyVBO *vbo = &sky_vbo; - rows = 4; - columns = 4 * gl_sky_detail; - - vbosize = 2 * rows * (columns * 2 + 2) + columns * 2; + Shader_SetUniforms(NULL, NULL, NULL, NULL); // Build the sky dome! Yes! - if (lasttex != skytexnum) + if (sky->rebuild) { // delete VBO when already exists if (gl_ext_arb_vertex_buffer_object) { - if (vbo->id) - pglDeleteBuffers(1, &vbo->id); + if (sky->vbo) + pglDeleteBuffers(1, &sky->vbo); } - lasttex = skytexnum; - gld_BuildSky(rows, columns); - if (gl_ext_arb_vertex_buffer_object) { // generate a new VBO and get the associated ID - pglGenBuffers(1, &vbo->id); + pglGenBuffers(1, &sky->vbo); // bind VBO in order to use - pglBindBuffer(GL_ARRAY_BUFFER, vbo->id); + pglBindBuffer(GL_ARRAY_BUFFER, sky->vbo); // upload data to VBO - pglBufferData(GL_ARRAY_BUFFER, vbosize * sizeof(vbo->data[0]), vbo->data, GL_STATIC_DRAW); + pglBufferData(GL_ARRAY_BUFFER, sky->vertex_count * sizeof(sky->data[0]), sky->data, GL_STATIC_DRAW); } + + sky->rebuild = false; } // bind VBO in order to use if (gl_ext_arb_vertex_buffer_object) - pglBindBuffer(GL_ARRAY_BUFFER, vbo->id); + pglBindBuffer(GL_ARRAY_BUFFER, sky->vbo); // activate and specify pointers to arrays - pglVertexPointer(3, GL_FLOAT, sizeof(vbo->data[0]), sky_vbo_x); - pglTexCoordPointer(2, GL_FLOAT, sizeof(vbo->data[0]), sky_vbo_u); - pglColorPointer(4, GL_UNSIGNED_BYTE, sizeof(vbo->data[0]), sky_vbo_r); + pglVertexPointer(3, GL_FLOAT, sizeof(sky->data[0]), sky_vbo_x); + pglTexCoordPointer(2, GL_FLOAT, sizeof(sky->data[0]), sky_vbo_u); + pglColorPointer(4, GL_UNSIGNED_BYTE, sizeof(sky->data[0]), sky_vbo_r); // activate color arrays pglEnableClientState(GL_COLOR_ARRAY); // set transforms - pglScalef(1.0f, (float)texh / 230.0f, 1.0f); + pglScalef(1.0f, (float)sky->height / 200.0f, 1.0f); pglRotatef(270.0f, 0.0f, 1.0f, 0.0f); for (j = 0; j < 2; j++) { - for (i = 0; i < vbo->loopcount; i++) + for (i = 0; i < sky->loopcount; i++) { - GLSkyLoopDef *loop = &vbo->loops[i]; + gl_skyloopdef_t *loop = &sky->loops[i]; + unsigned int mode = 0; if (j == 0 ? loop->use_texture : !loop->use_texture) continue; - pglDrawArrays(loop->mode, loop->vertexindex, loop->vertexcount); + switch (loop->mode) + { + case HWD_SKYLOOP_FAN: + mode = GL_TRIANGLE_FAN; + break; + case HWD_SKYLOOP_STRIP: + mode = GL_TRIANGLE_STRIP; + break; + default: + continue; + } + + pglDrawArrays(mode, loop->vertexindex, loop->vertexcount); } } @@ -2328,16 +2181,6 @@ static void RenderDome(INT32 skytexnum) pglDisableClientState(GL_COLOR_ARRAY); } -EXPORT void HWRAPI(RenderSkyDome) (INT32 tex, INT32 texture_width, INT32 texture_height, FTransform transform) -{ - SetBlend(PF_Translucent|PF_NoDepthTest|PF_Modulated); - SetTransform(&transform); - texw = texture_width; - texh = texture_height; - RenderDome(tex); - SetBlend(0); -} - // ========================================================================== // // ========================================================================== -- 2.54.0 From 4fca31049f4204bde5f40cf5c67263c121abaa90 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 7 Dec 2024 12:52:00 +0100 Subject: [PATCH 119/143] no need to set all that stuff manually --- src/hardware/hw_defs.h | 10 +++++----- src/hardware/hw_main.c | 25 ++++++++----------------- 2 files changed, 13 insertions(+), 22 deletions(-) diff --git a/src/hardware/hw_defs.h b/src/hardware/hw_defs.h index 41d86c89c..91146f228 100644 --- a/src/hardware/hw_defs.h +++ b/src/hardware/hw_defs.h @@ -132,14 +132,14 @@ typedef struct { FLOAT x,y,z; // position #ifdef USE_FTRANSFORM_ANGLEZ - FLOAT anglex,angley,anglez; // aimingangle / viewangle - FLOAT anglex2,anglez2; // secondaries + FLOAT anglex, angley, anglez; // aimingangle / viewangle + FLOAT anglex2, anglez2; // secondaries #else - FLOAT anglex,angley; // aimingangle / viewangle + FLOAT anglex, angley; // aimingangle / viewangle FLOAT anglex2; // secondaries #endif - FLOAT scalex,scaley,scalez; - FLOAT spritexscale,spriteyscale; + FLOAT scalex, scaley, scalez; + FLOAT spritexscale, spriteyscale; FLOAT fovxangle, fovyangle; UINT8 splitscreen; boolean flip; // screenflip diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 204405ae3..5e24e6eae 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -5065,7 +5065,7 @@ void HWR_BuildSkyDome(void) static boolean drewsky = false; -static void HWR_DrawSkyBackground(float fpov) +static void HWR_DrawSkyBackground(void) { FTransform dometransform; @@ -5074,25 +5074,17 @@ static void HWR_DrawSkyBackground(float fpov) HWD.pfnSetBlend(PF_Translucent|PF_NoDepthTest|PF_Modulated); - memset(&dometransform, 0x00, sizeof(FTransform)); + memcpy(&dometransform, &atransform, sizeof(FTransform)); + + dometransform.x = 0.0; + dometransform.y = 0.0; + dometransform.z = 0.0; //04/01/2000: Hurdler: added for T&L // It should replace all other gl_viewxxx when finished HWR_SetTransformAiming(&dometransform); dometransform.angley = (float)((viewangle-ANGLE_270)>>ANGLETOFINESHIFT)*(360.0f/(float)FINEANGLES); - dometransform.flip = atransform.flip; - dometransform.mirror = atransform.mirror; - dometransform.mirrorflip = atransform.mirrorflip; - - dometransform.scalex = 1; - dometransform.scaley = (float)vid.width/vid.height; - dometransform.scalez = 1; - dometransform.fovxangle = fpov; // Tails - dometransform.fovyangle = fpov; // Tails - HWR_RollTransform(&dometransform, viewroll); - dometransform.splitscreen = splitscreen; - HWR_GetTexture(texturetranslation[skytexture], false); if (gl_sky.texture != texturetranslation[skytexture]) @@ -5107,7 +5099,6 @@ static void HWR_DrawSkyBackground(float fpov) HWD.pfnRenderSkyDome(&gl_sky); } - // -----------------+ // HWR_ClearView : clear the viewwindow, with maximum z value. also clears stencil buffer. // -----------------+ @@ -5321,7 +5312,7 @@ void HWR_RenderViewpoint(gl_portal_t *rootportal, const float fpov, player_t *pl HWR_SkyWallList_Clear(); HWR_SetStencilState(HWR_STENCIL_NORMAL, 1); drewsky = false; - HWR_DrawSkyBackground(fpov); + HWR_DrawSkyBackground(); HWR_SetStencilState(HWR_STENCIL_NORMAL, 0); HWD.pfnClearBuffer(false, false, true, 0);// clear skywall markings from the stencil buffer HWR_SetTransform(fpov, player);// restore transform @@ -5386,7 +5377,7 @@ static void HWR_RenderFrame(INT32 viewnumber, player_t *player, boolean skybox) ST_doPaletteStuff(); // Draw the sky background. - HWR_DrawSkyBackground(fpov); + HWR_DrawSkyBackground(); if (skybox) drewsky = true; -- 2.54.0 From 9abd34baa391811bea1b1f9f1a5838a8eece2dc0 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 8 Dec 2024 01:33:44 +0100 Subject: [PATCH 120/143] proper macros --- src/byteptr.h | 51 ++++++++++++++++++++++++++++----------------------- 1 file changed, 28 insertions(+), 23 deletions(-) diff --git a/src/byteptr.h b/src/byteptr.h index 9756e7d95..0345038b8 100644 --- a/src/byteptr.h +++ b/src/byteptr.h @@ -1,7 +1,7 @@ // SONIC ROBO BLAST 2 //----------------------------------------------------------------------------- // Copyright (C) 1998-2000 by DooM Legacy Team. -// Copyright (C) 1999-2018 by Sonic Team Junior. +// Copyright (C) 1999-2024 by Sonic Team Junior. // // This program is free software distributed under the // terms of the GNU General Public License, version 2. @@ -11,6 +11,9 @@ /// \brief Macros to read/write from/to a UINT8 *, /// used for packet creation and such +#ifndef __BYTEPTR_H__ +#define __BYTEPTR_H__ + #if defined (__alpha__) || defined (__arm__) || defined (__mips__) || defined (__ia64__) || defined (__clang__) #define DEALIGNED #endif @@ -150,7 +153,7 @@ FUNCINLINE static ATTRINLINE UINT32 readulong(void *ptr) #undef DEALIGNED -#define WRITESTRINGN(p, s, n) ({ \ +#define WRITESTRINGN(p, s, n) do { \ size_t tmp_i; \ \ for (tmp_i = 0; tmp_i < n && s[tmp_i] != '\0'; tmp_i++) \ @@ -158,70 +161,72 @@ FUNCINLINE static ATTRINLINE UINT32 readulong(void *ptr) \ if (tmp_i < n) \ WRITECHAR(p, '\0'); \ -}) +} while (0) -#define WRITESTRINGL(p, s, n) ({ \ +#define WRITESTRINGL(p, s, n) do { \ size_t tmp_i; \ \ for (tmp_i = 0; tmp_i < n - 1 && s[tmp_i] != '\0'; tmp_i++) \ WRITECHAR(p, s[tmp_i]); \ \ WRITECHAR(p, '\0'); \ -}) +} while (0) -#define WRITESTRING(p, s) ({ \ +#define WRITESTRING(p, s) do { \ size_t tmp_i; \ \ for (tmp_i = 0; s[tmp_i] != '\0'; tmp_i++) \ WRITECHAR(p, s[tmp_i]); \ \ WRITECHAR(p, '\0'); \ -}) +} while (0) -#define WRITEMEM(p, s, n) ({ \ - memcpy(p, s, n); \ - p += n; \ -}) +#define WRITEMEM(p, s, n) do { \ + memcpy(p, s, n); \ + p += n; \ +} while (0) #define SKIPSTRING(p) while (READCHAR(p) != '\0') -#define SKIPSTRINGN(p, n) ({ \ +#define SKIPSTRINGN(p, n) do { \ size_t tmp_i = 0; \ \ while (tmp_i < n && READCHAR(p) != '\0') \ tmp_i++; \ -}) +} while (0) #define SKIPSTRINGL(p, n) SKIPSTRINGN(p, n) -#define READSTRINGN(p, s, n) ({ \ +#define READSTRINGN(p, s, n) do { \ size_t tmp_i = 0; \ \ while (tmp_i < n && (s[tmp_i] = READCHAR(p)) != '\0') \ tmp_i++; \ \ s[tmp_i] = '\0'; \ -}) +} while (0) -#define READSTRINGL(p, s, n) ({ \ +#define READSTRINGL(p, s, n) do { \ size_t tmp_i = 0; \ \ while (tmp_i < n - 1 && (s[tmp_i] = READCHAR(p)) != '\0') \ tmp_i++; \ \ s[tmp_i] = '\0'; \ -}) +} while (0) -#define READSTRING(p, s) ({ \ +#define READSTRING(p, s) do { \ size_t tmp_i = 0; \ \ while ((s[tmp_i] = READCHAR(p)) != '\0') \ tmp_i++; \ \ s[tmp_i] = '\0'; \ -}) +} while (0) -#define READMEM(p, s, n) ({ \ - memcpy(s, p, n); \ - p += n; \ -}) +#define READMEM(p, s, n) do { \ + memcpy(s, p, n); \ + p += n; \ +} while (0) + +#endif // __BYTEPTR_H__ -- 2.54.0 From 0e843c2a96dcb1df8aeebaea8391f90b4ae34b6f Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 8 Dec 2024 01:27:57 +0100 Subject: [PATCH 121/143] stuff --- src/hardware/hw_cache.c | 9 +++------ src/hardware/hw_data.h | 12 +++++++----- 2 files changed, 10 insertions(+), 11 deletions(-) diff --git a/src/hardware/hw_cache.c b/src/hardware/hw_cache.c index c67f1b75c..652e1e903 100644 --- a/src/hardware/hw_cache.c +++ b/src/hardware/hw_cache.c @@ -336,8 +336,8 @@ static void HWR_GenerateTexture(INT32 texnum, GLMapTexture_t *gltex, boolean noe else gltex->mipmap.flags = TF_CHROMAKEYED | TF_WRAPXY; - gltex->mipmap.width = (UINT16)texture->width; - gltex->mipmap.height = (UINT16)texture->height; + gltex->mipmap.width = SHORT(texture->width); + gltex->mipmap.height = SHORT(texture->height); if (skyspecial) gltex->mipmap.format = GL_TEXFMT_RGBA; // that skyspecial code below assumes this format ... @@ -416,14 +416,13 @@ void HWR_MakePatch (patch_t *patch, GLPatch_t *glPatch, GLMipmap_t *glMipmap, bo glPatch->leftoffset = SHORT(patch->leftoffset); glPatch->topoffset = SHORT(patch->topoffset); - //glMipmap->width = (UINT16)SHORT(patch->width); - //glMipmap->height = (UINT16)SHORT(patch->height); glMipmap->width = glMipmap->height = 1; while (glMipmap->width < glPatch->width) glMipmap->width <<= 1; while (glMipmap->height < glPatch->height) glMipmap->height <<= 1; // no wrap around, no chroma key glMipmap->flags = 0; + // setup the texture info glMipmap->format = patchformat; @@ -443,8 +442,6 @@ void HWR_MakePatch (patch_t *patch, GLPatch_t *glPatch, GLMipmap_t *glMipmap, bo glPatch->width, glPatch->height, patch); } - - //glPatch->max_s = glPatch->max_t = 1.0f; } // ================================================= diff --git a/src/hardware/hw_data.h b/src/hardware/hw_data.h index b149493c5..1f16ebf2a 100644 --- a/src/hardware/hw_data.h +++ b/src/hardware/hw_data.h @@ -33,16 +33,18 @@ typedef enum GLTextureFormat_e GL_TEXFMT_ALPHA_INTENSITY_88 = 0x22, } GLTextureFormat_t; -// data holds the address of the graphics data cached in heap memory -// NULL if the texture is not in Doom heap cache. +// Texture information (misleadingly named "mipmap" all over the code.) +// The *data pointer holds the address of the graphics data cached in heap memory. +// NULL if the texture is not in SRB2's heap cache. struct GLMipmap_s { + // for UpdateTexture GLTextureFormat_t format; void *data; UINT32 flags; UINT16 width, height; - UINT32 downloaded; // tex_downloaded + UINT32 downloaded; // The GPU has this texture. struct GLMipmap_s *nextcolormap; const UINT8 *colormap; @@ -50,12 +52,12 @@ struct GLMipmap_s typedef struct GLMipmap_s GLMipmap_t; // -// Doom texture info, as cached for hardware rendering +// Level textures, as cached for hardware rendering. // struct GLMapTexture_s { GLMipmap_t mipmap; - float scaleX; //used for scaling textures on walls + float scaleX; //used for scaling textures on walls float scaleY; }; typedef struct GLMapTexture_s GLMapTexture_t; -- 2.54.0 From de4bcec78202b5179f857abd8ea7569220805233 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 8 Dec 2024 01:34:16 +0100 Subject: [PATCH 122/143] make those less chaotic --- src/hardware/r_opengl/r_opengl.c | 23 ++++++++++++++--------- 1 file changed, 14 insertions(+), 9 deletions(-) diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index 92fb78d35..19c03a7be 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -23,20 +23,25 @@ #include #include -#include "../../r_local.h" // For rendertimefrac, used for the leveltime shader uniform -#include "../../i_video.h" // for UseScreenFBO -#include "r_opengl.h" -#include "r_vbo.h" -#include "../hw_shaders.h" -#include "../hw_main.h" -#include "../hw_clip.h" // Eeeeh not sure is this right way, but it works < sry :c < sry again it had to go :c -extern fixed_t fovtan; // also extremely bad, I'm just too lazy!!! - #if defined (HWRENDER) && !defined (NOROPENGL) +#include "r_opengl.h" +#include "r_vbo.h" + +#include "../hw_batching.h" +#include "../hw_clip.h" +#include "../hw_main.h" +#include "../hw_shaders.h" + +#include "../../f_finale.h" +#include "../../r_local.h" // For rendertimefrac, used for the leveltime shader uniform +#include "../../i_video.h" + +extern fixed_t fovtan; // also extremely bad, I'm just too lazy!!! + struct GLRGBAFloat { GLfloat red; -- 2.54.0 From 7b2e763d07c480539d9eef7c625556b9d9d20b0c Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 8 Dec 2024 03:34:19 +0100 Subject: [PATCH 123/143] inline those two smol speedup --- src/r_main.c | 39 --------------------------------------- src/r_main.h | 42 ++++++++++++++++++++++++++++++++++++++++-- 2 files changed, 40 insertions(+), 41 deletions(-) diff --git a/src/r_main.c b/src/r_main.c index b68bde658..ccf872bba 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -298,32 +298,6 @@ static void Precipstuff_OnChange(void) P_SpawnPrecipitation(); } -// -// R_PointOnSide -// Traverse BSP (sub) tree, -// check point against partition plane. -// Returns side 0 (front) or 1 (back). -// -// killough 5/2/98: reformatted -// -PUREFUNC INT32 R_PointOnSide(fixed_t x, fixed_t y, const node_t *restrict node) -{ - if (!node->dx) - return x <= node->x ? node->dy > 0 : node->dy < 0; - - if (!node->dy) - return y <= node->y ? node->dx < 0 : node->dx > 0; - - x -= node->x; - y -= node->y; - - // Try to quickly decide by looking at sign bits. - // also use a mask to avoid branch prediction - INT32 mask = (node->dy ^ node->dx ^ x ^ y) >> 31; - return (mask & ((node->dy ^ x) < 0)) | // (left is negative) - (~mask & (FixedMul(y, node->dx>>FRACBITS) >= FixedMul(node->dy>>FRACBITS, x))); -} - // // R_PointToAngle // To get a global angle from cartesian coordinates, @@ -1052,19 +1026,6 @@ void R_Init(void) framecount = 0; } -// -// R_PointInSubsector -// -subsector_t *R_PointInSubsector(fixed_t x, fixed_t y) -{ - size_t nodenum = numnodes-1; - - while (!(nodenum & NF_SUBSECTOR)) - nodenum = nodes[nodenum].children[R_PointOnSide(x, y, nodes+nodenum)]; - - return &subsectors[nodenum & ~NF_SUBSECTOR]; -} - // // R_IsPointInSubsector, same as above but returns 0 if not in subsector // diff --git a/src/r_main.h b/src/r_main.h index 553f6a79f..523e924d5 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -72,7 +72,32 @@ extern lighttable_t *zlight[LIGHTLEVELS][MAXLIGHTZ]; #define COLORMAP_REMAPOFFSET COLORMAP_SIZE // Utility functions. -INT32 R_PointOnSide(fixed_t x, fixed_t y, const node_t *node); + +// +// R_PointOnSide +// Traverse BSP (sub) tree, +// check point against partition plane. +// Returns side 0 (front) or 1 (back). +// +// killough 5/2/98: reformatted +// +FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSide(fixed_t x, fixed_t y, const node_t *restrict node) +{ + if (!node->dx) + return x <= node->x ? node->dy > 0 : node->dy < 0; + + if (!node->dy) + return y <= node->y ? node->dx < 0 : node->dx > 0; + + x -= node->x; + y -= node->y; + + // Try to quickly decide by looking at sign bits. + // also use a mask to avoid branch prediction + INT32 mask = (node->dy ^ node->dx ^ x ^ y) >> 31; + return (mask & ((node->dy ^ x) < 0)) | // (left is negative) + (~mask & (FixedMul(y, node->dx>>FRACBITS) >= FixedMul(node->dy>>FRACBITS, x))); +} // This is not as accurate // SHOULD NOT BE USED FOR ANYTHING GAMEPLAY RELATED!! @@ -99,9 +124,22 @@ angle_t R_PointToAngle2(fixed_t px2, fixed_t py2, fixed_t px1, fixed_t py1); angle_t R_PlayerSliptideAngle(player_t *player); fixed_t R_ScaleFromGlobalAngle(angle_t visangle); -subsector_t *R_PointInSubsector(fixed_t x, fixed_t y); + subsector_t *R_IsPointInSubsector(fixed_t x, fixed_t y); +// +// R_PointInSubsector +// +FUNCINLINE static ATTRINLINE subsector_t *R_PointInSubsector(fixed_t x, fixed_t y) +{ + size_t nodenum = numnodes-1; + + while (!(nodenum & NF_SUBSECTOR)) + nodenum = nodes[nodenum].children[R_PointOnSide(x, y, nodes+nodenum)]; + + return &subsectors[nodenum & ~NF_SUBSECTOR]; +} + // uses R_PointOnSideFast // SHOULD NOT BE USED FOR ANYTHING GAMEPLAY RELATED!! FUNCINLINE static ATTRINLINE subsector_t *R_PointInSubsectorFast(fixed_t x, fixed_t y) -- 2.54.0 From f7c7dae3a5e6a83c1ac39e4e8570c459cfcbd838 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 8 Dec 2024 15:14:04 +0100 Subject: [PATCH 124/143] smol cleanup p_sight --- src/p_sight.c | 109 ++++++++++++++++---------------------------------- 1 file changed, 35 insertions(+), 74 deletions(-) diff --git a/src/p_sight.c b/src/p_sight.c index b482403cb..5ca186b85 100644 --- a/src/p_sight.c +++ b/src/p_sight.c @@ -38,66 +38,21 @@ static INT32 sightcounts[2]; // // Returns side 0 (front), 1 (back), or 2 (on). // -static INT32 P_DivlineSide(fixed_t x, fixed_t y, divline_t *node) +// killough 4/19/98: made static, cleaned up +static INT32 P_DivlineSide(fixed_t x, fixed_t y, const divline_t *node) { - fixed_t dx, dy, left, right; - - if (!node->dx) - { - if (x == node->x) - return 2; - - if (x <= node->x) - return (node->dy > 0); - - return (node->dy < 0); - } - - if (!node->dy) - { - if (y == node->y) - return 2; - - if (y <= node->y) - return (node->dx < 0); - - return (node->dx > 0); - } - - dx = x - node->x; - dy = y - node->y; - - left = (node->dy>>FRACBITS) * (dx>>FRACBITS); - right = (dy>>FRACBITS) * (node->dx>>FRACBITS); - - if (right < left) - return 0; // front side - - if (left == right) - return 2; - - return 1; // back side + fixed_t left, right; + return + !node->dx ? x == node->x ? 2 : x <= node->x ? node->dy > 0 : node->dy < 0 : + !node->dy ? y == node->y ? 2 : y <= node->y ? node->dx < 0 : node->dx > 0 : + (right = ((y - node->y) >> FRACBITS) * (node->dx >> FRACBITS)) < + (left = ((x - node->x) >> FRACBITS) * (node->dy >> FRACBITS)) ? 0 : + right == left ? 2 : 1; } -// -// P_InterceptVector2 -// -// Returns the fractional intercept point along the first divline. -// This is only called by the addthings and addlines traversers. -// -static fixed_t P_InterceptVector2(divline_t *v2, divline_t *v1) +static INT32 P_DivlineCrossed(fixed_t x1, fixed_t y1, fixed_t x2, fixed_t y2, const divline_t *node) { - fixed_t frac, num, den; - - den = FixedMul(v1->dy>>8, v2->dx) - FixedMul(v1->dx>>8, v2->dy); - - if (!den) - return 0; - - num = FixedMul((v1->x - v2->x)>>8, v1->dy) + FixedMul((v2->y - v1->y)>>8, v1->dx); - frac = FixedDiv(num, den); - - return frac; + return (P_DivlineSide(x1, y1, node) == P_DivlineSide(x2, y2, node)); } static boolean P_CrossSubsecPolyObj(polyobj_t *po, register los_t *los) @@ -135,23 +90,21 @@ static boolean P_CrossSubsecPolyObj(polyobj_t *po, register los_t *los) v2 = line->v2; // line isn't crossed? - if (P_DivlineSide(v1->x, v1->y, &los->strace) == - P_DivlineSide(v2->x, v2->y, &los->strace)) + if (P_DivlineCrossed(v1->x, v1->y, v2->x, v2->y, &los->strace)) continue; divl.dx = v2->x - (divl.x = v1->x); divl.dy = v2->y - (divl.y = v1->y); // line isn't crossed? - if (P_DivlineSide(los->strace.x, los->strace.y, &divl) == - P_DivlineSide(los->t2x, los->t2y, &divl)) + if (P_DivlineCrossed(los->strace.x, los->strace.y, los->t2x, los->t2y, &divl)) continue; // stop because it is not two sided //if (!(po->flags & POF_TESTHEIGHT)) //return false; - frac = P_InterceptVector2(&los->strace, &divl); + frac = P_InterceptVector(&los->strace, &divl); // get slopes of top and bottom of this polyobject line topslope = FixedDiv(polysec->ceilingheight - los->sightzstart , frac); @@ -232,16 +185,14 @@ static boolean P_CrossSubsector(size_t num, register los_t *los) v2 = line->v2; // line isn't crossed? - if (P_DivlineSide(v1->x, v1->y, &los->strace) == - P_DivlineSide(v2->x, v2->y, &los->strace)) + if (P_DivlineCrossed(v1->x, v1->y, v2->x, v2->y, &los->strace)) continue; divl.dx = v2->x - (divl.x = v1->x); divl.dy = v2->y - (divl.y = v1->y); // line isn't crossed? - if (P_DivlineSide(los->strace.x, los->strace.y, &divl) == - P_DivlineSide(los->t2x, los->t2y, &divl)) + if (P_DivlineCrossed(los->strace.x, los->strace.y, los->t2x, los->t2y, &divl)) continue; // stop because it is not two sided anyway @@ -249,7 +200,7 @@ static boolean P_CrossSubsector(size_t num, register los_t *los) return false; // calculate fractional intercept (how far along we are divided by how far we are from t2) - frac = P_InterceptVector2(&los->strace, &divl); + frac = P_InterceptVector(&los->strace, &divl); front = seg->frontsector; back = seg->backsector; @@ -354,19 +305,29 @@ static boolean P_CrossBSPNode(INT32 bspnum, register los_t *los) while (!(bspnum & NF_SUBSECTOR)) { register node_t *bsp = nodes + bspnum; + INT32 side = P_DivlineSide(los->strace.x,los->strace.y,(divline_t *)bsp)&1; - if (side == P_DivlineSide(los->t2x, los->t2y, (divline_t *) bsp)) - bspnum = bsp->children[side]; // doesn't touch the other side - else // the partition plane is crossed here + INT32 side2 = P_DivlineSide(los->t2x, los->t2y, (divline_t *) bsp); + + if (side == side2) { + bspnum = bsp->children[side]; // doesn't touch the other side + } + else + { + // the partition plane is crossed here if (!P_CrossBSPNode(bsp->children[side], los)) - return 0; // cross the starting side + { + return false; // cross the starting side + } else - bspnum = bsp->children[side^1]; // cross the ending side + { + bspnum = bsp->children[side ^ 1]; // cross the ending side + } } } - return - P_CrossSubsector((bspnum == -1 ? 0 : bspnum & ~NF_SUBSECTOR), los); + + return P_CrossSubsector((bspnum == -1 ? 0 : bspnum & ~NF_SUBSECTOR), los); } // @@ -493,4 +454,4 @@ boolean P_CheckSight(mobj_t *t1, mobj_t *t2) // the head node is the last node output return P_CrossBSPNode((INT32)numnodes - 1, &los); -} \ No newline at end of file +} -- 2.54.0 From 3080f2953d9f2a841eafa52fa54c8bab716f0712 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 8 Dec 2024 15:26:40 +0100 Subject: [PATCH 125/143] optimized checksight for nametags and camera idk should this be exposed to lua too? --- src/k_kart.c | 2 +- src/p_local.h | 6 +++++- src/p_mobj.c | 2 +- src/p_sight.c | 13 ++++++------- 4 files changed, 13 insertions(+), 10 deletions(-) diff --git a/src/k_kart.c b/src/k_kart.c index 2a348a85b..066c8a4e3 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -9118,7 +9118,7 @@ static void K_drawNameTags(void) distance = R_PointToDist(players[i].mo->x, players[i].mo->y); if (distance > maxdistance) continue; - if (!P_CheckSight(stplyr->mo, players[i].mo)) + if (!P_CheckSightFast(stplyr->mo, players[i].mo)) continue; switch (cv_nametagtrans.value) diff --git a/src/p_local.h b/src/p_local.h index 7cf7c4389..08323e052 100644 --- a/src/p_local.h +++ b/src/p_local.h @@ -364,7 +364,11 @@ boolean P_MoveOrigin(mobj_t *thing, fixed_t x, fixed_t y, fixed_t z); void P_SlideMove(mobj_t *mo, boolean forceslide); void P_BouncePlayerMove(mobj_t *mo); void P_BounceMove(mobj_t *mo); -boolean P_CheckSight(mobj_t *t1, mobj_t *t2); + +#define P_CheckSight(t1, t2) P_CheckSight2(t1, t2, false) +#define P_CheckSightFast(t1, t2) P_CheckSight2(t1, t2, true) +boolean P_CheckSight2(mobj_t *t1, mobj_t *t2, boolean fast); + void P_CheckHoopPosition(mobj_t *hoopthing, fixed_t x, fixed_t y, fixed_t z, fixed_t radius); boolean P_CheckSector(sector_t *sector, boolean crunch); diff --git a/src/p_mobj.c b/src/p_mobj.c index d2ed232e1..7bef4d727 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -3294,7 +3294,7 @@ boolean P_CameraThinker(player_t *player, camera_t *thiscam, boolean resetcalled if (player->pflags & PF_TIMEOVER) player->kartstuff[k_timeovercam] = (2*TICRATE)+1; - if (!resetcalled && !(player->pflags & PF_NOCLIP || leveltime < introtime) && !P_CheckSight(&dummy, player->mo)) // TODO: "P_CheckCameraSight" instead. + if (!resetcalled && !(player->pflags & PF_NOCLIP || leveltime < introtime) && !P_CheckSightFast(&dummy, player->mo)) // TODO: "P_CheckCameraSight" instead. P_ResetCamera(player, thiscam); else P_SlideCameraMove(thiscam); diff --git a/src/p_sight.c b/src/p_sight.c index 5ca186b85..bf98fe470 100644 --- a/src/p_sight.c +++ b/src/p_sight.c @@ -299,15 +299,14 @@ static boolean P_CrossSubsector(size_t num, register los_t *los) // if strace crosses the given node successfully. // // killough 4/20/98: rewritten to remove tail recursion, clean up, and optimize - -static boolean P_CrossBSPNode(INT32 bspnum, register los_t *los) +static boolean P_CrossBSPNode(INT32 bspnum, register los_t *los, boolean fast) { while (!(bspnum & NF_SUBSECTOR)) { register node_t *bsp = nodes + bspnum; - INT32 side = P_DivlineSide(los->strace.x,los->strace.y,(divline_t *)bsp)&1; - INT32 side2 = P_DivlineSide(los->t2x, los->t2y, (divline_t *) bsp); + INT32 side = fast ? R_PointOnSideFast(los->strace.x, los->strace.y, bsp) : (P_DivlineSide(los->strace.x,los->strace.y,(divline_t *)bsp) & 1); + INT32 side2 = fast ? R_PointOnSideFast(los->t2x, los->t2y, bsp) : P_DivlineSide(los->t2x, los->t2y, (divline_t *) bsp); if (side == side2) { @@ -316,7 +315,7 @@ static boolean P_CrossBSPNode(INT32 bspnum, register los_t *los) else { // the partition plane is crossed here - if (!P_CrossBSPNode(bsp->children[side], los)) + if (!P_CrossBSPNode(bsp->children[side], los, fast)) { return false; // cross the starting side } @@ -336,7 +335,7 @@ static boolean P_CrossBSPNode(INT32 bspnum, register los_t *los) // Returns true if a straight line between t1 and t2 is unobstructed. // Uses REJECT. // -boolean P_CheckSight(mobj_t *t1, mobj_t *t2) +boolean P_CheckSight2(mobj_t *t1, mobj_t *t2, boolean fast) { const sector_t *s1, *s2; size_t pnum; @@ -453,5 +452,5 @@ boolean P_CheckSight(mobj_t *t1, mobj_t *t2) } // the head node is the last node output - return P_CrossBSPNode((INT32)numnodes - 1, &los); + return (P_CrossBSPNode((INT32)numnodes - 1, &los, fast)); } -- 2.54.0 From 97cae4de591e14ef3bbb8a54e15410ab0819aed0 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 8 Dec 2024 21:18:39 +0100 Subject: [PATCH 126/143] smol things --- src/k_kart.c | 2 ++ src/p_tick.c | 4 ++-- src/s_sound.c | 5 +---- src/sdl/mixer_sound.c | 1 + 4 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/k_kart.c b/src/k_kart.c index 066c8a4e3..a86d93ff1 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -6039,10 +6039,12 @@ void K_MoveKartPlayer(player_t *player, boolean onground) P_SetScale(overlay, player->mo->scale); } player->kartstuff[k_invincibilitytimer] = itemtime+(2*TICRATE); // 10 seconds + if (P_IsLocalPlayer(player) && cv_supermusic.value == 1 && cv_birdmusic.value) S_ChangeMusicSpecial("kinvnc"); else S_StartSound(player->mo, (cv_kartinvinsfx.value ? sfx_alarmi : sfx_kinvnc)); + P_RestoreMusic(player); K_PlayPowerGloatSound(player->mo); player->kartstuff[k_itemamount]--; diff --git a/src/p_tick.c b/src/p_tick.c index 266defd74..3b0cadde8 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -720,12 +720,12 @@ void P_Ticker(boolean run) continue; const boolean skybox = (skyboxmo[0] && cv_skybox.value); - boolean isSkyVisibleForPlayer = skyVisiblePerPlayer[i]; - if (isSkyVisibleForPlayer && skybox) + if (skyVisiblePerPlayer[i] && skybox) { R_SkyboxFrame(i); } + R_SetupFrame(i, skybox); } } diff --git a/src/s_sound.c b/src/s_sound.c index 122b07525..119b0cbb9 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -1854,10 +1854,7 @@ void S_StopMusic(void) || demo.title) // SRB2Kart: Demos don't interrupt title screen music return; - if (cv_birdmusic.value && (strcasecmp(music_name, mapmusname) == 0)) - mapmusresume = I_GetSongPosition(); - else - mapmusresume = 0; + mapmusresume = (cv_birdmusic.value && (strcasecmp(music_name, mapmusname) == 0)) ? I_GetSongPosition() : 0; if (I_SongPaused()) I_ResumeSong(); diff --git a/src/sdl/mixer_sound.c b/src/sdl/mixer_sound.c index 20cd3107c..ced911eba 100644 --- a/src/sdl/mixer_sound.c +++ b/src/sdl/mixer_sound.c @@ -615,6 +615,7 @@ Countstutter (int len) } else bytes = ( music_bytes - music_stutter_bytes ); + I_SetSongPosition((int)( bytes/4/44100.0*1000 )); } } -- 2.54.0 From 4da9c5ac07074264b5062ac6be9a6aa2144d7598 Mon Sep 17 00:00:00 2001 From: Alug Date: Mon, 9 Dec 2024 10:48:50 +0100 Subject: [PATCH 127/143] "P_CheckSightFast" for lua should be faster than normal P_CheckSight only to be used for things like nametags etc so nothing gameplaywise as it will desynch --- src/lua_baselib.c | 13 +++++++++++++ src/p_sight.c | 6 +++--- 2 files changed, 16 insertions(+), 3 deletions(-) diff --git a/src/lua_baselib.c b/src/lua_baselib.c index 13e578d5c..b1d77d737 100644 --- a/src/lua_baselib.c +++ b/src/lua_baselib.c @@ -1102,6 +1102,18 @@ static int lib_pCheckSight(lua_State *L) return 1; } +// DONT USE THIS FOR ANYTHING GAMEPLAY, THIS WILL DESYNCH! +static int lib_pCheckSightFast(lua_State *L) +{ + mobj_t *t1 = *((mobj_t **)luaL_checkudata(L, 1, META_MOBJ)); + mobj_t *t2 = *((mobj_t **)luaL_checkudata(L, 2, META_MOBJ)); + //HUDSAFE? + if (!t1 || !t2) + return LUA_ErrInvalid(L, "mobj_t"); + lua_pushboolean(L, P_CheckSightFast(t1, t2)); + return 1; +} + static int lib_pCheckHoopPosition(lua_State *L) { mobj_t *hoopthing = *((mobj_t **)luaL_checkudata(L, 1, META_MOBJ)); @@ -3154,6 +3166,7 @@ static luaL_Reg lib[] = { {"P_SlideMove",lib_pSlideMove}, {"P_BounceMove",lib_pBounceMove}, {"P_CheckSight", lib_pCheckSight}, + {"P_CheckSightFast", lib_pCheckSightFast}, {"P_CheckHoopPosition",lib_pCheckHoopPosition}, {"P_RadiusAttack",lib_pRadiusAttack}, {"P_FloorzAtPos",lib_pFloorzAtPos}, diff --git a/src/p_sight.c b/src/p_sight.c index bf98fe470..1d71e5553 100644 --- a/src/p_sight.c +++ b/src/p_sight.c @@ -305,8 +305,8 @@ static boolean P_CrossBSPNode(INT32 bspnum, register los_t *los, boolean fast) { register node_t *bsp = nodes + bspnum; - INT32 side = fast ? R_PointOnSideFast(los->strace.x, los->strace.y, bsp) : (P_DivlineSide(los->strace.x,los->strace.y,(divline_t *)bsp) & 1); - INT32 side2 = fast ? R_PointOnSideFast(los->t2x, los->t2y, bsp) : P_DivlineSide(los->t2x, los->t2y, (divline_t *) bsp); + INT32 side = (fast ? R_PointOnSideFast(los->strace.x, los->strace.y, bsp) : (P_DivlineSide(los->strace.x,los->strace.y, (divline_t *)bsp) & 1)); + INT32 side2 = (fast ? R_PointOnSideFast(los->t2x, los->t2y, bsp) : P_DivlineSide(los->t2x, los->t2y, (divline_t *) bsp)); if (side == side2) { @@ -321,7 +321,7 @@ static boolean P_CrossBSPNode(INT32 bspnum, register los_t *los, boolean fast) } else { - bspnum = bsp->children[side ^ 1]; // cross the ending side + bspnum = bsp->children[side^1]; // cross the ending side } } } -- 2.54.0 From f6f66001184ed7018ce2857b978aab16065720a7 Mon Sep 17 00:00:00 2001 From: Alug Date: Mon, 9 Dec 2024 23:19:58 +0100 Subject: [PATCH 128/143] interp.subsector is unused so dont need to assign it nor call pointinsubsector for nothing --- src/r_fps.c | 10 ++++------ src/r_fps.h | 2 +- 2 files changed, 5 insertions(+), 7 deletions(-) diff --git a/src/r_fps.c b/src/r_fps.c index 4dd7fa044..4d74da5a2 100644 --- a/src/r_fps.c +++ b/src/r_fps.c @@ -301,7 +301,7 @@ void R_InterpolateMobjState(mobj_t *mobj, fixed_t frac, interpmobjstate_t *out) out->y = mobj->y; out->z = mobj->z; out->scale = mobj->scale; - out->subsector = mobj->subsector; + //out->subsector = mobj->subsector; out->angle = mobj->player ? mobj->player->frameangle : mobj->angle; out->pitch = mobj->pitch; out->roll = mobj->roll; @@ -322,8 +322,7 @@ void R_InterpolateMobjState(mobj_t *mobj, fixed_t frac, interpmobjstate_t *out) out->spritexoffset = mobj->resetinterp ? mobj->spritexoffset : R_LerpFixed(mobj->old_spritexoffset, mobj->spritexoffset, frac); out->spriteyoffset = mobj->resetinterp ? mobj->spriteyoffset : R_LerpFixed(mobj->old_spriteyoffset, mobj->spriteyoffset, frac); out->scale = mobj->resetinterp ? mobj->scale : R_LerpFixed(mobj->old_scale, mobj->scale, frac); - //out->subsector = R_PointInSubsector(out->x, out->y); // why was this even done? - out->subsector = mobj->subsector; + //out->subsector = R_PointInSubsector(out->x, out->y); // this is unused if (mobj->player) out->angle = mobj->resetinterp ? mobj->player->frameangle : R_LerpAngle(mobj->player->old_frameangle, mobj->player->frameangle, frac); @@ -359,7 +358,7 @@ void R_InterpolatePrecipMobjState(precipmobj_t *mobj, fixed_t frac, interpmobjst out->y = mobj->y; out->z = mobj->z; out->scale = cv_mobjscaleprecip.value ? mapobjectscale : FRACUNIT; - out->subsector = mobj->subsector; + //out->subsector = mobj->subsector; out->angle = mobj->angle; out->spritexscale = mobj->spritexscale; out->spriteyscale = mobj->spriteyscale; @@ -376,9 +375,8 @@ void R_InterpolatePrecipMobjState(precipmobj_t *mobj, fixed_t frac, interpmobjst out->spriteyscale = mobj->spriteyscale; out->spritexoffset = mobj->spritexoffset; out->spriteyoffset = mobj->spriteyoffset; + //out->subsector = R_PointInSubsector(out->x, out->y); // this is unused - //out->subsector = R_PointInSubsector(out->x, out->y); // i dont understand lol - out->subsector = mobj->subsector; out->angle = R_LerpAngle(mobj->old_angle, mobj->angle, frac); } diff --git a/src/r_fps.h b/src/r_fps.h index a4aef71cd..5ac6cfe90 100644 --- a/src/r_fps.h +++ b/src/r_fps.h @@ -59,7 +59,7 @@ typedef struct { fixed_t x; fixed_t y; fixed_t z; - subsector_t *subsector; + //subsector_t *subsector; angle_t angle; fixed_t scale; fixed_t spritexscale; -- 2.54.0 From 83b6a63f13f46a344ad158578feb873f595f5a67 Mon Sep 17 00:00:00 2001 From: Alug Date: Mon, 9 Dec 2024 22:36:30 +0100 Subject: [PATCH 129/143] dont pass fwrapv to compiler flags this technically changes behavior of some things, even if it MAY fix some undefined behaviour --- src/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Makefile b/src/Makefile index 4df4e1fe8..ccfe7603e 100644 --- a/src/Makefile +++ b/src/Makefile @@ -298,7 +298,7 @@ else $(OBJDIR)/hw_md2load.o $(OBJDIR)/hw_md3load.o $(OBJDIR)/hw_model.o $(OBJDIR)/u_list.o $(OBJDIR)/hw_batching.o $(OBJDIR)/hw_shaders.o endif -OPTS += -DCOMPVERSION -fwrapv +OPTS += -DCOMPVERSION ifndef NONX86 ifndef GCC29 -- 2.54.0 From 3b64263dc649043a2ef0853d56fdd44468cd0b52 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 10 Dec 2024 21:16:06 +0100 Subject: [PATCH 130/143] Unconditionally interpolate view even if it may NOT change but i get the feeling it may cause some issues --- src/r_fps.c | 23 ++++++++++++++++------- 1 file changed, 16 insertions(+), 7 deletions(-) diff --git a/src/r_fps.c b/src/r_fps.c index 4d74da5a2..3dab44398 100644 --- a/src/r_fps.c +++ b/src/r_fps.c @@ -91,6 +91,15 @@ static levelinterpolator_t **levelinterpolators; static size_t levelinterpolators_len; static size_t levelinterpolators_size; +static inline fixed_t R_LerpFixedView(fixed_t from, fixed_t to, fixed_t frac) +{ + return from + FixedMul(frac, to - from); +} + +static inline angle_t R_LerpAngleView(angle_t from, angle_t to, fixed_t frac) +{ + return from + FixedMul(frac, to - from); +} static inline fixed_t R_LerpFixed(fixed_t from, fixed_t to, fixed_t frac) { @@ -153,7 +162,7 @@ static void R_SetupFreelook(void) void R_InterpolateViewRollAngle(fixed_t frac) { - viewroll = R_LerpAngle(oldview->roll, newview->roll, frac); + viewroll = R_LerpAngleView(oldview->roll, newview->roll, frac); } void R_InterpolateView(fixed_t frac, boolean forceinvalid) @@ -181,13 +190,13 @@ void R_InterpolateView(fixed_t frac, boolean forceinvalid) prevview = newview; } - viewx = R_LerpFixed(prevview->x, newview->x, frac); - viewy = R_LerpFixed(prevview->y, newview->y, frac); - viewz = R_LerpFixed(prevview->z, newview->z, frac); + viewx = R_LerpFixedView(prevview->x, newview->x, frac); + viewy = R_LerpFixedView(prevview->y, newview->y, frac); + viewz = R_LerpFixedView(prevview->z, newview->z, frac); - viewangle = R_LerpAngle(prevview->angle, newview->angle, frac); - aimingangle = R_LerpAngle(prevview->aim, newview->aim, frac); - viewroll = R_LerpAngle(prevview->roll, newview->roll, frac); + viewangle = R_LerpAngleView(prevview->angle, newview->angle, frac); + aimingangle = R_LerpAngleView(prevview->aim, newview->aim, frac); + viewroll = R_LerpAngleView(prevview->roll, newview->roll, frac); viewsin = FINESINE(viewangle>>ANGLETOFINESHIFT); viewcos = FINECOSINE(viewangle>>ANGLETOFINESHIFT); -- 2.54.0 From 727a31fdb5618abdf67ca26be176719ff6c057c5 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 10 Dec 2024 21:17:50 +0100 Subject: [PATCH 131/143] one line those --- src/r_fps.c | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/src/r_fps.c b/src/r_fps.c index 3dab44398..637ce1cf4 100644 --- a/src/r_fps.c +++ b/src/r_fps.c @@ -103,16 +103,12 @@ static inline angle_t R_LerpAngleView(angle_t from, angle_t to, fixed_t frac) static inline fixed_t R_LerpFixed(fixed_t from, fixed_t to, fixed_t frac) { - if (from == to) - return to; - return from + FixedMul(frac, to - from); + return ((from == to) ? to : from + FixedMul(frac, to - from)); } static inline angle_t R_LerpAngle(angle_t from, angle_t to, fixed_t frac) { - if (from == to) - return to; - return from + FixedMul(frac, to - from); + return ((from == to) ? to : from + FixedMul(frac, to - from)); } /*static vector2_t *R_LerpVector2(const vector2_t *from, const vector2_t *to, fixed_t frac, vector2_t *out) -- 2.54.0 From 0eaedd4b5efaf5a8a0ee565acbd703750447da17 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 11 Dec 2024 01:25:29 +0100 Subject: [PATCH 132/143] "extra safety" --- src/r_fps.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/r_fps.c b/src/r_fps.c index 637ce1cf4..b861dea56 100644 --- a/src/r_fps.c +++ b/src/r_fps.c @@ -103,12 +103,12 @@ static inline angle_t R_LerpAngleView(angle_t from, angle_t to, fixed_t frac) static inline fixed_t R_LerpFixed(fixed_t from, fixed_t to, fixed_t frac) { - return ((from == to) ? to : from + FixedMul(frac, to - from)); + return ((from == to) ? to : (from + FixedMul(frac, to - from))); } static inline angle_t R_LerpAngle(angle_t from, angle_t to, fixed_t frac) { - return ((from == to) ? to : from + FixedMul(frac, to - from)); + return ((from == to) ? to : (from + FixedMul(frac, to - from))); } /*static vector2_t *R_LerpVector2(const vector2_t *from, const vector2_t *to, fixed_t frac, vector2_t *out) -- 2.54.0 From 91b6143f15b6efa8be44c6e9af6a3d1d79b29a9c Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 10 Dec 2024 22:15:53 +0100 Subject: [PATCH 133/143] clean up this stuff; make splitwall behave more like vanilla changes some splitwall issues slightly but gives bit better performance in some cases --- src/hardware/hw_main.c | 47 ++++++++++++++++-------------------------- 1 file changed, 18 insertions(+), 29 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 5e24e6eae..0ab84f345 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -505,7 +505,6 @@ static void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, bool if (!xsub->planepoly) return; - pv = xsub->planepoly->pts; nrPlaneVerts = xsub->planepoly->numpts; if (nrPlaneVerts < 3) //not even a triangle ? @@ -575,6 +574,8 @@ static void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, bool break; } + pv = xsub->planepoly->pts; + // reference point for flat texture coord for each vertex around the polygon flatxref = (float)(((fixed_t)pv->x & (~flatflag)) / fflatsize); flatyref = (float)(((fixed_t)pv->y & (~flatflag)) / fflatsize); @@ -1008,20 +1009,12 @@ static void HWR_SplitWall(sector_t *sector, FOutVector *wallVerts, INT32 texnum, endbheight = endrealbot; } - if (endbheight > endtop) - endbot = endtop; - - if (bheight >= top) + if (endbheight >= endtop && bheight >= top) continue; // Found a break - // The heights are clamped to ensure the polygon doesn't cross itself. - bot = bheight; - - if (bot < realbot) - bot = realbot; - - endbot = min(max(endbheight, endrealbot), endtop); + bot = max(bheight, realbot); + endbot = max(endbheight, endrealbot); Surf->PolyColor.s.alpha = alpha; @@ -1150,7 +1143,7 @@ static void HWR_DrawSkyWall(FOutVector *wallVerts, FSurfaceInfo *Surf) } // Returns true if the midtexture is visible, and false if... it isn't... -static boolean HWR_BlendMidtextureSurface(FSurfaceInfo *pSurf) +static inline boolean HWR_BlendMidtextureSurface(FSurfaceInfo *pSurf) { FUINT blendmode = PF_Masked; @@ -1188,23 +1181,16 @@ static boolean HWR_BlendMidtextureSurface(FSurfaceInfo *pSurf) case 908: blendmode = HWR_TranstableToAlpha(tr_trans90, pSurf); break; - // Translucent + // Translucent linedef types case 102: - case 121: - case 123: - case 124: - case 125: - case 141: - case 142: - case 144: - case 145: + case 121 ... 125: + case 141 ... 145: case 174: case 175: case 192: case 195: case 221: - case 253: - case 256: + case 253 ... 256: blendmode = PF_Translucent; break; default: @@ -1216,9 +1202,10 @@ static boolean HWR_BlendMidtextureSurface(FSurfaceInfo *pSurf) { // Polyobject translucency is shared between all of its lines if (gl_curline->polyseg->translucency >= NUMTRANSMAPS) // wall not drawn + { + pSurf->PolyColor.s.alpha = 0x00; // This shouldn't draw anything regardless of blendmode return false; - //Surf.PolyColor.s.alpha = 0x00; // This shouldn't draw anything regardless of blendmode - //blendmode = PF_Masked; + } else blendmode = HWR_TranstableToAlpha(gl_curline->polyseg->translucency, pSurf); } @@ -1315,7 +1302,9 @@ void HWR_ProcessSeg(void) // Sort of like GLWall::Process in GZDoom lightnum = (HWR_ShouldUsePaletteRendering() && colormap) ? lightnum : HWR_CalcWallLight(lightnum, gl_curline); FSurfaceInfo Surf; - Surf.PolyColor.s.alpha = 255; + + if (gl_frontsector) + Surf.PolyColor.s.alpha = 255; INT32 gl_midtexture = R_GetTextureNum(gl_sidedef->midtexture); GLMapTexture_t *glTex = NULL; @@ -1711,6 +1700,8 @@ void HWR_ProcessSeg(void) // Sort of like GLWall::Process in GZDoom // Single sided line... Deal only with the middletexture (if one exists) if (gl_midtexture && gl_linedef->special != HORIZONSPECIAL) // Ignore horizon line for OGL { + glTex = HWR_GetTexture(gl_midtexture, noencore); + fixed_t texturevpeg; // PEGGING @@ -1721,8 +1712,6 @@ void HWR_ProcessSeg(void) // Sort of like GLWall::Process in GZDoom else texturevpeg = gl_sidedef->rowoffset; // top of texture at top - glTex = HWR_GetTexture(gl_midtexture, noencore); - wallVerts[3].t = wallVerts[2].t = texturevpeg * glTex->scaleY; wallVerts[0].t = wallVerts[1].t = (texturevpeg + gl_frontsector->ceilingheight - gl_frontsector->floorheight) * glTex->scaleY; wallVerts[0].s = wallVerts[3].s = cliplow * glTex->scaleX; -- 2.54.0 From a05c38b1fe85484797a4651402a94531cbdce2ee Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 10 Dec 2024 22:20:44 +0100 Subject: [PATCH 134/143] those should better be clamped oops --- src/hardware/hw_main.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 0ab84f345..4c10a2af4 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -1013,8 +1013,9 @@ static void HWR_SplitWall(sector_t *sector, FOutVector *wallVerts, INT32 texnum, continue; // Found a break - bot = max(bheight, realbot); - endbot = max(endbheight, endrealbot); + // The heights are clamped to ensure the polygon doesn't cross itself. + bot = CLAMP(bheight,realbot , top); + endbot = CLAMP(endbheight, endrealbot, endtop); Surf->PolyColor.s.alpha = alpha; -- 2.54.0 From dbe5f8a4ba716a1e62a09e683d75072db4129d56 Mon Sep 17 00:00:00 2001 From: Alug Date: Tue, 10 Dec 2024 23:06:08 +0100 Subject: [PATCH 135/143] clamp splitsprite heights aswell --- src/hardware/hw_main.c | 27 +++++++++++---------------- 1 file changed, 11 insertions(+), 16 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 4c10a2af4..fa2f9cfb7 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -943,7 +943,7 @@ static void HWR_SplitWall(sector_t *sector, FOutVector *wallVerts, INT32 texnum, for (INT32 i = 0; i < sector->numlights; i++) { - if (endtop < endrealbot && top < realbot) + if ((endtop < endrealbot) && (top < realbot)) return; lightlist_t *list = sector->lightlist; @@ -1009,12 +1009,12 @@ static void HWR_SplitWall(sector_t *sector, FOutVector *wallVerts, INT32 texnum, endbheight = endrealbot; } - if (endbheight >= endtop && bheight >= top) + if ((endbheight >= endtop) && (bheight >= top)) continue; // Found a break // The heights are clamped to ensure the polygon doesn't cross itself. - bot = CLAMP(bheight,realbot , top); + bot = CLAMP(bheight, realbot, top); endbot = CLAMP(endbheight, endrealbot, endtop); Surf->PolyColor.s.alpha = alpha; @@ -1043,7 +1043,7 @@ static void HWR_SplitWall(sector_t *sector, FOutVector *wallVerts, INT32 texnum, bot = realbot; endbot = endrealbot; - if (endtop <= endrealbot && top <= realbot) + if ((endtop <= endrealbot) && (top <= realbot)) return; Surf->PolyColor.s.alpha = alpha; @@ -3621,7 +3621,7 @@ static void HWR_SplitSprite(gl_vissprite_t *spr, const boolean papersprite) for (i = 0; i < sector->numlights; i++) { - if (endtop < endrealbot && top < realbot) + if ((endtop < endrealbot) && (top < realbot)) return; // even if we aren't changing colormap or lightlevel, we still need to continue drawing down the sprite @@ -3645,18 +3645,13 @@ static void HWR_SplitSprite(gl_vissprite_t *spr, const boolean papersprite) endbheight = endrealbot; } - if (endbheight >= endtop && bheight >= top) + if ((endbheight >= endtop) && (bheight >= top)) continue; - bot = bheight; - - if (bot < realbot) - bot = realbot; - - endbot = endbheight; - - if (endbot < endrealbot) - endbot = endrealbot; + // Found a break + // The heights are clamped to ensure the polygon doesn't cross itself. + bot = CLAMP(bheight, realbot, top); + endbot = CLAMP(endbheight, endrealbot, endtop); wallVerts[3].t = towtop + ((realtop - top) * towmult); wallVerts[2].t = towtop + ((endrealtop - endtop) * towmult); @@ -3704,7 +3699,7 @@ static void HWR_SplitSprite(gl_vissprite_t *spr, const boolean papersprite) bot = realbot; endbot = endrealbot; - if (endtop <= endrealbot && top <= realbot) + if ((endtop <= endrealbot) && (top <= realbot)) return; // If we're ever down here, somehow the above loop hasn't draw all the light levels of sprite -- 2.54.0 From f8dfc954a0351d4d57c806404f48b6a2304be64a Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 11 Dec 2024 00:32:34 +0100 Subject: [PATCH 136/143] test "or" --- src/hardware/hw_main.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index fa2f9cfb7..5e45a9163 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -1009,7 +1009,10 @@ static void HWR_SplitWall(sector_t *sector, FOutVector *wallVerts, INT32 texnum, endbheight = endrealbot; } - if ((endbheight >= endtop) && (bheight >= top)) + if (endbheight >= endtop) + continue; + + if (bheight >= top) continue; // Found a break @@ -3645,7 +3648,10 @@ static void HWR_SplitSprite(gl_vissprite_t *spr, const boolean papersprite) endbheight = endrealbot; } - if ((endbheight >= endtop) && (bheight >= top)) + if (endbheight >= endtop) + continue; + + if (bheight >= top) continue; // Found a break -- 2.54.0 From 0e1bfbb0b5f97a9f1fc5d4e03cc4f5b4269b8568 Mon Sep 17 00:00:00 2001 From: Alug Date: Wed, 11 Dec 2024 23:23:27 +0100 Subject: [PATCH 137/143] clean up hw_cache stuff + fix accidental wrong cast --- src/hardware/hw_cache.c | 46 +++++++++++++++++++++-------------------- 1 file changed, 24 insertions(+), 22 deletions(-) diff --git a/src/hardware/hw_cache.c b/src/hardware/hw_cache.c index 652e1e903..b058bde99 100644 --- a/src/hardware/hw_cache.c +++ b/src/hardware/hw_cache.c @@ -54,10 +54,10 @@ static INT32 format2bpp(GLTextureFormat_t format) // It is now split from it for my sanity! (and the sanity of others) // -- Monster Iestyn (13/02/19) static void HWR_DrawColumnInCache(const column_t *patchcol, UINT8 *block, GLMipmap_t *mipmap, - INT32 pblockheight, INT32 blockmodulo, - fixed_t yfracstep, fixed_t scale_y, - texpatch_t *originPatch, INT32 patchheight, - INT32 bpp, RGBA_t *palette) + INT32 pblockheight, INT32 blockmodulo, + fixed_t yfracstep, fixed_t scale_y, + texpatch_t *originPatch, INT32 patchheight, + INT32 bpp, RGBA_t *palette) { fixed_t yfrac, position, count; UINT8 *dest; @@ -73,9 +73,6 @@ static void HWR_DrawColumnInCache(const column_t *patchcol, UINT8 *block, GLMipm (void)patchheight; // This parameter is unused - if (!mipmap || mipmap == NULL) - return; - if (originPatch) // originPatch can be NULL here, unlike in the software version originy = originPatch->originy; @@ -111,10 +108,10 @@ static void HWR_DrawColumnInCache(const column_t *patchcol, UINT8 *block, GLMipm count--; texel = source[yfrac>>FRACBITS]; - alpha = 0xff; + alpha = 0xFF; - //Hurdler: not perfect, but better than holes - if (texel == HWR_PATCHES_CHROMAKEY_COLORINDEX && (mipmap->flags & TF_CHROMAKEYED)) + // Make pixel transparent if chroma keyed + if ((mipmap->flags & TF_CHROMAKEYED) && (texel == HWR_PATCHES_CHROMAKEY_COLORINDEX)) alpha = 0x00; //Hurdler: 25/04/2000: now support colormap in hardware mode @@ -126,7 +123,8 @@ static void HWR_DrawColumnInCache(const column_t *patchcol, UINT8 *block, GLMipm // Alam: SRB2 uses Mingw, HUGS switch (bpp) { - case 2 : texelu16 = (UINT16)((alpha<<8) | texel); + case 2 : // uhhhhhhhh.......... + texelu16 = (UINT16)((alpha<<8) | texel); memcpy(dest, &texelu16, sizeof(UINT16)); break; case 3 : colortemp = palette[texel]; @@ -144,6 +142,7 @@ static void HWR_DrawColumnInCache(const column_t *patchcol, UINT8 *block, GLMipm dest += blockmodulo; yfrac += yfracstep; } + patchcol = (const column_t *)((const UINT8 *)patchcol + patchcol->length + 4); } } @@ -185,6 +184,7 @@ static void HWR_DrawPatchInCache(GLMipmap_t *mipmap, if (bpp < 1 || bpp > 4) I_Error("HWR_DrawPatchInCache: no drawer defined for this bpp (%d)\n",bpp); + // NOTE: should this actually be pblockwidth*bpp? blockmodulo = pblockwidth*bpp; // Draw each column to the block cache @@ -263,6 +263,7 @@ static void HWR_DrawTexturePatchInCache(GLMipmap_t *mipmap, if (bpp < 1 || bpp > 4) I_Error("HWR_DrawTexturePatchInCache: no drawer defined for this bpp (%d)\n",bpp); + // NOTE: should this actually be pblockwidth*bpp? blockmodulo = pblockwidth*bpp; // Draw each column to the block cache @@ -336,8 +337,8 @@ static void HWR_GenerateTexture(INT32 texnum, GLMapTexture_t *gltex, boolean noe else gltex->mipmap.flags = TF_CHROMAKEYED | TF_WRAPXY; - gltex->mipmap.width = SHORT(texture->width); - gltex->mipmap.height = SHORT(texture->height); + gltex->mipmap.width = (UINT16)(texture->width); + gltex->mipmap.height = (UINT16)(texture->height); if (skyspecial) gltex->mipmap.format = GL_TEXFMT_RGBA; // that skyspecial code below assumes this format ... @@ -362,14 +363,17 @@ static void HWR_GenerateTexture(INT32 texnum, GLMapTexture_t *gltex, boolean noe RGBA_t col; col = palette[HWR_CHROMAKEY_EQUIVALENTCOLORINDEX]; + for (j = 0; j < blockheight; j++) { for (i = 0; i < blockwidth; i++) { - block[4*(j*blockwidth+i)+0] = col.s.red; - block[4*(j*blockwidth+i)+1] = col.s.green; - block[4*(j*blockwidth+i)+2] = col.s.blue; - block[4*(j*blockwidth+i)+3] = 0xff; + int idx = (j*blockwidth+i); + + block[4*idx+0] = col.s.red; + block[4*idx+1] = col.s.green; + block[4*idx+2] = col.s.blue; + block[4*idx+3] = 0xff; } } } @@ -378,15 +382,12 @@ static void HWR_GenerateTexture(INT32 texnum, GLMapTexture_t *gltex, boolean noe for (i = 0, patch = texture->patches; i < texture->patchcount; i++, patch++) { realpatch = W_CacheLumpNumPwad(patch->wad, patch->lump, PU_CACHE); - HWR_DrawTexturePatchInCache(&gltex->mipmap, - blockwidth, blockheight, - texture, patch, - realpatch); + HWR_DrawTexturePatchInCache(&gltex->mipmap, blockwidth, blockheight, texture, patch, realpatch); Z_ChangeTag(realpatch, PU_HWRCACHE_UNLOCKED); } //Hurdler: not efficient at all but I don't remember exactly how HWR_DrawPatchInCache works :( - if (format2bpp(gltex->mipmap.format)==4) + if (format2bpp(gltex->mipmap.format) == 4) { for (i = 3; i < blocksize*4; i += 4) // blocksize*4 because blocksize doesn't include the bpp { @@ -437,6 +438,7 @@ void HWR_MakePatch (patch_t *patch, GLPatch_t *glPatch, GLMipmap_t *glMipmap, bo if (makebitmap) { MakeBlock(glMipmap); + HWR_DrawPatchInCache(glMipmap, glMipmap->width, glMipmap->height, glPatch->width, glPatch->height, -- 2.54.0 From 7ae361cb7c40d1a67ad3cb301fcb8c0d7f8938ad Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 12 Dec 2024 00:11:42 +0100 Subject: [PATCH 138/143] better cv_lessprecip handling idk what i was thinking lmao --- src/p_mobj.c | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/src/p_mobj.c b/src/p_mobj.c index 7bef4d727..b7c86cbd5 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -10201,19 +10201,26 @@ void P_SpawnPrecipitation(void) if (dedicated || !cv_drawdist_precip.value || curWeather == PRECIP_NONE) // SRB2Kart return; + fixed_t density = (cv_mobjscaleprecip.value ? mapobjectscale : FRACUNIT); + + if (cv_lessprecip.value) + density *= 2; // just spawn half the precip + // Use the blockmap to narrow down our placing patterns for (i = 0; i < bmapwidth*bmapheight; ++i) { basex = bmaporgx + (i % bmapwidth) * MAPBLOCKSIZE; basey = bmaporgy + (i / bmapwidth) * MAPBLOCKSIZE; - for (j = 0; j < FRACUNIT; j += cv_mobjscaleprecip.value ? mapobjectscale : FRACUNIT) + // If mobjscale < FRACUNIT, each blockmap cell covers + // more area so spawn more precipitation in that area. + for (j = 0; j < FRACUNIT; j += density) { INT32 floorz; INT32 ceilingz; - x = ((cv_lessprecip.value ? basex*1.5 : basex) + ((M_RandomKey(MAPBLOCKUNITS<<3)<>3)); - y = ((cv_lessprecip.value ? basey*1.5 : basey) + ((M_RandomKey(MAPBLOCKUNITS<<3)<>3)); + x = basex + ((M_RandomKey(MAPBLOCKUNITS << 3) << FRACBITS) >> 3); + y = basey + ((M_RandomKey(MAPBLOCKUNITS << 3) << FRACBITS) >> 3); precipsector = R_IsPointInSubsector(x, y); -- 2.54.0 From 13ad27bc9065a407642c6747d2a90e74b995fc26 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 12 Dec 2024 00:30:37 +0100 Subject: [PATCH 139/143] remove some precip code dupe --- src/p_spec.c | 89 ++++++++++++++++++---------------------------------- 1 file changed, 31 insertions(+), 58 deletions(-) diff --git a/src/p_spec.c b/src/p_spec.c index 2ab2c20df..2472c5dbf 100644 --- a/src/p_spec.c +++ b/src/p_spec.c @@ -1807,27 +1807,23 @@ void P_SwitchWeather(INT32 weathernum) precipmobj = (precipmobj_t *)think; + mobjtype_t type = 0; + INT32 z = 0; + + if (swap == PRECIP_BLANK || swap == PRECIP_STORM_NORAIN) // Remove precip, but keep it around for reuse. + { + precipmobj->precipflags |= PCF_INVISIBLE; + continue; + } + if (swap == PRECIP_RAIN) // Snow To Rain { - precipmobj->type = MT_RAIN; // proper set the type - precipmobj->info = &mobjinfo[MT_RAIN]; - precipmobj->flags = mobjinfo[MT_RAIN].flags; - st = &states[mobjinfo[MT_RAIN].spawnstate]; - precipmobj->state = st; - precipmobj->tics = st->tics; - precipmobj->sprite = st->sprite; - precipmobj->frame = st->frame; - precipmobj->momz = cv_mobjscaleprecip.value ? FixedMul(mobjinfo[MT_RAIN].speed, mapobjectscale) : mobjinfo[MT_RAIN].speed; - - precipmobj->precipflags &= ~(PCF_INVISIBLE|PCF_SPLASH); // P_PrecipThinker will add this again if it needs to + type = MT_RAIN; } else if (swap == PRECIP_SNOW) // Rain To Snow { - INT32 z; + type = MT_SNOWFLAKE; - precipmobj->type = MT_SNOWFLAKE; // proper set the type - precipmobj->info = &mobjinfo[MT_SNOWFLAKE]; - precipmobj->flags = mobjinfo[MT_SNOWFLAKE].flags; z = M_RandomByte(); if (z < 64) @@ -1836,92 +1832,69 @@ void P_SwitchWeather(INT32 weathernum) z = 1; else z = 0; - - st = &states[mobjinfo[MT_SNOWFLAKE].spawnstate+z]; - precipmobj->state = st; - precipmobj->tics = st->tics; - precipmobj->sprite = st->sprite; - precipmobj->frame = st->frame; - precipmobj->momz = cv_mobjscaleprecip.value ? FixedMul(mobjinfo[MT_SNOWFLAKE].speed, mapobjectscale) : mobjinfo[MT_SNOWFLAKE].speed; - - precipmobj->precipflags &= ~(PCF_INVISIBLE|PCF_SPLASH); // P_PrecipThinker will add this again if it needs to - } - else if (swap == PRECIP_BLANK || swap == PRECIP_STORM_NORAIN) // Remove precip, but keep it around for reuse. - { - precipmobj->precipflags |= PCF_INVISIBLE; } + + precipmobj->type = type; // proper set the type + precipmobj->info = &mobjinfo[type]; + precipmobj->flags = mobjinfo[type].flags; + + st = &states[mobjinfo[type].spawnstate+z]; + + precipmobj->state = st; + precipmobj->tics = st->tics; + precipmobj->sprite = st->sprite; + precipmobj->frame = st->frame; + precipmobj->momz = (cv_mobjscaleprecip.value ? FixedMul(mobjinfo[type].speed, mapobjectscale) : mobjinfo[type].speed); + + precipmobj->precipflags &= ~(PCF_INVISIBLE|PCF_SPLASH); // P_PrecipThinker will add this again if it needs to } } + boolean dontspawn = false; + switch (weathernum) { case PRECIP_SNOW: // snow curWeather = PRECIP_SNOW; - - if (!swap) - P_SpawnPrecipitation(); - break; case PRECIP_RAIN: // rain { - boolean dontspawn = false; - if (curWeather == PRECIP_RAIN || curWeather == PRECIP_STORM || curWeather == PRECIP_STORM_NOSTRIKES) dontspawn = true; curWeather = PRECIP_RAIN; - - if (!dontspawn && !swap) - P_SpawnPrecipitation(); - break; } case PRECIP_STORM: // storm { - boolean dontspawn = false; - if (curWeather == PRECIP_RAIN || curWeather == PRECIP_STORM || curWeather == PRECIP_STORM_NOSTRIKES) dontspawn = true; curWeather = PRECIP_STORM; - - if (!dontspawn && !swap) - P_SpawnPrecipitation(); - break; } case PRECIP_STORM_NOSTRIKES: // storm w/o lightning { - boolean dontspawn = false; - if (curWeather == PRECIP_RAIN || curWeather == PRECIP_STORM || curWeather == PRECIP_STORM_NOSTRIKES) dontspawn = true; curWeather = PRECIP_STORM_NOSTRIKES; - - if (!dontspawn && !swap) - P_SpawnPrecipitation(); - break; } case PRECIP_STORM_NORAIN: // storm w/o rain curWeather = PRECIP_STORM_NORAIN; - - if (!swap) - P_SpawnPrecipitation(); - break; case PRECIP_BLANK: curWeather = PRECIP_BLANK; - - if (!swap) - P_SpawnPrecipitation(); - break; default: + dontspawn = true; curWeather = PRECIP_NONE; break; } + + if (!dontspawn && !swap) + P_SpawnPrecipitation(); } /** Gets an object. -- 2.54.0 From 7b550200f05c8a9e436617a708774f77c5e35ef9 Mon Sep 17 00:00:00 2001 From: Indev Date: Thu, 12 Dec 2024 17:52:36 +0300 Subject: [PATCH 140/143] Change gl_extension to use glGetStringi instead of glGetString --- src/hardware/hw_main.c | 5 +++-- src/hardware/r_opengl/ogl_win.c | 22 ++++++++++++++++---- src/hardware/r_opengl/r_opengl.c | 35 ++++++++++++-------------------- src/hardware/r_opengl/r_opengl.h | 7 +++++-- src/sdl/ogl_sdl.c | 19 ++++++++++++++--- 5 files changed, 55 insertions(+), 33 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 3a9cc3319..ef2a4cd72 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -5623,7 +5623,6 @@ static void COM_HWR_glinfo(void) CONS_Printf("Unrecognized argument: %s\n", argv); return; } - } CONS_Printf("\x88OpenGL %s\x80\n", gl_version); @@ -5633,7 +5632,9 @@ static void COM_HWR_glinfo(void) CONS_Printf("%u GL extensions present.\n", gl_num_extensions); if (list_extensions) { - CONS_Printf("%s\n", gl_extensions); + for (GLuint i = 0; i < gl_num_extensions; ++i) + CONS_Printf("%s ", gl_extensions[i]); + CONS_Printf("\n"); } else { diff --git a/src/hardware/r_opengl/ogl_win.c b/src/hardware/r_opengl/ogl_win.c index 8ce44d788..782010ce9 100644 --- a/src/hardware/r_opengl/ogl_win.c +++ b/src/hardware/r_opengl/ogl_win.c @@ -55,6 +55,7 @@ PFNWGLEXTSWAPCONTROLPROC wglSwapIntervalEXT = NULL; PFNglClear pglClear; PFNglGetIntegerv pglGetIntegerv; PFNglGetString pglGetString; +PFNglGetStringi pglGetStringi; #define MAX_VIDEO_MODES 32 static vmode_t video_modes[MAX_VIDEO_MODES]; @@ -323,7 +324,16 @@ static INT32 WINAPI SetRes(viddef_t *lvid, vmode_t *pcurrentmode) } } - gl_extensions = pglGetString(GL_EXTENSIONS); + pglGetIntegerv(GL_NUM_EXTENSIONS, (GLint*)&gl_num_extensions); + + if (gl_extensions != NULL) + free(gl_extensions); + + gl_extensions = calloc(gl_num_extensions, sizeof(GLubyte*)); + + for (GLuint i = 0; i < gl_num_extensions; ++i) + gl_extensions[i] = pglGetStringi(GL_EXTENSIONS, i); + // Get info and extensions. //BP: why don't we make it earlier ? //Hurdler: we cannot do that before intialising gl context @@ -331,7 +341,11 @@ static INT32 WINAPI SetRes(viddef_t *lvid, vmode_t *pcurrentmode) DBG_Printf("Vendor : %s\n", pglGetString(GL_VENDOR)); DBG_Printf("Renderer : %s\n", renderer); DBG_Printf("Version : %s\n", pglGetString(GL_VERSION)); - DBG_Printf("Extensions : %s\n", gl_extensions); + DBG_Printf("Extensions :"); + + for (GLuint i = 0; i < gl_num_extensions; ++i) + DBG_Printf(" %s", gl_extensions[i]); + DBG_Printf("\n"); // BP: disable advenced feature that don't work on somes hardware // Hurdler: Now works on G400 with bios 1.6 and certified drivers 6.04 @@ -339,13 +353,13 @@ static INT32 WINAPI SetRes(viddef_t *lvid, vmode_t *pcurrentmode) DBG_Printf("oglflags : 0x%X\n", oglflags); #ifdef USE_WGL_SWAP - if (isExtAvailable("WGL_EXT_swap_control",gl_extensions)) + if (isExtAvailable("WGL_EXT_swap_control")) wglSwapIntervalEXT = GetGLFunc("wglSwapIntervalEXT"); else wglSwapIntervalEXT = NULL; #endif - if (isExtAvailable("GL_EXT_texture_filter_anisotropic",gl_extensions)) + if (isExtAvailable("GL_EXT_texture_filter_anisotropic")) pglGetIntegerv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &maximumAnisotropy); else maximumAnisotropy = 0; diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index f411f9202..af2e5abad 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -113,10 +113,10 @@ static GLint anisotropic_filter = 0; boolean supportMipMap = false; static FTransform md2_transform; -const GLubyte *gl_version = NULL; -const GLubyte *gl_renderer = NULL; -const GLubyte *gl_extensions = NULL; -const GLubyte *gl_vendor = NULL; +const GLubyte *gl_version = NULL; +const GLubyte *gl_renderer = NULL; +const GLubyte **gl_extensions = NULL; +const GLubyte *gl_vendor = NULL; GLuint gl_num_extensions; // Loaded OpenGL version @@ -544,6 +544,7 @@ boolean SetupGLfunc(void) GETOPENGLFUNC(pglGetFloatv, glGetFloatv) GETOPENGLFUNC(pglGetIntegerv, glGetIntegerv) GETOPENGLFUNC(pglGetString, glGetString) + GETOPENGLFUNC(pglGetStringi, glGetStringi) GETOPENGLFUNC(pglClearDepth, glClearDepth) GETOPENGLFUNC(pglDepthFunc, glDepthFunc) @@ -721,7 +722,7 @@ static boolean GLFramebuffer_CheckExt(void) return false; // check if all needed gl extensions are available - return (isExtAvailable("GL_ARB_framebuffer_no_attachments", gl_extensions) && isExtAvailable("GL_ARB_framebuffer_object", gl_extensions) && isExtAvailable("GL_ARB_framebuffer_sRGB", gl_extensions)); + return (isExtAvailable("GL_ARB_framebuffer_no_attachments") && isExtAvailable("GL_ARB_framebuffer_object") && isExtAvailable("GL_ARB_framebuffer_sRGB")); } #endif @@ -1217,26 +1218,16 @@ void Flush(void) // isExtAvailable : Look if an OpenGL extension is available // Returns : true if extension available // -----------------+ -INT32 isExtAvailable(const char *extension, const GLubyte *start) +INT32 isExtAvailable(const char *extension) { - GLubyte *where, *terminator; - - if (!extension || !start) return 0; - where = (GLubyte *) strchr(extension, ' '); - if (where || *extension == '\0') + // Shouldn't really happen + if (gl_extensions == NULL) return 0; - for (;;) - { - where = (GLubyte *) strstr((const char *) start, extension); - if (!where) - break; - terminator = where + strlen(extension); - if (where == start || *(where - 1) == ' ') - if (*terminator == ' ' || *terminator == '\0') - return 1; - start = terminator; - } + for (GLuint i = 0; i < gl_num_extensions; ++i) + if (strcmp((const char*)gl_extensions[i], extension) == 0) + return 1; + return 0; } diff --git a/src/hardware/r_opengl/r_opengl.h b/src/hardware/r_opengl/r_opengl.h index 0762afde0..77502682f 100644 --- a/src/hardware/r_opengl/r_opengl.h +++ b/src/hardware/r_opengl/r_opengl.h @@ -70,7 +70,7 @@ void *GetGLFunc(const char *proc); boolean SetupGLfunc(void); void SetupGLFunc4(void); void Flush(void); -INT32 isExtAvailable(const char *extension, const GLubyte *start); +INT32 isExtAvailable(const char *extension); void SetModelView(GLint w, GLint h); void SetStates(void); @@ -90,6 +90,7 @@ extern PFNWGLEXTGETSWAPINTERVALPROC wglGetSwapIntervalEXT; #define pglClear glClear #define pglGetIntegerv glGetIntegerv #define pglGetString glGetString +#define pglGetStringi glGetStringi #else /* 1.0 Miscellaneous functions */ typedef void (APIENTRY * PFNglClear) (GLbitfield mask); @@ -98,6 +99,8 @@ typedef void (APIENTRY * PFNglGetIntegerv) (GLenum pname, GLint *params); extern PFNglGetIntegerv pglGetIntegerv; typedef const GLubyte* (APIENTRY * PFNglGetString) (GLenum name); extern PFNglGetString pglGetString; +typedef const GLubyte* (APIENTRY * PFNglGetStringi) (GLenum name, GLuint index); +extern PFNglGetStringi pglGetStringi; #endif #ifdef USE_FBO_OGL @@ -118,7 +121,7 @@ extern boolean supportFBO; extern const GLubyte *gl_version; extern const GLubyte *gl_renderer; -extern const GLubyte *gl_extensions; +extern const GLubyte **gl_extensions; extern const GLubyte *gl_vendor; extern GLuint gl_num_extensions; diff --git a/src/sdl/ogl_sdl.c b/src/sdl/ogl_sdl.c index fa18c0b1b..7face874b 100644 --- a/src/sdl/ogl_sdl.c +++ b/src/sdl/ogl_sdl.c @@ -66,6 +66,7 @@ PFNGLXSWAPINTERVALPROC glXSwapIntervalSGIEXT = NULL; PFNglClear pglClear; PFNglGetIntegerv pglGetIntegerv; PFNglGetString pglGetString; +PFNglGetStringi pglGetStringi; #endif #ifdef USE_FBO_OGL @@ -148,13 +149,25 @@ boolean OglSdlSurface(INT32 w, INT32 h) gl_version = pglGetString(GL_VERSION); gl_renderer = pglGetString(GL_RENDERER); - gl_extensions = pglGetString(GL_EXTENSIONS); pglGetIntegerv(GL_NUM_EXTENSIONS, (GLint*)&gl_num_extensions); + + if (gl_extensions != NULL) + free(gl_extensions); + + gl_extensions = calloc(gl_num_extensions, sizeof(GLubyte*)); + + for (GLuint i = 0; i < gl_num_extensions; ++i) + gl_extensions[i] = pglGetStringi(GL_EXTENSIONS, i); + gl_vendor = pglGetString(GL_VENDOR); GL_DBG_Printf("OpenGL %s\n", gl_version); GL_DBG_Printf("GPU: %s\n", gl_renderer); - GL_DBG_Printf("Extensions: %s\n", gl_extensions); + + GL_DBG_Printf("Extensions:"); + for (GLuint i = 0; i < gl_num_extensions; ++i) + GL_DBG_Printf(" %s", gl_extensions[i]); + GL_DBG_Printf("\n"); if (strcmp((const char*)gl_renderer, "GDI Generic") == 0 && strcmp((const char*)gl_version, "1.1.0") == 0) @@ -178,7 +191,7 @@ boolean OglSdlSurface(INT32 w, INT32 h) else supportMipMap = true; - if (isExtAvailable("GL_EXT_texture_filter_anisotropic", gl_extensions)) + if (isExtAvailable("GL_EXT_texture_filter_anisotropic")) pglGetIntegerv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &maximumAnisotropy); else maximumAnisotropy = 1; -- 2.54.0 From 1cbfc71fc61c565e859622e56a18fc0cf8985c3d Mon Sep 17 00:00:00 2001 From: Indev Date: Thu, 12 Dec 2024 18:03:16 +0300 Subject: [PATCH 141/143] Revert "Change gl_extension to use glGetStringi instead of glGetString" This reverts commit 7b550200f05c8a9e436617a708774f77c5e35ef9. Not supported on opengl version before 3.0 unfortunately --- src/hardware/hw_main.c | 5 ++--- src/hardware/r_opengl/ogl_win.c | 22 ++++---------------- src/hardware/r_opengl/r_opengl.c | 35 ++++++++++++++++++++------------ src/hardware/r_opengl/r_opengl.h | 7 ++----- src/sdl/ogl_sdl.c | 19 +++-------------- 5 files changed, 33 insertions(+), 55 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index ef2a4cd72..3a9cc3319 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -5623,6 +5623,7 @@ static void COM_HWR_glinfo(void) CONS_Printf("Unrecognized argument: %s\n", argv); return; } + } CONS_Printf("\x88OpenGL %s\x80\n", gl_version); @@ -5632,9 +5633,7 @@ static void COM_HWR_glinfo(void) CONS_Printf("%u GL extensions present.\n", gl_num_extensions); if (list_extensions) { - for (GLuint i = 0; i < gl_num_extensions; ++i) - CONS_Printf("%s ", gl_extensions[i]); - CONS_Printf("\n"); + CONS_Printf("%s\n", gl_extensions); } else { diff --git a/src/hardware/r_opengl/ogl_win.c b/src/hardware/r_opengl/ogl_win.c index 782010ce9..8ce44d788 100644 --- a/src/hardware/r_opengl/ogl_win.c +++ b/src/hardware/r_opengl/ogl_win.c @@ -55,7 +55,6 @@ PFNWGLEXTSWAPCONTROLPROC wglSwapIntervalEXT = NULL; PFNglClear pglClear; PFNglGetIntegerv pglGetIntegerv; PFNglGetString pglGetString; -PFNglGetStringi pglGetStringi; #define MAX_VIDEO_MODES 32 static vmode_t video_modes[MAX_VIDEO_MODES]; @@ -324,16 +323,7 @@ static INT32 WINAPI SetRes(viddef_t *lvid, vmode_t *pcurrentmode) } } - pglGetIntegerv(GL_NUM_EXTENSIONS, (GLint*)&gl_num_extensions); - - if (gl_extensions != NULL) - free(gl_extensions); - - gl_extensions = calloc(gl_num_extensions, sizeof(GLubyte*)); - - for (GLuint i = 0; i < gl_num_extensions; ++i) - gl_extensions[i] = pglGetStringi(GL_EXTENSIONS, i); - + gl_extensions = pglGetString(GL_EXTENSIONS); // Get info and extensions. //BP: why don't we make it earlier ? //Hurdler: we cannot do that before intialising gl context @@ -341,11 +331,7 @@ static INT32 WINAPI SetRes(viddef_t *lvid, vmode_t *pcurrentmode) DBG_Printf("Vendor : %s\n", pglGetString(GL_VENDOR)); DBG_Printf("Renderer : %s\n", renderer); DBG_Printf("Version : %s\n", pglGetString(GL_VERSION)); - DBG_Printf("Extensions :"); - - for (GLuint i = 0; i < gl_num_extensions; ++i) - DBG_Printf(" %s", gl_extensions[i]); - DBG_Printf("\n"); + DBG_Printf("Extensions : %s\n", gl_extensions); // BP: disable advenced feature that don't work on somes hardware // Hurdler: Now works on G400 with bios 1.6 and certified drivers 6.04 @@ -353,13 +339,13 @@ static INT32 WINAPI SetRes(viddef_t *lvid, vmode_t *pcurrentmode) DBG_Printf("oglflags : 0x%X\n", oglflags); #ifdef USE_WGL_SWAP - if (isExtAvailable("WGL_EXT_swap_control")) + if (isExtAvailable("WGL_EXT_swap_control",gl_extensions)) wglSwapIntervalEXT = GetGLFunc("wglSwapIntervalEXT"); else wglSwapIntervalEXT = NULL; #endif - if (isExtAvailable("GL_EXT_texture_filter_anisotropic")) + if (isExtAvailable("GL_EXT_texture_filter_anisotropic",gl_extensions)) pglGetIntegerv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &maximumAnisotropy); else maximumAnisotropy = 0; diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index af2e5abad..f411f9202 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -113,10 +113,10 @@ static GLint anisotropic_filter = 0; boolean supportMipMap = false; static FTransform md2_transform; -const GLubyte *gl_version = NULL; -const GLubyte *gl_renderer = NULL; -const GLubyte **gl_extensions = NULL; -const GLubyte *gl_vendor = NULL; +const GLubyte *gl_version = NULL; +const GLubyte *gl_renderer = NULL; +const GLubyte *gl_extensions = NULL; +const GLubyte *gl_vendor = NULL; GLuint gl_num_extensions; // Loaded OpenGL version @@ -544,7 +544,6 @@ boolean SetupGLfunc(void) GETOPENGLFUNC(pglGetFloatv, glGetFloatv) GETOPENGLFUNC(pglGetIntegerv, glGetIntegerv) GETOPENGLFUNC(pglGetString, glGetString) - GETOPENGLFUNC(pglGetStringi, glGetStringi) GETOPENGLFUNC(pglClearDepth, glClearDepth) GETOPENGLFUNC(pglDepthFunc, glDepthFunc) @@ -722,7 +721,7 @@ static boolean GLFramebuffer_CheckExt(void) return false; // check if all needed gl extensions are available - return (isExtAvailable("GL_ARB_framebuffer_no_attachments") && isExtAvailable("GL_ARB_framebuffer_object") && isExtAvailable("GL_ARB_framebuffer_sRGB")); + return (isExtAvailable("GL_ARB_framebuffer_no_attachments", gl_extensions) && isExtAvailable("GL_ARB_framebuffer_object", gl_extensions) && isExtAvailable("GL_ARB_framebuffer_sRGB", gl_extensions)); } #endif @@ -1218,16 +1217,26 @@ void Flush(void) // isExtAvailable : Look if an OpenGL extension is available // Returns : true if extension available // -----------------+ -INT32 isExtAvailable(const char *extension) +INT32 isExtAvailable(const char *extension, const GLubyte *start) { - // Shouldn't really happen - if (gl_extensions == NULL) + GLubyte *where, *terminator; + + if (!extension || !start) return 0; + where = (GLubyte *) strchr(extension, ' '); + if (where || *extension == '\0') return 0; - for (GLuint i = 0; i < gl_num_extensions; ++i) - if (strcmp((const char*)gl_extensions[i], extension) == 0) - return 1; - + for (;;) + { + where = (GLubyte *) strstr((const char *) start, extension); + if (!where) + break; + terminator = where + strlen(extension); + if (where == start || *(where - 1) == ' ') + if (*terminator == ' ' || *terminator == '\0') + return 1; + start = terminator; + } return 0; } diff --git a/src/hardware/r_opengl/r_opengl.h b/src/hardware/r_opengl/r_opengl.h index 77502682f..0762afde0 100644 --- a/src/hardware/r_opengl/r_opengl.h +++ b/src/hardware/r_opengl/r_opengl.h @@ -70,7 +70,7 @@ void *GetGLFunc(const char *proc); boolean SetupGLfunc(void); void SetupGLFunc4(void); void Flush(void); -INT32 isExtAvailable(const char *extension); +INT32 isExtAvailable(const char *extension, const GLubyte *start); void SetModelView(GLint w, GLint h); void SetStates(void); @@ -90,7 +90,6 @@ extern PFNWGLEXTGETSWAPINTERVALPROC wglGetSwapIntervalEXT; #define pglClear glClear #define pglGetIntegerv glGetIntegerv #define pglGetString glGetString -#define pglGetStringi glGetStringi #else /* 1.0 Miscellaneous functions */ typedef void (APIENTRY * PFNglClear) (GLbitfield mask); @@ -99,8 +98,6 @@ typedef void (APIENTRY * PFNglGetIntegerv) (GLenum pname, GLint *params); extern PFNglGetIntegerv pglGetIntegerv; typedef const GLubyte* (APIENTRY * PFNglGetString) (GLenum name); extern PFNglGetString pglGetString; -typedef const GLubyte* (APIENTRY * PFNglGetStringi) (GLenum name, GLuint index); -extern PFNglGetStringi pglGetStringi; #endif #ifdef USE_FBO_OGL @@ -121,7 +118,7 @@ extern boolean supportFBO; extern const GLubyte *gl_version; extern const GLubyte *gl_renderer; -extern const GLubyte **gl_extensions; +extern const GLubyte *gl_extensions; extern const GLubyte *gl_vendor; extern GLuint gl_num_extensions; diff --git a/src/sdl/ogl_sdl.c b/src/sdl/ogl_sdl.c index 7face874b..fa18c0b1b 100644 --- a/src/sdl/ogl_sdl.c +++ b/src/sdl/ogl_sdl.c @@ -66,7 +66,6 @@ PFNGLXSWAPINTERVALPROC glXSwapIntervalSGIEXT = NULL; PFNglClear pglClear; PFNglGetIntegerv pglGetIntegerv; PFNglGetString pglGetString; -PFNglGetStringi pglGetStringi; #endif #ifdef USE_FBO_OGL @@ -149,25 +148,13 @@ boolean OglSdlSurface(INT32 w, INT32 h) gl_version = pglGetString(GL_VERSION); gl_renderer = pglGetString(GL_RENDERER); + gl_extensions = pglGetString(GL_EXTENSIONS); pglGetIntegerv(GL_NUM_EXTENSIONS, (GLint*)&gl_num_extensions); - - if (gl_extensions != NULL) - free(gl_extensions); - - gl_extensions = calloc(gl_num_extensions, sizeof(GLubyte*)); - - for (GLuint i = 0; i < gl_num_extensions; ++i) - gl_extensions[i] = pglGetStringi(GL_EXTENSIONS, i); - gl_vendor = pglGetString(GL_VENDOR); GL_DBG_Printf("OpenGL %s\n", gl_version); GL_DBG_Printf("GPU: %s\n", gl_renderer); - - GL_DBG_Printf("Extensions:"); - for (GLuint i = 0; i < gl_num_extensions; ++i) - GL_DBG_Printf(" %s", gl_extensions[i]); - GL_DBG_Printf("\n"); + GL_DBG_Printf("Extensions: %s\n", gl_extensions); if (strcmp((const char*)gl_renderer, "GDI Generic") == 0 && strcmp((const char*)gl_version, "1.1.0") == 0) @@ -191,7 +178,7 @@ boolean OglSdlSurface(INT32 w, INT32 h) else supportMipMap = true; - if (isExtAvailable("GL_EXT_texture_filter_anisotropic")) + if (isExtAvailable("GL_EXT_texture_filter_anisotropic", gl_extensions)) pglGetIntegerv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &maximumAnisotropy); else maximumAnisotropy = 1; -- 2.54.0 From 939084d57b3dcd937b5ef8f9ee31c667983ae046 Mon Sep 17 00:00:00 2001 From: Indev Date: Thu, 12 Dec 2024 18:47:35 +0300 Subject: [PATCH 142/143] Avoid overflowing CONS_Printf's buffer by using vsnprintf --- src/console.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/console.c b/src/console.c index 9781078fa..f36b3b7cb 100644 --- a/src/console.c +++ b/src/console.c @@ -1236,7 +1236,7 @@ void CONS_Printf(const char *fmt, ...) txt = malloc(8192); va_start(argptr, fmt); - vsprintf(txt, fmt, argptr); + vsnprintf(txt, 8192, fmt, argptr); va_end(argptr); // echo console prints to log file -- 2.54.0 From 331f09cdd9d638a6aa47aafd378c5b7af8ab94d4 Mon Sep 17 00:00:00 2001 From: "H. Utku Maden" Date: Thu, 12 Dec 2024 18:57:26 +0300 Subject: [PATCH 143/143] Fixed gr_glinfo crash when there are way too many extensions present. --- src/hardware/hw_main.c | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 6afffad75..b0d50553d 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -5461,7 +5461,25 @@ static void COM_HWR_glinfo(void) CONS_Printf("%u GL extensions present.\n", gl_num_extensions); if (list_extensions) { - CONS_Printf("%s\n", gl_extensions); + // We need this strtok loop because we cannot write the extensions list directly + // to the output buffer, because it will overflow the output buffer of CONS_Printf + // if the GPU is super new and supports a bajillion extensions - xyzzy + + char *copy = strdup((const char*)gl_extensions); + char *ext = strtok(copy, " "); + + if (copy == NULL) + { + CONS_Printf("Ran out of memory listing extensions?!?!"); + return; + } + + do + { + CONS_Printf(" - %s\n", ext); + } while ((ext = strtok(NULL, " ")) != NULL); + + free(copy); } else { -- 2.54.0