diff --git a/basegraph.cpp b/basegraph.cpp index 14e9abb5..48869fd8 100644 --- a/basegraph.cpp +++ b/basegraph.cpp @@ -14,6 +14,7 @@ int utfsize(char c) { } int get_sightrange() { return getDistLimit() + sightrange_bonus; } +int get_sightrange_ambush() { return max(get_sightrange(), ambush_distance); } namespace stereo { eStereo mode; diff --git a/game.cpp b/game.cpp index 3406cbdc..7e59d83a 100644 --- a/game.cpp +++ b/game.cpp @@ -2743,9 +2743,34 @@ bool nogoSlow(cell *to, cell *from) { } // pathdist begin +cell *pd_from; +int pd_range; + +void compute_graphical_distance() { + cell *c1 = centerover.c ? centerover.c : cwt.c; + int sr = get_sightrange_ambush(); + if(pd_from == c1 && pd_range == sr) return; + for(auto c: pathq) c->pathdist = PINFD; + pathq.clear(); + + pd_from = c1; + pd_range = sr; + c1->pathdist = 0; + pathq.push_back(pd_from); + + for(int qb=0; qbpathdist == pd_range) break; + forCellEx(c1, c) + if(c1->pathdist == PINFD) + c1->pathdist = c->pathdist + 1, + pathq.push_back(c1); + } + } + void computePathdist(eMonster param) { - int pqs = size(pathq); - for(int i=0; ipathdist = PINFD; + pd_from = NULL; + for(auto c: pathq) c->pathdist = PINFD; pathq.clear(); pathqm.clear(); reachedfrom.clear(); diff --git a/graph.cpp b/graph.cpp index f14ea870..3abc3f39 100644 --- a/graph.cpp +++ b/graph.cpp @@ -8,7 +8,6 @@ int inmirrorcount = 0; bool wmspatial, wmescher, wmplain, wmblack, wmascii; bool mmspatial, mmhigh, mmmon, mmitem; -int maxreclevel, reclevel; int detaillevel = 0; @@ -2814,7 +2813,7 @@ void setcolors(cell *c, int& wcol, int &fcol) { // xcol = (c->landparam&1) ? 0xD00000 : 0x00D000; fcol = 0x10101 * (32 + (c->landparam&1) * 32) - 0x000010; int ed = edgeDepth(c); - int sr = max(get_sightrange(), ambush_distance); + int sr = get_sightrange_ambush(); while(ed > clev + sr) ed -= 2; while(ed < clev - sr) ed += 2; fcol = gradient(fcol, 0x0000D0, clev-sr, edgeDepth(c), clev+sr); @@ -3296,19 +3295,14 @@ void pushdown(cell *c, int& q, const transmatrix &V, double down, bool rezoom, b } bool dodrawcell(cell *c) { - // todo: fix when scrolling - if(!buggyGeneration && !debugmode && c->land != laCanvas && sightrange_bonus < 3) { - // not yet created - if(c->mpdist > 7 && !cheater) return false; - // always show on the torus rug - if(rug::rugged && torus) return true; - if(cmode & sm::TORUSCONFIG) return true; - // in the Yendor Challenge, scrolling back is forbidden - if(c->cpdist > 7 && (yendor::on && !cheater)) return false; - // (incorrect comment) too far, no bugs nearby - if(playermoved && c->cpdist > get_sightrange() && c->cpdist > ambush_distance) return false; - } - + // do not display out of range cells, unless on torus + if(c->pathdist == PINFD && geometry != gTorus) + return false; + // do not display not fully generated cells, unless a cheater + if(c->mpdist > 7 && !cheater) return false; + // in the Yendor Challenge, scrolling back is forbidden + if(c->cpdist > 7 && yendor::on && !cheater) return false; + return true; } @@ -5054,7 +5048,7 @@ void drawMarkers() { cell *keycell = NULL; int i; for(i=0; icpdist <= get_sightrange()) { + if(yi[yii].path[i]->cpdist <= get_sightrange_ambush()) { keycell = yi[yii].path[i]; break; } @@ -5273,6 +5267,8 @@ void drawthemap() { modist = 1e20; mouseover = NULL; modist2 = 1e20; mouseover2 = NULL; + compute_graphical_distance(); + centdist = 1e20; if(!euclid) centerover.c = NULL; @@ -5296,17 +5292,8 @@ void drawthemap() { profile_start(1); if(euclid) drawEuclidean(); - else { - int sr = max(get_sightrange(), ambush_distance); - maxreclevel = - conformal::on ? sr + 2: - (!playermoved) ? sr+1 : sr + 4; - - if(S3>3) maxreclevel+=2; - if(gp::on) maxreclevel += gp::dist_2(); - - drawrec(viewctr, maxreclevel, hsOrigin, cview()); - } + else + drawrec(viewctr, hsOrigin, cview()); drawWormSegments(); drawBlizzards(); drawArrowTraps(); @@ -5941,7 +5928,7 @@ cell *viewcenter() { bool inscreenrange(cell *c) { if(sphere) return true; - if(euclid) return celldistance(viewcenter(), c) <= get_sightrange(); + if(euclid) return celldistance(viewcenter(), c) <= get_sightrange_ambush(); return heptdistance(viewcenter(), c) <= 5; } diff --git a/hyper.h b/hyper.h index 40725b57..7a6f899e 100644 --- a/hyper.h +++ b/hyper.h @@ -3016,6 +3016,8 @@ namespace gp { } int get_sightrange(); +int get_sightrange_ambush(); + int gamerange(); int numplayers(); diff --git a/hypgraph.cpp b/hypgraph.cpp index 4ad05953..0062fc70 100644 --- a/hypgraph.cpp +++ b/hypgraph.cpp @@ -464,6 +464,12 @@ transmatrix applyspin(const heptspin& hs, const transmatrix& V) { return (hs.spin || nonbitrunc) ? V * spin(hs.spin*2*M_PI/S7) : V; } +// in hyperbolic quotient geometries, relying on pathdist is not sufficient +bool in_qrange(const transmatrix& V) { + if(!quotient || !hyperbolic) return true; + return V[2][2] < cosh(crossf * get_sightrange_ambush()); + } + namespace gp { /* @@ -486,7 +492,9 @@ void drawrec(cell *c, const transmatrix& V) { if(fix6(dir) != fix6(li.total_dir)) printf("totaldir %d/%d\n", dir, li.total_dir); if(at != li.relative) printf("at %s/%s\n", disp(at), disp(li.relative)); if(maindir != li.last_dir) printf("ld %d/%d\n", maindir, li.last_dir); */ - drawcell(c, V * Tf[maindir][at.first&31][at.second&31][fix6(dir)], 0, false); + transmatrix V1 = V * Tf[maindir][at.first&31][at.second&31][fix6(dir)]; + if(in_qrange(V1)) + drawcell(c, V1, 0, false); } for(int i=0; itype; i++) { cell *c2 = c->mov[i]; @@ -509,8 +517,8 @@ void drawrec(cell *c, const transmatrix& V) { } } } - -void drawrec(const heptspin& hs, int lev, hstate s, const transmatrix& V) { + +void drawrec(const heptspin& hs, hstate s, const transmatrix& V) { // shmup::calc_relative_matrix(cwt.c, hs.h); @@ -523,30 +531,29 @@ void drawrec(const heptspin& hs, int lev, hstate s, const transmatrix& V) { gp::drawrec(c, actualV(hs, V1)); } - else if(dodrawcell(c)) { - reclevel = maxreclevel - lev; - transmatrix V2 = actualV(hs, V1); - drawcell(c, V2, 0, hs.mirrored); - } - - if(lev <= 0) return; - - if(!nonbitrunc) for(int d=0; dmov[ds] && c->spn(ds) == 0 && dodrawcell(c->mov[ds])) { - drawcell(c->mov[ds], V1 * hexmove[d], 0, hs.mirrored ^ c->mirror(ds)); + else { + if(dodrawcell(c)) { + transmatrix V2 = actualV(hs, V1); + drawcell(c, V2, 0, hs.mirrored); + } + + if(!nonbitrunc) for(int d=0; dmov[ds] && c->spn(ds) == 0 && dodrawcell(c->mov[ds])) { + transmatrix V2 = V1 * hexmove[d]; + if(in_qrange(V2)) + drawcell(c->mov[ds], V2, 0, hs.mirrored ^ c->mirror(ds)); + } } } - if(lev <= 1) return; - + if(c->pathdist < PINFD && in_qrange(V)) for(int d=0; d