mirror of
https://github.com/zenorogue/hyperrogue.git
synced 2025-05-10 11:14:07 +00:00
tetrahedral-octahedral honeycomb
This commit is contained in:
parent
b31b987aa7
commit
15c3089fce
@ -755,7 +755,7 @@ enum eGeometry {
|
|||||||
gHalfBring,
|
gHalfBring,
|
||||||
gAperiodicHat,
|
gAperiodicHat,
|
||||||
gSierpinski3, gSierpinski4, gSixFlake, gMengerSponge, gSierpinskiTet,
|
gSierpinski3, gSierpinski4, gSixFlake, gMengerSponge, gSierpinskiTet,
|
||||||
gAperiodicSpectre,
|
gAperiodicSpectre, gOctTet3,
|
||||||
gGUARD};
|
gGUARD};
|
||||||
|
|
||||||
enum eGeometryClass { gcHyperbolic, gcEuclid, gcSphere, gcSol, gcNIH, gcSolN, gcNil, gcProduct, gcSL2 };
|
enum eGeometryClass { gcHyperbolic, gcEuclid, gcSphere, gcSol, gcNIH, gcSolN, gcNil, gcProduct, gcSL2 };
|
||||||
@ -972,6 +972,7 @@ EX vector<geometryinfo> ginf = {
|
|||||||
{"{4,3,4}","none", "Menger sponge", "S8", 6, 4, qFRACTAL, giEuclid3, {{10, 10}}, eVariation::pure},
|
{"{4,3,4}","none", "Menger sponge", "S8", 6, 4, qFRACTAL, giEuclid3, {{10, 10}}, eVariation::pure},
|
||||||
{"rh{4,3,4}","none", "Sierpiński tetrahedron", "S4b", 12, 3, qFRACTAL, giEuclid3, {{10, 10}}, eVariation::pure},
|
{"rh{4,3,4}","none", "Sierpiński tetrahedron", "S4b", 12, 3, qFRACTAL, giEuclid3, {{10, 10}}, eVariation::pure},
|
||||||
{"spectre","none", "aperiodic spectre", "spectre", 14, 3, qAPERIODIC | qHAT, giEuclid2, {{7, 7}}, eVariation::pure},
|
{"spectre","none", "aperiodic spectre", "spectre", 14, 3, qAPERIODIC | qHAT, giEuclid2, {{7, 7}}, eVariation::pure},
|
||||||
|
{"ot{4,3,4}","none", "octahedral-tetrahedral honeycomb", "ot434", 8, 3, qOPTQ, giEuclid3, {{7, 5}}, eVariation::pure},
|
||||||
};
|
};
|
||||||
// bits: 9, 10, 15, 16, (reserved for later) 17, 18
|
// bits: 9, 10, 15, 16, (reserved for later) 17, 18
|
||||||
|
|
||||||
|
@ -3652,7 +3652,7 @@ EX namespace windmap {
|
|||||||
// cw.spin = 0;
|
// cw.spin = 0;
|
||||||
neighbors.emplace_back();
|
neighbors.emplace_back();
|
||||||
auto &v = neighbors.back();
|
auto &v = neighbors.back();
|
||||||
if(NONSTDVAR && !sphere && !arcm::in() && !mhybrid && !INVERSE && WDIM == 2)
|
if(NONSTDVAR && !sphere && !arcm::in() && !mhybrid && !INVERSE && WDIM == 2 && geometry != gOctTet3)
|
||||||
for(int l=0; l<S7; l++) {
|
for(int l=0; l<S7; l++) {
|
||||||
v.push_back(getId(cw + cth + l + wstep + cth));
|
v.push_back(getId(cw + cth + l + wstep + cth));
|
||||||
}
|
}
|
||||||
|
@ -1627,6 +1627,7 @@ EX void initConfig() {
|
|||||||
param_f(sightranges[gECell120], "sight-120cell-elliptic", M_PI);
|
param_f(sightranges[gECell120], "sight-120cell-elliptic", M_PI);
|
||||||
param_f(sightranges[gRhombic3], "sight-rhombic", 10.5 * emul);
|
param_f(sightranges[gRhombic3], "sight-rhombic", 10.5 * emul);
|
||||||
param_f(sightranges[gBitrunc3], "sight-bitrunc", 12 * emul);
|
param_f(sightranges[gBitrunc3], "sight-bitrunc", 12 * emul);
|
||||||
|
param_f(sightranges[gOctTet3], "sight-octtet", 12 * emul);
|
||||||
param_f(sightranges[gSpace534], "sight-534", 4 + bonus);
|
param_f(sightranges[gSpace534], "sight-534", 4 + bonus);
|
||||||
param_f(sightranges[gSpace435], "sight-435", 3.8 + bonus);
|
param_f(sightranges[gSpace435], "sight-435", 3.8 + bonus);
|
||||||
|
|
||||||
|
79
euclid.cpp
79
euclid.cpp
@ -34,6 +34,18 @@ EX namespace euc {
|
|||||||
|
|
||||||
static constexpr intmatrix main_axes = make_array<coord>(coord(1,0,0), coord(0,1,0), coord(0,0,1));
|
static constexpr intmatrix main_axes = make_array<coord>(coord(1,0,0), coord(0,1,0), coord(0,0,1));
|
||||||
|
|
||||||
|
EX int octtet_shvid(coord at) {
|
||||||
|
if(at[0] % 2 == 0) return 0;
|
||||||
|
return ((at[0] + at[1] + at[2]) & 2) ? 2 : 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
EX bool octtet_valid(coord at) {
|
||||||
|
bool b = (at[0] & 1) == (at[1] & 1) && (at[0] & 1) == (at[2] & 1);
|
||||||
|
if(!b) return false;
|
||||||
|
if((at[0] & 1) == 0) return ((at[0] + at[1] + at[2]) & 2) == 0;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
EX vector<coord> get_shifttable() {
|
EX vector<coord> get_shifttable() {
|
||||||
static const coord D0 = main_axes[0];
|
static const coord D0 = main_axes[0];
|
||||||
static const coord D1 = main_axes[1];
|
static const coord D1 = main_axes[1];
|
||||||
@ -70,6 +82,13 @@ EX namespace euc {
|
|||||||
shifttable = { D0, D1, -D0, -D1 };
|
shifttable = { D0, D1, -D0, -D1 };
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case gOctTet3:
|
||||||
|
shifttable = {
|
||||||
|
D0+D1+D2, D0-D1-D2, -D0+D1-D2, -D0-D1+D2,
|
||||||
|
-D0-D1-D2,-D0+D1+D2, +D0-D1+D2, +D0+D1-D2
|
||||||
|
};
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
throw hr_exception("euc::get_shifttable() called in geometry that is not euclid3");
|
throw hr_exception("euc::get_shifttable() called in geometry that is not euclid3");
|
||||||
}
|
}
|
||||||
@ -184,9 +203,11 @@ EX namespace euc {
|
|||||||
if(spacemap.count(at))
|
if(spacemap.count(at))
|
||||||
return spacemap[at];
|
return spacemap[at];
|
||||||
else {
|
else {
|
||||||
auto h = init_heptagon(S7);
|
int type = S7;
|
||||||
|
if(geometry == gOctTet3 && octtet_shvid(at)) type = 4;
|
||||||
|
auto h = init_heptagon(type);
|
||||||
if(!IRREGULAR)
|
if(!IRREGULAR)
|
||||||
h->c7 = newCell(S7, h);
|
h->c7 = newCell(type, h);
|
||||||
#if CAP_IRR
|
#if CAP_IRR
|
||||||
else {
|
else {
|
||||||
coord m0 = shifttable[0];
|
coord m0 = shifttable[0];
|
||||||
@ -216,8 +237,16 @@ EX namespace euc {
|
|||||||
int d1 = (d+S7/2)%S7;
|
int d1 = (d+S7/2)%S7;
|
||||||
bool mirr = false;
|
bool mirr = false;
|
||||||
transmatrix I;
|
transmatrix I;
|
||||||
auto v = ispacemap[parent] + shifttable[d];
|
auto dx = d;
|
||||||
auto st = shifttable[d1];
|
auto at = ispacemap[parent];
|
||||||
|
auto d2 = d1;
|
||||||
|
if(geometry == gOctTet3) {
|
||||||
|
auto id = octtet_shvid(at);
|
||||||
|
if(id == 2) { dx += 4; d1 &= 3; }
|
||||||
|
if(id == 0) { d1 &= 3; }
|
||||||
|
}
|
||||||
|
auto v = at + shifttable[dx];
|
||||||
|
auto st = shifttable[d2];
|
||||||
eu.canonicalize(v, st, I, mirr);
|
eu.canonicalize(v, st, I, mirr);
|
||||||
if(eu.twisted)
|
if(eu.twisted)
|
||||||
for(int i=0; i<S7; i++) if(shifttable[i] == st) d1 = i;
|
for(int i=0; i<S7; i++) if(shifttable[i] == st) d1 = i;
|
||||||
@ -228,6 +257,7 @@ EX namespace euc {
|
|||||||
}
|
}
|
||||||
|
|
||||||
transmatrix adj(heptagon *h, int i) override {
|
transmatrix adj(heptagon *h, int i) override {
|
||||||
|
if(geometry == gOctTet3 && octtet_shvid(ispacemap[h]) == 2) i += 4;
|
||||||
if(!eu.twisted) return tmatrix[i];
|
if(!eu.twisted) return tmatrix[i];
|
||||||
transmatrix res = tmatrix[i];
|
transmatrix res = tmatrix[i];
|
||||||
coord id = ispacemap[h];
|
coord id = ispacemap[h];
|
||||||
@ -260,7 +290,7 @@ EX namespace euc {
|
|||||||
bool draw = drawcell_subs(c, V * spin(master_to_c7_angle()));
|
bool draw = drawcell_subs(c, V * spin(master_to_c7_angle()));
|
||||||
if(in_wallopt() && isWall3(c) && isize(dq::drawqueue) > 1000 && !hybrid::pmap) continue;
|
if(in_wallopt() && isWall3(c) && isize(dq::drawqueue) > 1000 && !hybrid::pmap) continue;
|
||||||
|
|
||||||
if(draw) for(int i=0; i<S7; i++) {
|
if(draw) for(int i=0; i<h->type; i++) {
|
||||||
auto V1 = V * adj(h, i);
|
auto V1 = V * adj(h, i);
|
||||||
if(geom3::apply_break_cylinder && cgi.emb->break_cylinder(V, V1)) continue;
|
if(geom3::apply_break_cylinder && cgi.emb->break_cylinder(V, V1)) continue;
|
||||||
dq::enqueue_by_matrix(h->move(i), optimized_shift(V1));
|
dq::enqueue_by_matrix(h->move(i), optimized_shift(V1));
|
||||||
@ -301,7 +331,8 @@ EX namespace euc {
|
|||||||
}
|
}
|
||||||
|
|
||||||
subcellshape& get_cellshape(cell* c) override {
|
subcellshape& get_cellshape(cell* c) override {
|
||||||
return *cgi.heptshape;
|
if(geometry != gOctTet3) return *cgi.heptshape;
|
||||||
|
return cgi.subshapes[shvid(c)];
|
||||||
}
|
}
|
||||||
|
|
||||||
int pattern_value(cell *c) override {
|
int pattern_value(cell *c) override {
|
||||||
@ -317,6 +348,20 @@ EX namespace euc {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int shvid(cell *c) override {
|
||||||
|
if(geometry == gOctTet3)
|
||||||
|
return octtet_shvid(ispacemap[c->master]);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
transmatrix ray_iadj(cell *c, int i) override {
|
||||||
|
if(geometry != gOctTet3) return hrmap_standard::ray_iadj(c, i);
|
||||||
|
auto& v = get_cellshape(c).faces_local[i];
|
||||||
|
hyperpoint h = project_on_triangle(v[0], v[1], v[2]);
|
||||||
|
transmatrix T = rspintox(h);
|
||||||
|
return T * xpush(-2*hdist0(h)) * spintox(h);
|
||||||
|
}
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
hrmap_euclidean* cubemap() {
|
hrmap_euclidean* cubemap() {
|
||||||
@ -667,7 +712,7 @@ EX namespace euc {
|
|||||||
}
|
}
|
||||||
|
|
||||||
EX void build_torus3() {
|
EX void build_torus3() {
|
||||||
for(eGeometry g: { gEuclid, gEuclidSquare, gCubeTiling, gRhombic3, gBitrunc3})
|
for(eGeometry g: { gEuclid, gEuclidSquare, gCubeTiling, gRhombic3, gBitrunc3, gOctTet3})
|
||||||
build_torus3(g);
|
build_torus3(g);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1021,7 +1066,7 @@ EX namespace euc {
|
|||||||
dialog::addBreak(50);
|
dialog::addBreak(50);
|
||||||
|
|
||||||
char xch = 'p';
|
char xch = 'p';
|
||||||
for(eGeometry g: {gCubeTiling, gRhombic3, gBitrunc3}) {
|
for(eGeometry g: {gCubeTiling, gRhombic3, gBitrunc3, gOctTet3}) {
|
||||||
if(dim == 2) g = geometry;
|
if(dim == 2) g = geometry;
|
||||||
dialog::addItem(XLAT(ginf[g].menu_displayed_name), xch++);
|
dialog::addItem(XLAT(ginf[g].menu_displayed_name), xch++);
|
||||||
dialog::add_action([g] {
|
dialog::add_action([g] {
|
||||||
@ -1370,6 +1415,24 @@ EX void generate() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(S7 == 8) {
|
||||||
|
cgi.subshapes.resize(3);
|
||||||
|
for(int id=0; id<3; id++) {
|
||||||
|
auto& s = cgi.subshapes[id];
|
||||||
|
auto& cs = s.faces;
|
||||||
|
cs.clear(); cs.resize(id == 0 ? 8 : 4);
|
||||||
|
for(int w=0; w<isize(cs); w++) for(int i=0; i<3; i++) {
|
||||||
|
auto t = v[w + (id == 2 ? 4 : 0)];
|
||||||
|
if(id == 0)
|
||||||
|
cs[w].push_back(hpxy3(i==0?2*t[0]:0, i==1?2*t[1]:0, i==2?2*t[2]:0));
|
||||||
|
else
|
||||||
|
cs[w].push_back(hpxy3((i==0?-1:1)*t[0], (i==1?-1:1)*t[1], (i==2?-1:1)*t[2]));
|
||||||
|
}
|
||||||
|
s.compute_sub();
|
||||||
|
}
|
||||||
|
cs = cgi.subshapes[0].faces;
|
||||||
|
}
|
||||||
|
|
||||||
hsh.compute_hept();
|
hsh.compute_hept();
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
@ -4207,6 +4207,7 @@ EX int get_darkval(cell *c, int d) {
|
|||||||
const int darkval_kite[12] = {0, 2, 0, 2, 4, 4, 6, 6, 6, 6, 6, 6};
|
const int darkval_kite[12] = {0, 2, 0, 2, 4, 4, 6, 6, 6, 6, 6, 6};
|
||||||
const int darkval_nil[8] = {6,6,0,3,6,6,0,3};
|
const int darkval_nil[8] = {6,6,0,3,6,6,0,3};
|
||||||
const int darkval_nih[11] = {0,2,0,2,4,6,6,6,6,6,6};
|
const int darkval_nih[11] = {0,2,0,2,4,6,6,6,6,6,6};
|
||||||
|
const int darkval_ot[8] = {0,1,2,3,6,5,4,3};
|
||||||
#if MAXMDIM >= 4
|
#if MAXMDIM >= 4
|
||||||
if(among(variation, eVariation::dual_subcubes, eVariation::bch, eVariation::bch_oct, eVariation::coxeter)) {
|
if(among(variation, eVariation::dual_subcubes, eVariation::bch, eVariation::bch_oct, eVariation::coxeter)) {
|
||||||
int v = reg3::get_face_vertex_count(c, d);
|
int v = reg3::get_face_vertex_count(c, d);
|
||||||
@ -4219,6 +4220,7 @@ EX int get_darkval(cell *c, int d) {
|
|||||||
if(euclid && S7 == 14) return darkval_e14[d];
|
if(euclid && S7 == 14) return darkval_e14[d];
|
||||||
if(geometry == gHoroHex) return darkval_hh[d];
|
if(geometry == gHoroHex) return darkval_hh[d];
|
||||||
if(geometry == gHoroRec) return darkval_hrec[d];
|
if(geometry == gHoroRec) return darkval_hrec[d];
|
||||||
|
if(geometry == gOctTet3) return darkval_ot[d + (shvid(c) == 2 ? 4 : 0)];
|
||||||
if(kite::in()) return darkval_kite[d];
|
if(kite::in()) return darkval_kite[d];
|
||||||
if(asonov::in()) return darkval_arnold[d];
|
if(asonov::in()) return darkval_arnold[d];
|
||||||
if(sol) return darkval_sol[d];
|
if(sol) return darkval_sol[d];
|
||||||
@ -4487,7 +4489,7 @@ EX subcellshape& generate_subcellshape_if_needed(cell *c, int id) {
|
|||||||
int hrmap::wall_offset(cell *c) {
|
int hrmap::wall_offset(cell *c) {
|
||||||
int id = currentmap->full_shvid(c);
|
int id = currentmap->full_shvid(c);
|
||||||
|
|
||||||
if(WDIM == 3 && !mhybrid && !reg3::in()) return 0;
|
if(WDIM == 3 && !mhybrid && !reg3::in() && geometry != gOctTet3) return 0;
|
||||||
|
|
||||||
if(isize(cgi.walloffsets) <= id) cgi.walloffsets.resize(id+1, {-1, nullptr});
|
if(isize(cgi.walloffsets) <= id) cgi.walloffsets.resize(id+1, {-1, nullptr});
|
||||||
auto &wop = cgi.walloffsets[id];
|
auto &wop = cgi.walloffsets[id];
|
||||||
|
@ -1696,6 +1696,11 @@ EX namespace hybrid {
|
|||||||
});
|
});
|
||||||
|
|
||||||
EX vector<pair<int, cell*>> gen_sample_list() {
|
EX vector<pair<int, cell*>> gen_sample_list() {
|
||||||
|
if(geometry == gOctTet3) {
|
||||||
|
auto c = centerover;
|
||||||
|
if(currentmap->shvid(c)) c = c->cmove(0);
|
||||||
|
return {make_pair(0, c), make_pair(8, c->cmove(4)), make_pair(12, c->cmove(0)), make_pair(16, nullptr)};
|
||||||
|
}
|
||||||
if(!mhybrid && WDIM != 2 && PURE)
|
if(!mhybrid && WDIM != 2 && PURE)
|
||||||
return {make_pair(0, centerover), make_pair(centerover->type, nullptr)};
|
return {make_pair(0, centerover), make_pair(centerover->type, nullptr)};
|
||||||
vector<pair<int, cell*>> result;
|
vector<pair<int, cell*>> result;
|
||||||
|
@ -1067,7 +1067,7 @@ void geometry_information::create_wall3d() {
|
|||||||
walloffsets.clear();
|
walloffsets.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
else if(reg3::in() && !PURE) {
|
else if((reg3::in() && !PURE) || geometry == gOctTet3) {
|
||||||
int tot = 0;
|
int tot = 0;
|
||||||
for(auto& ss: cgi.subshapes) tot += isize(ss.faces);
|
for(auto& ss: cgi.subshapes) tot += isize(ss.faces);
|
||||||
reserve_wall3d(tot);
|
reserve_wall3d(tot);
|
||||||
|
@ -376,7 +376,7 @@ void raygen::compute_which_and_dist(int flat1, int flat2) {
|
|||||||
else if(in_h2xe() && hybrid::underlying == gBinaryTiling)
|
else if(in_h2xe() && hybrid::underlying == gBinaryTiling)
|
||||||
fmain += "for(int i=0; i<=4; i++) if(i == 0 || i == 4) {";
|
fmain += "for(int i=0; i<=4; i++) if(i == 0 || i == 4) {";
|
||||||
else
|
else
|
||||||
fmain += "for(int i="+its(flat1)+"; i<"+(gproduct ? "sides-2" : ((WDIM == 2 || is_subcube_based(variation) || intra::in) && !bt::in()) ? "sides" : its(flat2))+"; i++) {\n";
|
fmain += "for(int i="+its(flat1)+"; i<"+(gproduct ? "sides-2" : ((WDIM == 2 || is_subcube_based(variation) || intra::in || geometry == gOctTet3) && !bt::in()) ? "sides" : its(flat2))+"; i++) {\n";
|
||||||
|
|
||||||
fmain += " mediump mat4 m = " + getM("walloffset+i") + ";\n";
|
fmain += " mediump mat4 m = " + getM("walloffset+i") + ";\n";
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user