From 41ff733fcd05d5e56064026ede8e8eb0595574bd Mon Sep 17 00:00:00 2001 From: terminx Date: Fri, 9 Aug 2019 09:28:27 +0000 Subject: [PATCH] Happier try_facespr_intersect() I'm prejudiced against 30-line functions with statements nested 5 levels deep. git-svn-id: https://svn.eduke32.com/eduke32@7933 1a8010ca-5511-0410-912e-c29ae57300e0 --- source/build/include/build.h | 4 +- source/build/src/clip.cpp | 74 ++++++++++++++++-------------------- source/build/src/engine.cpp | 2 +- 3 files changed, 36 insertions(+), 44 deletions(-) diff --git a/source/build/include/build.h b/source/build/include/build.h index b9534f202..1b540a573 100644 --- a/source/build/include/build.h +++ b/source/build/include/build.h @@ -1177,9 +1177,9 @@ int32_t cansee(int32_t x1, int32_t y1, int32_t z1, int16_t sect1, int32_t inside(int32_t x, int32_t y, int16_t sectnum); void dragpoint(int16_t pointhighlight, int32_t dax, int32_t day, uint8_t flags); void setfirstwall(int16_t sectnum, int16_t newfirstwall); -int32_t try_facespr_intersect(uspriteptr_t const spr, const vec3_t *refpos, +int32_t try_facespr_intersect(uspriteptr_t const spr, vec3_t const in, int32_t vx, int32_t vy, int32_t vz, - vec3_t *intp, int32_t strictly_smaller_than_p); + vec3_t * const intp, int32_t strictly_smaller_than_p); #define MAXUPDATESECTORDIST 1536 #define INITIALUPDATESECTORDIST 256 diff --git a/source/build/src/clip.cpp b/source/build/src/clip.cpp index 65a315917..a0a494b1e 100644 --- a/source/build/src/clip.cpp +++ b/source/build/src/clip.cpp @@ -1976,51 +1976,43 @@ restart_grand: // intp: point of currently best (closest) intersection -int32_t try_facespr_intersect(uspriteptr_t const spr, const vec3_t *refpos, - int32_t vx, int32_t vy, int32_t vz, - vec3_t *intp, int32_t strictly_smaller_than_p) +int32_t try_facespr_intersect(uspriteptr_t const spr, vec3_t const in, + int32_t vx, int32_t vy, int32_t vz, + vec3_t * const intp, int32_t strictly_smaller_than_p) { - const int32_t x1=spr->x, y1=spr->y; - const int32_t xs=refpos->x, ys=refpos->y; + vec3_t const sprpos = spr->pos; - const int32_t topt = vx*(x1-xs) + vy*(y1-ys); - if (topt > 0) - { - const int32_t bot = vx*vx + vy*vy; - if (bot != 0) - { - int32_t i; - const int32_t intz = refpos->z + scale(vz,topt,bot); - const int32_t z1 = spr->z + spriteheightofsptr(spr, &i, 1); + int32_t const topt = vx * (sprpos.x - in.x) + vy * (sprpos.y - in.y); - if (intz >= z1-i && intz <= z1) - { - const int32_t topu = vx*(y1-ys) - vy*(x1-xs); + if (topt <= 0) return 0; - const int32_t offx = scale(vx,topu,bot); - const int32_t offy = scale(vy,topu,bot); - const int32_t dist = offx*offx + offy*offy; + int32_t const bot = vx * vx + vy * vy; - i = tilesiz[spr->picnum].x*spr->xrepeat; - if (dist <= mulscale7(i,i)) - { - const int32_t intx = xs + scale(vx,topt,bot); - const int32_t inty = ys + scale(vy,topt,bot); + if (!bot) return 0; - if (klabs(intx-xs)+klabs(inty-ys) + strictly_smaller_than_p - <= klabs(intp->x-xs)+klabs(intp->y-ys)) - { - intp->x = intx; - intp->y = inty; - intp->z = intz; - return 1; - } - } - } - } - } + vec3_t newpos = { 0, 0, in.z + scale(vz, topt, bot) }; + int32_t siz; + int32_t const z1 = sprpos.z + spriteheightofsptr(spr, &siz, 1); - return 0; + if (newpos.z < z1 - siz || newpos.z > z1) + return 0; + + int32_t const topu = vx * (sprpos.y - in.y) - vy * (sprpos.x - in.x); + vec2_t const off = { scale(vx, topu, bot), scale(vy, topu, bot) }; + int32_t const dist = off.x * off.x + off.y * off.y; + + siz = tilesiz[spr->picnum].x * spr->xrepeat; + + if (dist > mulscale7(siz, siz)) return 0; + + newpos.vec2 = { in.x + scale(vx, topt, bot), in.y + scale(vy, topt, bot) }; + + if (klabs(newpos.x - in.x) + klabs(newpos.y - in.y) + strictly_smaller_than_p > + klabs(intp->x - in.x) + klabs(intp->y - in.y)) + return 0; + + *intp = newpos; + return 1; } static inline void hit_set(hitdata_t *hit, int32_t sectnum, int32_t wallnum, int32_t spritenum, @@ -2277,7 +2269,7 @@ restart_grand: for (z=headspritesect[dasector]; z>=0; z=nextspritesect[z]) { auto const spr = (uspriteptr_t)&sprite[z]; - const int32_t cstat = spr->cstat; + uint32_t const cstat = spr->cstat; #ifdef USE_OPENGL if (!hitallsprites) #endif @@ -2288,7 +2280,7 @@ restart_grand: // try and see whether this sprite's picnum has sector-like clipping data i = pictoidx[spr->picnum]; // handle sector-like floor sprites separately - while (i>=0 && (spr->cstat&32) != (clipmapinfo.sector[sectq[clipinfo[i].qbeg]].CM_CSTAT&32)) + while (i>=0 && (cstat&32) != (clipmapinfo.sector[sectq[clipinfo[i].qbeg]].CM_CSTAT&32)) i = clipinfo[i].next; if (i>=0 && clipspritenumpos, 0)) + if (try_facespr_intersect(spr, *sv, vx, vy, vz, &hit->pos, 0)) { hit->sect = dasector; hit->wall = -1; diff --git a/source/build/src/engine.cpp b/source/build/src/engine.cpp index 1204febf5..b85d79583 100644 --- a/source/build/src/engine.cpp +++ b/source/build/src/engine.cpp @@ -11191,7 +11191,7 @@ void neartag(int32_t xs, int32_t ys, int32_t zs, int16_t sectnum, int16_t ange, if (((tagsearch&1) && spr->lotag) || ((tagsearch&2) && spr->hitag)) { - if (try_facespr_intersect(spr, &sv, vx, vy, 0, &hitv, 1)) + if (try_facespr_intersect(spr, sv, vx, vy, 0, &hitv, 1)) { *neartagsprite = z; *neartaghitdist = dmulscale14(hitv.x-xs, sintable[(ange+2560)&2047],