diff --git a/source/src/protos.h b/source/src/protos.h index 18611c24..1c02c271 100644 --- a/source/src/protos.h +++ b/source/src/protos.h @@ -299,7 +299,7 @@ extern void setuptmu(int n, const char *rgbfunc = NULL, const char *alphafunc = extern void mipstats(int a, int b, int c); extern void render_flat(int tex, int x, int y, int size, int h, sqr *l1, sqr *l2, sqr *l3, sqr *l4, bool isceil); extern void render_flatdelta(int wtex, int x, int y, int size, float h1, float h2, float h3, float h4, sqr *l1, sqr *l2, sqr *l3, sqr *l4, bool isceil); -extern void render_square(int wtex, float floor1, float floor2, float ceil1, float ceil2, int x1, int y1, int x2, int y2, int size, sqr *l1, sqr *l2, bool topleft); +extern void render_square(int wtex, float floor1, float floor2, float ceil1, float ceil2, int x1, int y1, int x2, int y2, int size, sqr *l1, sqr *l2, bool topleft, int dir); extern void render_tris(int x, int y, int size, bool topleft, sqr *h1, sqr *h2, sqr *s, sqr *t, sqr *u, sqr *v); extern void resetcubes(); extern void setupstrips(); diff --git a/source/src/rendercubes.cpp b/source/src/rendercubes.cpp index 7845e473..b0efe9c0 100644 --- a/source/src/rendercubes.cpp +++ b/source/src/rendercubes.cpp @@ -113,11 +113,19 @@ void addstrip(int type, int tex, int start, int n) v.r = ls->r; v.g = ls->g; v.b = ls->b; v.a = 255; \ } +enum +{ + STRIP_FLOOR = 1, + STRIP_DELTA, + STRIP_WALL +}; + int nquads; const float TEXTURESCALE = 32.0f; -bool floorstrip = false, deltastrip = false; -int oh, oy, ox, striptex; // the o* vars are used by the stripification -int ol3r, ol3g, ol3b, ol4r, ol4g, ol4b; +int striptype = 0, striptex, oh, oy, ox, odir; // the o* vars are used by the stripification +int ol1r, ol1g, ol1b, ol2r, ol2g, ol2b; +float ofloor, oceil; +bool ohf; int firstindex; bool showm = false; @@ -129,14 +137,14 @@ COMMAND(showmip, ARG_NONE); VAR(mergestrips, 0, 1, 1); #define stripend(verts) \ - if(floorstrip || deltastrip) { \ + if(striptype) { \ int type = GL_TRIANGLE_STRIP, len = verts.length()-firstindex; \ if(mergestrips) switch(len) { \ case 3: type = GL_TRIANGLES; break; \ case 4: type = GL_QUADS; swap(verts.last(), verts[verts.length()-2]); break; \ } \ addstrip(type, striptex, firstindex, len); \ - floorstrip = deltastrip = false; \ + striptype = 0; \ } void finishstrips() { stripend(verts); } @@ -156,7 +164,7 @@ void render_flat(int wtex, int x, int y, int size, int h, sqr *l1, sqr *l4, sqr float xo = xf*x; float yo = yf*y; - bool first = !floorstrip || x!=ox+size || striptex!=wtex || h!=oh || y!=oy; + bool first = striptype!=STRIP_FLOOR || x!=ox+size || striptex!=wtex || h!=oh || y!=oy; if(first) // start strip here { @@ -165,7 +173,7 @@ void render_flat(int wtex, int x, int y, int size, int h, sqr *l1, sqr *l4, sqr striptex = wtex; oh = h; oy = y; - floorstrip = true; + striptype = STRIP_FLOOR; if(isceil) { vert(x, y, h, l1, xo, yo); @@ -176,33 +184,33 @@ void render_flat(int wtex, int x, int y, int size, int h, sqr *l1, sqr *l4, sqr vert(x, y+size, h, l2, xo, yo+ys); vert(x, y, h, l1, xo, yo); } - ol3r = l1->r; - ol3g = l1->g; - ol3b = l1->b; - ol4r = l2->r; - ol4g = l2->g; - ol4b = l2->b; + ol1r = l1->r; + ol1g = l1->g; + ol1b = l1->b; + ol2r = l2->r; + ol2g = l2->g; + ol2b = l2->b; } else // continue strip { int lighterr = lighterror*2; - if((abs(ol3r-l3->r)r)g)g)b)b)r)r)g)g)b)b)r; - ol3g = l1->g; - ol3b = l1->b; - ol4r = l2->r; - ol4g = l2->g; - ol4b = l2->b; } if(isceil) @@ -313,34 +315,77 @@ void render_tris(int x, int y, int size, bool topleft, } } -void render_square(int wtex, float floor1, float floor2, float ceil1, float ceil2, int x1, int y1, int x2, int y2, int size, sqr *l1, sqr *l2, bool flip) // wall quads +void render_square(int wtex, float floor1, float floor2, float ceil1, float ceil2, int x1, int y1, int x2, int y2, int size, sqr *l1, sqr *l2, bool flip, int dir) // wall quads { - stripend(verts); if(showm) { l1 = &sbright; l2 = &sdark; } Texture *t = lookupworldtexture(wtex); float xf = TEXTURESCALE/t->xs; - float yf = TEXTURESCALE/t->ys; + float yf = -TEXTURESCALE/t->ys; float xs = size*xf; float xo = xf*(x1==x2 ? min(y1,y2) : min(x1,x2)); + bool first = striptype!=STRIP_WALL || striptex!=wtex || ox!=x1 || oy!=y1 || ofloor!=floor1 || oceil!=ceil1 || odir!=dir, + hf = floor1!=floor2 || ceil1!=ceil2; + + if(first) + { + stripend(verts); + firstindex = verts.length(); + striptex = wtex; + striptype = STRIP_WALL; + + if(!flip) + { + vert(x1, y1, ceil1, l1, xo, yf*ceil1); + vert(x1, y1, floor1, l1, xo, yf*floor1); + } + else + { + vert(x1, y1, floor1, l1, xo, yf*floor1); + vert(x1, y1, ceil1, l1, xo, yf*ceil1); + } + ol1r = l1->r; + ol1g = l1->g; + ol1b = l1->b; + } + else // continue strip + { + int lighterr = lighterror*2; + if((!hf && !ohf + && abs(ol1r-l2->r)g)b)type==SEMISOLID) @@ -16,7 +16,7 @@ void render_wall(sqr *o, sqr *s, int x1, int y1, int x2, int y2, int mip, sqr *d float f2 = s->ceil; if(s->type==CHF) { f1 += d1->vdelta/4.0f; f2 += d2->vdelta/4.0f; } //if(f1-c1<=0 && f2-c2<=0) return; - render_square(o->wtex, c1, c2, f1, f2, x1<wtex, c1, c2, f1, f2, x1<vdelta/4.0f; } if(f1>=c1 && f2>=c2) goto skip; - render_square(o->wtex, f1, f2, c1, c2, x1<wtex, f1, f2, c1, c2, x1<vdelta/4.0f; } if(c1<=f1 && c2<=f2) return; - render_square(o->utex, f1, f2, c1, c2, x1<utex, f1, f2, c1, c2, x1<occluded) continue; \ - if(s->defer && !s->occluded && mip && xx>=lx && xx=ly && yydefer && mip && xx>=lx && xx=ly && yyceil-w->floor < v->ceil-v->floor; if(z->ceil-z->floor < t->ceil-t->floor) { - if(wv) { render_wall(h1 = s, h2 = v, xx+1, yy, xx, yy+1, mip, t, v, false); topleft = false; } - else { render_wall(h1 = s, h2 = w, xx, yy, xx+1, yy+1, mip, s, u, false); } + if(wv) { render_wall(h1 = s, h2 = v, xx+1, yy, xx, yy+1, mip, t, v, false, 4); topleft = false; } + else { render_wall(h1 = s, h2 = w, xx, yy, xx+1, yy+1, mip, s, u, false, 5); } } else { - if(wv) { render_wall(h2 = s, h1 = v, xx+1, yy+1, xx, yy, mip, u, s, false); } - else { render_wall(h2 = s, h1 = w, xx, yy+1, xx+1, yy, mip, v, t, false); topleft = false; } + if(wv) { render_wall(h2 = s, h1 = v, xx+1, yy+1, xx, yy, mip, u, s, false, 6); } + else { render_wall(h2 = s, h1 = w, xx, yy+1, xx+1, yy, mip, v, t, false, 7); topleft = false; } } } render_tris(xx<=vxx && xx!=0 && yy!=sz-1 && !SOLID(z) && (!SOLID(s) || z->type!=CORNER) && (z->type!=SEMISOLID || issemi(mip, xx-1, yy, 1, 0, 1, 1))) - render_wall(s, z, xx, yy, xx, yy+1, mip, s, v, true); + render_wall(s, z, xx, yy, xx, yy+1, mip, s, v, true, 0); if(xx<=vxx && inner && !SOLID(t) && (!SOLID(s) || t->type!=CORNER) && (t->type!=SEMISOLID || issemi(mip, xx+1, yy, 0, 0, 0, 1))) - render_wall(s, t, xx+1, yy, xx+1, yy+1, mip, t, u, false); + render_wall(s, t, xx+1, yy, xx+1, yy+1, mip, t, u, false, 1); if(yy>=vyy && yy!=0 && xx!=sz-1 && !SOLID(w) && (!SOLID(s) || w->type!=CORNER) && (w->type!=SEMISOLID || issemi(mip, xx, yy-1, 0, 1, 1, 1))) - render_wall(s, w, xx, yy, xx+1, yy, mip, s, t, false); + render_wall(s, w, xx, yy, xx+1, yy, mip, s, t, false, 2); if(yy<=vyy && inner && !SOLID(v) && (!SOLID(s) || v->type!=CORNER) && (v->type!=SEMISOLID || issemi(mip, xx, yy+1, 0, 0, 1, 0))) - render_wall(s, v, xx, yy+1, xx+1, yy+1, mip, v, u, true); + render_wall(s, v, xx, yy+1, xx+1, yy+1, mip, v, u, true, 3); } }} - } void distlod(int &low, int &high, int angle, float widef)