mirror of
https://github.com/zenorogue/hyperrogue.git
synced 2024-11-27 22:39:53 +00:00
faster drawing of convex shapes online
This commit is contained in:
parent
ef83f1ef23
commit
d40680358c
69
polygons.cpp
69
polygons.cpp
@ -31,6 +31,11 @@ static const int POLY_HASSHADOW = 1024;
|
|||||||
// Goldberg shapes
|
// Goldberg shapes
|
||||||
static const int POLY_GP = 2048;
|
static const int POLY_GP = 2048;
|
||||||
|
|
||||||
|
// Convex shape (vertex)
|
||||||
|
static const int POLY_VCONVEX = 4096;
|
||||||
|
// Convex shape (central)
|
||||||
|
static const int POLY_CCONVEX = 8192;
|
||||||
|
|
||||||
vector<hyperpoint> hpc;
|
vector<hyperpoint> hpc;
|
||||||
|
|
||||||
int prehpc;
|
int prehpc;
|
||||||
@ -272,6 +277,14 @@ void setmatrix(int useV, const transmatrix& V) {
|
|||||||
glhr::id_modelview();
|
glhr::id_modelview();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifndef MINIMIZE_GL_CALLS
|
||||||
|
#ifdef EMSCRIPTEN
|
||||||
|
#define MINIMIZE_GL_CALLS 1
|
||||||
|
#else
|
||||||
|
#define MINIMIZE_GL_CALLS 0
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
void gldraw(int useV, const transmatrix& V, const vector<glvertex>& v, int ps, int pq, int col, int outline, int flags, textureinfo *tinf) {
|
void gldraw(int useV, const transmatrix& V, const vector<glvertex>& v, int ps, int pq, int col, int outline, int flags, textureinfo *tinf) {
|
||||||
|
|
||||||
if(tinf) {
|
if(tinf) {
|
||||||
@ -303,12 +316,17 @@ void gldraw(int useV, const transmatrix& V, const vector<glvertex>& v, int ps, i
|
|||||||
setmatrix(useV, V);
|
setmatrix(useV, V);
|
||||||
|
|
||||||
if(draw) {
|
if(draw) {
|
||||||
#ifdef DIRTY
|
if((flags & POLY_VCONVEX) && MINIMIZE_GL_CALLS) {
|
||||||
#warning dirty
|
|
||||||
glhr::vertices(v);
|
glhr::vertices(v);
|
||||||
glhr::color2(col);
|
glhr::color2(col);
|
||||||
glDrawArrays(tinf ? GL_TRIANGLES : GL_TRIANGLE_FAN, ps, pq);
|
glDrawArrays(tinf ? GL_TRIANGLES : GL_TRIANGLE_FAN, ps, pq);
|
||||||
#else
|
}
|
||||||
|
else if((flags & POLY_CCONVEX) && MINIMIZE_GL_CALLS) {
|
||||||
|
glhr::vertices(v);
|
||||||
|
glhr::color2(col);
|
||||||
|
glDrawArrays(tinf ? GL_TRIANGLES : GL_TRIANGLE_FAN, ps-1, pq+1);
|
||||||
|
}
|
||||||
|
else {
|
||||||
glEnable(GL_STENCIL_TEST);
|
glEnable(GL_STENCIL_TEST);
|
||||||
|
|
||||||
glColorMask( GL_FALSE,GL_FALSE,GL_FALSE,GL_FALSE );
|
glColorMask( GL_FALSE,GL_FALSE,GL_FALSE,GL_FALSE );
|
||||||
@ -346,7 +364,7 @@ void gldraw(int useV, const transmatrix& V, const vector<glvertex>& v, int ps, i
|
|||||||
}
|
}
|
||||||
|
|
||||||
glDisable(GL_STENCIL_TEST);
|
glDisable(GL_STENCIL_TEST);
|
||||||
#endif
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(outline) {
|
if(outline) {
|
||||||
@ -603,7 +621,7 @@ void drawpolyline(polytodraw& p) {
|
|||||||
#if CAP_GL
|
#if CAP_GL
|
||||||
if(vid.usingGL && pmodel == mdDisk && !spherespecial) {
|
if(vid.usingGL && pmodel == mdDisk && !spherespecial) {
|
||||||
glLineWidth(linewidthat(tC0(pp.V), pp.minwidth));
|
glLineWidth(linewidthat(tC0(pp.V), pp.minwidth));
|
||||||
gldraw(1, pp.V, *pp.tab, pp.offset, pp.cnt, p.col, pp.outline, 0, pp.tinf);
|
gldraw(1, pp.V, *pp.tab, pp.offset, pp.cnt, p.col, pp.outline, pp.flags &~ POLY_INVERSE, pp.tinf);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
@ -1205,6 +1223,8 @@ hyperpoint turtlevertex(int u, double x, double y, double z) {
|
|||||||
return hpxd(scale, x, y, z);
|
return hpxd(scale, x, y, z);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
vector<hpcshape*> allshapes;
|
||||||
|
|
||||||
void finishshape() {
|
void finishshape() {
|
||||||
last->e = size(hpc);
|
last->e = size(hpc);
|
||||||
double area = 0;
|
double area = 0;
|
||||||
@ -1212,6 +1232,28 @@ void finishshape() {
|
|||||||
area += hpc[i][0] * hpc[i+1][1] - hpc[i+1][0] * hpc[i][1];
|
area += hpc[i][0] * hpc[i+1][1] - hpc[i+1][0] * hpc[i][1];
|
||||||
if(abs(area) < 1e-9) last->flags |= POLY_ISSIDE;
|
if(abs(area) < 1e-9) last->flags |= POLY_ISSIDE;
|
||||||
if(area >= 0) last->flags |= POLY_INVERSE;
|
if(area >= 0) last->flags |= POLY_INVERSE;
|
||||||
|
|
||||||
|
bool allplus = true, allminus = true;
|
||||||
|
for(int i=last->s; i<last->e-1; i++) {
|
||||||
|
ld v = hpc[i][0] * hpc[i+1][1] - hpc[i+1][0] * hpc[i][1];
|
||||||
|
if(v > 1e-6) allplus = false;
|
||||||
|
if(v < -1e-6) allminus = false;
|
||||||
|
}
|
||||||
|
if(allminus || allplus) last->flags |= POLY_CCONVEX;
|
||||||
|
|
||||||
|
allplus = true, allminus = true;
|
||||||
|
ld cx = hpc[last->s][0], cy = hpc[last->s][1];
|
||||||
|
|
||||||
|
for(int i=last->s; i<last->e-1; i++) {
|
||||||
|
ld v = (hpc[i][0]-cx) * (hpc[i+1][1]-cy) - (hpc[i+1][0]-cx) * (hpc[i][1]-cy);
|
||||||
|
if(v > 1e-6) allplus = false;
|
||||||
|
if(v < -1e-6) allminus = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(allminus || allplus) last->flags |= POLY_VCONVEX;
|
||||||
|
|
||||||
|
allshapes.push_back(last);
|
||||||
|
|
||||||
/* if(isnan(area)) ;
|
/* if(isnan(area)) ;
|
||||||
else if(intval(hpc[last->s], hpc[last->e-1]) > 1e-6)
|
else if(intval(hpc[last->s], hpc[last->e-1]) > 1e-6)
|
||||||
printf("bad end\n"); */
|
printf("bad end\n"); */
|
||||||
@ -1219,6 +1261,7 @@ void finishshape() {
|
|||||||
|
|
||||||
void bshape(hpcshape& sh, int p) {
|
void bshape(hpcshape& sh, int p) {
|
||||||
if(last) finishshape();
|
if(last) finishshape();
|
||||||
|
hpc.push_back(hpxy(0,0));
|
||||||
last = &sh;
|
last = &sh;
|
||||||
last->s = size(hpc), last->prio = p;
|
last->s = size(hpc), last->prio = p;
|
||||||
last->flags = 0;
|
last->flags = 0;
|
||||||
@ -1360,6 +1403,7 @@ ld dlow_table[SIDEPARS], dhi_table[SIDEPARS];
|
|||||||
void buildpolys() {
|
void buildpolys() {
|
||||||
|
|
||||||
symmetriesAt.clear();
|
symmetriesAt.clear();
|
||||||
|
allshapes.clear();
|
||||||
geom3::compute();
|
geom3::compute();
|
||||||
gp::clear_plainshapes();
|
gp::clear_plainshapes();
|
||||||
DEBB(DF_INIT, (debugfile,"buildpolys\n"));
|
DEBB(DF_INIT, (debugfile,"buildpolys\n"));
|
||||||
@ -2186,8 +2230,21 @@ void buildpolys() {
|
|||||||
|
|
||||||
static int qhpc0;
|
static int qhpc0;
|
||||||
int qhpc = size(hpc);
|
int qhpc = size(hpc);
|
||||||
if(qhpc != qhpc0 && debug_geometry)
|
if(qhpc != qhpc0 && debug_geometry) {
|
||||||
printf("qhpc = %d (%d+%d)\n", qhpc0 = qhpc, prehpc, qhpc-prehpc);
|
printf("qhpc = %d (%d+%d)\n", qhpc0 = qhpc, prehpc, qhpc-prehpc);
|
||||||
|
printf("shapes = %d\n", size(allshapes));
|
||||||
|
int inve=0, issi=0, vcon=0, ccon=0;
|
||||||
|
for(auto sh: allshapes) {
|
||||||
|
if(sh->flags & POLY_INVERSE) inve++;
|
||||||
|
if(sh->flags & POLY_ISSIDE) issi++;
|
||||||
|
if(sh->flags & POLY_VCONVEX) vcon++;
|
||||||
|
if(sh->flags & POLY_CCONVEX) ccon++;
|
||||||
|
}
|
||||||
|
printf("triangle flags = %x\n", shTriangle.flags);
|
||||||
|
printf("plain floor flags = %x\n", shFloor.b[0].flags);
|
||||||
|
printf("ball flags = %x\n", shDisk.flags);
|
||||||
|
printf("inverse = %d isside = %d vcon = %d ccon = %d\n", inve, issi, vcon, ccon);
|
||||||
|
}
|
||||||
|
|
||||||
initPolyForGL();
|
initPolyForGL();
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user