From afca521fe5b40f1628ebe15900a295c502aba219 Mon Sep 17 00:00:00 2001 From: Alug Date: Thu, 17 Oct 2024 22:54:44 +0200 Subject: [PATCH 01/11] dont run director if theres only one player ingame idk if this is good lol --- src/g_game.h | 12 ++---------- src/k_director.c | 17 ++++++++++++++++- src/st_stuff.c | 2 +- 3 files changed, 19 insertions(+), 12 deletions(-) diff --git a/src/g_game.h b/src/g_game.h index aaafa233c..b00bf1343 100644 --- a/src/g_game.h +++ b/src/g_game.h @@ -419,19 +419,9 @@ void G_SetGamestate(gamestate_t newstate); // Gamedata record shit void G_AllocMainRecordData(INT16 i); -//void G_AllocNightsRecordData(INT16 i); void G_ClearRecords(void); -//UINT32 G_GetBestScore(INT16 map); tic_t G_GetBestTime(INT16 map); -//tic_t G_GetBestLap(INT16 map); -//UINT16 G_GetBestRings(INT16 map); -//UINT32 G_GetBestNightsScore(INT16 map, UINT8 mare); -//tic_t G_GetBestNightsTime(INT16 map, UINT8 mare); -//UINT8 G_GetBestNightsGrade(INT16 map, UINT8 mare); - -//void G_AddTempNightsRecords(UINT32 pscore, tic_t ptime, UINT8 mare); -//void G_SetNightsRecords(void); FUNCMATH INT32 G_TicsToHours(tic_t tics); FUNCMATH INT32 G_TicsToMinutes(tic_t tics, boolean full); @@ -439,6 +429,8 @@ FUNCMATH INT32 G_TicsToSeconds(tic_t tics); FUNCMATH INT32 G_TicsToCentiseconds(tic_t tics); FUNCMATH INT32 G_TicsToMilliseconds(tic_t tics); +boolean K_DirectorIsPlayerAlone(void); // idk where else to put this lol + // Don't split up TOL handling INT16 G_TOLFlag(INT32 pgametype); diff --git a/src/k_director.c b/src/k_director.c index 3c5938713..1bbe438b9 100644 --- a/src/k_director.c +++ b/src/k_director.c @@ -38,6 +38,21 @@ struct directorinfo INT32 boredom[MAXPLAYERS]; // how long has a given position had no credible attackers? } directorinfo; +boolean K_DirectorIsPlayerAlone(void) +{ + UINT8 pingame = 0; + + // Gotta check how many players are active at this moment. + for (UINT8 i = 0; i < MAXPLAYERS; i++) + { + if (!playeringame[i] || players[i].spectator) + continue; + pingame++; + } + + return (pingame <= 1); +} + static inline boolean race_rules(void) { return gametype == GT_RACE; @@ -50,7 +65,7 @@ static fixed_t ScaleFromMap(fixed_t n, fixed_t scale) static boolean K_DirectorIsEnabled(void) { - return cv_director.value && !splitscreen && (gamestate == GS_LEVEL && (((stplyr && !stplyr->spectator) && (!playeringame[consoleplayer] || players[consoleplayer].spectator)) || (demo.playback && !demo.freecam && (!demo.title || !modeattacking)))); + return cv_director.value && !splitscreen && (gamestate == GS_LEVEL && (((stplyr && !stplyr->spectator) && (!playeringame[consoleplayer] || players[consoleplayer].spectator)) || (demo.playback && !demo.freecam && (!demo.title || !modeattacking))) && !K_DirectorIsPlayerAlone()); } void K_InitDirector(void) diff --git a/src/st_stuff.c b/src/st_stuff.c index dd6bd5f6b..8b15e711a 100644 --- a/src/st_stuff.c +++ b/src/st_stuff.c @@ -664,7 +664,7 @@ static void ST_overlayDrawer(void) if (!hu_showscores) // hide the following if TAB is held { - if (cv_showdirectorhud.value && ((demo.playback && !demo.freecam && (!demo.title || !modeattacking)) || !P_IsLocalPlayer(stplyr)) && !splitscreen) + if (cv_showdirectorhud.value && !splitscreen && ((demo.playback && !demo.freecam && (!demo.title || !modeattacking)) || !P_IsLocalPlayer(stplyr)) && !K_DirectorIsPlayerAlone()) { char directortext[20] = {0}; From 7a6f43bece9dfbc22022f6605bc5c09fc252f6f5 Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 18 Oct 2024 20:34:00 +0200 Subject: [PATCH 02/11] dont show encore toggle text in record attack menu dont think you can even record attack in encore hmm --- src/m_menu.c | 19 +++++++++++-------- 1 file changed, 11 insertions(+), 8 deletions(-) diff --git a/src/m_menu.c b/src/m_menu.c index 101afbd8d..94b5f8f3b 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -9991,16 +9991,19 @@ static void M_DrawLevelSelectOnly(boolean leftfade, boolean rightfade) patch_t *PictureOfLevel; INT32 x, y, w, i, oldval, trans, dupadjust = ((vid.width/vid.dupx) - BASEVIDWIDTH)>>1; - char encoretoggle[32] = {0}; - const char *item1 = gamecontrol[gc_fire][0] != 0 ? G_KeynumToString(gamecontrol[gc_fire][0]) : NULL; - const char *item2 = gamecontrol[gc_fire][1] != 0 ? G_KeynumToString(gamecontrol[gc_fire][1]) : NULL; + if (levellistmode != LLM_RECORDATTACK) // so it doesent show in record attack menu + { + char encoretoggle[32] = {0}; + const char *item1 = gamecontrol[gc_fire][0] != 0 ? G_KeynumToString(gamecontrol[gc_fire][0]) : NULL; + const char *item2 = gamecontrol[gc_fire][1] != 0 ? G_KeynumToString(gamecontrol[gc_fire][1]) : NULL; - if (item1 != NULL && item2 != NULL) - snprintf(encoretoggle, 32, "%s/%s: Toggle Encore", item1, item2); - else - snprintf(encoretoggle, 32, "%s: Toggle Encore", item1 != NULL ? item1 : item2 != NULL ? item2 : "Item"); + if (item1 != NULL && item2 != NULL) + snprintf(encoretoggle, 32, "%s/%s: Toggle Encore", item1, item2); + else + snprintf(encoretoggle, 32, "%s: Toggle Encore", item1 != NULL ? item1 : item2 != NULL ? item2 : "Item"); - V_DrawThinString(1, BASEVIDHEIGHT-8-1, V_SNAPTOLEFT|V_SNAPTOBOTTOM|V_TRANSLUCENT|V_ALLOWLOWERCASE, encoretoggle); + V_DrawThinString(1, BASEVIDHEIGHT-8-1, V_SNAPTOLEFT|V_SNAPTOBOTTOM|V_TRANSLUCENT|V_ALLOWLOWERCASE, encoretoggle); + } // A 160x100 image of the level as entry MAPxxP if (cv_nextmap.value) From fbe97556de4a2b8366af60a1a44b63cc1f934e62 Mon Sep 17 00:00:00 2001 From: Alug Date: Fri, 18 Oct 2024 20:36:16 +0200 Subject: [PATCH 03/11] change versionstring also remove the fbo one, its honestly not necessary anymore --- src/doomdef.h | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/src/doomdef.h b/src/doomdef.h index ff53c8c8e..046cd6897 100644 --- a/src/doomdef.h +++ b/src/doomdef.h @@ -127,13 +127,8 @@ extern char logfilename[1024]; #else #define VERSION 1 // Game version #define SUBVERSION 6 // more precise version number -#ifndef USE_FBO_OGL -#define VERSIONSTRING "Saturn v7" -#define VERSIONSTRINGW L"Saturn v7" -#else -#define VERSIONSTRING "Saturn v7 - FBO " -#define VERSIONSTRINGW L"Saturn v7 - FBO" -#endif +#define VERSIONSTRING "Saturn v7.1" +#define VERSIONSTRINGW L"Saturn v7.1" // Hey! If you change this, add 1 to the MODVERSION below! Otherwise we can't force updates! // And change CMakeLists.txt (not src/, but in root), for CMake users! // AND appveyor.yml, for the build bots! From 0af52ba3ae2a7f42d194fa71a2616dd714d16107 Mon Sep 17 00:00:00 2001 From: Alug Date: Sat, 19 Oct 2024 21:14:45 +0200 Subject: [PATCH 04/11] dont need to always check this 16 times if we already know theres more than one player ingame --- src/k_director.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/k_director.c b/src/k_director.c index 1bbe438b9..fc6e211f6 100644 --- a/src/k_director.c +++ b/src/k_director.c @@ -47,7 +47,11 @@ boolean K_DirectorIsPlayerAlone(void) { if (!playeringame[i] || players[i].spectator) continue; + pingame++; + + if (pingame >= 2) // we dont need to check further + break; } return (pingame <= 1); From d30c96e8cbcc56c55e96d161731642b3c15a3127 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 20 Oct 2024 00:21:48 +0200 Subject: [PATCH 05/11] fix a maybe-uninitialized warning --- src/r_things.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/r_things.c b/src/r_things.c index 3f96ed419..7c1b7d9b5 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -2448,8 +2448,8 @@ static boolean R_CheckSpriteVisible(vissprite_t *spr, INT32 x1, INT32 x2) INT16 sz = spr->sz; INT16 szt = spr->szt; - fixed_t texturemid, yscale, scalestep = spr->scalestep; - INT32 height; + fixed_t texturemid = 0, yscale = 0, scalestep = spr->scalestep; // "= 0" pleases the compiler + INT32 height = 0; if (scalestep) { From 86ed1b709e7e6e5448081001625c28bdc443bb8e Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 20 Oct 2024 02:01:02 +0200 Subject: [PATCH 06/11] fix some rendering issues and crashes in software renderer - Increase MINZ from 4 fracunits to 16 - R_StoreWallRange: do not render textures with holes - fix off-by-one error in R_ProjectSprite - Avoid rendering unused left/right edges of screen while rolling - Clamp patch column post drawing bounds - Vissprites: set dc.texheight - Add null check for column in R_DrawMaskedColumn --- src/r_draw.c | 1 + src/r_draw.h | 1 + src/r_draw8.c | 107 ++++++++++++++++++++++++++++++++++++++++++++++--- src/r_main.c | 2 +- src/r_segs.c | 20 ++++++--- src/r_things.c | 81 +++++++++++++++++++++++-------------- src/r_things.h | 4 ++ 7 files changed, 174 insertions(+), 42 deletions(-) diff --git a/src/r_draw.c b/src/r_draw.c index fa19a6ac2..faa9ba638 100644 --- a/src/r_draw.c +++ b/src/r_draw.c @@ -78,6 +78,7 @@ fixed_t dc_iscale, dc_texturemid; UINT8 dc_hires; // under MSVC boolean is a byte, while on other systems, it a bit, // soo lets make it a byte on all system for the ASM code UINT8 *dc_source; +INT32 dc_sourcelength; // ----------------------- // translucency stuff here diff --git a/src/r_draw.h b/src/r_draw.h index 58775fe1d..7dbeda7c9 100644 --- a/src/r_draw.h +++ b/src/r_draw.h @@ -62,6 +62,7 @@ extern lighttable_t *ds_colormap; extern fixed_t ds_xfrac, ds_yfrac, ds_xstep, ds_ystep; extern INT32 ds_waterofs, ds_bgofs; extern UINT8 *ds_source; // start of a 64*64 tile image +extern INT32 dc_sourcelength; extern UINT8 *ds_transmap; extern INT32 ds_bgofs; diff --git a/src/r_draw8.c b/src/r_draw8.c index 6aabdb6dd..bf3b9740d 100644 --- a/src/r_draw8.c +++ b/src/r_draw8.c @@ -28,6 +28,8 @@ void R_DrawColumn_8(void) register UINT8 *dest; register fixed_t frac; fixed_t fracstep; + INT32 npow2min; + INT32 npow2max; count = dc_yh - dc_yl; @@ -51,13 +53,26 @@ void R_DrawColumn_8(void) fracstep = dc_iscale; frac = (dc_texturemid + FixedMul((dc_yl << FRACBITS) - centeryfrac, fracstep))*(!dc_hires); - // Inner loop that does the actual texture mapping, e.g. a DDA-like scaling. // This is as fast as it gets. { register const UINT8 *source = dc_source; register const lighttable_t *colormap = dc_colormap; register INT32 heightmask = dc_texheight-1; + + if (dc_sourcelength <= 0) + { + // Note: we need to unconditionally clamp in npow2 draw loop to avoid a CPU branch + // This is to just render it effectively the identity function. + npow2min = INT32_MIN; + npow2max = INT32_MAX; + } + else + { + npow2min = -1; + npow2max = dc_sourcelength; + } + if (dc_texheight & heightmask) // not a power of 2 -- killough { heightmask++; @@ -74,7 +89,10 @@ void R_DrawColumn_8(void) // Re-map color indices from wall texture column // using a lighting/special effects LUT. // heightmask is the Tutti-Frutti fix - *dest = colormap[source[frac>>FRACBITS]]; + + // -1 is the lower clamp bound because column posts have a "safe" byte before the real data + // and a few bytes after as well + *dest = colormap[source[CLAMP(frac>>FRACBITS, npow2min, npow2max)]]; dest += vid.width; // Avoid overflow. @@ -115,6 +133,8 @@ void R_Draw2sMultiPatchColumn_8(void) register UINT8 *dest; register fixed_t frac; fixed_t fracstep; + INT32 npow2min; + INT32 npow2max; count = dc_yh - dc_yl; @@ -147,6 +167,20 @@ void R_Draw2sMultiPatchColumn_8(void) register const lighttable_t *colormap = dc_colormap; register INT32 heightmask = dc_texheight-1; register UINT8 val; + + if (dc_sourcelength <= 0) + { + // Note: we need to unconditionally clamp in npow2 draw loop to avoid a CPU branch + // This is to just render it effectively the identity function. + npow2min = INT32_MIN; + npow2max = INT32_MAX; + } + else + { + npow2min = -1; + npow2max = dc_sourcelength; + } + if (dc_texheight & heightmask) // not a power of 2 -- killough { heightmask++; @@ -163,7 +197,10 @@ void R_Draw2sMultiPatchColumn_8(void) // Re-map color indices from wall texture column // using a lighting/special effects LUT. // heightmask is the Tutti-Frutti fix - val = source[frac>>FRACBITS]; + + // -1 is the lower clamp bound because column posts have a "safe" byte before the real data + // and a few bytes after as well + val = source[CLAMP(frac>>FRACBITS, npow2min, npow2max)]; if (val != TRANSPARENTPIXEL) { @@ -223,6 +260,8 @@ void R_Draw2sMultiPatchTranslucentColumn_8(void) register UINT8 *dest; register fixed_t frac; fixed_t fracstep; + INT32 npow2min; + INT32 npow2max; count = dc_yh - dc_yl; @@ -256,6 +295,20 @@ void R_Draw2sMultiPatchTranslucentColumn_8(void) register const lighttable_t *colormap = dc_colormap; register INT32 heightmask = dc_texheight-1; register UINT8 val; + + if (dc_sourcelength <= 0) + { + // Note: we need to unconditionally clamp in npow2 draw loop to avoid a CPU branch + // This is to just render it effectively the identity function. + npow2min = INT32_MIN; + npow2max = INT32_MAX; + } + else + { + npow2min = -1; + npow2max = dc_sourcelength; + } + if (dc_texheight & heightmask) // not a power of 2 -- killough { heightmask++; @@ -272,7 +325,10 @@ void R_Draw2sMultiPatchTranslucentColumn_8(void) // Re-map color indices from wall texture column // using a lighting/special effects LUT. // heightmask is the Tutti-Frutti fix - val = source[frac>>FRACBITS]; + + // -1 is the lower clamp bound because column posts have a "safe" byte before the real data + // and a few bytes after as well + val = source[CLAMP(frac>>FRACBITS, npow2min, npow2max)]; if (val != TRANSPARENTPIXEL) { @@ -376,6 +432,8 @@ void R_DrawTranslucentColumn_8(void) register INT32 count; register UINT8 *dest; register fixed_t frac, fracstep; + INT32 npow2min; + INT32 npow2max; count = dc_yh - dc_yl + 1; @@ -403,6 +461,20 @@ void R_DrawTranslucentColumn_8(void) register const UINT8 *transmap = dc_transmap; register const lighttable_t *colormap = dc_colormap; register INT32 heightmask = dc_texheight - 1; + + if (dc_sourcelength <= 0) + { + // Note: we need to unconditionally clamp in npow2 draw loop to avoid a CPU branch + // This is to just render it effectively the identity function. + npow2min = INT32_MIN; + npow2max = INT32_MAX; + } + else + { + npow2min = -1; + npow2max = dc_sourcelength; + } + if (dc_texheight & heightmask) { heightmask++; @@ -420,7 +492,11 @@ void R_DrawTranslucentColumn_8(void) // Re-map color indices from wall texture column // using a lighting/special effects LUT. // heightmask is the Tutti-Frutti fix - *dest = *(transmap + (colormap[source[frac>>FRACBITS]]<<8) + (*dest)); + + // -1 is the lower clamp bound because column posts have a "safe" byte before the real data + // and a few bytes after as well + *dest = *(transmap + (colormap[source[CLAMP(frac>>FRACBITS, npow2min, npow2max)]]<<8) + (*dest)); + dest += vid.width; if ((frac += fracstep) >= heightmask) @@ -458,6 +534,8 @@ void R_DrawTranslatedTranslucentColumn_8(void) register INT32 count; register UINT8 *dest; register fixed_t frac, fracstep; + INT32 npow2min; + INT32 npow2max; count = dc_yh - dc_yl + 1; @@ -477,6 +555,20 @@ void R_DrawTranslatedTranslucentColumn_8(void) // This is as fast as it gets. { register INT32 heightmask = dc_texheight - 1; + + if (dc_sourcelength <= 0) + { + // Note: we need to unconditionally clamp in npow2 draw loop to avoid a CPU branch + // This is to just render it effectively the identity function. + npow2min = INT32_MIN; + npow2max = INT32_MAX; + } + else + { + npow2min = -1; + npow2max = dc_sourcelength; + } + if (dc_texheight & heightmask) { heightmask++; @@ -494,7 +586,10 @@ void R_DrawTranslatedTranslucentColumn_8(void) // Re-map color indices from wall texture column // using a lighting/special effects LUT. // heightmask is the Tutti-Frutti fix - *dest = *(dc_transmap + (dc_colormap[dc_translation[dc_source[frac>>FRACBITS]]]<<8) + (*dest)); + + // -1 is the lower clamp bound because column posts have a "safe" byte before the real data + // and a few bytes after as well + *dest = *(dc_transmap + (dc_colormap[dc_translation[dc_source[CLAMP(frac>>FRACBITS, npow2min, npow2max)]]]<<8) + (*dest)); dest += vid.width; if ((frac += fracstep) >= heightmask) diff --git a/src/r_main.c b/src/r_main.c index 75ff41126..2f7ecfb6e 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -1706,7 +1706,7 @@ void R_RenderPlayerView(player_t *player) else { portalclipstart = 0; - portalclipend = viewwidth-1; + portalclipend = viewwidth; R_ClearClipSegs(); } R_ClearDrawSegs(); diff --git a/src/r_segs.c b/src/r_segs.c index e89a10780..452351aa3 100644 --- a/src/r_segs.c +++ b/src/r_segs.c @@ -275,6 +275,7 @@ static void R_Render2sidedMultiPatchColumn(column_t *column) if (dc_yl <= dc_yh && dc_yh < vid.height && dc_yh > 0) { dc_source = (UINT8 *)column + 3; + dc_sourcelength = 0; if (colfunc == wallcolfunc) twosmultipatchfunc(); @@ -1446,6 +1447,7 @@ static void R_RenderSegLoop (void) dc_texturemid = rw_midtexturemid; dc_source = R_GetColumn(midtexture,texturecolumn); dc_texheight = textureheight[midtexture]>>FRACBITS; + dc_sourcelength = 0; colfunc(); // dont draw anything more for this column, since @@ -1493,6 +1495,7 @@ static void R_RenderSegLoop (void) dc_texturemid = rw_toptexturemid; dc_source = R_GetColumn(toptexture,texturecolumn); dc_texheight = textureheight[toptexture]>>FRACBITS; + dc_sourcelength = 0; colfunc(); ceilingclip[rw_x] = (INT16)mid; } @@ -1530,6 +1533,7 @@ static void R_RenderSegLoop (void) dc_source = R_GetColumn(bottomtexture, texturecolumn); dc_texheight = textureheight[bottomtexture]>>FRACBITS; + dc_sourcelength = 0; colfunc(); floorclip[rw_x] = (INT16)mid; } @@ -1605,6 +1609,12 @@ static INT64 R_CalcSegDist(seg_t* seg, INT64 x2, INT64 y2) } } +static inline INT32 get_flat_tex (INT32 texnum) +{ + texnum = R_GetTextureNum(texnum); + return textures[texnum]->holes ? 0 : texnum; // R_DrawWallColumn cannot render holey textures +} + // // R_StoreWallRange // A wall segment will be drawn @@ -1862,7 +1872,7 @@ void R_StoreWallRange(INT32 start, INT32 stop) { fixed_t texheight; // single sided line - midtexture = R_GetTextureNum(sidedef->midtexture); + midtexture = get_flat_tex(sidedef->midtexture); texheight = textureheight[midtexture]; // a single sided line is terminal, so it must mark ends markfloor = markceiling = true; @@ -2045,15 +2055,15 @@ void R_StoreWallRange(INT32 start, INT32 stop) { // Special case... use offsets from 2nd side but only if it has a texture. side_t *def = &sides[linedef->sidenum[1]]; - toptexture = R_GetTextureNum(def->toptexture); + toptexture = get_flat_tex(def->toptexture); if (!toptexture) //Second side has no texture, use the first side's instead. - toptexture = R_GetTextureNum(sidedef->toptexture); + toptexture = get_flat_tex(sidedef->toptexture); texheight = textureheight[toptexture]; } else { - toptexture = R_GetTextureNum(sidedef->toptexture); + toptexture = get_flat_tex(sidedef->toptexture); texheight = textureheight[toptexture]; } if (!(linedef->flags & ML_EFFECT1)) { // Ignore slopes for lower/upper textures unless flag is checked @@ -2078,7 +2088,7 @@ void R_StoreWallRange(INT32 start, INT32 stop) if (worldlow > worldbottom || worldlowslope > worldbottomslope) // Only if VISIBLE!!! { // bottom texture - bottomtexture = R_GetTextureNum(sidedef->bottomtexture); + bottomtexture = get_flat_tex(sidedef->bottomtexture); if (!(linedef->flags & ML_EFFECT1)) { // Ignore slopes for lower/upper textures unless flag is checked if (linedef->flags & ML_DONTPEGBOTTOM) diff --git a/src/r_things.c b/src/r_things.c index 7c1b7d9b5..a5c09dc13 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -43,7 +43,7 @@ CV_PossibleValue_t Forceskin_cons_t[MAXSKINS+2]; static void R_InitSkins(void); -#define MINZ (FRACUNIT*4) +#define MINZ (FRACUNIT*16) #define BASEYCENTER (BASEVIDHEIGHT/2) typedef struct @@ -583,6 +583,9 @@ void R_DrawMaskedColumn(column_t *column) basetexturemid = dc_texturemid; + if (!column || column == 0) + return; + for (; column->topdelta != 0xff ;) { // calculate unclipped screen coordinates @@ -618,6 +621,7 @@ void R_DrawMaskedColumn(column_t *column) if (dc_yl <= dc_yh && dc_yh > 0 && column->length != 0) { dc_source = (UINT8 *)column + 3; + dc_sourcelength = column->length; dc_texturemid = basetexturemid - (topdelta< 0 && column->length != 0) { dc_source = ZZ_Alloc(column->length); + dc_sourcelength = column->length; for (s = (UINT8 *)column+2+column->length, d = dc_source; d < dc_source+column->length; --s) *d++ = *s; dc_texturemid = basetexturemid - (topdelta<texturemid; - dc_texheight = 0; + dc_texheight = SHORT(patch->height); frac = vis->startfrac; windowtop = windowbottom = sprbotscreen = INT32_MAX; @@ -808,8 +813,10 @@ static void R_DrawVisSprite(vissprite_t *vis) this_scale = FixedMul(this_scale, ((skin_t *)vis->mobj->localskin)->highresscale); else if (vis->mobj->skin && ((skin_t *)vis->mobj->skin)->flags & SF_HIRES) this_scale = FixedMul(this_scale, ((skin_t *)vis->mobj->skin)->highresscale); + if (this_scale <= 0) this_scale = 1; + if (this_scale != FRACUNIT) { if (!vis->isScaled) @@ -875,12 +882,10 @@ static void R_DrawVisSprite(vissprite_t *vis) } else { - pwidth = SHORT(patch->width); - // Non-paper drawing loop for (dc_x = vis->x1; dc_x <= vis->x2; dc_x++, frac += vis->xiscale) - { - texturecolumn = CLAMP(frac >> FRACBITS, 0, pwidth - 1); + { + texturecolumn = CLAMP(frac >> FRACBITS, 0, SHORT(patch->width) - 1); column = (column_t *)((UINT8 *)patch + LONG(patch->columnofs[texturecolumn])); localcolfunc (column); @@ -926,7 +931,7 @@ static void R_DrawPrecipitationVisSprite(vissprite_t *vis) dc_iscale = FixedDiv(FRACUNIT, vis->scale); dc_texturemid = FixedDiv(vis->texturemid, this_scale); - dc_texheight = 0; + dc_texheight = SHORT(patch->height); frac = vis->startfrac; spryscale = vis->scale; @@ -941,7 +946,14 @@ static void R_DrawPrecipitationVisSprite(vissprite_t *vis) for (dc_x = vis->x1; dc_x <= vis->x2; dc_x++, frac += vis->xiscale) { - texturecolumn = CLAMP(frac >> FRACBITS, 0, SHORT(patch->width) - 1); + texturecolumn = frac>>FRACBITS; + + if (texturecolumn < 0 || texturecolumn >= patch->width) + { + CONS_Debug(DBG_RENDER, "R_DrawPrecipitationSpriteRange: bad texturecolumn\n"); + break; + } + column = (column_t *)((UINT8 *)patch + LONG(patch->columnofs[texturecolumn])); R_DrawMaskedColumn(column); @@ -1110,6 +1122,7 @@ static void R_ProjectSprite(mobj_t *thing) fixed_t xscale, yscale, sortscale; //added : 02-02-98 : aaargll..if I were a math-guy!!! INT32 x1, x2; + INT32 x1test = 0, x2test = 0; spritedef_t *sprdef; spriteframe_t *sprframe; @@ -1512,6 +1525,11 @@ static void R_ProjectSprite(mobj_t *thing) //x1 = (centerxfrac + FixedMul(tx,xscale))>>FRACBITS; x1 = centerx + (FixedMul(tx,xscale) / FRACUNIT); + x1test = (centerxfrac + FixedMul(tx,xscale))>>FRACBITS; + + if (x1test > viewwidth) + x1test = 0; + // off the right side? if (x1 > viewwidth) return; @@ -1520,6 +1538,11 @@ static void R_ProjectSprite(mobj_t *thing) //x2 = ((centerxfrac + FixedMul(tx,xscale))>>FRACBITS); x2--; x2 = (centerx + (FixedMul(tx,xscale) / FRACUNIT)) - 1; + x2test = ((centerxfrac + FixedMul(tx,xscale))>>FRACBITS) - 1; + + if (x2test < 0) + x2test = 0; + // off the left side if (x2 < 0) return; @@ -1528,9 +1551,15 @@ static void R_ProjectSprite(mobj_t *thing) // PORTAL SPRITE CLIPPING if (portalrender && portalclipline) { - if (x2 < portalclipstart || x1 > portalclipend) + if (x2 < portalclipstart || x1 >= portalclipend) return; + if (x2test < portalclipstart || x1test >= portalclipend) + { + x1test = 0; + x2test = 0; + } + if (P_PointOnLineSide(interp.x, interp.y, portalclipline) != 0) return; } @@ -1621,17 +1650,11 @@ static void R_ProjectSprite(mobj_t *thing) vis->mobj = thing; // Easy access! Tails 06-07-2002 - vis->x1 = x1 < 0 ? 0 : x1; - vis->x2 = x2 >= viewwidth ? viewwidth-1 : x2; + vis->x1 = x1 < portalclipstart ? portalclipstart : x1; + vis->x2 = x2 >= portalclipend ? portalclipend-1 : x2; - // PORTAL SEMI-CLIPPING - if (portalrender && portalclipline) - { - if (vis->x1 < portalclipstart) - vis->x1 = portalclipstart; - if (vis->x2 > portalclipend) - vis->x2 = portalclipend; - } + vis->x1test = x1test < portalclipstart ? portalclipstart : x1test; + vis->x2test = x2test >= portalclipend ? portalclipend-1 : x2test; vis->sector = thing->subsector->sector; vis->szt = (INT16)((centeryfrac - FixedMul(vis->gzt - viewz, sortscale))>>FRACBITS); @@ -1658,6 +1681,7 @@ static void R_ProjectSprite(mobj_t *thing) { vis->startfrac = spr_width-1; vis->xiscale = -iscale; + vis->xiscaletest = -vis->xiscaletest; } else { @@ -1665,10 +1689,13 @@ static void R_ProjectSprite(mobj_t *thing) vis->xiscale = iscale; } + vis->startfractest = vis->startfrac; + if (vis->x1 > x1) { vis->startfrac += FixedDiv(vis->xiscale, this_scale) * (vis->x1 - x1); vis->scale += FixedMul(scalestep, spriteyscale) * (vis->x1 - x1); + vis->startfractest += FixedDiv(vis->xiscaletest, this_scale) * (vis->x1test - x1test); } //Fab: lumppat is the lump number of the patch to use, this is different @@ -1841,7 +1868,7 @@ static void R_ProjectPrecipitationSprite(precipmobj_t *thing) // PORTAL SPRITE CLIPPING if (portalrender && portalclipline) { - if (x2 < portalclipstart || x1 > portalclipend) + if (x2 < portalclipstart || x1 >= portalclipend) return; if (P_PointOnLineSide(interp.x, interp.y, portalclipline) != 0) @@ -1875,17 +1902,11 @@ static void R_ProjectPrecipitationSprite(precipmobj_t *thing) vis->scalestep = 0; vis->paperdistance = 0; - vis->x1 = x1 < 0 ? 0 : x1; - vis->x2 = x2 >= viewwidth ? viewwidth-1 : x2; + vis->x1 = x1 < portalclipstart ? portalclipstart : x1; + vis->x2 = x2 >= portalclipend ? portalclipend-1 : x2; - // PORTAL SEMI-CLIPPING - if (portalrender && portalclipline) - { - if (vis->x1 < portalclipstart) - vis->x1 = portalclipstart; - if (vis->x2 > portalclipend) - vis->x2 = portalclipend; - } + vis->x1test = 0; + vis->x2test = 0; vis->xscale = xscale; //SoM: 4/17/2000 vis->sector = thing->subsector->sector; diff --git a/src/r_things.h b/src/r_things.h index 0e99c490c..ce0f9f841 100644 --- a/src/r_things.h +++ b/src/r_things.h @@ -55,6 +55,7 @@ extern fixed_t sprtopscreen; extern fixed_t sprbotscreen; extern fixed_t windowtop; extern fixed_t windowbottom; +extern INT32 lengthcol; fixed_t R_GetShadowZ(mobj_t *thing, pslope_t **shadowslope); @@ -142,6 +143,9 @@ typedef struct vissprite_s mobj_t *mobj; // for easy access INT32 x1, x2; + INT32 x1test, x2test; + fixed_t xiscaletest; + fixed_t startfractest; fixed_t gx, gy; // for line side calculation fixed_t gz, gzt; // global bottom/top for silhouette clipping From 7076c35521bdd1d7b9e73d94e94839824b036b88 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 20 Oct 2024 04:14:54 +0200 Subject: [PATCH 07/11] HWR_RenderPlane can be static --- src/hardware/hw_main.c | 2 +- src/hardware/hw_main.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 5d243d4c3..741e29814 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -652,7 +652,7 @@ static FUINT HWR_CalcSlopeLight(FUINT lightnum, pslope_t *slope) // HWR_RenderPlane // Render a floor or ceiling convex polygon -void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, boolean isceiling, fixed_t fixedheight, FBITFIELD PolyFlags, INT32 lightlevel, lumpnum_t lumpnum, sector_t *FOFsector, UINT8 alpha, extracolormap_t *planecolormap) +static void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, boolean isceiling, fixed_t fixedheight, FBITFIELD PolyFlags, INT32 lightlevel, lumpnum_t lumpnum, sector_t *FOFsector, UINT8 alpha, extracolormap_t *planecolormap) { FSurfaceInfo Surf; FOutVector *v3d; diff --git a/src/hardware/hw_main.h b/src/hardware/hw_main.h index bd6258ef4..2abb6dda6 100644 --- a/src/hardware/hw_main.h +++ b/src/hardware/hw_main.h @@ -116,7 +116,7 @@ void HWR_MakeScreenFinalTexture(void); void HWR_DrawScreenFinalTexture(INT32 width, INT32 height); // hw_main.c: Planes -void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, boolean isceiling, fixed_t fixedheight, FBITFIELD PolyFlags, INT32 lightlevel, lumpnum_t lumpnum, sector_t *FOFsector, UINT8 alpha, extracolormap_t *planecolormap); +//void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, boolean isceiling, fixed_t fixedheight, FBITFIELD PolyFlags, INT32 lightlevel, lumpnum_t lumpnum, sector_t *FOFsector, UINT8 alpha, extracolormap_t *planecolormap); void HWR_AddTransparentFloor(lumpnum_t lumpnum, extrasubsector_t *xsub, boolean isceiling, fixed_t fixedheight, INT32 lightlevel, INT32 alpha, sector_t *FOFSector, FBITFIELD blend, boolean fogplane, extracolormap_t *planecolormap); void HWR_RenderPolyObjectPlane(polyobj_t *polysector, boolean isceiling, fixed_t fixedheight, FBITFIELD blendmode, UINT8 lightlevel, lumpnum_t lumpnum, sector_t *FOFsector, UINT8 alpha, extracolormap_t *planecolormap); From c6fbf405bf06bba7cf30fdea4fcc68d1285a4bcc Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 20 Oct 2024 15:16:37 +0200 Subject: [PATCH 08/11] optimize R_PointOnSegSide its only used for 2 rendering functions, so being potentially inaccurate is not that dangerous and the speedup in some instances might be worth the tradeoff --- src/r_main.c | 23 ----------------------- src/r_main.h | 13 ++++++++++++- 2 files changed, 12 insertions(+), 24 deletions(-) diff --git a/src/r_main.c b/src/r_main.c index 2f7ecfb6e..4d79fda92 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -325,29 +325,6 @@ PUREFUNC INT32 R_PointOnSide(fixed_t x, fixed_t y, const node_t *restrict node) (~mask & (FixedMul(y, node->dx>>FRACBITS) >= FixedMul(node->dy>>FRACBITS, x))); } -// killough 5/2/98: reformatted -PUREFUNC INT32 R_PointOnSegSide(fixed_t x, fixed_t y, const seg_t *line) -{ - fixed_t lx = line->v1->x; - fixed_t ly = line->v1->y; - fixed_t ldx = line->v2->x - lx; - fixed_t ldy = line->v2->y - ly; - - if (!ldx) - return x <= lx ? ldy > 0 : ldy < 0; - - if (!ldy) - return y <= ly ? ldx < 0 : ldx > 0; - - x -= lx; - y -= ly; - - // Try to quickly decide by looking at sign bits. - if ((ldy ^ ldx ^ x ^ y) < 0) - return (ldy ^ x) < 0; // (left is negative) - return FixedMul(y, ldx>>FRACBITS) >= FixedMul(ldy>>FRACBITS, x); -} - // // R_PointToAngle // To get a global angle from cartesian coordinates, diff --git a/src/r_main.h b/src/r_main.h index 2d7503ea7..0bfa8bfa5 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -73,7 +73,18 @@ extern lighttable_t *zlight[LIGHTLEVELS][MAXLIGHTZ]; // Utility functions. INT32 R_PointOnSide(fixed_t x, fixed_t y, const node_t *node); -INT32 R_PointOnSegSide(fixed_t x, fixed_t y, const seg_t *line); + +FUNCINLINE static ATTRINLINE PUREFUNC INT32 R_PointOnSegSide(fixed_t x, fixed_t y, const seg_t *line) +{ + fixed_t lx = line->v1->x; + fixed_t ly = line->v1->y; + fixed_t ldx = line->v2->x - lx; + fixed_t ldy = line->v2->y - ly; + + // heavily optimized version of R_PointOnSide, stolen from GZDoom. + return (INT64)(y - ly) * ldx + (INT64)(lx - x) * ldy > 0; +} + angle_t R_PointToAngle(fixed_t x, fixed_t y); angle_t R_PointToAngle64(INT64 x, INT64 y); angle_t R_PointToAngle2(fixed_t px2, fixed_t py2, fixed_t px1, fixed_t py1); From 2c665fef6f5b177b09790abfb9b076cc792e49e1 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 20 Oct 2024 15:21:42 +0200 Subject: [PATCH 09/11] remove this again --- src/r_things.c | 27 --------------------------- src/r_things.h | 3 --- 2 files changed, 30 deletions(-) diff --git a/src/r_things.c b/src/r_things.c index a5c09dc13..61fdef8dc 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -1122,7 +1122,6 @@ static void R_ProjectSprite(mobj_t *thing) fixed_t xscale, yscale, sortscale; //added : 02-02-98 : aaargll..if I were a math-guy!!! INT32 x1, x2; - INT32 x1test = 0, x2test = 0; spritedef_t *sprdef; spriteframe_t *sprframe; @@ -1525,11 +1524,6 @@ static void R_ProjectSprite(mobj_t *thing) //x1 = (centerxfrac + FixedMul(tx,xscale))>>FRACBITS; x1 = centerx + (FixedMul(tx,xscale) / FRACUNIT); - x1test = (centerxfrac + FixedMul(tx,xscale))>>FRACBITS; - - if (x1test > viewwidth) - x1test = 0; - // off the right side? if (x1 > viewwidth) return; @@ -1538,11 +1532,6 @@ static void R_ProjectSprite(mobj_t *thing) //x2 = ((centerxfrac + FixedMul(tx,xscale))>>FRACBITS); x2--; x2 = (centerx + (FixedMul(tx,xscale) / FRACUNIT)) - 1; - x2test = ((centerxfrac + FixedMul(tx,xscale))>>FRACBITS) - 1; - - if (x2test < 0) - x2test = 0; - // off the left side if (x2 < 0) return; @@ -1554,12 +1543,6 @@ static void R_ProjectSprite(mobj_t *thing) if (x2 < portalclipstart || x1 >= portalclipend) return; - if (x2test < portalclipstart || x1test >= portalclipend) - { - x1test = 0; - x2test = 0; - } - if (P_PointOnLineSide(interp.x, interp.y, portalclipline) != 0) return; } @@ -1653,9 +1636,6 @@ static void R_ProjectSprite(mobj_t *thing) vis->x1 = x1 < portalclipstart ? portalclipstart : x1; vis->x2 = x2 >= portalclipend ? portalclipend-1 : x2; - vis->x1test = x1test < portalclipstart ? portalclipstart : x1test; - vis->x2test = x2test >= portalclipend ? portalclipend-1 : x2test; - vis->sector = thing->subsector->sector; vis->szt = (INT16)((centeryfrac - FixedMul(vis->gzt - viewz, sortscale))>>FRACBITS); vis->sz = (INT16)((centeryfrac - FixedMul(vis->gz - viewz, sortscale))>>FRACBITS); @@ -1681,7 +1661,6 @@ static void R_ProjectSprite(mobj_t *thing) { vis->startfrac = spr_width-1; vis->xiscale = -iscale; - vis->xiscaletest = -vis->xiscaletest; } else { @@ -1689,13 +1668,10 @@ static void R_ProjectSprite(mobj_t *thing) vis->xiscale = iscale; } - vis->startfractest = vis->startfrac; - if (vis->x1 > x1) { vis->startfrac += FixedDiv(vis->xiscale, this_scale) * (vis->x1 - x1); vis->scale += FixedMul(scalestep, spriteyscale) * (vis->x1 - x1); - vis->startfractest += FixedDiv(vis->xiscaletest, this_scale) * (vis->x1test - x1test); } //Fab: lumppat is the lump number of the patch to use, this is different @@ -1905,9 +1881,6 @@ static void R_ProjectPrecipitationSprite(precipmobj_t *thing) vis->x1 = x1 < portalclipstart ? portalclipstart : x1; vis->x2 = x2 >= portalclipend ? portalclipend-1 : x2; - vis->x1test = 0; - vis->x2test = 0; - vis->xscale = xscale; //SoM: 4/17/2000 vis->sector = thing->subsector->sector; vis->szt = (INT16)((centeryfrac - FixedMul(vis->gzt - viewz, yscale))>>FRACBITS); diff --git a/src/r_things.h b/src/r_things.h index ce0f9f841..898cc7ecd 100644 --- a/src/r_things.h +++ b/src/r_things.h @@ -143,9 +143,6 @@ typedef struct vissprite_s mobj_t *mobj; // for easy access INT32 x1, x2; - INT32 x1test, x2test; - fixed_t xiscaletest; - fixed_t startfractest; fixed_t gx, gy; // for line side calculation fixed_t gz, gzt; // global bottom/top for silhouette clipping From de1b801bdaec9e6cfde830e7807f08dde7b58498 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 20 Oct 2024 15:59:31 +0200 Subject: [PATCH 10/11] try to take some registers for span drawers too --- src/r_draw8.c | 57 ++++++++++++++++++++++++++------------------------- 1 file changed, 29 insertions(+), 28 deletions(-) diff --git a/src/r_draw8.c b/src/r_draw8.c index bf3b9740d..3c7562beb 100644 --- a/src/r_draw8.c +++ b/src/r_draw8.c @@ -681,14 +681,14 @@ void R_DrawSpan_8 (void) fixed_t xposition; fixed_t yposition; fixed_t xstep, ystep; - UINT32 bit; + register UINT32 bit; UINT8 *source; UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; const UINT8 *deststop = screens[0] + vid.rowbytes * vid.height; - size_t count = (ds_x2 - ds_x1 + 1); + register size_t count = (ds_x2 - ds_x1 + 1); size_t i; xposition = ds_xfrac; yposition = ds_yfrac; @@ -776,13 +776,13 @@ void R_DrawTiltedSpan_8(void) UINT8 *source; UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; double startz, startu, startv; double izstep, uzstep, vzstep; double endz, endu, endv; UINT32 stepu, stepv; - UINT32 bit; + register UINT32 bit; iz = ds_szp->z + ds_szp->y*(centery-ds_y) + ds_szp->x*(ds_x1-centerx); @@ -917,13 +917,13 @@ void R_DrawTiltedTranslucentSpan_8(void) UINT8 *source; UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; double startz, startu, startv; double izstep, uzstep, vzstep; double endz, endu, endv; UINT32 stepu, stepv; - UINT32 bit; + register UINT32 bit; iz = ds_szp->z + ds_szp->y*(centery-ds_y) + ds_szp->x*(ds_x1-centerx); @@ -1059,14 +1059,14 @@ void R_DrawTiltedTranslucentWaterSpan_8(void) UINT8 *source; UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; UINT8 *dsrc; double startz, startu, startv; double izstep, uzstep, vzstep; double endz, endu, endv; UINT32 stepu, stepv; - UINT32 bit; + register UINT32 bit; iz = ds_szp->z + ds_szp->y*(centery-ds_y) + ds_szp->x*(ds_x1-centerx); @@ -1200,7 +1200,7 @@ void R_DrawTiltedSplat_8(void) UINT8 *source; UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; UINT8 val; @@ -1208,7 +1208,7 @@ void R_DrawTiltedSplat_8(void) double izstep, uzstep, vzstep; double endz, endu, endv; UINT32 stepu, stepv; - UINT32 bit; + register UINT32 bit; iz = ds_szp->z + ds_szp->y*(centery-ds_y) + ds_szp->x*(ds_x1-centerx); @@ -1352,13 +1352,13 @@ void R_DrawSplat_8 (void) UINT32 xposition; UINT32 yposition; UINT32 xstep, ystep; - UINT32 bit; + register UINT32 bit; UINT8 *source; UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; - size_t count; + register size_t count; size_t i; UINT32 val; @@ -1422,13 +1422,13 @@ void R_DrawTranslucentSplat_8 (void) UINT32 xposition; UINT32 yposition; UINT32 xstep, ystep; - UINT32 bit; + register UINT32 bit; UINT8 *source; UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; - size_t count; + register size_t count; size_t i; UINT8 val; @@ -1487,14 +1487,14 @@ void R_DrawTranslucentSpan_8 (void) fixed_t xposition; fixed_t yposition; fixed_t xstep, ystep; - UINT32 bit; + register UINT32 bit; UINT8 *source; UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; const UINT8 *deststop = screens[0] + vid.rowbytes * vid.height; - size_t count = (ds_x2 - ds_x1 + 1); + register size_t count = (ds_x2 - ds_x1 + 1); size_t i; xposition = ds_xfrac; yposition = ds_yfrac; @@ -1546,14 +1546,14 @@ void R_DrawTranslucentWaterSpan_8(void) UINT32 xposition; UINT32 yposition; UINT32 xstep, ystep; - UINT32 bit; + register UINT32 bit; UINT8 *source; UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; UINT8 *dsrc; - size_t count; + register size_t count; size_t i; // SoM: we only need 6 bits for the integer part (0 thru 63) so the rest @@ -1605,9 +1605,9 @@ void R_DrawTranslucentWaterSpan_8(void) void R_DrawFogSpan_8(void) { UINT8 *colormap; - UINT8 *dest; + register UINT8 *dest; - size_t count; + register size_t count; colormap = ds_colormap; //dest = ylookup[ds_y] + columnofs[ds_x1]; @@ -1638,8 +1638,8 @@ void R_DrawFogSpan_8(void) */ void R_DrawFogColumn_8(void) { - INT32 count; - UINT8 *dest; + register INT32 count; + register UINT8 *dest; count = dc_yh - dc_yl; @@ -1674,7 +1674,8 @@ void R_DrawFogColumn_8(void) */ void R_DrawColumnShadowed_8(void) { - INT32 count, realyh, i, height, bheight = 0, solid = 0; + register INT32 count; + INT32 realyh, i, height, bheight = 0, solid = 0; realyh = dc_yh; From 81d415c5ba9bc62b7344f5e10d0573e70c975ae9 Mon Sep 17 00:00:00 2001 From: Alug Date: Sun, 20 Oct 2024 16:25:12 +0200 Subject: [PATCH 11/11] attempt to optimize some p_maputl stuff --- src/p_maputl.c | 91 +++++++++++++++----------------------------------- 1 file changed, 27 insertions(+), 64 deletions(-) diff --git a/src/p_maputl.c b/src/p_maputl.c index 3c91dc922..f2fc0867e 100644 --- a/src/p_maputl.c +++ b/src/p_maputl.c @@ -35,33 +35,23 @@ void P_ClosestPointOnLine(fixed_t x, fixed_t y, line_t *line, vertex_t *result) fixed_t dy = line->dy; // Determine t (the length of the vector from �Line[0]� to �p�) - fixed_t cx, cy; - fixed_t vx, vy; fixed_t magnitude; fixed_t t; - //Sub (p, &Line[0], &c); - cx = x - startx; - cy = y - starty; - - //Sub (&Line[1], &Line[0], &V); - vx = dx; - vy = dy; - //Normalize (&V, &V); magnitude = R_PointToDist2(line->v2->x, line->v2->y, startx, starty); - vx = FixedDiv(vx, magnitude); - vy = FixedDiv(vy, magnitude); + dx = FixedDiv(dx, magnitude); + dy = FixedDiv(dy, magnitude); - t = (FixedMul(vx, cx) + FixedMul(vy, cy)); + t = (FixedMul(dx, (x - startx)) + FixedMul(dy, (y - starty))); // Return the point between �Line[0]� and �Line[1]� - vx = FixedMul(vx, t); - vy = FixedMul(vy, t); + dx = FixedMul(dx, t); + dy = FixedMul(dy, t); //Add (&Line[0], &V, out); - result->x = startx + vx; - result->y = starty + vy; + result->x = startx + dx; + result->y = starty + dy; return; } @@ -79,28 +69,15 @@ void P_ClosestPointOnLine3D(fixed_t x, fixed_t y, fixed_t z, line_t *line, verte fixed_t dz = line->v2->z - line->v1->z; // Determine t (the length of the vector from �Line[0]� to �p�) - fixed_t cx, cy, cz; - fixed_t vx, vy, vz; fixed_t magnitude; fixed_t t; - //Sub (p, &Line[0], &c); - cx = x - startx; - cy = y - starty; - cz = z - startz; - - //Sub (&Line[1], &Line[0], &V); - vx = dx; - vy = dy; - vz = dz; - - //Normalize (&V, &V); magnitude = R_PointToDist2(0, line->v2->z, R_PointToDist2(line->v2->x, line->v2->y, startx, starty), startz); - vx = FixedDiv(vx, magnitude); - vy = FixedDiv(vy, magnitude); - vz = FixedDiv(vz, magnitude); + dx = FixedDiv(dx, magnitude); + dy = FixedDiv(dy, magnitude); + dz = FixedDiv(dz, magnitude); - t = (FixedMul(vx, cx) + FixedMul(vy, cy) + FixedMul(vz, cz)); + t = (FixedMul(dx, (x - startx)) + FixedMul(dy, (y - starty)) + FixedMul(dz, (z - startz))); // Set closest point to the end if it extends past -Red if (t <= 0) @@ -119,14 +96,14 @@ void P_ClosestPointOnLine3D(fixed_t x, fixed_t y, fixed_t z, line_t *line, verte } // Return the point between �Line[0]� and �Line[1]� - vx = FixedMul(vx, t); - vy = FixedMul(vy, t); - vz = FixedMul(vz, t); + dx = FixedMul(dx, t); + dy = FixedMul(dy, t); + dz = FixedMul(dz, t); //Add (&Line[0], &V, out); - result->x = startx + vx; - result->y = starty + vy; - result->z = startz + vz; + result->x = startx + dx; + result->y = starty + dy; + result->z = startz + dz; return; } @@ -136,21 +113,16 @@ void P_ClosestPointOnLine3D(fixed_t x, fixed_t y, fixed_t z, line_t *line, verte // INT32 P_PointOnLineSide(fixed_t x, fixed_t y, const line_t *line) { - fixed_t dx, dy, left, right; - if (!line->dx) return x <= line->v1->x ? line->dy > 0 : line->dy < 0; if (!line->dy) return y <= line->v1->y ? line->dx < 0 : line->dx > 0; - dx = (x - line->v1->x); - dy = (y - line->v1->y); + x -= line->v1->x; + y -= line->v1->y; - left = FixedMul(line->dy>>FRACBITS, dx); - right = FixedMul(dy, line->dx>>FRACBITS); - - return right < left ? 0 : 1; + return FixedMul(y, line->dx>>FRACBITS) < FixedMul(line->dy>>FRACBITS, x) ? 0 : 1; } // @@ -210,28 +182,22 @@ INT32 P_BoxOnLineSide(fixed_t *tmbox, const line_t *ld) // static INT32 P_PointOnDivlineSide(fixed_t x, fixed_t y, divline_t *line) { - fixed_t dx, dy, left, right; - if (!line->dx) return x <= line->x ? line->dy > 0 : line->dy < 0; if (!line->dy) return y <= line->y ? line->dx < 0 : line->dx > 0; - dx = (x - line->x); - dy = (y - line->y); + x -= line->x; + y -= line->y; // try to quickly decide by looking at sign bits - if ((line->dy ^ line->dx ^ dx ^ dy) & 0x80000000) - return ((line->dy ^ dx) & 0x80000000) ? 1 : 0; + if ((line->dy ^ line->dx ^ x ^ y) & 0x80000000) + return ((line->dy ^ x) & 0x80000000) ? 1 : 0; - left = FixedMul(line->dy>>8, dx>>8); - right = FixedMul(dy>>8, line->dx>>8); - - return right < left ? 0 : 1; + return FixedMul(y>>8, line->dx>>8) < FixedMul(line->dy>>8, x>>8) ? 0 : 1; } - // // P_MakeDivline // @@ -250,17 +216,14 @@ void P_MakeDivline(line_t *li, divline_t *dl) // fixed_t P_InterceptVector(divline_t *v2, divline_t *v1) { - fixed_t frac, num, den; + fixed_t 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 (FixedDiv(FixedMul((v1->x - v2->x)>>8, v1->dy) + FixedMul((v2->y - v1->y)>>8, v1->dx), den)); } //