mirror of
https://github.com/KartKrewDev/RingRacers.git
synced 2025-10-30 08:01:28 +00:00
Merge branch 'blockmap-precip' into 'master'
Render precip through blockmap instead of during BSP See merge request KartKrew/Kart!1147
This commit is contained in:
commit
94e3803eb0
10 changed files with 165 additions and 65 deletions
|
|
@ -69,6 +69,7 @@ struct hwdriver_s hwdriver;
|
|||
static void HWR_AddSprites(sector_t *sec);
|
||||
static void HWR_ProjectSprite(mobj_t *thing);
|
||||
#ifdef HWPRECIP
|
||||
static void HWR_AddPrecipitationSprites(void);
|
||||
static void HWR_ProjectPrecipitationSprite(precipmobj_t *thing);
|
||||
#endif
|
||||
static void HWR_ProjectBoundingBox(mobj_t *thing);
|
||||
|
|
@ -5052,9 +5053,6 @@ static UINT8 sectorlight;
|
|||
static void HWR_AddSprites(sector_t *sec)
|
||||
{
|
||||
mobj_t *thing;
|
||||
#ifdef HWPRECIP
|
||||
precipmobj_t *precipthing;
|
||||
#endif
|
||||
fixed_t limit_dist;
|
||||
|
||||
// BSP is traversed by subsector.
|
||||
|
|
@ -5085,19 +5083,45 @@ static void HWR_AddSprites(sector_t *sec)
|
|||
HWR_ProjectBoundingBox(thing);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef HWPRECIP
|
||||
// --------------------------------------------------------------------------
|
||||
// HWR_AddPrecipitationSprites
|
||||
// This renders through the blockmap instead of BSP to avoid
|
||||
// iterating a huge amount of precipitation sprites in sectors
|
||||
// that are beyond drawdist.
|
||||
// --------------------------------------------------------------------------
|
||||
static void HWR_AddPrecipitationSprites(void)
|
||||
{
|
||||
const fixed_t drawdist = cv_drawdist_precip.value * mapobjectscale;
|
||||
|
||||
INT32 xl, xh, yl, yh, bx, by;
|
||||
precipmobj_t *th;
|
||||
|
||||
// no, no infinite draw distance for precipitation. this option at zero is supposed to turn it off
|
||||
if ((limit_dist = (fixed_t)cv_drawdist_precip.value * mapobjectscale))
|
||||
if (drawdist == 0)
|
||||
{
|
||||
for (precipthing = sec->preciplist; precipthing; precipthing = precipthing->snext)
|
||||
return;
|
||||
}
|
||||
|
||||
R_GetRenderBlockMapDimensions(drawdist, &xl, &xh, &yl, &yh);
|
||||
|
||||
for (bx = xl; bx <= xh; bx++)
|
||||
{
|
||||
for (by = yl; by <= yh; by++)
|
||||
{
|
||||
if (R_PrecipThingVisible(precipthing, limit_dist))
|
||||
HWR_ProjectPrecipitationSprite(precipthing);
|
||||
for (th = precipblocklinks[(by * bmapwidth) + bx]; th; th = th->bnext)
|
||||
{
|
||||
if (R_PrecipThingVisible(th))
|
||||
{
|
||||
HWR_ProjectPrecipitationSprite(th);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
// --------------------------------------------------------------------------
|
||||
// HWR_ProjectSprite
|
||||
|
|
@ -6315,6 +6339,10 @@ static void HWR_RenderViewpoint(player_t *player, boolean drawSkyTexture, boolea
|
|||
|
||||
HWR_RenderBSPNode((INT32)numnodes-1);
|
||||
|
||||
#ifdef HWPRECIP
|
||||
HWR_AddPrecipitationSprites();
|
||||
#endif
|
||||
|
||||
#ifndef NEWCLIP
|
||||
// Make a viewangle int so we can render things based on mouselook
|
||||
viewangle = localaiming[viewssnum];
|
||||
|
|
|
|||
|
|
@ -510,6 +510,7 @@ extern INT32 bmapheight; // in mapblocks
|
|||
extern fixed_t bmaporgx;
|
||||
extern fixed_t bmaporgy; // origin of block map
|
||||
extern mobj_t **blocklinks; // for thing chains
|
||||
extern precipmobj_t **precipblocklinks; // special blockmap for precip rendering
|
||||
|
||||
extern struct minimapinfo
|
||||
{
|
||||
|
|
|
|||
|
|
@ -1006,15 +1006,45 @@ void P_UnsetThingPosition(mobj_t *thing)
|
|||
|
||||
void P_UnsetPrecipThingPosition(precipmobj_t *thing)
|
||||
{
|
||||
precipmobj_t **sprev = thing->sprev;
|
||||
precipmobj_t *snext = thing->snext;
|
||||
if ((*sprev = snext) != NULL) // unlink from sector list
|
||||
snext->sprev = sprev;
|
||||
precipmobj_t **bprev = thing->bprev;
|
||||
precipmobj_t *bnext = thing->bnext;
|
||||
|
||||
if (bprev && (*bprev = bnext) != NULL) // unlink from block map
|
||||
bnext->bprev = bprev;
|
||||
|
||||
precipsector_list = thing->touching_sectorlist;
|
||||
thing->touching_sectorlist = NULL; //to be restored by P_SetPrecipThingPosition
|
||||
}
|
||||
|
||||
static void P_LinkToBlockMap(mobj_t *thing, mobj_t **bmap)
|
||||
{
|
||||
const INT32 blockx = (unsigned)(thing->x - bmaporgx) >> MAPBLOCKSHIFT;
|
||||
const INT32 blocky = (unsigned)(thing->y - bmaporgy) >> MAPBLOCKSHIFT;
|
||||
|
||||
if (blockx >= 0 && blockx < bmapwidth
|
||||
&& blocky >= 0 && blocky < bmapheight)
|
||||
{
|
||||
// killough 8/11/98: simpler scheme using
|
||||
// pointer-to-pointer prev pointers --
|
||||
// allows head nodes to be treated like everything else
|
||||
|
||||
mobj_t **link = &bmap[(blocky * bmapwidth) + blockx];
|
||||
mobj_t *bnext = *link;
|
||||
|
||||
thing->bnext = bnext;
|
||||
|
||||
if (bnext != NULL)
|
||||
bnext->bprev = &thing->bnext;
|
||||
|
||||
thing->bprev = link;
|
||||
*link = thing;
|
||||
}
|
||||
else // thing is off the map
|
||||
{
|
||||
thing->bnext = NULL, thing->bprev = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// P_SetThingPosition
|
||||
// Links a thing into both a block and a subsector
|
||||
|
|
@ -1071,24 +1101,7 @@ void P_SetThingPosition(mobj_t *thing)
|
|||
if (!(thing->flags & MF_NOBLOCKMAP))
|
||||
{
|
||||
// inert things don't need to be in blockmap
|
||||
const INT32 blockx = (unsigned)(thing->x - bmaporgx)>>MAPBLOCKSHIFT;
|
||||
const INT32 blocky = (unsigned)(thing->y - bmaporgy)>>MAPBLOCKSHIFT;
|
||||
if (blockx >= 0 && blockx < bmapwidth
|
||||
&& blocky >= 0 && blocky < bmapheight)
|
||||
{
|
||||
// killough 8/11/98: simpler scheme using
|
||||
// pointer-to-pointer prev pointers --
|
||||
// allows head nodes to be treated like everything else
|
||||
|
||||
mobj_t **link = &blocklinks[blocky*bmapwidth + blockx];
|
||||
mobj_t *bnext = *link;
|
||||
if ((thing->bnext = bnext) != NULL)
|
||||
bnext->bprev = &thing->bnext;
|
||||
thing->bprev = link;
|
||||
*link = thing;
|
||||
}
|
||||
else // thing is off the map
|
||||
thing->bnext = NULL, thing->bprev = NULL;
|
||||
P_LinkToBlockMap(thing, blocklinks);
|
||||
}
|
||||
|
||||
// Allows you to 'step' on a new linedef exec when the previous
|
||||
|
|
@ -1143,18 +1156,15 @@ void P_SetUnderlayPosition(mobj_t *thing)
|
|||
|
||||
void P_SetPrecipitationThingPosition(precipmobj_t *thing)
|
||||
{
|
||||
subsector_t *ss = thing->subsector = R_PointInSubsector(thing->x, thing->y);
|
||||
|
||||
precipmobj_t **link = &ss->sector->preciplist;
|
||||
precipmobj_t *snext = *link;
|
||||
if ((thing->snext = snext) != NULL)
|
||||
snext->sprev = &thing->snext;
|
||||
thing->sprev = link;
|
||||
*link = thing;
|
||||
thing->subsector = R_PointInSubsector(thing->x, thing->y);
|
||||
|
||||
P_CreatePrecipSecNodeList(thing, thing->x, thing->y);
|
||||
thing->touching_sectorlist = precipsector_list; // Attach to Thing's precipmobj_t
|
||||
precipsector_list = NULL; // clear for next time
|
||||
|
||||
// NOTE: this works because bnext/bprev are at the same
|
||||
// offsets in precipmobj_t and mobj_t
|
||||
P_LinkToBlockMap((mobj_t*)thing, (mobj_t**)precipblocklinks);
|
||||
}
|
||||
|
||||
//
|
||||
|
|
|
|||
21
src/p_mobj.h
21
src/p_mobj.h
|
|
@ -291,9 +291,10 @@ struct mobj_t
|
|||
mobjtype_t type;
|
||||
const mobjinfo_t *info; // &mobjinfo[mobj->type]
|
||||
|
||||
// More list: links in sector (if needed)
|
||||
mobj_t *snext;
|
||||
mobj_t **sprev; // killough 8/11/98: change to ptr-to-ptr
|
||||
// Interaction info, by BLOCKMAP.
|
||||
// Links in blocks (if needed).
|
||||
mobj_t *bnext;
|
||||
mobj_t **bprev; // killough 8/11/98: change to ptr-to-ptr
|
||||
|
||||
// More drawing info: to determine current sprite.
|
||||
angle_t angle, pitch, roll; // orientation
|
||||
|
|
@ -347,10 +348,9 @@ struct mobj_t
|
|||
// using an internal color lookup table for re-indexing.
|
||||
UINT16 color; // This replaces MF_TRANSLATION. Use 0 for default (no translation).
|
||||
|
||||
// Interaction info, by BLOCKMAP.
|
||||
// Links in blocks (if needed).
|
||||
mobj_t *bnext;
|
||||
mobj_t **bprev; // killough 8/11/98: change to ptr-to-ptr
|
||||
// More list: links in sector (if needed)
|
||||
mobj_t *snext;
|
||||
mobj_t **sprev; // killough 8/11/98: change to ptr-to-ptr
|
||||
|
||||
// Additional pointers for NiGHTS hoops
|
||||
mobj_t *hnext;
|
||||
|
|
@ -448,9 +448,10 @@ struct precipmobj_t
|
|||
mobjtype_t type;
|
||||
const mobjinfo_t *info; // &mobjinfo[mobj->type]
|
||||
|
||||
// More list: links in sector (if needed)
|
||||
precipmobj_t *snext;
|
||||
precipmobj_t **sprev; // killough 8/11/98: change to ptr-to-ptr
|
||||
// Links in blocks (if needed).
|
||||
// The blockmap is only used by precip to render.
|
||||
precipmobj_t *bnext;
|
||||
precipmobj_t **bprev; // killough 8/11/98: change to ptr-to-ptr
|
||||
|
||||
// More drawing info: to determine current sprite.
|
||||
angle_t angle, pitch, roll; // orientation
|
||||
|
|
|
|||
|
|
@ -160,6 +160,7 @@ INT32 *blockmaplump; // Big blockmap
|
|||
fixed_t bmaporgx, bmaporgy;
|
||||
// for thing chains
|
||||
mobj_t **blocklinks;
|
||||
precipmobj_t **precipblocklinks;
|
||||
|
||||
// REJECT
|
||||
// For fast sight rejection.
|
||||
|
|
@ -882,7 +883,6 @@ static void P_InitializeSector(sector_t *ss)
|
|||
|
||||
ss->floorspeed = ss->ceilspeed = 0;
|
||||
|
||||
ss->preciplist = NULL;
|
||||
ss->touching_preciplist = NULL;
|
||||
|
||||
ss->f_slope = NULL;
|
||||
|
|
@ -3547,6 +3547,10 @@ static boolean P_LoadBlockMap(UINT8 *data, size_t count)
|
|||
// haleyjd 2/22/06: setup polyobject blockmap
|
||||
count = sizeof(*polyblocklinks) * bmapwidth * bmapheight;
|
||||
polyblocklinks = Z_Calloc(count, PU_LEVEL, NULL);
|
||||
|
||||
count = sizeof (*precipblocklinks)* bmapwidth*bmapheight;
|
||||
precipblocklinks = Z_Calloc(count, PU_LEVEL, NULL);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
@ -3800,6 +3804,9 @@ static void P_CreateBlockMap(void)
|
|||
// haleyjd 2/22/06: setup polyobject blockmap
|
||||
count = sizeof(*polyblocklinks) * bmapwidth * bmapheight;
|
||||
polyblocklinks = Z_Calloc(count, PU_LEVEL, NULL);
|
||||
|
||||
count = sizeof (*precipblocklinks)* bmapwidth*bmapheight;
|
||||
precipblocklinks = Z_Calloc(count, PU_LEVEL, NULL);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -524,7 +524,6 @@ struct sector_t
|
|||
fixed_t floorspeed, ceilspeed;
|
||||
|
||||
// list of precipitation mobjs in sector
|
||||
precipmobj_t *preciplist;
|
||||
mprecipsecnode_t *touching_preciplist;
|
||||
|
||||
// Eternity engine slope
|
||||
|
|
|
|||
29
src/r_main.c
29
src/r_main.c
|
|
@ -493,6 +493,33 @@ boolean R_DoCulling(line_t *cullheight, line_t *viewcullheight, fixed_t vz, fixe
|
|||
return false;
|
||||
}
|
||||
|
||||
// Returns search dimensions within a blockmap, in the direction of viewangle and out to a certain distance.
|
||||
void R_GetRenderBlockMapDimensions(fixed_t drawdist, INT32 *xl, INT32 *xh, INT32 *yl, INT32 *yh)
|
||||
{
|
||||
const angle_t left = viewangle - clipangle[viewssnum];
|
||||
const angle_t right = viewangle + clipangle[viewssnum];
|
||||
|
||||
const fixed_t vxleft = viewx + FixedMul(drawdist, FCOS(left));
|
||||
const fixed_t vyleft = viewy + FixedMul(drawdist, FSIN(left));
|
||||
|
||||
const fixed_t vxright = viewx + FixedMul(drawdist, FCOS(right));
|
||||
const fixed_t vyright = viewy + FixedMul(drawdist, FSIN(right));
|
||||
|
||||
// Try to narrow the search to within only the field of view
|
||||
*xl = (unsigned)(min(viewx, min(vxleft, vxright)) - bmaporgx)>>MAPBLOCKSHIFT;
|
||||
*xh = (unsigned)(max(viewx, max(vxleft, vxright)) - bmaporgx)>>MAPBLOCKSHIFT;
|
||||
*yl = (unsigned)(min(viewy, min(vyleft, vyright)) - bmaporgy)>>MAPBLOCKSHIFT;
|
||||
*yh = (unsigned)(max(viewy, max(vyleft, vyright)) - bmaporgy)>>MAPBLOCKSHIFT;
|
||||
|
||||
if (*xh >= bmapwidth)
|
||||
*xh = bmapwidth - 1;
|
||||
|
||||
if (*yh >= bmapheight)
|
||||
*yh = bmapheight - 1;
|
||||
|
||||
BMBOUNDFIX(*xl, *xh, *yl, *yh);
|
||||
}
|
||||
|
||||
//
|
||||
// R_InitTextureMapping
|
||||
//
|
||||
|
|
@ -1485,6 +1512,7 @@ static void R_RenderViewpoint(maskcount_t* mask)
|
|||
curdrawsegs = ds_p;
|
||||
|
||||
R_RenderBSPNode((INT32)numnodes - 1);
|
||||
R_AddPrecipitationSprites();
|
||||
|
||||
Mask_Post(mask);
|
||||
}
|
||||
|
|
@ -1556,7 +1584,6 @@ void R_RenderPlayerView(void)
|
|||
ps_bsptime = I_GetPreciseTime();
|
||||
R_RenderViewpoint(&masks[nummasks - 1]);
|
||||
ps_bsptime = I_GetPreciseTime() - ps_bsptime;
|
||||
ps_numsprites = visspritecount;
|
||||
#ifdef TIMING
|
||||
RDMSR(0x10, &mycount);
|
||||
mytotal += mycount; // 64bit add
|
||||
|
|
|
|||
|
|
@ -87,6 +87,8 @@ subsector_t *R_PointInSubsectorOrNull(fixed_t x, fixed_t y);
|
|||
|
||||
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);
|
||||
|
||||
// Render stats
|
||||
|
||||
extern precise_t ps_prevframetime;// time when previous frame was rendered
|
||||
|
|
|
|||
|
|
@ -2639,7 +2639,6 @@ weatherthink:
|
|||
void R_AddSprites(sector_t *sec, INT32 lightlevel)
|
||||
{
|
||||
mobj_t *thing;
|
||||
precipmobj_t *precipthing; // Tails 08-25-2002
|
||||
INT32 lightnum;
|
||||
fixed_t limit_dist;
|
||||
|
||||
|
|
@ -2696,14 +2695,45 @@ void R_AddSprites(sector_t *sec, INT32 lightlevel)
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// R_AddPrecipitationSprites
|
||||
// This renders through the blockmap instead of BSP to avoid
|
||||
// iterating a huge amount of precipitation sprites in sectors
|
||||
// that are beyond drawdist.
|
||||
//
|
||||
void R_AddPrecipitationSprites(void)
|
||||
{
|
||||
const fixed_t drawdist = cv_drawdist_precip.value * mapobjectscale;
|
||||
|
||||
INT32 xl, xh, yl, yh, bx, by;
|
||||
precipmobj_t *th;
|
||||
|
||||
// no, no infinite draw distance for precipitation. this option at zero is supposed to turn it off
|
||||
if ((limit_dist = (fixed_t)cv_drawdist_precip.value * mapobjectscale) && !portalskipprecipmobjs)
|
||||
if (drawdist == 0)
|
||||
{
|
||||
for (precipthing = sec->preciplist; precipthing; precipthing = precipthing->snext)
|
||||
return;
|
||||
}
|
||||
|
||||
// do not render in skybox
|
||||
if (portalskipprecipmobjs)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
R_GetRenderBlockMapDimensions(drawdist, &xl, &xh, &yl, &yh);
|
||||
|
||||
for (bx = xl; bx <= xh; bx++)
|
||||
{
|
||||
for (by = yl; by <= yh; by++)
|
||||
{
|
||||
if (R_PrecipThingVisible(precipthing, limit_dist))
|
||||
R_ProjectPrecipitationSprite(precipthing);
|
||||
for (th = precipblocklinks[(by * bmapwidth) + bx]; th; th = th->bnext)
|
||||
{
|
||||
if (R_PrecipThingVisible(th))
|
||||
{
|
||||
R_ProjectPrecipitationSprite(th);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -3652,17 +3682,12 @@ boolean R_ThingWithinDist (mobj_t *thing, fixed_t limit_dist)
|
|||
}
|
||||
|
||||
/* Check if precipitation may be drawn from our current view. */
|
||||
boolean R_PrecipThingVisible (precipmobj_t *precipthing,
|
||||
fixed_t limit_dist)
|
||||
boolean R_PrecipThingVisible (precipmobj_t *precipthing)
|
||||
{
|
||||
fixed_t approx_dist;
|
||||
|
||||
if (( precipthing->precipflags & PCF_INVISIBLE ))
|
||||
return false;
|
||||
|
||||
approx_dist = P_AproxDistance(viewx-precipthing->x, viewy-precipthing->y);
|
||||
|
||||
return ( approx_dist <= limit_dist );
|
||||
return true;
|
||||
}
|
||||
|
||||
boolean R_ThingHorizontallyFlipped(mobj_t *thing)
|
||||
|
|
|
|||
|
|
@ -67,6 +67,7 @@ fixed_t R_GetShadowZ(mobj_t *thing, pslope_t **shadowslope);
|
|||
|
||||
//SoM: 6/5/2000: Light sprites correctly!
|
||||
void R_AddSprites(sector_t *sec, INT32 lightlevel);
|
||||
void R_AddPrecipitationSprites(void);
|
||||
void R_InitSprites(void);
|
||||
void R_ClearSprites(void);
|
||||
|
||||
|
|
@ -78,8 +79,7 @@ boolean R_ThingVisible (mobj_t *thing);
|
|||
boolean R_ThingWithinDist (mobj_t *thing,
|
||||
fixed_t draw_dist);
|
||||
|
||||
boolean R_PrecipThingVisible (precipmobj_t *precipthing,
|
||||
fixed_t precip_draw_dist);
|
||||
boolean R_PrecipThingVisible (precipmobj_t *precipthing);
|
||||
|
||||
boolean R_ThingHorizontallyFlipped (mobj_t *thing);
|
||||
boolean R_ThingVerticallyFlipped (mobj_t *thing);
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue