Skip to content
Snippets Groups Projects
Commit 3c39edc1 authored by Hanicef's avatar Hanicef
Browse files

Fall back to old algorithm when on the line

parent a90f495b
No related branches found
No related tags found
No related merge requests found
......@@ -246,6 +246,55 @@ static void FlipCam2_OnChange(void)
SendWeaponPref2();
}
//
// R_PointOnSide
// Traverse BSP (sub) tree,
// check point against partition plane.
// Returns side 0 (front) or 1 (back).
//
// killough 5/2/98: reformatted
//
INT32 R_OldPointOnSide(fixed_t x, fixed_t y, node_t *restrict node)
{
if (!node->dx)
return x <= node->x ? node->dy > 0 : node->dy < 0;
if (!node->dy)
return y <= node->y ? node->dx < 0 : node->dx > 0;
fixed_t dx = (x >> 1) - (node->x >> 1);
fixed_t dy = (y >> 1) - (node->y >> 1);
// Try to quickly decide by looking at sign bits.
// also use a mask to avoid branch prediction
INT32 mask = (node->dy ^ node->dx ^ dx ^ dy) >> 31;
return (mask & ((node->dy ^ dx) < 0)) | // (left is negative)
(~mask & (FixedMul(dy, node->dx>>FRACBITS) >= FixedMul(node->dy>>FRACBITS, dx)));
}
// killough 5/2/98: reformatted
INT32 R_OldPointOnSegSide(fixed_t x, fixed_t y, 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;
fixed_t dx = (x >> 1) - (lx >> 1);
fixed_t dy = (y >> 1) - (ly >> 1);
// Try to quickly decide by looking at sign bits.
if ((ldy ^ ldx ^ dx ^ dy) < 0)
return (ldy ^ dx) < 0; // (left is negative)
return FixedMul(dy, ldx>>FRACBITS) >= FixedMul(ldy>>FRACBITS, dx);
}
//
// R_PointToAngle
// To get a global angle from cartesian coordinates,
......
......@@ -71,11 +71,17 @@ extern lighttable_t *zlight[LIGHTLEVELS][MAXLIGHTZ];
// There a 0-31, i.e. 32 LUT in the COLORMAP lump.
#define NUMCOLORMAPS 32
INT32 R_OldPointOnSide(fixed_t x, fixed_t y, node_t *node);
INT32 R_OldPointOnSegSide(fixed_t x, fixed_t y, seg_t *line);
// Utility functions.
static inline INT32 R_PointOnSide(fixed_t x, fixed_t y, node_t *node)
{
// use cross product to determine side quickly
return ((INT64)y - node->y) * node->dx - ((INT64)x - node->x) * node->dy > 0;
INT64 v = ((INT64)y - node->y) * node->dx - ((INT64)x - node->x) * node->dy;
if (v == 0) // if we're on the line, use the old algorithm
return R_OldPointOnSide(x, y, node);
return v > 0;
}
static inline INT32 R_PointOnSegSide(fixed_t x, fixed_t y, seg_t *line)
......@@ -86,7 +92,10 @@ static inline INT32 R_PointOnSegSide(fixed_t x, fixed_t y, seg_t *line)
fixed_t ldy = line->v2->y - ly;
// use cross product to determine side quickly
return ((INT64)y - ly) * ldx - ((INT64)x - lx) * ldy > 0;
INT64 v = ((INT64)y - ly) * ldx - ((INT64)x - lx) * ldy > 0;
if (v == 0) // if we're on the line, use the old algorithm
return R_OldPointOnSegSide(x, y, line);
return v > 0;
}
angle_t R_PointToAngle(fixed_t x, fixed_t y);
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment