From: John Tsiombikas Date: Thu, 13 Oct 2022 23:33:59 +0000 (+0300) Subject: foo X-Git-Url: http://git.mutantstargoat.com/user/nuclear/?p=voxscape;a=commitdiff_plain;h=7efa828ba87fe6c90b8c55019f4789066d2e4af3 foo --- diff --git a/src/voxscape.c b/src/voxscape.c index b9a18c3..df34f20 100644 --- a/src/voxscape.c +++ b/src/voxscape.c @@ -14,6 +14,7 @@ struct voxscape { int xsz, ysz; unsigned char *height; uint32_t *color; + int xshift, xmask, ymask; /* framebuffer */ uint32_t *fb; @@ -22,11 +23,13 @@ struct voxscape { /* view */ int32_t x, y, angle; + int vheight; /* projection */ int fov, znear, zfar; int nslices; - int32_t *slicelen; /* 24.8 */ + int32_t *slicelen; + int proj_dist; unsigned int valid; }; @@ -52,6 +55,17 @@ struct voxscape *vox_create(int xsz, int ysz) vox->xsz = xsz; vox->ysz = ysz; + vox->xmask = vox->xsz - 1; + vox->ymask = vox->ysz - 1; + + vox->xshift = -1; + while(xsz) { + xsz >>= 1; + vox->xshift++; + } + + vox->proj_dist = 2; /* TODO */ + return vox; } @@ -124,13 +138,11 @@ void vox_view(struct voxscape *vox, int32_t x, int32_t y, int32_t angle) vox->angle = angle; /* TODO precalc stuff */ - valid &= ~SLICELEN; + vox->valid &= ~SLICELEN; } void vox_proj(struct voxscape *vox, int fov, int znear, int zfar) { - int i; - vox->fov = fov; vox->znear = znear; vox->zfar = zfar; @@ -142,7 +154,7 @@ void vox_proj(struct voxscape *vox, int fov, int znear, int zfar) return; } - valid &= ~SLICELEN; + vox->valid &= ~SLICELEN; } /* algorithm: @@ -165,14 +177,17 @@ void vox_begin(struct voxscape *vox) { int i; + /* for(i=0; ifbwidth; i++) { vox->coltop[i] = vox->fbheight; } + */ + memset(vox->coltop, 0, vox->fbwidth * sizeof *vox->coltop); if(!(vox->valid & SLICELEN)) { float theta = (float)vox->angle * M_PI / 360.0f; /* half angle */ for(i=0; inslices; i++) { - vox->slicelen[i] = (int32_t)((vox->znear + i) * tan(theta) * 2.0f * 256.0f) + vox->slicelen[i] = (int32_t)((vox->znear + i) * tan(theta) * 2.0f * 65536.0f); } vox->valid |= SLICELEN; } @@ -180,9 +195,33 @@ void vox_begin(struct voxscape *vox) void vox_render_slice(struct voxscape *vox, int n) { - int32_t len; + int i, j, tx, ty, hval, colstart, colheight; + int32_t x, y, len, xstep; + uint32_t color; + uint32_t *fbptr; len = vox->slicelen[n]; + xstep = len / vox->fbwidth; - /* TODO cont. */ + x = vox->x - xstep * (vox->fbwidth >> 1); + y = vox->y + (vox->znear << 16); + for(i=0; ifbwidth; i++) { + tx = (x >> 16) & vox->xmask; + ty = (y >> 16) & vox->ymask; + + hval = (vox->height[(ty << vox->xshift) + tx] - vox->vheight) * vox->proj_dist / y; + if(hval > vox->coltop[i]) { + color = vox->color[(ty << vox->xshift) + tx]; + colstart = vox->fbheight - 1 - hval; + colheight = hval - vox->coltop[i]; + fbptr = vox->fb + colstart * vox->fbwidth + i; + + for(j=0; jfbwidth; + } + } + + x += xstep; + } }