mirror of
https://github.com/zenorogue/hyperrogue.git
synced 2024-12-24 17:10:36 +00:00
'siblings' patterns on spheres
This commit is contained in:
parent
3c600d7d6b
commit
dadbbf244f
57
cell.cpp
57
cell.cpp
@ -85,6 +85,8 @@ int spherecells() {
|
|||||||
if(S7 == 1) return 1;
|
if(S7 == 1) return 1;
|
||||||
return 12;
|
return 12;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
vector<int> siblings;
|
||||||
|
|
||||||
struct hrmap_spherical : hrmap {
|
struct hrmap_spherical : hrmap {
|
||||||
heptagon *dodecahedron[12];
|
heptagon *dodecahedron[12];
|
||||||
@ -102,10 +104,15 @@ struct hrmap_spherical : hrmap {
|
|||||||
h.alt = NULL;
|
h.alt = NULL;
|
||||||
h.cdata = NULL;
|
h.cdata = NULL;
|
||||||
h.spintable = 0;
|
h.spintable = 0;
|
||||||
|
h.fieldval = i;
|
||||||
for(int i=0; i<S7; i++) h.move[i] = NULL;
|
for(int i=0; i<S7; i++) h.move[i] = NULL;
|
||||||
h.c7 = newCell(S7, &h);
|
h.c7 = newCell(S7, &h);
|
||||||
}
|
}
|
||||||
for(int i=0; i<S7; i++) {
|
if(S7 == 5)
|
||||||
|
siblings = {1, 0, 10, 4, 3, 8, 9, 11, 5, 6, 2, 7};
|
||||||
|
else
|
||||||
|
siblings = {1, 0, 3, 2, 5, 4};
|
||||||
|
for(int i=0; i<S7; i++) {
|
||||||
dodecahedron[0]->move[i] = dodecahedron[i+1];
|
dodecahedron[0]->move[i] = dodecahedron[i+1];
|
||||||
dodecahedron[0]->setspin(i, 0);
|
dodecahedron[0]->setspin(i, 0);
|
||||||
dodecahedron[i+1]->move[0] = dodecahedron[0];
|
dodecahedron[i+1]->move[0] = dodecahedron[0];
|
||||||
@ -1540,3 +1547,51 @@ int getHemisphere(cell *c, int which) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct sphereinfo {
|
||||||
|
int id;
|
||||||
|
int dir;
|
||||||
|
bool reflect;
|
||||||
|
};
|
||||||
|
|
||||||
|
sphereinfo valsphere(cell *c) {
|
||||||
|
sphereinfo si;
|
||||||
|
if(ctof(c)) {
|
||||||
|
int d = c->master->fieldval;
|
||||||
|
si.id = (d < siblings[d]) ? 0 : 1;
|
||||||
|
for(int i=0; i<S7; i++) {
|
||||||
|
int di = c->master->move[i]->fieldval;
|
||||||
|
if(di == siblings[d]) si.dir = i;
|
||||||
|
}
|
||||||
|
si.reflect = false;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
int ids = 0, tids = 0, td = 0;
|
||||||
|
for(int i=0; i<S3; i++) {
|
||||||
|
int d = c->mov[i*2]->master->fieldval;
|
||||||
|
ids |= (1<<d); tids += d;
|
||||||
|
}
|
||||||
|
for(int i=0; i<S3; i++) {
|
||||||
|
int d = c->mov[i*2]->master->fieldval;
|
||||||
|
if(ids & (1<<siblings[d])) td += d;
|
||||||
|
}
|
||||||
|
if(td) {
|
||||||
|
si.id = 4;
|
||||||
|
for(int i=0; i<S3; i++) {
|
||||||
|
int d = c->mov[i*2]->master->fieldval;
|
||||||
|
if(!(ids & (1<<siblings[d]))) si.dir = 2*i;
|
||||||
|
}
|
||||||
|
si.reflect = false;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
si.id = 8;
|
||||||
|
si.dir = 0; // whatever
|
||||||
|
sphereinfo si2 = valsphere(c->mov[0]);
|
||||||
|
int di = si2.dir - c->spin(0);
|
||||||
|
di %= S7;
|
||||||
|
if(di<0) di += S7;
|
||||||
|
si.reflect = di > S7/2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return si;
|
||||||
|
}
|
||||||
|
|
||||||
|
@ -332,6 +332,7 @@ namespace mapeditor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool reflectPatternAt(cell *c, char p = whichPattern) {
|
bool reflectPatternAt(cell *c, char p = whichPattern) {
|
||||||
|
if(p == 'p' && sphere) return valsphere(c).reflect;
|
||||||
if(p == 'p' && polarb50(c)) return true;
|
if(p == 'p' && polarb50(c)) return true;
|
||||||
if(p == 0) {
|
if(p == 0) {
|
||||||
int np = nopattern(c);
|
int np = nopattern(c);
|
||||||
@ -378,13 +379,16 @@ namespace mapeditor {
|
|||||||
return i;
|
return i;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int patterndir(cell *c, char w) {
|
int patterndir(cell *c, char w) {
|
||||||
|
if(w != 'H') {
|
||||||
|
if(a46) return patterndir46(c, w == 'z' ? 3 : w == 'p' ? 2 : 1);
|
||||||
|
if(a4) return patterndir457(c);
|
||||||
|
if(a38) return patterndir38(c);
|
||||||
|
if(sphere) return valsphere(c).dir;
|
||||||
|
}
|
||||||
switch(w) {
|
switch(w) {
|
||||||
case 'z': {
|
case 'z': {
|
||||||
if(a46) return patterndir46(c, 3);
|
|
||||||
if(a4) return patterndir457(c);
|
|
||||||
if(a38) return patterndir38(c);
|
|
||||||
int t = zebra40(c);
|
int t = zebra40(c);
|
||||||
|
|
||||||
if(euclid) return (t*4) % 6;
|
if(euclid) return (t*4) % 6;
|
||||||
@ -407,9 +411,6 @@ namespace mapeditor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
case 'f': {
|
case 'f': {
|
||||||
if(a46) return patterndir46(c, 1);
|
|
||||||
if(a38) return patterndir38(c);
|
|
||||||
if(a4) return patterndir457(c);
|
|
||||||
int t = emeraldval(c);
|
int t = emeraldval(c);
|
||||||
if(euclid) return 0;
|
if(euclid) return 0;
|
||||||
int tcdir = 0, tbest = (t&3);
|
int tcdir = 0, tbest = (t&3);
|
||||||
@ -425,9 +426,6 @@ namespace mapeditor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
case 'p': {
|
case 'p': {
|
||||||
if(a46) return patterndir46(c, 2);
|
|
||||||
if(a4) return patterndir457(c);
|
|
||||||
if(a38) return patterndir38(c);
|
|
||||||
int tcdir = -1, tbest = -1;
|
int tcdir = -1, tbest = -1;
|
||||||
int pa = polara50(c);
|
int pa = polara50(c);
|
||||||
int pb = polarb50(c);
|
int pb = polarb50(c);
|
||||||
@ -446,9 +444,6 @@ namespace mapeditor {
|
|||||||
|
|
||||||
case 0: {
|
case 0: {
|
||||||
if(euclid) return 0;
|
if(euclid) return 0;
|
||||||
if(a46) return patterndir46(c, 1);
|
|
||||||
if(a4) return patterndir457(c);
|
|
||||||
if(a38) return patterndir38(c);
|
|
||||||
int u = nopattern(c);
|
int u = nopattern(c);
|
||||||
|
|
||||||
if(u == 6) {
|
if(u == 6) {
|
||||||
@ -807,6 +802,9 @@ namespace mapeditor {
|
|||||||
dialog::addBoolItem(XLAT("Palace Pattern"), (whichPattern == 'p'), 'p');
|
dialog::addBoolItem(XLAT("Palace Pattern"), (whichPattern == 'p'), 'p');
|
||||||
dialog::addBoolItem(XLAT("three colors rotated"), (whichPattern == 'z'), 'z');
|
dialog::addBoolItem(XLAT("three colors rotated"), (whichPattern == 'z'), 'z');
|
||||||
}
|
}
|
||||||
|
else if(sphere) {
|
||||||
|
dialog::addBoolItem(XLAT("siblings"), (whichPattern == 'p'), 'p');
|
||||||
|
}
|
||||||
else {
|
else {
|
||||||
if(!stdhyperbolic)
|
if(!stdhyperbolic)
|
||||||
dialog::addInfo("patterns do not work correctly in this geometry!");
|
dialog::addInfo("patterns do not work correctly in this geometry!");
|
||||||
@ -817,7 +815,9 @@ namespace mapeditor {
|
|||||||
}
|
}
|
||||||
if(euclid)
|
if(euclid)
|
||||||
dialog::addBoolItem(XLAT("torus pattern"), (whichPattern == 'F'), 'F');
|
dialog::addBoolItem(XLAT("torus pattern"), (whichPattern == 'F'), 'F');
|
||||||
else if(!sphere)
|
else if(sphere)
|
||||||
|
dialog::addBoolItem(XLAT("single cells"), (whichPattern == 'F'), 'F');
|
||||||
|
else
|
||||||
dialog::addBoolItem(XLAT("field pattern"), (whichPattern == 'F'), 'F');
|
dialog::addBoolItem(XLAT("field pattern"), (whichPattern == 'F'), 'F');
|
||||||
|
|
||||||
if(whichPattern == 'f' && stdhyperbolic) symRotation = true;
|
if(whichPattern == 'f' && stdhyperbolic) symRotation = true;
|
||||||
@ -837,9 +837,12 @@ namespace mapeditor {
|
|||||||
dialog::addBoolItem(XLAT("display only hexagons"), (whichShape == '6'), '6');
|
dialog::addBoolItem(XLAT("display only hexagons"), (whichShape == '6'), '6');
|
||||||
dialog::addBoolItem(XLAT("display only heptagons"), (whichShape == '7'), '7');
|
dialog::addBoolItem(XLAT("display only heptagons"), (whichShape == '7'), '7');
|
||||||
dialog::addBoolItem(XLAT("display the triheptagonal grid"), (whichShape == '8'), '8');
|
dialog::addBoolItem(XLAT("display the triheptagonal grid"), (whichShape == '8'), '8');
|
||||||
dialog::addItem(XLAT("line patterns"), 'l');
|
if(cheater || autocheat) dialog::addItem(XLAT("line patterns"), 'l');
|
||||||
|
else dialog::addInfo("enable the cheat mode to use line patterns");
|
||||||
|
|
||||||
|
if(!needConfirmation()) dialog::addItem(XLAT("predesigned patterns"), 'r');
|
||||||
|
else dialog::addInfo("start a new game to use predesigned patterns");
|
||||||
|
|
||||||
dialog::addItem(XLAT("predesigned patterns"), 'r');
|
|
||||||
dialog::display();
|
dialog::display();
|
||||||
|
|
||||||
keyhandler = [] (int sym, int uni) {
|
keyhandler = [] (int sym, int uni) {
|
||||||
@ -862,10 +865,10 @@ namespace mapeditor {
|
|||||||
else if(uni == 'd') displaycodes = displaycodes == 1 ? 0 : 1;
|
else if(uni == 'd') displaycodes = displaycodes == 1 ? 0 : 1;
|
||||||
else if(uni == 's') displaycodes = displaycodes == 2 ? 0 : 2;
|
else if(uni == 's') displaycodes = displaycodes == 2 ? 0 : 2;
|
||||||
|
|
||||||
else if(uni == 'l')
|
else if(uni == 'l' && (cheater || autocheat))
|
||||||
pushScreen(linepatterns::showMenu);
|
pushScreen(linepatterns::showMenu);
|
||||||
|
|
||||||
else if(uni == 'r') pushScreen(showPrePattern);
|
else if(uni == 'r' && !needConfirmation()) pushScreen(showPrePattern);
|
||||||
|
|
||||||
else if(doexiton(sym, uni)) popScreen();
|
else if(doexiton(sym, uni)) popScreen();
|
||||||
};
|
};
|
||||||
@ -955,7 +958,7 @@ namespace mapeditor {
|
|||||||
displayButton(8, 8+fs*12, XLAT("f = flip %1", ONOFF(copysource.mirrored)), 'u', 0);
|
displayButton(8, 8+fs*12, XLAT("f = flip %1", ONOFF(copysource.mirrored)), 'u', 0);
|
||||||
displayButton(8, 8+fs*13, XLAT("r = regular"), 'r', 0);
|
displayButton(8, 8+fs*13, XLAT("r = regular"), 'r', 0);
|
||||||
displayButton(8, 8+fs*14, XLAT("p = paint"), 'p', 0);
|
displayButton(8, 8+fs*14, XLAT("p = paint"), 'p', 0);
|
||||||
|
|
||||||
displayFunctionKeys();
|
displayFunctionKeys();
|
||||||
|
|
||||||
keyhandler = handleKeyMap;
|
keyhandler = handleKeyMap;
|
||||||
@ -1011,6 +1014,7 @@ namespace mapeditor {
|
|||||||
case 'p': {
|
case 'p': {
|
||||||
if(a46) return subpatternEmerald(val46(c));
|
if(a46) return subpatternEmerald(val46(c));
|
||||||
if(a38) return val38(c);
|
if(a38) return val38(c);
|
||||||
|
if(sphere) return subpatternEmerald(valsphere(c).id);
|
||||||
int i = fiftyval049(c);
|
int i = fiftyval049(c);
|
||||||
i *= 4;
|
i *= 4;
|
||||||
if(polara50(c)) i|=1;
|
if(polara50(c)) i|=1;
|
||||||
@ -1020,7 +1024,6 @@ namespace mapeditor {
|
|||||||
case 'P':
|
case 'P':
|
||||||
return fiftyval(c);
|
return fiftyval(c);
|
||||||
case 'H':
|
case 'H':
|
||||||
return realpattern(c);
|
|
||||||
case 'F':
|
case 'F':
|
||||||
return realpattern(c);
|
return realpattern(c);
|
||||||
}
|
}
|
||||||
@ -1036,6 +1039,7 @@ namespace mapeditor {
|
|||||||
case 'p': {
|
case 'p': {
|
||||||
if(a46) return val46(c);
|
if(a46) return val46(c);
|
||||||
if(a38) return val38(c);
|
if(a38) return val38(c);
|
||||||
|
if(sphere) return valsphere(c).id;
|
||||||
int i = fiftyval049(c);
|
int i = fiftyval049(c);
|
||||||
i *= 4;
|
i *= 4;
|
||||||
if(polara50(c)) i|=1;
|
if(polara50(c)) i|=1;
|
||||||
@ -1045,26 +1049,20 @@ namespace mapeditor {
|
|||||||
case 'H':
|
case 'H':
|
||||||
return towerval(c);
|
return towerval(c);
|
||||||
case 'F': {
|
case 'F': {
|
||||||
if(euclid) {
|
if(euclid)
|
||||||
using namespace torusconfig;
|
// use the torus ID
|
||||||
eucoord cx, cy;
|
return fieldpattern::fieldval_uniq(c);
|
||||||
decodeMaster(c->master, cx, cy);
|
else if(nontruncated)
|
||||||
int cd = cx * dx + cy * dy;
|
// use the actual field codes
|
||||||
cd %= qty; if(cd<0) cd += qty;
|
return fieldpattern::fieldval(c).first;
|
||||||
return cd;
|
else
|
||||||
}
|
// use the small numbers from windmap
|
||||||
pair<int, bool> p = fieldpattern::fieldval(c);
|
return windmap::getId(c);
|
||||||
return 10*p.first + (p.second?6:7);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return nopattern(c);
|
return nopattern(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
int realpatternsh(cell *c) {
|
|
||||||
if(whichPattern == 'F') return nopattern(c);
|
|
||||||
else return realpattern(c);
|
|
||||||
}
|
|
||||||
|
|
||||||
int cellShapeGroup() {
|
int cellShapeGroup() {
|
||||||
if(whichPattern == 'f') return 4;
|
if(whichPattern == 'f') return 4;
|
||||||
if(whichPattern == 'p') return 5;
|
if(whichPattern == 'p') return 5;
|
||||||
@ -1084,7 +1082,7 @@ namespace mapeditor {
|
|||||||
if(drawcell == cwt.c) return vid.cs.charid;
|
if(drawcell == cwt.c) return vid.cs.charid;
|
||||||
if(drawcell->monst) return drawcell->monst;
|
if(drawcell->monst) return drawcell->monst;
|
||||||
if(drawcell->item) return drawcell->item;
|
if(drawcell->item) return drawcell->item;
|
||||||
return subpattern(drawcell) % (USERSHAPEIDS);
|
return subpattern(drawcell);
|
||||||
}
|
}
|
||||||
|
|
||||||
int subpatternShape(int i) {
|
int subpatternShape(int i) {
|
||||||
@ -1450,6 +1448,7 @@ namespace mapeditor {
|
|||||||
cmode = sm::DRAW;
|
cmode = sm::DRAW;
|
||||||
gamescreen(0);
|
gamescreen(0);
|
||||||
drawGrid();
|
drawGrid();
|
||||||
|
callhandlers(false, hooks_prestats);
|
||||||
|
|
||||||
if(!mouseout()) getcstat = '-';
|
if(!mouseout()) getcstat = '-';
|
||||||
|
|
||||||
@ -1481,7 +1480,7 @@ namespace mapeditor {
|
|||||||
|
|
||||||
default:
|
default:
|
||||||
line1 = XLAT("floor/pattern");
|
line1 = XLAT("floor/pattern");
|
||||||
line2 = "#" + its(subpattern(cwt.c));
|
line2 = "#" + its(subpattern(drawcell));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1491,7 +1490,10 @@ namespace mapeditor {
|
|||||||
|
|
||||||
// displayButton(8, 8+fs*9, XLAT("l = lands"), 'l', 0);
|
// displayButton(8, 8+fs*9, XLAT("l = lands"), 'l', 0);
|
||||||
displayfr(8, 8+fs, 2, vid.fsize, line1, 0xC0C0C0, 0);
|
displayfr(8, 8+fs, 2, vid.fsize, line1, 0xC0C0C0, 0);
|
||||||
displayfr(8, 8+fs*2, 2, vid.fsize, line2, 0xC0C0C0, 0);
|
if(sg >= 3)
|
||||||
|
displayButton(8, 8+fs*2, line2 + XLAT(" (r = complex tesselations)"), 'r', 0);
|
||||||
|
else
|
||||||
|
displayfr(8, 8+fs*2, 2, vid.fsize, line2, 0xC0C0C0, 0);
|
||||||
displayButton(8, 8+fs*3, XLAT("l = layers: %1", its(dslayer)), 'l', 0);
|
displayButton(8, 8+fs*3, XLAT("l = layers: %1", its(dslayer)), 'l', 0);
|
||||||
if(us && size(us->d[dslayer].list)) {
|
if(us && size(us->d[dslayer].list)) {
|
||||||
usershapelayer& ds(us->d[dslayer]);
|
usershapelayer& ds(us->d[dslayer]);
|
||||||
@ -1836,7 +1838,12 @@ namespace mapeditor {
|
|||||||
if(uni == 'g') coldcenter = ccenter, ccenter = mh;
|
if(uni == 'g') coldcenter = ccenter, ccenter = mh;
|
||||||
if(uni == 'c') ew = ewsearch;
|
if(uni == 'c') ew = ewsearch;
|
||||||
if(uni == 'b') autochoose = !autochoose;
|
if(uni == 'b') autochoose = !autochoose;
|
||||||
|
|
||||||
|
if(uni == 'r') {
|
||||||
|
pushScreen(showPattern);
|
||||||
|
if(drawplayer)
|
||||||
|
addMessage(XLAT("Hint: use F7 to edit floor under the player"));
|
||||||
|
}
|
||||||
|
|
||||||
if(uni == 'S') {
|
if(uni == 'S') {
|
||||||
for(int i=0; i<USERSHAPEGROUPS; i++) for(int j=0; j<USERSHAPEIDS; j++) {
|
for(int i=0; i<USERSHAPEGROUPS; i++) for(int j=0; j<USERSHAPEIDS; j++) {
|
||||||
@ -2068,6 +2075,8 @@ namespace mapeditor {
|
|||||||
return false;
|
return false;
|
||||||
#else
|
#else
|
||||||
|
|
||||||
|
id = id % USERSHAPEIDS;
|
||||||
|
|
||||||
usershape *us = usershapes[group][id];
|
usershape *us = usershapes[group][id];
|
||||||
if(us) {
|
if(us) {
|
||||||
for(int i=0; i<USERLAYERS; i++) {
|
for(int i=0; i<USERLAYERS; i++) {
|
||||||
|
Loading…
Reference in New Issue
Block a user