Fix normals for flat-shaded non-VBO sculpt drawing.
authorNicholas Bishop <nicholasbishop@gmail.com>
Mon, 20 Feb 2012 21:25:24 +0000 (21:25 +0000)
committerNicholas Bishop <nicholasbishop@gmail.com>
Mon, 20 Feb 2012 21:25:24 +0000 (21:25 +0000)
Example here, original on left, fixed normals on right:
http://www.pasteall.org/pic/show.php?id=26925

source/blender/gpu/intern/gpu_buffers.c

index b128a6e46e738331acb6bd27e97dfbaf4ee37332..8318d906f72d6ff5fd73c9757dcabd8400cc8e3e 100644 (file)
@@ -1294,6 +1294,7 @@ struct GPU_Buffers {
        int gridsize;
 
        unsigned int tot_tri, tot_quad;
+       int smooth;
 };
 
 void GPU_update_mesh_buffers(GPU_Buffers *buffers, MVert *mvert,
@@ -1462,6 +1463,7 @@ void GPU_update_grid_buffers(GPU_Buffers *buffers, DMGridData **grids,
        buffers->grid_indices = grid_indices;
        buffers->totgrid = totgrid;
        buffers->gridsize = gridsize;
+       buffers->smooth = smooth;
 
        //printf("node updated %p\n", buffers);
 }
@@ -1556,6 +1558,78 @@ GPU_Buffers *GPU_build_grid_buffers(DMGridData **UNUSED(grids), int *UNUSED(grid
        return buffers;
 }
 
+static void gpu_draw_buffers_legacy_mesh(GPU_Buffers *buffers)
+{
+       int i;
+
+       for(i = 0; i < buffers->totface; ++i) {
+               MFace *f = buffers->mface + buffers->face_indices[i];
+
+               glBegin((f->v4)? GL_QUADS: GL_TRIANGLES);
+               glNormal3sv(buffers->mvert[f->v1].no);
+               glVertex3fv(buffers->mvert[f->v1].co);
+               glNormal3sv(buffers->mvert[f->v2].no);
+               glVertex3fv(buffers->mvert[f->v2].co);
+               glNormal3sv(buffers->mvert[f->v3].no);
+               glVertex3fv(buffers->mvert[f->v3].co);
+               if(f->v4) {
+                       glNormal3sv(buffers->mvert[f->v4].no);
+                       glVertex3fv(buffers->mvert[f->v4].co);
+               }
+               glEnd();
+       }
+}
+
+static void gpu_draw_buffers_legacy_grids(GPU_Buffers *buffers)
+{
+       int i, x, y, gridsize = buffers->gridsize;
+
+       if(buffers->smooth) {
+               for(i = 0; i < buffers->totgrid; ++i) {
+                       DMGridData *grid = buffers->grids[buffers->grid_indices[i]];
+
+                       for(y = 0; y < gridsize-1; y++) {
+                               glBegin(GL_QUAD_STRIP);
+                               for(x = 0; x < gridsize; x++) {
+                                       DMGridData *a = &grid[y*gridsize + x];
+                                       DMGridData *b = &grid[(y+1)*gridsize + x];
+
+                                       glNormal3fv(a->no);
+                                       glVertex3fv(a->co);
+                                       glNormal3fv(b->no);
+                                       glVertex3fv(b->co);
+                               }
+                               glEnd();
+                       }
+               }
+       }
+       else {
+               for(i = 0; i < buffers->totgrid; ++i) {
+                       DMGridData *grid = buffers->grids[buffers->grid_indices[i]];
+
+                       for(y = 0; y < gridsize-1; y++) {
+                               glBegin(GL_QUAD_STRIP);
+                               for(x = 0; x < gridsize; x++) {
+                                       DMGridData *a = &grid[y*gridsize + x];
+                                       DMGridData *b = &grid[(y+1)*gridsize + x];
+
+                                       if(x > 0) {
+                                               DMGridData *c = &grid[y*gridsize + x-1];
+                                               DMGridData *d = &grid[(y+1)*gridsize + x-1];
+                                               float fno[3];
+                                               normal_quad_v3(fno, d->co, b->co, a->co, c->co);
+                                               glNormal3fv(fno);
+                                       }
+
+                                       glVertex3fv(a->co);
+                                       glVertex3fv(b->co);
+                               }
+                               glEnd();
+                       }
+               }
+       }
+}
+
 void GPU_draw_buffers(GPU_Buffers *buffers)
 {
        if(buffers->vert_buf && buffers->index_buf) {
@@ -1584,47 +1658,12 @@ void GPU_draw_buffers(GPU_Buffers *buffers)
                glDisableClientState(GL_VERTEX_ARRAY);
                glDisableClientState(GL_NORMAL_ARRAY);
        }
+       /* fallbacks if we are out of memory or VBO is disabled */
        else if(buffers->totface) {
-               /* fallback if we are out of memory */
-               int i;
-
-               for(i = 0; i < buffers->totface; ++i) {
-                       MFace *f = buffers->mface + buffers->face_indices[i];
-
-                       glBegin((f->v4)? GL_QUADS: GL_TRIANGLES);
-                       glNormal3sv(buffers->mvert[f->v1].no);
-                       glVertex3fv(buffers->mvert[f->v1].co);
-                       glNormal3sv(buffers->mvert[f->v2].no);
-                       glVertex3fv(buffers->mvert[f->v2].co);
-                       glNormal3sv(buffers->mvert[f->v3].no);
-                       glVertex3fv(buffers->mvert[f->v3].co);
-                       if(f->v4) {
-                               glNormal3sv(buffers->mvert[f->v4].no);
-                               glVertex3fv(buffers->mvert[f->v4].co);
-                       }
-                       glEnd();
-               }
+               gpu_draw_buffers_legacy_mesh(buffers);
        }
        else if(buffers->totgrid) {
-               int i, x, y, gridsize = buffers->gridsize;
-
-               for(i = 0; i < buffers->totgrid; ++i) {
-                       DMGridData *grid = buffers->grids[buffers->grid_indices[i]];
-
-                       for(y = 0; y < gridsize-1; y++) {
-                               glBegin(GL_QUAD_STRIP);
-                               for(x = 0; x < gridsize; x++) {
-                                       DMGridData *a = &grid[y*gridsize + x];
-                                       DMGridData *b = &grid[(y+1)*gridsize + x];
-
-                                       glNormal3fv(a->no);
-                                       glVertex3fv(a->co);
-                                       glNormal3fv(b->no);
-                                       glVertex3fv(b->co);
-                               }
-                               glEnd();
-                       }
-               }
+               gpu_draw_buffers_legacy_grids(buffers);
        }
 }