1
0
mirror of https://github.com/zenorogue/hyperrogue.git synced 2024-12-25 01:20:37 +00:00

better mode handling

This commit is contained in:
Zeno Rogue 2017-07-12 19:50:39 +02:00
parent 94efef5d65
commit a6f176510e
17 changed files with 706 additions and 156 deletions

View File

@ -423,7 +423,8 @@ void handleAllConfig(int sym, int uni) {
} }
void showGraphConfig() { void showGraphConfig() {
gamescreen(3); gamescreen(0);
cmode = sm::SIDE;
dialog::init(XLAT("graphics configuration")); dialog::init(XLAT("graphics configuration"));
@ -505,11 +506,9 @@ void showGraphConfig() {
if(xuni == 'u') vid.particles = !vid.particles; if(xuni == 'u') vid.particles = !vid.particles;
if(xuni == 'd') vid.graphglyph = (1+vid.graphglyph)%3; if(xuni == 'd') vid.graphglyph = (1+vid.graphglyph)%3;
if(xuni == 'j') { if(xuni == 'j')
dialog::editNumber(whatever, -10, 10, 1, 0, XLAT("whatever"), dialog::editNumber(whatever, -10, 10, 1, 0, XLAT("whatever"),
XLAT("Whatever.")); XLAT("Whatever."));
dialog::sidedialog = true;
}
if(xuni == 'a') dialog::editNumber(vid.sspeed, -5, 5, 1, 0, if(xuni == 'a') dialog::editNumber(vid.sspeed, -5, 5, 1, 0,
XLAT("scrolling speed"), XLAT("scrolling speed"),
@ -521,13 +520,11 @@ void showGraphConfig() {
XLAT("movement animation speed"), XLAT("movement animation speed"),
XLAT("+5 = move instantly")); XLAT("+5 = move instantly"));
if(xuni == 'r') { if(xuni == 'r')
dialog::editNumber(sightrange, 4, cheater ? 10 : 7, 1, 7, XLAT("sight range"), dialog::editNumber(sightrange, 4, cheater ? 10 : 7, 1, 7, XLAT("sight range"),
XLAT("Roughly 42% cells are on the edge of your sight range. Reducing " XLAT("Roughly 42% cells are on the edge of your sight range. Reducing "
"the sight range makes HyperRogue work faster, but also makes " "the sight range makes HyperRogue work faster, but also makes "
"the game effectively harder.")); "the game effectively harder."));
dialog::sidedialog = true;
}
if(xuni == 'k') { if(xuni == 'k') {
glyphsortorder = eGlyphsortorder((glyphsortorder+6+(shiftmul>0?1:-1)) % gsoMAX); glyphsortorder = eGlyphsortorder((glyphsortorder+6+(shiftmul>0?1:-1)) % gsoMAX);
@ -766,13 +763,12 @@ void projectionDialog() {
dialog::editNumber(vid.alpha, -5, 5, .1, 1, dialog::editNumber(vid.alpha, -5, 5, .1, 1,
XLAT("projection"), XLAT("projection"),
XLAT("HyperRogue uses the Minkowski hyperboloid model internally. " XLAT("HyperRogue uses the Minkowski hyperboloid model internally. "
"Klein and Poincar models can be obtained by perspective, " "Klein and Poincaré models can be obtained by perspective, "
"and the Gans model is obtained by orthogonal projection. " "and the Gans model is obtained by orthogonal projection. "
// "This parameter specifies the distance from the hyperboloid center " // "This parameter specifies the distance from the hyperboloid center "
// "to the eye. " // "to the eye. "
"See also the conformal mode (in the special modes menu) " "See also the conformal mode (in the special modes menu) "
"for more models.")); "for more models."));
dialog::sidedialog = true;
} }
string explain3D(ld *param) { string explain3D(ld *param) {
@ -825,7 +821,7 @@ string explain3D(ld *param) {
"from a point c absolute units above the plane, this corresponds " "from a point c absolute units above the plane, this corresponds "
"to viewing a Minkowski hyperboloid from a point " "to viewing a Minkowski hyperboloid from a point "
"tanh(g)/tanh(c) units below the center. This in turn corresponds to " "tanh(g)/tanh(c) units below the center. This in turn corresponds to "
"the Poincaré model for g=c, and Klein-Beltrami model for g=0."); "the PoincarÚ model for g=c, and Klein-Beltrami model for g=0.");
if(param == &wall_height) if(param == &wall_height)
return return
@ -856,7 +852,8 @@ string explain3D(ld *param) {
} }
void show3D() { void show3D() {
gamescreen(4); gamescreen(0);
cmode = sm::SIDE | sm::A3;
using namespace geom3; using namespace geom3;
dialog::init(XLAT("3D configuration")); dialog::init(XLAT("3D configuration"));
@ -902,8 +899,10 @@ void show3D() {
dialog::handleNavigation(sym, uni); dialog::handleNavigation(sym, uni);
if(uni == 'n') if(uni == 'n')
cmode &= sm::A3,
dialog::editNumber(geom3::highdetail, 0, 5, .5, 7, XLAT("High detail range"), ""); dialog::editNumber(geom3::highdetail, 0, 5, .5, 7, XLAT("High detail range"), "");
else if(uni == 'm') else if(uni == 'm')
cmode &= sm::A3,
dialog::editNumber(geom3::middetail, 0, 5, .5, 7, XLAT("Mid detail range"), ""); dialog::editNumber(geom3::middetail, 0, 5, .5, 7, XLAT("Mid detail range"), "");
else if(uni == 'c') else if(uni == 'c')
tc_camera = ticks, tc_camera = ticks,
@ -924,26 +923,29 @@ void show3D() {
else if(uni == 'h') else if(uni == 'h')
dialog::editNumber(geom3::human_wall_ratio, 0, 1, .1, .7, XLAT("Human to wall ratio"), ""); dialog::editNumber(geom3::human_wall_ratio, 0, 1, .1, .7, XLAT("Human to wall ratio"), "");
else if(uni == 'e') { else if(uni == 'e')
cmode &= sm::A3,
dialog::editNumber(vid.eye, -10, 10, 0.01, 0, XLAT("distance between eyes"), dialog::editNumber(vid.eye, -10, 10, 0.01, 0, XLAT("distance between eyes"),
XLAT("Watch the Minkowski hyperboloid or the hypersian rug mode with the " XLAT("Watch the Minkowski hyperboloid or the hypersian rug mode with the "
"red/cyan 3D glasses.")); "red/cyan 3D glasses."));
dialog::sidedialog = true;
}
else if(uni == 'y') else if(uni == 'y')
cmode &= sm::A3,
dialog::editNumber(vid.yshift, 0, 1, .1, 0, XLAT("Y shift"), dialog::editNumber(vid.yshift, 0, 1, .1, 0, XLAT("Y shift"),
"Don't center on the player character." "Don't center on the player character."
); );
else if(uni == 's') else if(uni == 's')
cmode &= sm::A3,
dialog::editNumber(vid.camera_angle, -180, 180, 5, 0, XLAT("camera rotation"), dialog::editNumber(vid.camera_angle, -180, 180, 5, 0, XLAT("camera rotation"),
"Rotate the camera. Can be used to obtain a first person perspective, " "Rotate the camera. Can be used to obtain a first person perspective, "
"or third person perspective when combined with Y shift." "or third person perspective when combined with Y shift."
); );
else if(uni == 'b') else if(uni == 'b')
cmode &= sm::A3,
dialog::editNumber(vid.ballangle, 0, 90, 5, 0, XLAT("camera rotation in ball model"), dialog::editNumber(vid.ballangle, 0, 90, 5, 0, XLAT("camera rotation in ball model"),
"Rotate the camera in ball/hyperboloid model."); "Rotate the camera in ball/hyperboloid model.");
else if(uni == 'x') else if(uni == 'x')
cmode &= sm::A3,
dialog::editNumber(vid.ballproj, 0, 100, .1, 0, XLAT("projection in ball model"), dialog::editNumber(vid.ballproj, 0, 100, .1, 0, XLAT("projection in ball model"),
"This parameter affects the ball model the same way as the projection parameter affects the disk model."); "This parameter affects the ball model the same way as the projection parameter affects the disk model.");
else if(uni == 'B') else if(uni == 'B')
@ -952,8 +954,6 @@ void show3D() {
pmodel = (pmodel == mdHyperboloid ? mdDisk : mdHyperboloid); pmodel = (pmodel == mdHyperboloid ? mdDisk : mdHyperboloid);
else if(doexiton(sym, uni)) popScreen(); else if(doexiton(sym, uni)) popScreen();
if(cmode2 == smNumber) dialog::sidedialog = true;
}; };
} }

View File

@ -533,6 +533,9 @@ namespace conformal {
}; };
void show() { void show() {
cmode = sm::SIDE;
gamescreen(0);
dialog::init(XLAT("conformal/history mode")); dialog::init(XLAT("conformal/history mode"));
dialog::addBoolItem(XLAT("include history"), (includeHistory), 'i'); dialog::addBoolItem(XLAT("include history"), (includeHistory), 'i');
@ -622,18 +625,12 @@ namespace conformal {
setvideomode(); setvideomode();
} */ } */
} }
else if(sym == 'x' && pmodel == mdPolygonal) { else if(sym == 'x' && pmodel == mdPolygonal)
dialog::editNumber(polygonal::SI, 3, 10, 1, 4, XLAT("polygon sides"), ""); dialog::editNumber(polygonal::SI, 3, 10, 1, 4, XLAT("polygon sides"), "");
dialog::sidedialog = true; else if(sym == 'y' && pmodel == mdPolygonal)
}
else if(sym == 'y' && pmodel == mdPolygonal) {
dialog::editNumber(polygonal::STAR, -1, 1, .1, 0, XLAT("star factor"), ""); dialog::editNumber(polygonal::STAR, -1, 1, .1, 0, XLAT("star factor"), "");
dialog::sidedialog = true; else if(sym == 'n' && pmodel == mdPolygonal)
}
else if(sym == 'n' && pmodel == mdPolygonal) {
dialog::editNumber(polygonal::deg, 2, polygonal::MSI-1, 1, 2, XLAT("degree of the approximation"), ""); dialog::editNumber(polygonal::deg, 2, polygonal::MSI-1, 1, 2, XLAT("degree of the approximation"), "");
dialog::sidedialog = true;
}
else if(sym == 'x' && pmodel == mdPolynomial) { else if(sym == 'x' && pmodel == mdPolynomial) {
polygonal::maxcoef = max(polygonal::maxcoef, polygonal::coefid); polygonal::maxcoef = max(polygonal::maxcoef, polygonal::coefid);
int ci = polygonal::coefid + 1; int ci = polygonal::coefid + 1;

View File

@ -308,7 +308,7 @@ void handleKeyNormal(int sym, int uni) {
// vid.yshift = 1 - vid.yshift; // vid.yshift = 1 - vid.yshift;
// vid.drawmousecircle = true; // vid.drawmousecircle = true;
} }
if(sym == 'm' && canmove && cmode2 == smNormal && (centerover == cwt.c ? mouseover : centerover)) if(sym == 'm' && canmove && (centerover == cwt.c ? mouseover : centerover))
performMarkCommand(mouseover); performMarkCommand(mouseover);
} }
@ -316,7 +316,7 @@ void handleKeyNormal(int sym, int uni) {
if(sym == '.' || sym == 's') movepcto(-1, 1); if(sym == '.' || sym == 's') movepcto(-1, 1);
if((sym == SDLK_DELETE || sym == SDLK_KP_PERIOD || sym == 'g') && uni != 'G' && uni != 'G'-64) if((sym == SDLK_DELETE || sym == SDLK_KP_PERIOD || sym == 'g') && uni != 'G' && uni != 'G'-64)
movepcto(MD_DROP, 1); movepcto(MD_DROP, 1);
if(sym == 't' && uni != 'T' && uni != 'T'-64 && canmove && cmode2 == smNormal) { if(sym == 't' && uni != 'T' && uni != 'T'-64 && canmove) {
if(playermoved && items[itStrongWind]) { if(playermoved && items[itStrongWind]) {
cell *c = whirlwind::jumpDestination(cwt.c); cell *c = whirlwind::jumpDestination(cwt.c);
if(c) centerover = c; if(c) centerover = c;
@ -416,10 +416,12 @@ void mainloopiter() {
cframelimit = vid.framelimit; cframelimit = vid.framelimit;
if(outoffocus && cframelimit > 10) cframelimit = 10; if(outoffocus && cframelimit > 10) cframelimit = 10;
if(DOSHMUP && cmode2 == smNormal) bool normal = cmode & sm::NORMAL;
if(DOSHMUP && normal)
timetowait = 0, shmup::turn(ticks - lastt); timetowait = 0, shmup::turn(ticks - lastt);
if(!DOSHMUP && (multi::alwaysuse || multi::players > 1) && cmode2 == smNormal) if(!DOSHMUP && (multi::alwaysuse || multi::players > 1) && normal)
timetowait = 0, multi::handleMulti(ticks - lastt); timetowait = 0, multi::handleMulti(ticks - lastt);
if(vid.sspeed >= 5 && gmatrix.count(cwt.c) && !elliptic) { if(vid.sspeed >= 5 && gmatrix.count(cwt.c) && !elliptic) {
@ -436,7 +438,7 @@ void mainloopiter() {
if(timetowait > 0) if(timetowait > 0)
SDL_Delay(timetowait); SDL_Delay(timetowait);
else { else {
if(cmode2 == smNormal) { if(cmode & sm::CENTER) {
if(playermoved && vid.sspeed > -4.99 && !outoffocus) if(playermoved && vid.sspeed > -4.99 && !outoffocus)
centerpc((ticks - lastt) / 1000.0 * exp(vid.sspeed)); centerpc((ticks - lastt) / 1000.0 * exp(vid.sspeed));
if(panjoyx || panjoyy) if(panjoyx || panjoyy)
@ -545,7 +547,9 @@ void mainloopiter() {
} }
} }
if(ev.type == SDL_JOYBUTTONDOWN && cmode2 == smShmupConfig && vid.scfg.setwhat) { bool shmupconf = cmode & sm::SHMUPCONFIG;
if(ev.type == SDL_JOYBUTTONDOWN && shmupconf && vid.scfg.setwhat) {
int joyid = ev.jbutton.which; int joyid = ev.jbutton.which;
int button = ev.jbutton.button; int button = ev.jbutton.button;
if(joyid < 8 && button < 32) if(joyid < 8 && button < 32)
@ -553,7 +557,7 @@ void mainloopiter() {
vid.scfg.setwhat = 0; vid.scfg.setwhat = 0;
} }
else if(ev.type == SDL_JOYHATMOTION && cmode2 == smShmupConfig && vid.scfg.setwhat) { else if(ev.type == SDL_JOYHATMOTION && shmupconf && vid.scfg.setwhat) {
int joyid = ev.jhat.which; int joyid = ev.jhat.which;
int hat = ev.jhat.hat; int hat = ev.jhat.hat;
int dir = 4; int dir = 4;
@ -588,11 +592,10 @@ void mainloopiter() {
dialog::handleZooming(ev); dialog::handleZooming(ev);
if(sym == SDLK_F1 && cmode2 == smNormal && playermoved) if(sym == SDLK_F1 && normal && playermoved)
help = "@"; help = "@";
bool rollchange = bool rollchange = (cmode & sm::OVERVIEW) && getcstat >= 2000 && cheater;
cmode2 == smOverview && getcstat >= 2000 && cheater;
if(ev.type == SDL_MOUSEBUTTONDOWN) { if(ev.type == SDL_MOUSEBUTTONDOWN) {
flashMessages(); flashMessages();
@ -666,7 +669,7 @@ void mainloopiter() {
} }
if(ev.type == SDL_QUIT) { if(ev.type == SDL_QUIT) {
if(needConfirmation() && cmode2 != smMission) showMissionScreen(); if(needConfirmation() && !(cmode & sm::MISSION)) showMissionScreen();
else quitmainloop = true; else quitmainloop = true;
} }

View File

@ -172,7 +172,7 @@ namespace dialog {
int dcenter, dwidth; int dcenter, dwidth;
bool sidedialog; int dialogflags;
int displayLong(string str, int siz, int y, bool measure) { int displayLong(string str, int siz, int y, bool measure) {
@ -251,13 +251,14 @@ namespace dialog {
dcenter = vid.xres/2; dcenter = vid.xres/2;
dwidth = vid.xres; dwidth = vid.xres;
measure();
if(sidescreen) { if(sidescreen) {
dwidth = vid.xres - vid.yres; dwidth = vid.xres - vid.yres;
dcenter = vid.xres - dwidth / 2; dcenter = vid.xres - dwidth / 2;
} }
measure();
while(tothei > vid.yres - 5 * vid.fsize) { while(tothei > vid.yres - 5 * vid.fsize) {
int adfsize = int(dfsize * sqrt((vid.yres - 5. * vid.fsize) / tothei)); int adfsize = int(dfsize * sqrt((vid.yres - 5. * vid.fsize) / tothei));
if(adfsize < dfsize-1) dfsize = adfsize + 1; if(adfsize < dfsize-1) dfsize = adfsize + 1;
@ -600,15 +601,17 @@ namespace dialog {
if(ne.editwhat == &geom3::middetail && geom3::highdetail > geom3::middetail) if(ne.editwhat == &geom3::middetail && geom3::highdetail > geom3::middetail)
geom3::highdetail = geom3::middetail; geom3::highdetail = geom3::middetail;
if(cmode & sm::A3) {
buildpolys(); buildpolys();
#ifdef GL #ifdef GL
resetGL(); resetGL();
#endif #endif
} }
}
void drawNumberDialog() { void drawNumberDialog() {
gamescreen(sidedialog ? 0 : 2); cmode = sm::NUMBER | dialogflags;
cmode2 = smNumber; gamescreen((cmode & sm::SIDE) ? 0 : 2);
init(ne.title); init(ne.title);
addInfo(ne.s); addInfo(ne.s);
addSlider(ne.scale(ne.vmin), ne.scale(*ne.editwhat), ne.scale(ne.vmax), 500); addSlider(ne.scale(ne.vmin), ne.scale(*ne.editwhat), ne.scale(ne.vmax), 500);
@ -623,7 +626,7 @@ namespace dialog {
addBreak(100); addBreak(100);
ne.help = explain3D(ne.editwhat); if(cmode && sm::A3) ne.help = explain3D(ne.editwhat);
if(ne.help != "") { if(ne.help != "") {
addHelp(ne.help); addHelp(ne.help);
@ -774,14 +777,14 @@ namespace dialog {
ne.scale = ne.inverse_scale = identity; ne.scale = ne.inverse_scale = identity;
ne.intval = NULL; ne.intval = NULL;
ne.positive = false; ne.positive = false;
sidedialog = false; dialogflags = (cmode & (sm::SIDE | sm::A3));
cmode |= sm::NUMBER;
pushScreen(drawNumberDialog); pushScreen(drawNumberDialog);
} }
void editNumber(int& x, int vmin, int vmax, int step, int dft, string title, string help) { void editNumber(int& x, int vmin, int vmax, int step, int dft, string title, string help) {
editNumber(ne.intbuf, vmin, vmax, step, dft, title, help); editNumber(ne.intbuf, vmin, vmax, step, dft, title, help);
ne.intbuf = x; ne.intval = &x; ne.s = its(x); ne.intbuf = x; ne.intval = &x; ne.s = its(x);
sidedialog = true;
} }
}; };

View File

@ -5425,7 +5425,7 @@ void checkmove() {
if(!canmove) { if(!canmove) {
achievement_final(true); achievement_final(true);
if(cmode2 == smNormal) showMissionScreen(); if(cmode & sm::NORMAL) showMissionScreen();
} }
if(canmove && timerstopped) { if(canmove && timerstopped) {

View File

@ -2509,7 +2509,7 @@ void setcolors(cell *c, int& wcol, int &fcol) {
if(c->wall == waAncientGrave || c->wall == waFreshGrave || c->wall == waThumperOn || c->wall == waThumperOff || c->wall == waBonfireOff) if(c->wall == waAncientGrave || c->wall == waFreshGrave || c->wall == waThumperOn || c->wall == waThumperOff || c->wall == waBonfireOff)
fcol = wcol; fcol = wcol;
if(c->land == laMinefield && c->wall == waMineMine && (cmode2 == smMap || !canmove)) if(c->land == laMinefield && c->wall == waMineMine && ((cmode && sm::MAP) || !canmove))
fcol = wcol = 0xFF4040; fcol = wcol = 0xFF4040;
if(mightBeMine(c) && mineMarkedSafe(c)) if(mightBeMine(c) && mineMarkedSafe(c))
@ -2682,7 +2682,7 @@ bool openorsafe(cell *c) {
#define Dark(x) darkena(x,0,0xFF) #define Dark(x) darkena(x,0,0xFF)
int gridcolor(cell *c1, cell *c2) { int gridcolor(cell *c1, cell *c2) {
if(cmode2 == smDraw) return Dark(forecolor); if(cmode & sm::DRAW) return Dark(forecolor);
if(!c2) if(!c2)
return 0x202020 >> darken; return 0x202020 >> darken;
int rd1 = rosedist(c1), rd2 = rosedist(c2); int rd1 = rosedist(c1), rd2 = rosedist(c2);
@ -2896,7 +2896,7 @@ void drawcell(cell *c, transmatrix V, int spinv, bool mirrored) {
if(!buggyGeneration && c->mpdist > 8 && !cheater) return; // not yet generated if(!buggyGeneration && c->mpdist > 8 && !cheater) return; // not yet generated
if(c->land == laNone && cmode2 == smMap) { if(c->land == laNone && (cmode & sm::MAP)) {
queuepoly(V, shTriangle, 0xFF0000FF); queuepoly(V, shTriangle, 0xFF0000FF);
} }
@ -2961,7 +2961,7 @@ void drawcell(cell *c, transmatrix V, int spinv, bool mirrored) {
hiddens = false; hiddens = false;
} }
if(hiddens && cmode2 != smMap) if(hiddens && !(cmode & sm::MAP))
it = itNone; it = itNone;
int icol = 0, moncol = 0xFF00FF; int icol = 0, moncol = 0xFF00FF;
@ -3088,7 +3088,7 @@ void drawcell(cell *c, transmatrix V, int spinv, bool mirrored) {
#ifndef NOEDIT #ifndef NOEDIT
if(mapeditor::drawUserShape(Vpdir, mapeditor::cellShapeGroup(), mapeditor::realpatternsh(c), if(mapeditor::drawUserShape(Vpdir, mapeditor::cellShapeGroup(), mapeditor::realpatternsh(c),
darkena(fcol, fd, cmode2 == smDraw ? 0xC0 : 0xFF), c)); darkena(fcol, fd, (cmode & sm::DRAW) ? 0xC0 : 0xFF), c));
else if(mapeditor::whichShape == '7') { else if(mapeditor::whichShape == '7') {
if(ishept(c)) if(ishept(c))
@ -3397,7 +3397,7 @@ void drawcell(cell *c, transmatrix V, int spinv, bool mirrored) {
} }
#endif #endif
if(cmode2 == smNumber && (dialog::editingDetail())) { if((cmode & sm::NUMBER) && (dialog::editingDetail())) {
int col = int col =
dist0 < geom3::highdetail ? 0xFF80FF80 : dist0 < geom3::highdetail ? 0xFF80FF80 :
dist0 >= geom3::middetail ? 0xFFFF8080 : dist0 >= geom3::middetail ? 0xFFFF8080 :
@ -3907,6 +3907,7 @@ void drawcell(cell *c, transmatrix V, int spinv, bool mirrored) {
} }
if(vid.grid) { if(vid.grid) {
vid.linewidth *= 3;
// sphere: 0.3948 // sphere: 0.3948
// sphere heptagonal: 0.5739 // sphere heptagonal: 0.5739
// sphere trihepta: 0.3467 // sphere trihepta: 0.3467
@ -3939,6 +3940,7 @@ void drawcell(cell *c, transmatrix V, int spinv, bool mirrored) {
V * ddspin(c,t,+S7) * xpush0(x), V * ddspin(c,t,+S7) * xpush0(x),
gridcolor(c, c->mov[t]), 1); gridcolor(c, c->mov[t]), 1);
} }
vid.linewidth /= 3;
} }
if(!euclid && (!pirateTreasureSeek || compassDist(c) < compassDist(pirateTreasureSeek))) if(!euclid && (!pirateTreasureSeek || compassDist(c) < compassDist(pirateTreasureSeek)))
@ -3995,7 +3997,7 @@ void drawcell(cell *c, transmatrix V, int spinv, bool mirrored) {
if(!inHighQual) { if(!inHighQual) {
#ifndef NOEDIT #ifndef NOEDIT
if(cmode2 == smMap && lmouseover && darken == 0 && if((cmode & sm::MAP) && lmouseover && darken == 0 &&
!mouseout() && !mouseout() &&
(mapeditor::whichPattern ? mapeditor::subpattern(c) == mapeditor::subpattern(lmouseover) : c == lmouseover)) { (mapeditor::whichPattern ? mapeditor::subpattern(c) == mapeditor::subpattern(lmouseover) : c == lmouseover)) {
queuecircle(V, .78, 0x00FFFFFF); queuecircle(V, .78, 0x00FFFFFF);
@ -4097,7 +4099,7 @@ void queuecircleat(cell *c, double rad, int col) {
void drawMarkers() { void drawMarkers() {
if(darken || cmode2 == smNumber) return; if(darken || !(cmode & sm::NORMAL)) return;
if(!inHighQual) { if(!inHighQual) {
@ -4188,7 +4190,7 @@ void drawMarkers() {
monsterToSummon = moNone; monsterToSummon = moNone;
orbToTarget = itNone; orbToTarget = itNone;
if(mouseover && targetclick && cmode2 == smNormal) { if(mouseover && targetclick) {
shmup::cpid = 0; shmup::cpid = 0;
orbToTarget = targetRangedOrb(mouseover, roCheck); orbToTarget = targetRangedOrb(mouseover, roCheck);
if(orbToTarget == itOrbSummon) { if(orbToTarget == itOrbSummon) {
@ -4408,7 +4410,7 @@ void drawthemap() {
Uint8 *keystate = SDL_GetKeyState(NULL); Uint8 *keystate = SDL_GetKeyState(NULL);
lmouseover = mouseover; lmouseover = mouseover;
bool useRangedOrb = (!(vid.shifttarget & 1) && haveRangedOrb() && lmouseover && lmouseover->cpdist > 1) || (keystate[SDLK_RSHIFT] | keystate[SDLK_LSHIFT]); bool useRangedOrb = (!(vid.shifttarget & 1) && haveRangedOrb() && lmouseover && lmouseover->cpdist > 1) || (keystate[SDLK_RSHIFT] | keystate[SDLK_LSHIFT]);
if(!useRangedOrb && cmode2 != smMap && DEFAULTCONTROL && !mouseout()) { if(!useRangedOrb && !(cmode & sm::MAP) && DEFAULTCONTROL && !mouseout()) {
void calcMousedest(); void calcMousedest();
calcMousedest(); calcMousedest();
cellwalker cw = cwt; bool f = flipplayer; cellwalker cw = cwt; bool f = flipplayer;
@ -4502,9 +4504,8 @@ void calcparam() {
vid.ycenter = vid.yres - realradius - vid.fsize - (ISIOS ? 10 : 0); vid.ycenter = vid.yres - realradius - vid.fsize - (ISIOS ? 10 : 0);
} }
else { else {
if(vid.xres >= vid.yres * 5/4-16 && dialog::sidedialog && cmode2 == smNumber) if(vid.xres >= vid.yres * 5/4-16 && (cmode & sm::SIDE))
sidescreen = true; sidescreen = true;
if(viewdists && cmode2 == smNormal && vid.xres > vid.yres) sidescreen = true;
#ifdef TOUR #ifdef TOUR
if(tour::on && (tour::slides[tour::currentslide].flags & tour::SIDESCREEN)) if(tour::on && (tour::slides[tour::currentslide].flags & tour::SIDESCREEN))
sidescreen = true; sidescreen = true;
@ -4571,7 +4572,7 @@ void drawfullmap() {
drawthemap(); drawthemap();
#ifndef NORUG #ifndef NORUG
if(!inHighQual) { if(!inHighQual) {
if(cmode2 == smNormal && !rug::rugged) { if((cmode & sm::NORMAL) && !rug::rugged) {
if(multi::players > 1) { if(multi::players > 1) {
transmatrix bcwtV = cwtV; transmatrix bcwtV = cwtV;
for(int i=0; i<multi::players; i++) if(multi::playerActive(i)) for(int i=0; i<multi::players; i++) if(multi::playerActive(i))
@ -4584,7 +4585,7 @@ void drawfullmap() {
drawmovestar(0, 0); drawmovestar(0, 0);
} }
if(rug::rugged && !rug::renderonce) queueline(C0, mouseh, 0xFF00FFFF, 5); if(rug::rugged && !rug::renderonce) queueline(C0, mouseh, 0xFF00FFFF, 5);
if(cmode2 == smDraw) mapeditor::drawGrid(); if(cmode & sm::DRAW) mapeditor::drawGrid();
} }
#endif #endif
profile_start(2); profile_start(2);
@ -4648,7 +4649,8 @@ void normalscreen() {
#endif #endif
if(!outofmap(mouseh)) getcstat = '-'; if(!outofmap(mouseh)) getcstat = '-';
cmode2 = smNormal; cmode = sm::NORMAL | sm::DOTOUR | sm::CENTER;
if(viewdists) cmode |= sm::SIDE;
gamescreen(hiliteclick && mmmon ? 1 : 0); drawStats(); gamescreen(hiliteclick && mmmon ? 1 : 0); drawStats();
if(nomenukey) if(nomenukey)
; ;
@ -4665,7 +4667,7 @@ void normalscreen() {
vector< function<void()> > screens = { normalscreen }; vector< function<void()> > screens = { normalscreen };
screenmode cmode2; int cmode;
void drawscreen() { void drawscreen() {
@ -4697,7 +4699,7 @@ void drawscreen() {
mouseovers = " "; mouseovers = " ";
cmode2 = smMenu; cmode = 0;
keyhandler = [] (int sym, int uni) { return false; }; keyhandler = [] (int sym, int uni) { return false; };
screens.back()(); screens.back()();
@ -4710,7 +4712,9 @@ void drawscreen() {
drawmessages(); drawmessages();
if((havewhat&HF_BUG) && darken == 0 && cmode2 == smNormal) for(int k=0; k<3; k++) bool normal = cmode & sm::NORMAL;
if((havewhat&HF_BUG) && darken == 0 && normal) for(int k=0; k<3; k++)
displayfr(vid.xres/2 + vid.fsize * 5 * (k-1), vid.fsize*2, 2, vid.fsize, displayfr(vid.xres/2 + vid.fsize * 5 * (k-1), vid.fsize*2, 2, vid.fsize,
its(hive::bugcount[k]), minf[moBug0+k].color, 8); its(hive::bugcount[k]), minf[moBug0+k].color, 8);
@ -4730,7 +4734,7 @@ void drawscreen() {
} }
} }
if((minefieldNearby || tmines) && !items[itOrbAether] && darken == 0 && cmode2 == smNormal) { if((minefieldNearby || tmines) && !items[itOrbAether] && darken == 0 && normal) {
string s; string s;
if(tmines > 7) tmines = 7; if(tmines > 7) tmines = 7;
int col = minecolors[tmines]; int col = minecolors[tmines];

View File

@ -673,7 +673,8 @@ void describeMouseover() {
} }
void showHelp() { void showHelp() {
cmode2 = smHelp; gamescreen(2);
cmode = sm::HELP | sm::DOTOUR;
getcstat = SDLK_ESCAPE; getcstat = SDLK_ESCAPE;
if(help == "HELPFUN") { if(help == "HELPFUN") {
help_delegate(); help_delegate();

View File

@ -291,12 +291,12 @@ void drawStats() {
if(geometry == gNormal && !purehepta) { if(geometry == gNormal && !purehepta) {
dialog::addBreak(200); dialog::addBreak(200);
dialog::addHelp("a(d+4) = a(d+3) + a(d+2) + a(d+1) - a(d)"); dialog::addHelp("a(d+4) = a(d+3) + a(d+2) + a(d+1) - a(d)");
dialog::addInfo("a(d) ~ 1.72208ᵈ", forecolor); dialog::addInfo("a(d) ~ 1.72208", forecolor);
} }
if(geometry == gNormal && purehepta) { if(geometry == gNormal && purehepta) {
dialog::addBreak(200); dialog::addBreak(200);
dialog::addHelp("a(d+2) = 3a(d+1) - a(d+2)"); dialog::addHelp("a(d+2) = 3a(d+1) - a(d+2)");
dialog::addInfo("a(d) ~ 2.61803ᵈ", forecolor); dialog::addInfo("a(d) ~ 2.61803", forecolor);
} }
if(geometry == gEuclid) { if(geometry == gEuclid) {
dialog::addBreak(300); dialog::addBreak(300);

19
hyper.h
View File

@ -1229,7 +1229,20 @@ extern bool dronemode;
extern ld whatever; extern ld whatever;
enum screenmode { smMenu, smNormal, smMission, smHelp, smMap, smDraw, smNumber, smShmupConfig, smOverview }; namespace sm {
static const int NORMAL = 1;
static const int MISSION = 2;
static const int HELP = 4;
static const int MAP = 8;
static const int DRAW = 16;
static const int NUMBER = 32;
static const int SHMUPCONFIG = 64;
static const int OVERVIEW = 128;
static const int SIDE = 256;
static const int DOTOUR = 512;
static const int CENTER = 1024;
static const int A3 = 2048; // affects poly
};
namespace linepatterns { namespace linepatterns {
@ -1430,7 +1443,7 @@ void gmodekeys(int sym, int uni);
void switchGL(); void switchGL();
void switchFullscreen(); void switchFullscreen();
extern screenmode cmode2; extern int cmode;
namespace scores { void load(); } namespace scores { void load(); }
@ -1454,3 +1467,5 @@ namespace leader { void showMenu(); void handleKey(int sym, int uni); }
#endif #endif
bool needConfirmation(); bool needConfirmation();
extern const char* geometrynames_short[gGUARD];

View File

@ -361,7 +361,7 @@ void run(const char *fname, int _perdist, double _maxfac) {
} }
void describe(cell *c) { void describe(cell *c) {
if(cmode2 == smHelp) return; if(cmode & sm::HELP) return;
neuron *n = getNeuronSlow(c); neuron *n = getNeuronSlow(c);
if(!n) return; if(!n) return;
help += "cell number: " + its(n - &net[0]) + "\n"; help += "cell number: " + its(n - &net[0]) + "\n";

View File

@ -790,7 +790,7 @@ namespace mapeditor {
} }
void showMapEditor() { void showMapEditor() {
cmode2 = smMap; cmode = sm::MAP;
gamescreen(0); gamescreen(0);
int fs = vid.fsize + 5; int fs = vid.fsize + 5;
@ -1279,7 +1279,7 @@ namespace mapeditor {
void drawHandleKey(int sym, int uni); void drawHandleKey(int sym, int uni);
void showDrawEditor() { void showDrawEditor() {
cmode2 = smDraw; cmode = sm::DRAW;
drawGrid(); drawGrid();
if(!mouseout()) getcstat = '-'; if(!mouseout()) getcstat = '-';
@ -1882,7 +1882,7 @@ namespace mapeditor {
} }
#ifndef NOEDIT #ifndef NOEDIT
if(cmode2 == smDraw && mapeditor::editingShape(group, id)) { if((cmode == sm::DRAW) && mapeditor::editingShape(group, id)) {
/* for(int a=0; a<size(ds.list); a++) { /* for(int a=0; a<size(ds.list); a++) {
hyperpoint P2 = V * ds.list[a]; hyperpoint P2 = V * ds.list[a];

View File

@ -163,16 +163,6 @@ void showOverview() {
// -- main menu -- // -- main menu --
bool checkHalloweenDate() {
time_t t = time(NULL);
struct tm tm = *localtime(&t);
int month = tm.tm_mon + 1;
int day = tm.tm_mday;
if(month == 10 && day >= 24) return true;
if(month == 11 && day <= 7) return true;
return false;
}
void showMainMenu() { void showMainMenu() {
gamescreen(2); gamescreen(2);
@ -213,8 +203,6 @@ void showMainMenu() {
if(inv::on) if(inv::on)
dialog::addItem(XLAT("inventory"), 'i'); dialog::addItem(XLAT("inventory"), 'i');
if(checkHalloweenDate()) dialog::addItem(XLAT("Halloween mini-game"), 'y'-96);
#ifdef ROGUEVIZ #ifdef ROGUEVIZ
dialog::addItem(XLAT("rogueviz menu"), 'u'); dialog::addItem(XLAT("rogueviz menu"), 'u');
#endif #endif
@ -247,21 +235,6 @@ void showMainMenu() {
#ifndef NOSAVE #ifndef NOSAVE
else if(sym == 't') scores::load(); else if(sym == 't') scores::load();
#endif #endif
else if(uni == 'y'-96) {
if(!sphere) {
euclidland = laHalloween;
restartGame('E');
vid.alpha = 999;
vid.scale = 998;
popScreen();
}
else {
restartGame('E');
vid.alpha = 1;
vid.scale = 1;
popScreen();
}
}
else if(sym == 'r' || sym == SDLK_F5) { else if(sym == 'r' || sym == SDLK_F5) {
restartGame(); restartGame();
popScreen(); popScreen();
@ -301,7 +274,8 @@ void showMainMenu() {
// -- display modes -- // -- display modes --
void showDisplayMode() { void showDisplayMode() {
gamescreen(3); cmode = sm::SIDE;
gamescreen(0);
dialog::init(XLAT("special display modes")); dialog::init(XLAT("special display modes"));
@ -353,7 +327,6 @@ void showDisplayMode() {
dialog::editNumber(vid.scale, .001, 1000, .1, 1, XLAT("scale factor"), dialog::editNumber(vid.scale, .001, 1000, .1, 1, XLAT("scale factor"),
XLAT("Scale the displayed model.")); XLAT("Scale the displayed model."));
dialog::scaleLog(); dialog::scaleLog();
dialog::sidedialog = true;
} }
if(xuni == 'm') { vid.monmode += 60 + (shiftmul > 0 ? 1 : -1); vid.monmode %= 6; } if(xuni == 'm') { vid.monmode += 60 + (shiftmul > 0 ? 1 : -1); vid.monmode %= 6; }
@ -369,7 +342,6 @@ void showDisplayMode() {
else if(xuni == 'x') { else if(xuni == 'x') {
viewdists = !viewdists; viewdists = !viewdists;
popScreen();
} }
#ifndef NORUG #ifndef NORUG
else if(xuni == 'u') { else if(xuni == 'u') {
@ -605,6 +577,11 @@ const char* geometrynames[gGUARD] = {
"Zebra quotient", "field quotient", "torus" "Zebra quotient", "field quotient", "torus"
}; };
const char* geometrynames_short[gGUARD] = {
"hyper", "Euclid", "sphere", "elliptic",
"Zebra", "field", "torus"
};
void showEuclideanMenu() { void showEuclideanMenu() {
gamescreen(4); gamescreen(4);
int s = vid.fsize; int s = vid.fsize;

View File

@ -633,6 +633,8 @@ namespace netgen {
} }
void show() { void show() {
cmode = sm::SIDE;
gamescreen(0);
if(true) { if(true) {
for(int i=0; i<CELLS; i++) { for(int i=0; i<CELLS; i++) {
int t = ct[i]; int t = ct[i];

528
quit.cpp Normal file
View File

@ -0,0 +1,528 @@
// -- mission screen --
bool quitsaves() { return (items[itOrbSafety] && havesave); }
bool needConfirmation() {
return canmove && (gold() >= 30 || tkills() >= 50) && !cheater && !quitsaves();
}
int msgscroll = 0;
string timeline() {
int timespent = (int) (savetime + (timerstopped ? 0 : (time(NULL) - timerstart)));
char buf[20];
sprintf(buf, "%d:%02d", timespent/60, timespent % 60);
return
shmup::on ?
XLAT("%1 knives (%2)", its(turncount), buf)
:
XLAT("%1 turns (%2)", its(turncount), buf);
}
struct hint {
time_t last;
function<bool()> usable;
function<void()> display;
function<void()> action;
};
void noaction() {}
function<void()> cancel = noaction;
string circlesizestr(int r) {
computeSizes();
string s;
int last = lastsize;
if(r <= last)
return llts(circlesize[r]);
else {
double d = log(circlesize[last]) + (log(circlesize[last]) - log(circlesize[last-1]))*(r-last);
int dlost = 0;
while(d > 10 * log(10)) d -= log(10), dlost++;
char buf[300]; sprintf(buf, "%.0f", exp(d));
string ss = XLAT("about ") + buf;
while(dlost % 9) dlost--, ss += '0';
for(int r = 0; r < 50 && dlost; r++) dlost -= 9, ss += " 000000000";
if(dlost) ss += XLAT(" (%1 more digits)", its(dlost));
return ss;
}
}
hint hints[] = {
{
0,
[]() {
return !inv::on && geometry == gNormal && items[localTreasureType()] >= 18;
},
[]() {
dialog::addHelp(XLAT(
"If you collect too many treasures in a given land, monsters will be "
"extremely dangerous. Try other lands once you have enough!"));
},
noaction},
{
0,
[]() {
return !ISMOBILE;
},
[]() {
dialog::addHelp(XLAT(
"Remember that you can right click mostly anything for more information."));
#ifdef MAC
dialog::addHelp(XLAT(
"(You can also use right Shift)\n\n"));
#endif
},
noaction},
{
0,
[]() { return !canmove; },
[]() {
dialog::addHelp(XLAT(
"Want to understand the geometry in HyperRogue? Try the Tutorial!"
));
dialog::addBreak(50);
dialog::addItem(XLAT("Tutorial"), 'z');
},
[]() {
tour::start();
}},
{
0,
[]() { return !inv::on; },
[]() {
dialog::addHelp(XLAT(
"Collecting 25 treasures in a given land is dangerous, "
"but allows magical Orbs of this land to appear in other places!"
));
},
noaction},
{
0,
[]() { return !canmove; },
[]() {
dialog::addInfo(XLAT(
"Press ESC to view this screen during the game."
));
},
[]() {
tour::start();
}},
{
0,
[]() { return true; },
[]() {
dialog::addInfo(XLAT(
#ifdef MOBILE
"The 'world overview' shows all the lands in HyperRogue."
#else
"Press 'o' to see all the lands in HyperRogue."
#endif
));
dialog::addBreak(50);
dialog::addItem(XLAT("world overview"), 'z');
},
[]() {
pushScreen(showOverview);
}},
{
0,
[]() { return !canmove; },
[]() {
dialog::addInfo(XLAT(
"Want another type of game? Want more challenge?\n"
"HyperRogue has many special modes and challenges that "
"significantly change the gameplay. Try them!"
));
dialog::addBreak(50);
dialog::addItem(XLAT("special game modes"), 'z');
},
[]() {
pushScreen(showChangeMode);
}},
{
0,
[]() { return true; },
[]() {
dialog::addInfo(XLAT(
"Hyperbolic geometry can be shown in many ways."
));
dialog::addBreak(50);
dialog::addItem(XLAT("special display modes"), 'z');
},
[]() {
pushScreen(showDisplayMode);
}},
{
0,
[]() { return !canmove && !inv::on; },
[]() {
dialog::addHelp(XLAT(
"You do not want to lose the game from a single mistake?\n"
"Do you want to use the Orbs strategically?\n"
"Try the Orb Strategy mode!")
);
dialog::addBreak(50);
#ifdef INF
dialog::addItem(XLAT("Orb Strategy mode"), 'z');
#else
dialog::addItem(XLAT("(paid versions only)"), 'z');
#endif
},
[]() {
#ifdef INV
restartGame('i');
#endif
}
},
{
0,
[]() { return geometry == gNormal; },
[]() {
dialog::addHelp(XLAT(
"Do you think you are playing on a ball? "
"This is far from the truth!\n"
));
dialog::addBreak(50);
dialog::addItem(XLAT("Hypersian Rug mode"), 'z');
},
[] () {
popScreen();
int wm, mm;
rug::init();
wm = vid.wallmode;
mm = vid.monmode;
vid.wallmode = 3;
vid.monmode = 2;
cancel = [wm, mm] () {
rug::close();
vid.wallmode = wm;
vid.monmode = mm;
};
}
},
{
0,
[]() { return !canmove && geometry == gNormal && celldist(cwt.c) >= 50; },
[]() {
dialog::addHelp(XLAT(
"Did you know that the path you take during the game "
"is very close to a straight line?\n"
));
dialog::addBreak(50);
dialog::addItem(XLAT("Show me!"), 'z');
},
[] () {
popScreen();
auto m = pmodel;
pmodel = mdBand;
int r = conformal::rotation;
bool h = conformal::includeHistory;
conformal::rotation = 0;
conformal::includeHistory = true;
conformal::create();
cancel = [m,r,h] () {
conformal::clear(); pmodel = m;
conformal::rotation = r;
conformal::includeHistory = h;
fullcenter(); };
}
},
{
0,
[]() { return !canmove && geometry == gNormal && celldist(cwt.c) >= 50; },
[]() {
int c = celldist(cwt.c);
string s = circlesizestr(c);
dialog::addHelp(XLAT(
"You are %1 cells away from the starting point, or "
"the place where you used an Orb of Safety last time. "
"There are %2 such cells.\n",
its(c), s
));
dialog::addBreak(50);
dialog::addItem(XLAT("expansion"), 'z');
},
[] () {
viewdists = !viewdists;
popScreen();
cancel = [] () { viewdists = false; };
}
},
{
0,
[]() {
if(canmove) return false;
time_t t = time(NULL);
struct tm tm = *localtime(&t);
int month = tm.tm_mon + 1;
int day = tm.tm_mday;
if(month == 10 && day >= 24) return true;
if(month == 11 && day <= 7) return true;
return false;
},
[]() {
dialog::addItem(XLAT("Halloween mini-game"), 'z');
},
[] () {
if(!sphere) {
euclidland = laHalloween;
targetgeometry = gSphere;
restartGame('E');
vid.alpha = 999;
vid.scale = 998;
popScreen();
}
else {
restartGame('E');
vid.alpha = 1;
vid.scale = 1;
popScreen();
}
}
},
{-1, []() { return false; }, noaction, noaction}
};
int hinttoshow;
void showMission() {
cmode = sm::DOTOUR | sm::MISSION | sm::CENTER;
gamescreen(1); drawStats();
keyhandler = handleKeyQuit;
dialog::init(
#ifdef TOUR
tour::on ? (canmove ? XLAT("Tutorial") : XLAT("GAME OVER")) :
#endif
cheater ? XLAT("It is a shame to cheat!") :
showoff ? XLAT("Showoff mode") :
(canmove && princess::challenge) ? XLAT("%1 Challenge", moPrincess) :
canmove ? XLAT("Quest status") :
XLAT("GAME OVER"),
0xC00000, 200, 100
);
dialog::addInfo(XLAT("Your score: %1", its(gold())));
dialog::addInfo(XLAT("Enemies killed: %1", its(tkills())));
#ifdef TOUR
if(tour::on) ; else
#endif
if(items[itOrbYendor]) {
dialog::addInfo(XLAT("Orbs of Yendor found: %1", its(items[itOrbYendor])), iinf[itOrbYendor].color);
dialog::addInfo(XLAT("CONGRATULATIONS!"), iinf[itOrbYendor].color);
}
else {
if(princess::challenge)
dialog::addInfo(XLAT("Follow the Mouse and escape with %the1!", moPrincess));
else if(gold() < R30)
dialog::addInfo(XLAT("Collect %1 $$$ to access more worlds", its(R30)));
else if(gold() < R60)
dialog::addInfo(XLAT("Collect %1 $$$ to access even more lands", its(R60)));
else if(!hellUnlocked())
dialog::addInfo(XLAT("Collect at least %1 treasures in each of 9 types to access Hell", its(R10)));
else if(items[itHell] < R10)
dialog::addInfo(XLAT("Collect at least %1 Demon Daisies to find the Orbs of Yendor", its(R10)));
else if(size(yendor::yi) == 0)
dialog::addInfo(XLAT("Look for the Orbs of Yendor in Hell or in the Crossroads!"));
else
dialog::addInfo(XLAT("Unlock the Orb of Yendor!"));
}
if(!timerstopped && !canmove) {
savetime += time(NULL) - timerstart;
timerstopped = true;
}
if(canmove && !timerstart)
timerstart = time(NULL);
if(princess::challenge) ;
#ifdef TOUR
else if(tour::on) ;
#endif
else if(tkills() < R100)
dialog::addInfo(XLAT("Defeat %1 enemies to access the Graveyard", its(R100)));
else if(kills[moVizier] == 0 && (items[itFernFlower] < U5 || items[itGold] < U5))
dialog::addInfo(XLAT("Kill a Vizier in the Palace to access Emerald Mine"));
else if(items[itEmerald] < U5)
dialog::addInfo(XLAT("Collect 5 Emeralds to access Camelot"));
else if(hellUnlocked() && !chaosmode) {
bool b = true;
for(int i=0; i<LAND_HYP; i++)
if(b && items[treasureType(land_hyp[i])] < R10) {
dialog::addInfo(
XLAT(
land_hyp[i] == laTortoise ? "Hyperstone Quest: collect at least %3 points in %the2" :
"Hyperstone Quest: collect at least %3 %1 in %the2",
treasureType(land_hyp[i]), land_hyp[i], its(R10)));
b = false;
}
if(b)
dialog::addInfo(XLAT("Hyperstone Quest completed!"), iinf[itHyperstone].color);
}
else dialog::addInfo(XLAT("Some lands unlock at specific treasures or kills"));
if(cheater) {
dialog::addInfo(XLAT("you have cheated %1 times", its(cheater)), 0xFF2020);
}
if(!cheater) {
dialog::addInfo(timeline(), 0xC0C0C0);
}
msgs.clear();
if(msgscroll < 0) msgscroll = 0;
int gls = size(gamelog) - msgscroll;
int mnum = 0;
for(int i=gls-5; i<gls; i++)
if(i>=0) {
msginfo m;
m.spamtype = 0;
m.flashout = true;
m.stamp = ticks-128*vid.flashtime-128*(gls-i);
m.msg = gamelog[i].msg;
m.quantity = gamelog[i].quantity;
mnum++,
msgs.push_back(m);
}
dialog::addBreak(100);
if(!tour::on) {
hints[hinttoshow].display();
dialog::addBreak(100);
}
bool intour = false;
#ifdef TOUR
intour = tour::on;
#endif
if(intour) {
#ifdef TOUR
if(canmove) {
dialog::addItem(XLAT("spherical geometry"), '1');
dialog::addItem(XLAT("Euclidean geometry"), '2');
dialog::addItem(XLAT("more curved hyperbolic geometry"), '3');
}
if(!items[itOrbTeleport])
dialog::addItem(XLAT("teleport away"), '4');
else if(!items[itOrbAether])
dialog::addItem(XLAT("move through walls"), '4');
else
dialog::addItem(XLAT("flash"), '4');
if(canmove) {
if(tour::slidecommand != "")
dialog::addItem(tour::slidecommand, '5');
dialog::addItem(XLAT("static mode"), '6');
dialog::addItem(XLAT("enable/disable texts"), '7');
dialog::addItem(XLAT("next slide"), SDLK_RETURN);
dialog::addItem(XLAT("previous slide"), SDLK_BACKSPACE);
dialog::addItem(XLAT("list of slides"), '9');
}
else
dialog::addBreak(200);
dialog::addItem(XLAT("main menu"), 'v');
#endif
}
else {
dialog::addItem(XLAT(canmove ? "continue" : "see how it ended"), SDLK_ESCAPE);
dialog::addItem(XLAT("main menu"), 'v');
dialog::addItem(XLAT("restart"), SDLK_F5);
#ifndef MOBILE
dialog::addItem(XLAT(quitsaves() ? "save" : "quit"), SDLK_F10);
#endif
#ifdef ANDROIDSHARE
dialog::addItem(XLAT("SHARE"), 's'-96);
#endif
dialog::addBreak(500);
}
dialog::display();
if(mnum)
displayfr(vid.xres/2, vid.yres-vid.fsize*(mnum+1), 2, vid.fsize/2, XLAT("last messages:"), 0xC0C0C0, 8);
}
void handleKeyQuit(int sym, int uni) {
dialog::handleNavigation(sym, uni);
// ignore the camera movement keys
#ifndef NORUG
if(rug::rugged && (sym == SDLK_UP || sym == SDLK_DOWN || sym == SDLK_PAGEUP || sym == SDLK_PAGEDOWN ||
sym == SDLK_RIGHT || sym == SDLK_LEFT))
sym = 0;
#endif
if(sym == SDLK_RETURN || sym == SDLK_KP_ENTER || sym == SDLK_F10) quitmainloop = true;
else if(uni == 'r' || sym == SDLK_F5) {
restartGame(), popScreen();
msgs.clear();
}
else if(sym == SDLK_UP || sym == SDLK_KP8 || sym == PSEUDOKEY_WHEELUP) msgscroll++;
else if(sym == SDLK_DOWN || sym == SDLK_KP2 || sym == PSEUDOKEY_WHEELDOWN) msgscroll--;
else if(sym == SDLK_PAGEUP || sym == SDLK_KP9) msgscroll+=5;
else if(sym == SDLK_PAGEDOWN || sym == SDLK_KP3) msgscroll-=5;
else if(uni == 'v') popScreenAll(), pushScreen(showMainMenu);
else if(uni == 'z') hints[hinttoshow].action();
else if(sym == SDLK_F3 || (sym == ' ' || sym == SDLK_HOME))
fullcenter();
else if(uni == 'o') setAppropriateOverview();
#ifdef INV
else if(uni == 'i' && inv::on)
pushScreen(inv::show);
#endif
#ifndef NOSAVE
else if(uni == 't') {
msgs.clear();
scores::load();
}
#endif
else if(doexiton(sym, uni) && !didsomething) {
popScreen();
msgscroll = 0;
msgs.clear();
if(!canmove) {
addMessage(XLAT("GAME OVER"));
addMessage(timeline());
}
}
}
int counthints() {
for(int h=0;; h++) if(hints[h].last < 0) return h;
}
void showMissionScreen() {
cancel(); cancel = noaction;
popScreenAll();
pushScreen(showMission);
achievement_final(false);
msgscroll = 0;
if(!tour::on) {
int ch = counthints();
hinttoshow = ch;
int h;
for(h=0; h < ch; h++) {
if(!hints[h].usable()) continue;
if(hinttoshow == ch || hints[h].last < hints[hinttoshow].last) hinttoshow = h;
}
hints[hinttoshow].last = time(NULL);
}
}

View File

@ -1755,7 +1755,7 @@ void showMenu() {
else if(uni == 'b') backcolor ^= 0xFFFFFF, bordcolor ^= 0xFFFFFF, forecolor ^= 0xFFFFFF; else if(uni == 'b') backcolor ^= 0xFFFFFF, bordcolor ^= 0xFFFFFF, forecolor ^= 0xFFFFFF;
else if(uni == 'g') { else if(uni == 'g') {
dialog::editNumber(ggamma, 0, 5, .01, 0.5, XLAT("gamma value for edges"), ""); dialog::editNumber(ggamma, 0, 5, .01, 0.5, XLAT("gamma value for edges"), "");
dialog::sidedialog = true; dialog::dialogflags = sm::SIDE;
} }
else if(uni == 'z') { else if(uni == 'z') {
for(int i=0; i<size(named)-1; i++) if(named[i] == cwt.c) for(int i=0; i<size(named)-1; i++) if(named[i] == cwt.c)

View File

@ -8,7 +8,6 @@ score *currentgame;
int scoresort = 2; int scoresort = 2;
int scoredisplay = 1; int scoredisplay = 1;
int scorefrom = 0; int scorefrom = 0;
int scoremode = 0;
bool scorerev = false; bool scorerev = false;
bool scorecompare(const score& s1, const score &s2) { bool scorecompare(const score& s1, const score &s2) {
@ -19,16 +18,60 @@ bool fakescore() {
return fakebox[scoredisplay]; return fakebox[scoredisplay];
} }
string csub(const string& str, int q) {
int i = 0;
for(int j=0; j<q && i<size(str); j++) getnext(str.c_str(), i);
return str.substr(0, i);
}
int colwidth() { int colwidth() {
if(scoredisplay == 0) return 5; if(scoredisplay == 0) return 5;
if(scoredisplay == 1) return 16; if(scoredisplay == 1) return 16;
if(scoredisplay == 5) return 8; if(scoredisplay == 5) return 8;
if(scoredisplay == POSSCORE) return 8;
return 4; return 4;
} }
bool isHardcore(score *S) {
return S->box[117] && S->box[118] < PUREHARDCORE_LEVEL;
}
int modediff(score *S) {
int diff = 0;
eGeometry g = (eGeometry) S->box[116];
if(S->box[238]) g = gSphere;
if(S->box[239]) g = gElliptic;
if(max(S->box[197], 1) != multi::players) diff += 8;
if(S->box[186] != purehepta) diff += 16;
if(S->box[196] != chaosmode) diff += 32;
if(S->box[119] != shmup::on) diff += 64;
if(pureHardcore() && !isHardcore(S)) diff += 128;
if(g != gNormal && S->box[120] != euclidland)
diff += 256;
if(g != geometry) {
diff += 512;
}
return -diff;
}
string modedesc(score *S) {
eGeometry g = (eGeometry) S->box[116];
if(S->box[238]) g = gSphere;
if(S->box[239]) g = gElliptic;
string s = geometrynames_short[g];
if(g != gNormal) s += " " + csub(XLATT1((eLand) S->box[120]), 3);
if(S->box[186]) s += "/7";
if(S->box[196]) s += "/C";
if(S->box[119]) s += "/s";
if(S->box[197] > 1) s += "/P" + its(S->box[197]);
if(isHardcore(S)) s += "/h";
return s;
}
string displayfor(score* S, bool shorten = false) { string displayfor(score* S, bool shorten = false) {
// printf("S=%p, scoredisplay = %d\n", S, scoredisplay); // printf("S=%p, scoredisplay = %d\n", S, scoredisplay);
if(S == NULL) { if(S == NULL) {
if(scoredisplay == POSSCORE) return "mode";
string str = XLATN(boxname[scoredisplay]); string str = XLATN(boxname[scoredisplay]);
if(!shorten) return str; if(!shorten) return str;
if(scoredisplay == 0 || scoredisplay == 65) return XLAT("time"); if(scoredisplay == 0 || scoredisplay == 65) return XLAT("time");
@ -39,9 +82,7 @@ string displayfor(score* S, bool shorten = false) {
if(scoredisplay == 67) return XLAT("cheats"); if(scoredisplay == 67) return XLAT("cheats");
if(scoredisplay == 66) return XLAT("saves"); if(scoredisplay == 66) return XLAT("saves");
if(scoredisplay == 197) return XLAT("players"); if(scoredisplay == 197) return XLAT("players");
int i = 0; return csub(str, 5);
for(int j=0; j<5; j++) if(i < size(str)) getnext(str.c_str(), i);
return str.substr(0, i);
} }
if(scoredisplay == 0 || scoredisplay == 65) { if(scoredisplay == 0 || scoredisplay == 65) {
char buf[20]; char buf[20];
@ -52,6 +93,7 @@ string displayfor(score* S, bool shorten = false) {
snprintf(buf, 20, "%d:%02d", t/60, t%60); snprintf(buf, 20, "%d:%02d", t/60, t%60);
return buf; return buf;
} }
if(scoredisplay == POSSCORE) return modedesc(S);
if(scoredisplay == 1) { if(scoredisplay == 1) {
time_t tim = S->box[1]; time_t tim = S->box[1];
char buf[128]; strftime(buf, 128, "%c", localtime(&tim)); char buf[128]; strftime(buf, 128, "%c", localtime(&tim));
@ -71,11 +113,6 @@ void sortScores() {
} }
} }
void shiftScoreDisplay(int delta) {
scoredisplay = (scoredisplay + POSSCORE + delta) % POSSCORE, scorerev = false;
if(fakescore()) shiftScoreDisplay(delta);
}
int curcol; int curcol;
vector<int> columns; vector<int> columns;
@ -90,7 +127,7 @@ void showPickScores() {
scorerev = false; scorerev = false;
for(int i=0; i<POSSCORE; i++) { for(int i=0; i<=POSSCORE; i++) {
scoredisplay = i; scoredisplay = i;
if(!fakescore()) { if(!fakescore()) {
string s = displayfor(NULL); string s = displayfor(NULL);
@ -126,7 +163,7 @@ void showPickScores() {
if(uni >= '1' && uni <= '9') uni = uni + 1000 - '1'; if(uni >= '1' && uni <= '9') uni = uni + 1000 - '1';
else if(uni >= 1000 && uni < 1000 + size(pickscore_options)) { else if(uni >= 1000 && uni < 1000 + size(pickscore_options)) {
scoredisplay = pickscore_options[uni - 1000].second; scoredisplay = pickscore_options[uni - 1000].second;
for(int i=0; i<POSSCORE; i++) for(int i=0; i<=POSSCORE; i++)
if(columns[i] == scoredisplay) swap(columns[i], columns[curcol]); if(columns[i] == scoredisplay) swap(columns[i], columns[curcol]);
popScreen(); popScreen();
} }
@ -137,7 +174,10 @@ void showPickScores() {
void show() { void show() {
if(columns.size() == 0) for(int i=0; i<POSSCORE; i++) columns.push_back(i); if(columns.size() == 0) {
columns.push_back(POSSCORE);
for(int i=0; i<POSSCORE; i++) columns.push_back(i);
}
int y = vid.fsize * 5/2; int y = vid.fsize * 5/2;
int bx = vid.fsize; int bx = vid.fsize;
getcstat = 0; getcstat = 0;
@ -146,7 +186,7 @@ void show() {
displaystr(bx*8, vid.fsize, 0, vid.fsize, XLAT("ver"), forecolor, 16); displaystr(bx*8, vid.fsize, 0, vid.fsize, XLAT("ver"), forecolor, 16);
int at = 9; int at = 9;
for(int i=0; i<POSSCORE; i++) { for(int i=0; i<=POSSCORE; i++) {
scoredisplay = columns[i]; scoredisplay = columns[i];
if(bx*at > vid.xres) break; if(bx*at > vid.xres) break;
if(displaystr(bx*at, vid.fsize, 0, vid.fsize, displayfor(NULL, true), i == curcol ? 0xFFD500 : forecolor, 0)) if(displaystr(bx*at, vid.fsize, 0, vid.fsize, displayfor(NULL, true), i == curcol ? 0xFFD500 : forecolor, 0))
@ -163,17 +203,6 @@ void show() {
score& S(scores[id]); score& S(scores[id]);
bool wrongtype = false;
wrongtype |= (euclid && (!S.box[116] || S.box[120] != euclidland));
wrongtype |= (!euclid && S.box[116]);
wrongtype |= (scoremode == 1 && !S.box[119]);
wrongtype |= (scoremode != 1 && S.box[119]);
wrongtype |= (scoremode == 2 && (!S.box[117] || S.box[118] >= PUREHARDCORE_LEVEL));
if(wrongtype) { id++; continue; }
if(omit) { omit--; rank++; id++; continue; } if(omit) { omit--; rank++; id++; continue; }
bool cur = S.box[MAXBOX-1]; bool cur = S.box[MAXBOX-1];
@ -191,7 +220,7 @@ void show() {
displaystr(bx*8, y, 0, vid.fsize, S.ver, col, 16); displaystr(bx*8, y, 0, vid.fsize, S.ver, col, 16);
int at = 9; int at = 9;
for(int i=0; i<POSSCORE; i++) { for(int i=0; i<=POSSCORE; i++) {
scoredisplay = columns[i]; scoredisplay = columns[i];
if(bx*at > vid.xres) break; if(bx*at > vid.xres) break;
at += colwidth(); at += colwidth();
@ -205,27 +234,18 @@ void show() {
int i0 = vid.yres - vid.fsize; int i0 = vid.yres - vid.fsize;
int xr = vid.xres / 80; int xr = vid.xres / 80;
string modes =
scoremode == 0 ? XLAT(", m - mode: normal") :
scoremode == 1 ? XLAT(", m - mode: shoot'em up") :
scoremode == 2 ? XLAT(", m - mode: hardcore only") :
"?";
if(euclid) modes += XLAT(" (E:%1)", euclidland);
displayButton(xr*10, i0, IFM("s - ") + XLAT("sort"), 's', 8); displayButton(xr*10, i0, IFM("s - ") + XLAT("sort"), 's', 8);
displayButton(xr*25, i0, IFM("t - ") + XLAT("choose"), 't', 8); displayButton(xr*30, i0, IFM("t - ") + XLAT("choose"), 't', 8);
displayButton(xr*40, i0, IFM("0 - ") + XLAT("play"), '0', 8); displayButton(xr*50, i0, IFM("0 - ") + XLAT("play"), '0', 8);
displayButton(xr*65, i0, IFM("m - ") + modes.substr(6), 'm', 8);
keyhandler = [] (int sym, int uni) { keyhandler = [] (int sym, int uni) {
if(sym == SDLK_LEFT || sym == SDLK_KP4 || sym == 'h' || sym == 'a') { if(sym == SDLK_LEFT || sym == SDLK_KP4 || sym == 'h' || sym == 'a') {
if(curcol > 0) curcol--; if(curcol > 0) curcol--;
} }
else if(sym == SDLK_RIGHT || sym == SDLK_KP6 || sym == 'l' || sym == 'd') { else if(sym == SDLK_RIGHT || sym == SDLK_KP6 || sym == 'l' || sym == 'd') {
if(curcol < POSSCORE-1) curcol++; if(curcol < POSSCORE) curcol++;
} }
else if(sym >= 1000 && sym < 1000+POSSCORE) else if(sym >= 1000 && sym <= 1000+POSSCORE)
curcol = sym - 1000; curcol = sym - 1000;
else if(sym == 't') { mapeditor::infix = ""; pushScreen(showPickScores); } else if(sym == 't') { mapeditor::infix = ""; pushScreen(showPickScores); }
else if(sym == SDLK_UP || sym == 'k' || sym == 'w') else if(sym == SDLK_UP || sym == 'k' || sym == 'w')
@ -237,7 +257,6 @@ void show() {
else if(sym == PSEUDOKEY_WHEELDOWN) else if(sym == PSEUDOKEY_WHEELDOWN)
scorefrom++; scorefrom++;
else if(sym == 's') sortScores(); else if(sym == 's') sortScores();
else if(sym == 'm') { scoremode++; scoremode %= 3; }
else if(doexiton(sym, uni)) popScreen(); else if(doexiton(sym, uni)) popScreen();
static int scoredragy; static int scoredragy;
@ -296,6 +315,7 @@ void load() {
sc.box[0] = sc.box[1] - sc.box[0]; // could not save then sc.box[0] = sc.box[1] - sc.box[0]; // could not save then
if(sc.box[2] == 0) continue; // do not list zero scores if(sc.box[2] == 0) continue; // do not list zero scores
sc.box[POSSCORE] = modediff(&sc);
if(ok && boxid > 20) scores.push_back(sc); if(ok && boxid > 20) scores.push_back(sc);
} }
@ -304,6 +324,7 @@ void load() {
saveBox(); saveBox();
score sc; score sc;
for(int i=0; i<POSSCORE; i++) sc.box[i] = savebox[i]; for(int i=0; i<POSSCORE; i++) sc.box[i] = savebox[i];
sc.box[POSSCORE] = 0;
sc.box[MAXBOX-1] = 1; sc.ver = "NOW"; sc.box[MAXBOX-1] = 1; sc.ver = "NOW";
scores.push_back(sc); scores.push_back(sc);
@ -312,12 +333,10 @@ void load() {
// addMessage(its(size(scores))+" games have been recorded in "+scorefile); // addMessage(its(size(scores))+" games have been recorded in "+scorefile);
pushScreen(show); pushScreen(show);
boxid = 0; applyBoxes(); boxid = 0; applyBoxes();
scoresort = 2; reverse(scores.begin(), scores.end()); reverse(scores.begin(), scores.end());
scoremode = 0;
if(shmup::on) scoremode = 1;
else if(hardcore) scoremode = 2;
scorefrom = 0; scorefrom = 0;
stable_sort(scores.begin(), scores.end(), scorecompare); scoresort = 2; stable_sort(scores.begin(), scores.end(), scorecompare);
scoresort = POSSCORE; stable_sort(scores.begin(), scores.end(), scorecompare);
} }
} }

View File

@ -82,10 +82,11 @@ void slidehelp() {
bool handleKeyTour(int sym, int uni) { bool handleKeyTour(int sym, int uni) {
if(!tour::on) return false; if(!tour::on) return false;
if(!cmode2) return false; if(!(cmode & sm::DOTOUR)) return false;
bool inhelp = cmode & sm::HELP;
int flags = slides[currentslide].flags; int flags = slides[currentslide].flags;
if((sym == SDLK_RETURN || sym == SDLK_KP_ENTER) && (cmode2 != smHelp || (flags & QUICKSKIP))) { if((sym == SDLK_RETURN || sym == SDLK_KP_ENTER) && (!inhelp || (flags & QUICKSKIP))) {
if(cmode2) popScreen(); if(inhelp) popScreen();
if(geometry || purehepta) { if(geometry || purehepta) {
restartGame(0, false); restartGame(0, false);
if(!(flags & QUICKGEO)) return true; if(!(flags & QUICKGEO)) return true;
@ -105,7 +106,7 @@ bool handleKeyTour(int sym, int uni) {
if(currentslide == 0) { slidehelp(); return true; } if(currentslide == 0) { slidehelp(); return true; }
presentation(pmStop); presentation(pmStop);
currentslide--; currentslide--;
if(cmode2 == smHelp) popScreen(), slidehelp(); if(inhelp) popScreen(), slidehelp();
presentation(pmStart); presentation(pmStart);
return true; return true;
} }