Add Z-buffer, fixes issue with pyramidal studs master
authorNick Downing <nick@ndcode.org>
Wed, 20 Apr 2022 09:46:19 +0000 (19:46 +1000)
committerNick Downing <nick@ndcode.org>
Wed, 20 Apr 2022 11:02:11 +0000 (21:02 +1000)
obj.c
render.c

diff --git a/obj.c b/obj.c
index 0863d73..5fb48ff 100644 (file)
--- a/obj.c
+++ b/obj.c
@@ -593,7 +593,6 @@ static void read_f(const char *line, struct obj *O, int si, int gi)
         for (i = 0; i < ic; ++i)
             if (_iv[i0 + 0]._ni < 0)
             {
- assert(0);
                 obj_get_vert_n(O, _iv[i0 + i]._vi, t);
                 t[0] += n[0];
                 t[1] += n[1];
index 70c11d0..bbc7da0 100644 (file)
--- a/render.c
+++ b/render.c
@@ -323,75 +323,6 @@ int main(void) {
       *(float *)array_index2(model_vertices_t, 1, i) = obj->vv[i].t[1];
     }
   }
-
-  // for some reason the vertex ordering is screwed up in Chest model,
-  // fix it by comparing our calculated normal with average vertex normal
-  {
-    int I = obj->sc;
-    for (int i = 0; i < I; ++i) {
-      int J = obj->sv[i].pc;
-      for (int j = 0; j < J; ++j) {
-        size_t v[3] = {
-          obj->sv[i].pv[j].vi[0],
-          obj->sv[i].pv[j].vi[1],
-          obj->sv[i].pv[j].vi[2]
-        };
-
-        struct array *v0 = array_new2_init(
-          3,
-          sizeof(float),
-          (float[3]){
-            obj->vv[v[0]].v[0],
-            obj->vv[v[0]].v[1],
-            obj->vv[v[0]].v[2]
-          }
-        );
-        struct array *v1 = array_new2_init(
-          3,
-          sizeof(float),
-          (float[3]){
-            obj->vv[v[1]].v[0],
-            obj->vv[v[1]].v[1],
-            obj->vv[v[1]].v[2]
-          }
-        );
-        struct array *v2 = array_new2_init(
-          3,
-          sizeof(float),
-          (float[3]){
-            obj->vv[v[2]].v[0],
-            obj->vv[v[2]].v[1],
-            obj->vv[v[2]].v[2]
-          }
-        );
-        struct array *dir1 = vec_sub(v1, v0);
-        struct array *dir2 = vec_sub(v2, v0);
-        struct array *norm = vec_cross(dir1, dir2); // outward pointing
-
-        struct array *ave_norm = array_new2_zero(3, sizeof(float));
-        for (int k = 0; k < 3; ++k) {
-          *(float *)array_index1(ave_norm, 0) += obj->vv[v[k]].n[0];
-          *(float *)array_index1(ave_norm, 1) += obj->vv[v[k]].n[1];
-          *(float *)array_index1(ave_norm, 2) += obj->vv[v[k]].n[2];
-        }
-
-        // if norms are opposite, reverse vertex order
-        if (vec_dot(norm, ave_norm) < 0.f) {
- assert(false);
-          obj->sv[i].pv[j].vi[1] = (int)v[2];
-          obj->sv[i].pv[j].vi[2] = (int)v[1];
-        }
-
-        array_free(ave_norm);
-        array_free(norm);
-        array_free(dir2);
-        array_free(dir1);
-        array_free(v2);
-        array_free(v1);
-        array_free(v0);
-      }
-    }
-  }
 #else
   struct array *model_vertices = array_new3(4, 8, sizeof(float));
   for (int i = 0; i < 2; ++i)
@@ -567,6 +498,8 @@ int main(void) {
   // main loop
   struct array *frame =
     array_new3(WINDOW_HEIGHT, WINDOW_WIDTH, sizeof(uint32_t));
+  struct array *frame_z =
+    array_new3(WINDOW_HEIGHT, WINDOW_WIDTH, sizeof(float));
   while (true) {
     SDL_Event event;
     while (SDL_PollEvent(&event))
@@ -635,7 +568,9 @@ int main(void) {
 
     // draw
     array_clear0(frame);
-    //memset(array_index2(frame, 50, 50), 0xff, frame->stride[2]);
+    for (int i = 0; i < WINDOW_HEIGHT; ++i)
+      for (int j = 0; j < WINDOW_WIDTH; ++j)
+        *(float *)array_index2(frame_z, i, j) = 1e30f;
 #if 1
     {
       int I = obj->sc;
@@ -706,12 +641,21 @@ int main(void) {
                 y >= 0 &&
                 y < WINDOW_HEIGHT
               ) {
-                uint8_t *m = array_index2(map, (size_t)v, (size_t)u);
-                uint8_t *f = array_index2(frame, (size_t)y, (size_t)x);
-                f[0] = m[0]; // b
-                f[1] = m[1]; // g
-                f[2] = m[2]; // r
-                f[3] = 0xff; // a
+                size_t xi = (size_t)x;
+                size_t yi = (size_t)y;
+                float z = *(float *)array_index2(qcb, 2, k);
+                float *fz = (float *)array_index2(frame_z, yi, xi);
+                if (z < *fz) {
+                  size_t ui = (size_t)u;
+                  size_t vi = (size_t)v;
+                  uint8_t *m = array_index2(map, vi, ui);
+                  uint8_t *f = array_index2(frame, yi, xi);
+                  f[0] = m[0]; // b
+                  f[1] = m[1]; // g
+                  f[2] = m[2]; // r
+                  f[3] = 0xff; // a
+                  *fz = z;
+                }
               }
             }
             array_free(qcbu);