diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 13f819664..f90d18450 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -53,6 +53,8 @@ #define ABS(x) ((x) < 0 ? -(x) : (x)) +#define SOFTLIGHT(llevel) HWR_ShouldUsePaletteRendering() ? ((llevel) >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : (llevel) + // ========================================================================== // the hardware driver object // ========================================================================== @@ -1129,7 +1131,7 @@ static void HWR_SplitWall(sector_t *sector, FOutVector *wallVerts, INT32 texnum, { if (HWR_ShouldUsePaletteRendering()) { - lightnum = (pfloor->master->frontsector->lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT; + lightnum = SOFTLIGHT(pfloor->master->frontsector->lightlevel); colormap = pfloor->master->frontsector->extra_colormap; lightnum = colormap ? lightnum : HWR_CalcWallLight(lightnum, v1x, v1y, v2x, v2y); }else{ @@ -1141,7 +1143,7 @@ static void HWR_SplitWall(sector_t *sector, FOutVector *wallVerts, INT32 texnum, { if (HWR_ShouldUsePaletteRendering()) { - lightnum = (*list[i].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT; + lightnum = SOFTLIGHT(*list[i].lightlevel); colormap = list[i].extra_colormap; lightnum = colormap ? lightnum : HWR_CalcWallLight(lightnum, v1x, v1y, v2x, v2y); }else{ @@ -1541,7 +1543,7 @@ void HWR_ProcessSeg(void) // Sort of like GLWall::Process in GZDoom if (HWR_ShouldUsePaletteRendering()) { - lightnum = (gr_frontsector->lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT; + lightnum = SOFTLIGHT(gr_frontsector->lightlevel); colormap = gr_frontsector->extra_colormap; lightnum = colormap ? lightnum : HWR_CalcWallLight(lightnum, vs.x, vs.y, ve.x, ve.y); }else{ @@ -2489,7 +2491,7 @@ void HWR_ProcessSeg(void) // Sort of like GLWall::Process in GZDoom if (HWR_ShouldUsePaletteRendering()) { - lightnum = (rover->master->frontsector->lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT; + lightnum = SOFTLIGHT(rover->master->frontsector->lightlevel); colormap = rover->master->frontsector->extra_colormap; lightnum = colormap ? lightnum : HWR_CalcWallLight(lightnum, vs.x, vs.y, ve.x, ve.y); }else{ @@ -2640,7 +2642,7 @@ void HWR_ProcessSeg(void) // Sort of like GLWall::Process in GZDoom if (HWR_ShouldUsePaletteRendering()) { - lightnum = (rover->master->frontsector->lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT; + lightnum = SOFTLIGHT(rover->master->frontsector->lightlevel); colormap = rover->master->frontsector->extra_colormap; lightnum = colormap ? lightnum : HWR_CalcWallLight(lightnum, vs.x, vs.y, ve.x, ve.y); }else{ @@ -3479,12 +3481,12 @@ void HWR_Subsector(size_t num) light = R_GetPlaneLight(gr_frontsector, locFloorHeight, false); if (gr_frontsector->floorlightsec == -1) - floorlightlevel = HWR_ShouldUsePaletteRendering() ? (*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *gr_frontsector->lightlist[light].lightlevel; + floorlightlevel = SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel); floorcolormap = gr_frontsector->lightlist[light].extra_colormap; light = R_GetPlaneLight(gr_frontsector, locCeilingHeight, false); if (gr_frontsector->ceilinglightsec == -1) - ceilinglightlevel = HWR_ShouldUsePaletteRendering() ? (*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *gr_frontsector->lightlist[light].lightlevel;; + ceilinglightlevel = SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel); ceilingcolormap = gr_frontsector->lightlist[light].extra_colormap; } @@ -3559,16 +3561,13 @@ void HWR_Subsector(size_t num) light = R_GetPlaneLight(gr_frontsector, centerHeight, viewz < cullHeight ? true : false); - if (HWR_ShouldUsePaletteRendering()) - alpha = HWR_FogBlockAlpha((*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT, rover->master->frontsector->extra_colormap); - else - alpha = HWR_FogBlockAlpha(*gr_frontsector->lightlist[light].lightlevel, rover->master->frontsector->extra_colormap); + alpha = HWR_FogBlockAlpha(SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel), rover->master->frontsector->extra_colormap); HWR_AddTransparentFloor(0, &extrasubsectors[num], false, *rover->bottomheight, - HWR_ShouldUsePaletteRendering() ? (*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *gr_frontsector->lightlist[light].lightlevel, + SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel), alpha, rover->master->frontsector, PF_Fog|PF_NoTexture, true, rover->master->frontsector->extra_colormap); } @@ -3579,7 +3578,7 @@ void HWR_Subsector(size_t num) &extrasubsectors[num], false, *rover->bottomheight, - HWR_ShouldUsePaletteRendering() ? (*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *gr_frontsector->lightlist[light].lightlevel, + SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel), max(0, min(rover->alpha, 255)), rover->master->frontsector, (rover->flags & FF_RIPPLE ? PF_Ripple : 0)|PF_Translucent, false, gr_frontsector->lightlist[light].extra_colormap); } @@ -3587,7 +3586,7 @@ void HWR_Subsector(size_t num) { HWR_GetFlat(levelflats[*rover->bottompic].lumpnum, R_NoEncore(gr_frontsector, false)); light = R_GetPlaneLight(gr_frontsector, centerHeight, viewz < cullHeight ? true : false); - HWR_RenderPlane(sub, &extrasubsectors[num], false, *rover->bottomheight, (rover->flags & FF_RIPPLE ? PF_Ripple : 0)|PF_Occlude, HWR_ShouldUsePaletteRendering() ? (*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *gr_frontsector->lightlist[light].lightlevel, levelflats[*rover->bottompic].lumpnum, + HWR_RenderPlane(sub, &extrasubsectors[num], false, *rover->bottomheight, (rover->flags & FF_RIPPLE ? PF_Ripple : 0)|PF_Occlude, SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel), levelflats[*rover->bottompic].lumpnum, rover->master->frontsector, 255, gr_frontsector->lightlist[light].extra_colormap); } } @@ -3613,17 +3612,14 @@ void HWR_Subsector(size_t num) UINT8 alpha; light = R_GetPlaneLight(gr_frontsector, centerHeight, viewz < cullHeight ? true : false); - - if (HWR_ShouldUsePaletteRendering()) - alpha = HWR_FogBlockAlpha((*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT, rover->master->frontsector->extra_colormap); - else - alpha = HWR_FogBlockAlpha(*gr_frontsector->lightlist[light].lightlevel, rover->master->frontsector->extra_colormap); + + alpha = HWR_FogBlockAlpha(SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel), rover->master->frontsector->extra_colormap); HWR_AddTransparentFloor(0, &extrasubsectors[num], true, *rover->topheight, - HWR_ShouldUsePaletteRendering() ? (*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *gr_frontsector->lightlist[light].lightlevel, + SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel), alpha, rover->master->frontsector, PF_Fog|PF_NoTexture, true, rover->master->frontsector->extra_colormap); } @@ -3634,7 +3630,7 @@ void HWR_Subsector(size_t num) &extrasubsectors[num], true, *rover->topheight, - HWR_ShouldUsePaletteRendering() ? (*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *gr_frontsector->lightlist[light].lightlevel, + SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel), max(0, min(rover->alpha, 255)), rover->master->frontsector, (rover->flags & FF_RIPPLE ? PF_Ripple : 0)|PF_Translucent, false, gr_frontsector->lightlist[light].extra_colormap); } @@ -3642,7 +3638,7 @@ void HWR_Subsector(size_t num) { HWR_GetFlat(levelflats[*rover->toppic].lumpnum, R_NoEncore(gr_frontsector, true)); light = R_GetPlaneLight(gr_frontsector, centerHeight, viewz < cullHeight ? true : false); - HWR_RenderPlane(sub, &extrasubsectors[num], true, *rover->topheight, (rover->flags & FF_RIPPLE ? PF_Ripple : 0)|PF_Occlude, HWR_ShouldUsePaletteRendering() ? (*gr_frontsector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *gr_frontsector->lightlist[light].lightlevel, levelflats[*rover->toppic].lumpnum, + HWR_RenderPlane(sub, &extrasubsectors[num], true, *rover->topheight, (rover->flags & FF_RIPPLE ? PF_Ripple : 0)|PF_Occlude, SOFTLIGHT(*gr_frontsector->lightlist[light].lightlevel), levelflats[*rover->toppic].lumpnum, rover->master->frontsector, 255, gr_frontsector->lightlist[light].extra_colormap); } } @@ -4112,8 +4108,10 @@ static void HWR_RotateSpritePolyToAim(gr_vissprite_t *spr, FOutVector *wallVerts interpmobjstate_t interp = {0}; float basey, lowy; + INT32 dist = R_QuickCamDist(spr->mobj->x, spr->mobj->y); + // do interpolation - if (R_UsingFrameInterpolation() && !paused) + if (R_UsingFrameInterpolation() && !paused && (!cv_grmaxinterpdist.value || dist < cv_grmaxinterpdist.value)) { if (precip) { @@ -4314,7 +4312,7 @@ static void HWR_SplitSprite(gr_vissprite_t *spr) // Start with the lightlevel and colormap from the top of the sprite - lightlevel = HWR_ShouldUsePaletteRendering() ? (*list[sector->numlights - 1].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *list[sector->numlights - 1].lightlevel; + lightlevel = SOFTLIGHT(*list[sector->numlights - 1].lightlevel); colormap = list[sector->numlights - 1].extra_colormap; i = 0; @@ -4331,7 +4329,7 @@ static void HWR_SplitSprite(gr_vissprite_t *spr) if (h <= temp) { if (!(spr->mobj->frame & FF_FULLBRIGHT)) - lightlevel = *list[i-1].lightlevel > 255 ? 255 : HWR_ShouldUsePaletteRendering() ? (*list[i-1].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *list[i-1].lightlevel; + lightlevel = *list[i-1].lightlevel > 255 ? 255 : SOFTLIGHT(*list[i-1].lightlevel); colormap = list[i-1].extra_colormap; break; } @@ -4339,7 +4337,7 @@ static void HWR_SplitSprite(gr_vissprite_t *spr) #else i = R_GetPlaneLight(sector, temp, false); if (!(spr->mobj->frame & FF_FULLBRIGHT)) - lightlevel = *list[i].lightlevel > 255 ? 255 : HWR_ShouldUsePaletteRendering() ? (*list[i].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *list[i].lightlevel; + lightlevel = *list[i].lightlevel > 255 ? 255 : SOFTLIGHT(*list[i].lightlevel); colormap = list[i].extra_colormap; #endif @@ -4355,7 +4353,7 @@ static void HWR_SplitSprite(gr_vissprite_t *spr) if (!(list[i].flags & FF_NOSHADE) && (list[i].flags & FF_CUTSPRITES)) { if (!(spr->mobj->frame & FF_FULLBRIGHT)) - lightlevel = *list[i].lightlevel > 255 ? 255 : HWR_ShouldUsePaletteRendering() ? (*list[i].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *list[i].lightlevel; + lightlevel = *list[i].lightlevel > 255 ? 255 : SOFTLIGHT(*list[i].lightlevel); colormap = list[i].extra_colormap; } @@ -4646,7 +4644,7 @@ static void HWR_DrawSprite(gr_vissprite_t *spr) extracolormap_t *colormap = sector->extra_colormap; if (!(spr->mobj->frame & FF_FULLBRIGHT)) - lightlevel = sector->lightlevel > 255 ? 255 : HWR_ShouldUsePaletteRendering() ? (sector->lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : sector->lightlevel; + lightlevel = sector->lightlevel > 255 ? 255 : SOFTLIGHT(sector->lightlevel); HWR_Lighting(&Surf, lightlevel, colormap); } @@ -4747,7 +4745,7 @@ static inline void HWR_DrawPrecipitationSprite(gr_vissprite_t *spr) light = R_GetPlaneLight(sector, spr->mobj->z + spr->mobj->height, false); // Always use the light at the top instead of whatever I was doing before if (!(spr->mobj->frame & FF_FULLBRIGHT)) - lightlevel = *sector->lightlist[light].lightlevel > 255 ? 255 : HWR_ShouldUsePaletteRendering() ? (*sector->lightlist[light].lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : *sector->lightlist[light].lightlevel; + lightlevel = *sector->lightlist[light].lightlevel > 255 ? 255 : SOFTLIGHT(*sector->lightlist[light].lightlevel); if (sector->lightlist[light].extra_colormap) colormap = sector->lightlist[light].extra_colormap; @@ -4755,7 +4753,7 @@ static inline void HWR_DrawPrecipitationSprite(gr_vissprite_t *spr) else { if (!(spr->mobj->frame & FF_FULLBRIGHT)) - lightlevel = sector->lightlevel > 255 ? 255 : HWR_ShouldUsePaletteRendering() ? (sector->lightlevel >> LIGHTSEGSHIFT) << LIGHTSEGSHIFT : sector->lightlevel; + lightlevel = sector->lightlevel > 255 ? 255 : SOFTLIGHT(sector->lightlevel); if (sector->extra_colormap) colormap = sector->extra_colormap; @@ -4817,6 +4815,7 @@ static int CompareVisSprites(const void *p1, const void *p2) return -1; } +#undef SOFTLIGHT static void HWR_SortVisSprites(void) { @@ -5326,7 +5325,9 @@ void HWR_ProjectSprite(mobj_t *thing) if (!thing) return; - if (R_UsingFrameInterpolation() && !paused) + INT32 dist = R_QuickCamDist(thing->x, thing->y); + + if (R_UsingFrameInterpolation() && !paused && (!cv_grmaxinterpdist.value || dist < cv_grmaxinterpdist.value)) { R_InterpolateMobjState(thing, rendertimefrac, &interp); } @@ -5666,12 +5667,14 @@ void HWR_ProjectPrecipitationSprite(precipmobj_t *thing) if (!thing) return; - + + INT32 dist = R_QuickCamDist(thing->x, thing->y); + // uncapped/interpolation interpmobjstate_t interp = {0}; // do interpolation - if (R_UsingFrameInterpolation() && !paused) + if (R_UsingFrameInterpolation() && !paused && (!cv_grmaxinterpdist.value || dist < cv_grmaxinterpdist.value)) { R_InterpolatePrecipMobjState(thing, rendertimefrac, &interp); } diff --git a/src/hardware/hw_md2.c b/src/hardware/hw_md2.c index 96a9d12da..b98d6cadd 100644 --- a/src/hardware/hw_md2.c +++ b/src/hardware/hw_md2.c @@ -1163,7 +1163,7 @@ void HWR_DrawMD2(gr_vissprite_t *spr) angle_t ang; interpmobjstate_t interp; - if (R_UsingFrameInterpolation() && !paused) + if (R_UsingFrameInterpolation() && !paused && (!cv_grmaxinterpdist.value || R_QuickCamDist(spr->mobj->x, spr->mobj->y) < cv_grmaxinterpdist.value)) { R_InterpolateMobjState(spr->mobj, rendertimefrac, &interp); } diff --git a/src/m_menu.c b/src/m_menu.c index e7471caf4..44d87ba59 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -1406,28 +1406,32 @@ static menuitem_t OP_ColorOptionsMenu[] = static menuitem_t OP_ExpOptionsMenu[] = { {IT_HEADER, NULL, "Experimental Options", NULL, 10}, - {IT_STRING | IT_CVAR, NULL, "Weather Interpolation", &cv_precipinterp, 25}, - {IT_STRING | IT_CVAR, NULL, "Less Weather Effects", &cv_lessprecip, 35}, + {IT_STRING|IT_CVAR, NULL, "Interpolation Distance", &cv_grmaxinterpdist, 25}, + {IT_STRING|IT_CVAR, NULL, "Mobj Subsector Interpolation", &cv_mobjssector, 35}, + {IT_STRING | IT_CVAR, NULL, "Weather Interpolation", &cv_precipinterp, 45}, + {IT_STRING | IT_CVAR, NULL, "Less Weather Effects", &cv_lessprecip, 55}, - {IT_STRING | IT_CVAR, NULL, "VHS effect", &cv_vhseffect, 55}, + {IT_STRING | IT_CVAR, NULL, "VHS effect", &cv_vhseffect, 75}, - {IT_STRING | IT_CVAR, NULL, "FFloorclip", &cv_ffloorclip, 75}, - {IT_STRING | IT_CVAR, NULL, "Spriteclip", &cv_spriteclip, 85}, + {IT_STRING | IT_CVAR, NULL, "FFloorclip", &cv_ffloorclip, 95}, + {IT_STRING | IT_CVAR, NULL, "Spriteclip", &cv_spriteclip, 105}, #ifdef HWRENDER - {IT_STRING | IT_CVAR, NULL, "Screen Textures", &cv_grscreentextures, 75}, + {IT_STRING | IT_CVAR, NULL, "Screen Textures", &cv_grscreentextures, 95}, - {IT_STRING | IT_CVAR, NULL, "Palette Depth", &cv_grpalettedepth, 85}, + {IT_STRING | IT_CVAR, NULL, "Palette Depth", &cv_grpalettedepth, 105}, - {IT_STRING | IT_CVAR, NULL, "Splitwall/Slope texture fix", &cv_splitwallfix, 105}, - {IT_STRING | IT_CVAR, NULL, "Slope midtexture peg fix", &cv_slopepegfix, 115}, - {IT_STRING | IT_CVAR, NULL, "ZFighting fix for fofs", &cv_fofzfightfix, 125}, - {IT_STRING | IT_CVAR, NULL, "FOF wall cutoff for slopes", &cv_grfofcut, 135}, + {IT_STRING | IT_CVAR, NULL, "Splitwall/Slope texture fix", &cv_splitwallfix, 125}, + {IT_STRING | IT_CVAR, NULL, "Slope midtexture peg fix", &cv_slopepegfix, 135}, + {IT_STRING | IT_CVAR, NULL, "ZFighting fix for fofs", &cv_fofzfightfix, 145}, + {IT_STRING | IT_CVAR, NULL, "FOF wall cutoff for slopes", &cv_grfofcut, 155}, #endif }; static const char* OP_ExpTooltips[] = { NULL, + "How far Mobj interpolation should take effect.", + "Toggles Mobj Subsector Interpolation.", "Should weather be interpolated? Weather should look about the\nsame but perform a bit better when disabled.", "When weather is on this will cut the object amount used in half.", "Show a VHS-like effect when the game is paused\n or youre rewinding replays.", @@ -1446,6 +1450,8 @@ static const char* OP_ExpTooltips[] = enum { op_exp_header, + op_exp_interpdist, + op_exp_mobjssector, op_exp_precipinter, op_exp_lessprecip, op_exp_vhs, diff --git a/src/r_fps.c b/src/r_fps.c index 07d34992d..33cd206c7 100644 --- a/src/r_fps.c +++ b/src/r_fps.c @@ -16,6 +16,7 @@ #include "r_main.h" #include "g_game.h" +#include "k_kart.h" // saltyhop stuffs #include "i_video.h" #include "r_plane.h" #include "p_spec.h" @@ -39,6 +40,8 @@ consvar_t cv_fpscap = {"fpscap", "Match refresh rate", CV_SAVE, fpscap_cons_t, N consvar_t cv_precipinterp = {"precipinterpolation", "On", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_mobjssector = {"mobjsubsectorinterp", "On", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; + UINT32 R_GetFramerateCap(void) { if (rendermode == render_none) @@ -95,7 +98,7 @@ static angle_t R_LerpAngle(angle_t from, angle_t to, fixed_t frac) return from + FixedMul(frac, to - from); } -static vector2_t *R_LerpVector2(const vector2_t *from, const vector2_t *to, fixed_t frac, vector2_t *out) +/*static vector2_t *R_LerpVector2(const vector2_t *from, const vector2_t *to, fixed_t frac, vector2_t *out) { FV2_SubEx(to, from, out); FV2_MulEx(out, frac, out); @@ -109,7 +112,7 @@ static vector3_t *R_LerpVector3(const vector3_t *from, const vector3_t *to, fixe FV3_MulEx(out, frac, out); FV3_AddEx(from, out, out); return out; -} +}*/ // recalc necessary stuff for mouseaiming // slopes are already calculated for the full possible view (which is 4*viewheight). @@ -252,7 +255,7 @@ void R_SetViewContext(enum viewcontext_e _viewcontext) } } -fixed_t R_InterpolateFixed(fixed_t from, fixed_t to) +/*fixed_t R_InterpolateFixed(fixed_t from, fixed_t to) { if (!R_UsingFrameInterpolation()) { @@ -270,7 +273,7 @@ angle_t R_InterpolateAngle(angle_t from, angle_t to) } return (R_LerpAngle(from, to, rendertimefrac)); -} +}*/ void R_InterpolateMobjState(mobj_t *mobj, fixed_t frac, interpmobjstate_t *out) { @@ -293,46 +296,87 @@ void R_InterpolateMobjState(mobj_t *mobj, fixed_t frac, interpmobjstate_t *out) return; } - out->x = R_LerpFixed(mobj->old_x, mobj->x, frac); - out->y = R_LerpFixed(mobj->old_y, mobj->y, frac); - out->z = R_LerpFixed(mobj->old_z, mobj->z, frac); - out->spritexscale = mobj->resetinterp ? mobj->spritexscale : R_LerpFixed(mobj->old_spritexscale, mobj->spritexscale, frac); - out->spriteyscale = mobj->resetinterp ? mobj->spriteyscale : R_LerpFixed(mobj->old_spriteyscale, mobj->spriteyscale, frac); - 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); - + if (mobj->x == mobj->old_x) + out->x = mobj->x; + else + out->x = R_LerpFixed(mobj->old_x, mobj->x, frac); + + if (mobj->y == mobj->old_y) + out->y = mobj->y; + else + out->y = R_LerpFixed(mobj->old_y, mobj->y, frac); + + if (mobj->z == mobj->old_z) + out->z = mobj->z; + else + out->z = R_LerpFixed(mobj->old_z, mobj->z, frac); + + if (mobj->spritexscale == mobj->old_spritexscale) + out->spritexscale = mobj->spritexscale; + else + out->spritexscale = mobj->resetinterp ? mobj->spritexscale : R_LerpFixed(mobj->old_spritexscale, mobj->spritexscale, frac); + + if (mobj->spriteyscale == mobj->old_spriteyscale) + out->spriteyscale = mobj->spriteyscale; + else + out->spriteyscale = mobj->resetinterp ? mobj->spriteyscale : R_LerpFixed(mobj->old_spriteyscale, mobj->spriteyscale, frac); + + if (mobj->spritexoffset == mobj->old_spritexoffset) + out->spritexoffset = mobj->spritexoffset; + else + out->spritexoffset = mobj->resetinterp ? mobj->spritexoffset : R_LerpFixed(mobj->old_spritexoffset, mobj->spritexoffset, frac); + + if (mobj->spriteyoffset == mobj->old_spriteyoffset) + out->spriteyoffset = mobj->spriteyoffset; + else + out->spriteyoffset = mobj->resetinterp ? mobj->spriteyoffset : R_LerpFixed(mobj->old_spriteyoffset, mobj->spriteyoffset, frac); + if (mobj->scale == mobj->old_scale) // Tiny optimisation - scale is usually unchanging, so let's skip a lerp, two FixedMuls, and two FixedDivs - { out->scale = mobj->scale; - } else - { out->scale = mobj->resetinterp ? mobj->scale : R_LerpFixed(mobj->old_scale, mobj->scale, frac); - } - // Sprite offsets are not interpolated until we have a way to interpolate them explicitly in Lua. - // It seems existing mods visually break more often than not if it is interpolated. - //out->spritexoffset = mobj->spritexoffset; - //out->spriteyoffset = mobj->spriteyoffset; - - out->subsector = R_PointInSubsector(out->x, out->y); + if (cv_mobjssector.value) + out->subsector = R_PointInSubsector(out->x, out->y); + else + out->subsector = mobj->subsector; if (mobj->player) { - out->angle = mobj->resetinterp ? mobj->player->frameangle : R_LerpAngle(mobj->player->old_frameangle, mobj->player->frameangle, frac); + if (mobj->angle == mobj->player->old_frameangle) + out->angle = mobj->player->frameangle; + else + out->angle = mobj->resetinterp ? mobj->player->frameangle : R_LerpAngle(mobj->player->old_frameangle, mobj->player->frameangle, frac); } else { - out->angle = mobj->resetinterp ? mobj->angle : R_LerpAngle(mobj->old_angle, mobj->angle, frac); + if (mobj->angle == mobj->old_angle) + out->angle = mobj->angle; + else + out->angle = mobj->resetinterp ? mobj->angle : R_LerpAngle(mobj->old_angle, mobj->angle, frac); } // pitch roll stuff - out->pitch = mobj->resetinterp ? mobj->pitch : R_LerpAngle(mobj->old_pitch, mobj->pitch, frac); - out->roll = mobj->resetinterp ? mobj->roll : R_LerpAngle(mobj->old_roll, mobj->roll, frac); + if (mobj->pitch == mobj->old_pitch) + out->pitch = mobj->pitch; + else + out->pitch = mobj->resetinterp ? mobj->pitch : R_LerpAngle(mobj->old_pitch, mobj->pitch, frac); + + if (mobj->roll == mobj->old_roll) + out->roll = mobj->roll; + else + out->roll = mobj->resetinterp ? mobj->roll : R_LerpAngle(mobj->old_roll, mobj->roll, frac); // and the slope stuff - out->slopepitch = mobj->resetinterp ? mobj->slopepitch : R_LerpAngle(mobj->old_slopepitch, mobj->slopepitch, frac); - out->sloperoll = mobj->resetinterp ? mobj->sloperoll : R_LerpAngle(mobj->old_sloperoll, mobj->sloperoll, frac); + if (mobj->slopepitch == mobj->old_slopepitch) + out->slopepitch = mobj->slopepitch; + else + out->slopepitch = mobj->resetinterp ? mobj->slopepitch : R_LerpAngle(mobj->old_slopepitch, mobj->slopepitch, frac); + + if (mobj->sloperoll == mobj->old_sloperoll) + out->sloperoll = mobj->sloperoll; + else + out->sloperoll = mobj->resetinterp ? mobj->sloperoll : R_LerpAngle(mobj->old_sloperoll, mobj->sloperoll, frac); } void R_InterpolatePrecipMobjState(precipmobj_t *mobj, fixed_t frac, interpmobjstate_t *out) @@ -361,9 +405,15 @@ void R_InterpolatePrecipMobjState(precipmobj_t *mobj, fixed_t frac, interpmobjst out->spritexoffset = mobj->spritexoffset; out->spriteyoffset = mobj->spriteyoffset; - out->subsector = R_PointInSubsector(out->x, out->y); + if (cv_mobjssector.value) + out->subsector = R_PointInSubsector(out->x, out->y); + else + out->subsector = mobj->subsector; - out->angle = R_LerpAngle(mobj->old_angle, mobj->angle, frac); + if (mobj->angle == mobj->old_angle) + out->angle = mobj->angle; + else + out->angle = R_LerpAngle(mobj->old_angle, mobj->angle, frac); } static void AddInterpolator(levelinterpolator_t* interpolator) @@ -463,7 +513,7 @@ void R_CreateInterpolator_Polyobj(thinker_t *thinker, polyobj_t *polyobj) interp->polyobj.oldcy = interp->polyobj.bakcy = polyobj->centerPt.y; } -void R_CreateInterpolator_DynSlope(thinker_t *thinker, pslope_t *slope) +/*void R_CreateInterpolator_DynSlope(thinker_t *thinker, pslope_t *slope) { levelinterpolator_t *interp = CreateInterpolator(LVLINTERP_DynSlope, thinker); interp->dynslope.slope = slope; @@ -475,7 +525,7 @@ void R_CreateInterpolator_DynSlope(thinker_t *thinker, pslope_t *slope) FV2_Copy(&interp->dynslope.bakd, &slope->d); interp->dynslope.oldzdelta = interp->dynslope.bakzdelta = slope->zdelta; -} +}*/ void R_InitializeLevelInterpolators(void) { @@ -519,7 +569,7 @@ static void UpdateLevelInterpolatorState(levelinterpolator_t *interp) interp->polyobj.bakcx = interp->polyobj.polyobj->centerPt.x; interp->polyobj.bakcy = interp->polyobj.polyobj->centerPt.y; break; - case LVLINTERP_DynSlope: + /*case LVLINTERP_DynSlope: FV3_Copy(&interp->dynslope.oldo, &interp->dynslope.bako); FV2_Copy(&interp->dynslope.oldd, &interp->dynslope.bakd); interp->dynslope.oldzdelta = interp->dynslope.bakzdelta; @@ -527,7 +577,7 @@ static void UpdateLevelInterpolatorState(levelinterpolator_t *interp) FV3_Copy(&interp->dynslope.bako, &interp->dynslope.slope->o); FV2_Copy(&interp->dynslope.bakd, &interp->dynslope.slope->d); interp->dynslope.bakzdelta = interp->dynslope.slope->zdelta; - break; + break;*/ } } @@ -573,44 +623,86 @@ void R_ApplyLevelInterpolators(fixed_t frac) case LVLINTERP_SectorPlane: if (interp->sectorplane.ceiling) { - interp->sectorplane.sector->ceilingheight = R_LerpFixed(interp->sectorplane.oldheight, interp->sectorplane.bakheight, frac); + if (interp->sectorplane.sector->ceilingheight == interp->sectorplane.oldheight) + interp->sectorplane.sector->ceilingheight = interp->sectorplane.bakheight; + else + interp->sectorplane.sector->ceilingheight = R_LerpFixed(interp->sectorplane.oldheight, interp->sectorplane.bakheight, frac); } else { - interp->sectorplane.sector->floorheight = R_LerpFixed(interp->sectorplane.oldheight, interp->sectorplane.bakheight, frac); + if (interp->sectorplane.sector->floorheight == interp->sectorplane.oldheight) + interp->sectorplane.sector->floorheight = interp->sectorplane.bakheight; + else + interp->sectorplane.sector->floorheight = R_LerpFixed(interp->sectorplane.oldheight, interp->sectorplane.bakheight, frac); } interp->sectorplane.sector->moved = true; break; case LVLINTERP_SectorScroll: if (interp->sectorscroll.ceiling) { - interp->sectorscroll.sector->ceiling_xoffs = R_LerpFixed(interp->sectorscroll.oldxoffs, interp->sectorscroll.bakxoffs, frac); - interp->sectorscroll.sector->ceiling_yoffs = R_LerpFixed(interp->sectorscroll.oldyoffs, interp->sectorscroll.bakyoffs, frac); + if (interp->sectorscroll.sector->ceiling_xoffs == interp->sectorscroll.oldxoffs) + interp->sectorscroll.sector->ceiling_xoffs = interp->sectorscroll.bakxoffs; + else + interp->sectorscroll.sector->ceiling_xoffs = R_LerpFixed(interp->sectorscroll.oldxoffs, interp->sectorscroll.bakxoffs, frac); + + if (interp->sectorscroll.sector->ceiling_yoffs == interp->sectorscroll.oldyoffs) + interp->sectorscroll.sector->ceiling_yoffs = interp->sectorscroll.bakyoffs; + else + interp->sectorscroll.sector->ceiling_yoffs = R_LerpFixed(interp->sectorscroll.oldyoffs, interp->sectorscroll.bakyoffs, frac); } else { - interp->sectorscroll.sector->floor_xoffs = R_LerpFixed(interp->sectorscroll.oldxoffs, interp->sectorscroll.bakxoffs, frac); - interp->sectorscroll.sector->floor_yoffs = R_LerpFixed(interp->sectorscroll.oldyoffs, interp->sectorscroll.bakyoffs, frac); + if (interp->sectorscroll.sector->floor_xoffs == interp->sectorscroll.oldxoffs) + interp->sectorscroll.sector->floor_xoffs = interp->sectorscroll.bakxoffs; + else + interp->sectorscroll.sector->floor_xoffs = R_LerpFixed(interp->sectorscroll.oldxoffs, interp->sectorscroll.bakxoffs, frac); + + if (interp->sectorscroll.sector->floor_yoffs == interp->sectorscroll.oldyoffs) + interp->sectorscroll.sector->floor_yoffs = interp->sectorscroll.bakyoffs; + else + interp->sectorscroll.sector->floor_yoffs = R_LerpFixed(interp->sectorscroll.oldyoffs, interp->sectorscroll.bakyoffs, frac); } break; case LVLINTERP_SideScroll: - interp->sidescroll.side->textureoffset = R_LerpFixed(interp->sidescroll.oldtextureoffset, interp->sidescroll.baktextureoffset, frac); - interp->sidescroll.side->rowoffset = R_LerpFixed(interp->sidescroll.oldrowoffset, interp->sidescroll.bakrowoffset, frac); + if (interp->sidescroll.side->textureoffset == interp->sidescroll.oldtextureoffset) + interp->sidescroll.side->textureoffset = interp->sidescroll.baktextureoffset; + else + interp->sidescroll.side->textureoffset = R_LerpFixed(interp->sidescroll.oldtextureoffset, interp->sidescroll.baktextureoffset, frac); + + if (interp->sidescroll.side->rowoffset == interp->sidescroll.oldrowoffset) + interp->sidescroll.side->rowoffset = interp->sidescroll.bakrowoffset; + else + interp->sidescroll.side->rowoffset = R_LerpFixed(interp->sidescroll.oldrowoffset, interp->sidescroll.bakrowoffset, frac); break; case LVLINTERP_Polyobj: for (ii = 0; ii < interp->polyobj.vertices_size; ii++) { - interp->polyobj.polyobj->vertices[ii]->x = R_LerpFixed(interp->polyobj.oldvertices[ii * 2 ], interp->polyobj.bakvertices[ii * 2 ], frac); - interp->polyobj.polyobj->vertices[ii]->y = R_LerpFixed(interp->polyobj.oldvertices[ii * 2 + 1], interp->polyobj.bakvertices[ii * 2 + 1], frac); + if (interp->polyobj.polyobj->vertices[ii]->x == interp->polyobj.oldvertices[ii * 2 ]) + interp->polyobj.polyobj->vertices[ii]->x = interp->polyobj.bakvertices[ii * 2 ]; + else + interp->polyobj.polyobj->vertices[ii]->x = R_LerpFixed(interp->polyobj.oldvertices[ii * 2 ], interp->polyobj.bakvertices[ii * 2 ], frac); + + if (interp->polyobj.polyobj->vertices[ii]->y == interp->polyobj.oldvertices[ii * 2 + 1]) + interp->polyobj.polyobj->vertices[ii]->y = interp->polyobj.bakvertices[ii * 2 + 1]; + else + interp->polyobj.polyobj->vertices[ii]->y = R_LerpFixed(interp->polyobj.oldvertices[ii * 2 + 1], interp->polyobj.bakvertices[ii * 2 + 1], frac); } - interp->polyobj.polyobj->centerPt.x = R_LerpFixed(interp->polyobj.oldcx, interp->polyobj.bakcx, frac); - interp->polyobj.polyobj->centerPt.y = R_LerpFixed(interp->polyobj.oldcy, interp->polyobj.bakcy, frac); + if (interp->polyobj.polyobj->centerPt.x == interp->polyobj.oldcx) + interp->polyobj.polyobj->centerPt.x = interp->polyobj.bakcx; + else + interp->polyobj.polyobj->centerPt.x = R_LerpFixed(interp->polyobj.oldcx, interp->polyobj.bakcx, frac); + + if (interp->polyobj.polyobj->centerPt.y == interp->polyobj.oldcy) + interp->polyobj.polyobj->centerPt.y = interp->polyobj.bakcy; + else + interp->polyobj.polyobj->centerPt.y = R_LerpFixed(interp->polyobj.oldcy, interp->polyobj.bakcy, frac); + break; - case LVLINTERP_DynSlope: + /*case LVLINTERP_DynSlope: R_LerpVector3(&interp->dynslope.oldo, &interp->dynslope.bako, frac, &interp->dynslope.slope->o); R_LerpVector2(&interp->dynslope.oldd, &interp->dynslope.bakd, frac, &interp->dynslope.slope->d); interp->dynslope.slope->zdelta = R_LerpFixed(interp->dynslope.oldzdelta, interp->dynslope.bakzdelta, frac); - break; + break;*/ } } } @@ -661,11 +753,11 @@ void R_RestoreLevelInterpolators(void) interp->polyobj.polyobj->centerPt.x = interp->polyobj.bakcx; interp->polyobj.polyobj->centerPt.y = interp->polyobj.bakcy; break; - case LVLINTERP_DynSlope: + /*case LVLINTERP_DynSlope: FV3_Copy(&interp->dynslope.slope->o, &interp->dynslope.bako); FV2_Copy(&interp->dynslope.slope->d, &interp->dynslope.bakd); interp->dynslope.slope->zdelta = interp->dynslope.bakzdelta; - break; + break;*/ } } } diff --git a/src/r_fps.h b/src/r_fps.h index deb0c8788..1c0f1f884 100644 --- a/src/r_fps.h +++ b/src/r_fps.h @@ -21,6 +21,7 @@ extern consvar_t cv_fpscap; extern consvar_t cv_precipinterp; +extern consvar_t cv_mobjssector; UINT32 R_GetFramerateCap(void); boolean R_UsingFrameInterpolation(void); @@ -77,7 +78,7 @@ typedef enum { LVLINTERP_SectorScroll, LVLINTERP_SideScroll, LVLINTERP_Polyobj, - LVLINTERP_DynSlope, + //LVLINTERP_DynSlope, } levelinterpolator_type_e; // Tagged union of a level interpolator diff --git a/src/r_main.c b/src/r_main.c index 297a06a68..ec1cd0bf9 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -153,6 +153,12 @@ static CV_PossibleValue_t drawdist_precip_cons_t[] = { {3072, "3072"}, {0, "None"}, {0, NULL}}; +static CV_PossibleValue_t maxinterpdist_cons_t[] = { + /*{256, "256"},*/ {512, "512"}, {768, "768"}, + {1024, "1024"}, {1536, "1536"}, {2048, "2048"}, + {3072, "3072"}, {4096, "4096"}, {6144, "6144"}, + {8192, "8192"}, {0, "Infinite"}, {0, NULL}}; + static CV_PossibleValue_t fov_cons_t[] = {{5*FRACUNIT, "MIN"}, {178*FRACUNIT, "MAX"}, {0, NULL}}; //static CV_PossibleValue_t precipdensity_cons_t[] = {{0, "None"}, {1, "Light"}, {2, "Moderate"}, {4, "Heavy"}, {6, "Thick"}, {8, "V.Thick"}, {0, NULL}}; @@ -201,6 +207,8 @@ consvar_t cv_drawdist_precip = {"drawdist_precip", "1024", CV_SAVE, drawdist_pre consvar_t cv_lessprecip = {"lessweathereffects", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; //consvar_t cv_precipdensity = {"precipdensity", "Moderate", CV_SAVE, precipdensity_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; +consvar_t cv_grmaxinterpdist = {"gr_maxinterpdist", "Infinite", CV_SAVE, maxinterpdist_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; + // cap fov, fov too high tears software apart. consvar_t cv_fov = {"fov", "90", CV_FLOAT|CV_CALL|CV_SAVE, fov_cons_t, Fov_OnChange, 0, NULL, NULL, 0, 0, NULL}; @@ -1862,6 +1870,8 @@ void R_RegisterEngineStuff(void) CV_RegisterVar(&cv_maxportals); + CV_RegisterVar(&cv_grmaxinterpdist); + // Default viewheight is changeable, // initialized to standard viewheight //CV_RegisterVar(&cv_viewheight); @@ -1869,4 +1879,5 @@ void R_RegisterEngineStuff(void) // Frame interpolation/uncapped CV_RegisterVar(&cv_fpscap); CV_RegisterVar(&cv_precipinterp); + CV_RegisterVar(&cv_mobjssector); } diff --git a/src/r_main.h b/src/r_main.h index c3e224380..4767c38ea 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -116,6 +116,7 @@ extern consvar_t /*cv_precipdensity,*/ cv_drawdist, /*cv_drawdist_nights,*/ cv_d extern consvar_t cv_fov; extern consvar_t cv_skybox; extern consvar_t cv_tailspickup; +extern consvar_t cv_grmaxinterpdist; // Called by startup code. void R_Init(void); diff --git a/src/r_things.c b/src/r_things.c index 6cc11b49f..1e9a116cc 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -1357,7 +1357,7 @@ static void R_ProjectSprite(mobj_t *thing) interpmobjstate_t interp = {0}; // do interpolation - if (R_UsingFrameInterpolation() && !paused) + if (R_UsingFrameInterpolation() && !paused && (!cv_grmaxinterpdist.value || R_QuickCamDist(thing->x, thing->y) < cv_grmaxinterpdist.value)) { R_InterpolateMobjState(oldthing, rendertimefrac, &interp); } @@ -1881,7 +1881,7 @@ static void R_ProjectPrecipitationSprite(precipmobj_t *thing) interpmobjstate_t interp = {0}; // do interpolation - if (R_UsingFrameInterpolation() && !paused) + if (R_UsingFrameInterpolation() && !paused && (!cv_grmaxinterpdist.value || R_QuickCamDist(thing->x, thing->y) < cv_grmaxinterpdist.value)) { R_InterpolatePrecipMobjState(thing, rendertimefrac, &interp); } diff --git a/src/r_things.h b/src/r_things.h index 823bad9a8..e6470a952 100644 --- a/src/r_things.h +++ b/src/r_things.h @@ -32,6 +32,12 @@ #define FEETADJUST (4<>FRACBITS) - (viewx>>FRACBITS)), abs(((y)>>FRACBITS) - (viewy>>FRACBITS))) + // Constant arrays used for psprite clipping // and initializing clipping. extern INT16 negonearray[MAXVIDWIDTH];