[Bf-blender-cvs] [1acc730ba1a] temp-pbvh-vbos: temp-pbvh-vbos: Fix face hiding and implement PBVH_BMESH.

Joseph Eagar noreply at git.blender.org
Wed Sep 14 12:50:00 CEST 2022


Commit: 1acc730ba1aa33bba00cd36fbb0d53486dd6f7a4
Author: Joseph Eagar
Date:   Wed Sep 14 03:49:15 2022 -0700
Branches: temp-pbvh-vbos
https://developer.blender.org/rB1acc730ba1aa33bba00cd36fbb0d53486dd6f7a4

temp-pbvh-vbos: Fix face hiding and implement PBVH_BMESH.

===================================================================

M	source/blender/blenkernel/intern/pbvh.c
M	source/blender/draw/DRW_engine.h
M	source/blender/draw/intern/draw_manager_data.c
M	source/blender/draw/intern/draw_pbvh.cc

===================================================================

diff --git a/source/blender/blenkernel/intern/pbvh.c b/source/blender/blenkernel/intern/pbvh.c
index cee2cbe6c8a..88fb9d49383 100644
--- a/source/blender/blenkernel/intern/pbvh.c
+++ b/source/blender/blenkernel/intern/pbvh.c
@@ -540,10 +540,6 @@ static void pbvh_draw_args(PBVH *pbvh, PBVH_GPU_Args *args, PBVHNode *node)
 {
   memset((void *)args, 0, sizeof(*args));
 
-  if (!node->prim_indices) {
-    printf("error! %s\n", __func__);
-  }
-
   args->pbvh_type = pbvh->header.type;
   args->mesh_verts_num = pbvh->totvert;
   args->mesh_grids_num = pbvh->totgrid;
diff --git a/source/blender/draw/DRW_engine.h b/source/blender/draw/DRW_engine.h
index 9dc8ac372ae..f7323b63f59 100644
--- a/source/blender/draw/DRW_engine.h
+++ b/source/blender/draw/DRW_engine.h
@@ -274,7 +274,7 @@ typedef struct PBVH_GPU_Args {
 
   int node_verts_num;
 
-  const struct GSet *bm_unique_vert, *bm_other_verts, *bm_faces;
+  struct GSet *bm_unique_vert, *bm_other_verts, *bm_faces;
   const struct MLoopTri *mlooptri;
   struct PBVHNode *node;
 } PBVH_GPU_Args;
diff --git a/source/blender/draw/intern/draw_manager_data.c b/source/blender/draw/intern/draw_manager_data.c
index 4612770b1d8..c8ed8bfd94b 100644
--- a/source/blender/draw/intern/draw_manager_data.c
+++ b/source/blender/draw/intern/draw_manager_data.c
@@ -1171,10 +1171,16 @@ ATTR_NO_OPT static void sculpt_draw_cb(DRWSculptCallbackData *scd,
     return;
   }
 
-  //GPUBatch *geom2 = GPU_pbvh_buffers_batch_get(buffers, scd->fast_mode, scd->use_wire);
+  // GPUBatch *geom2 = GPU_pbvh_buffers_batch_get(buffers, scd->fast_mode, scd->use_wire);
   int primcount;
-  GPUBatch *geom = DRW_pbvh_tris_get(
-      batches, scd->attrs, scd->attrs_num, pbvh_draw_args, &primcount);
+  GPUBatch *geom;
+
+  if (!scd->use_wire) {
+    geom = DRW_pbvh_tris_get(batches, scd->attrs, scd->attrs_num, pbvh_draw_args, &primcount);
+  }
+  else {
+    geom = DRW_pbvh_lines_get(batches, scd->attrs, scd->attrs_num, pbvh_draw_args, &primcount);
+  }
 
   short index = 0;
 
@@ -1299,16 +1305,15 @@ ATTR_NO_OPT static void drw_sculpt_generate_calls(DRWSculptCallbackData *scd)
   Mesh *mesh = scd->ob->data;
   BKE_pbvh_update_normals(pbvh, mesh->runtime.subdiv_ccg);
 
-  BKE_pbvh_draw_cb(
-      pbvh,
-      update_only_visible,
-      &update_frustum,
-      &draw_frustum,
-      (void (*)(void *, PBVHBatches *, PBVH_GPU_Args *))sculpt_draw_cb,
-      scd,
-      scd->use_mats,
-      scd->attrs,
-      scd->attrs_num);
+  BKE_pbvh_draw_cb(pbvh,
+                   update_only_visible,
+                   &update_frustum,
+                   &draw_frustum,
+                   (void (*)(void *, PBVHBatches *, PBVH_GPU_Args *))sculpt_draw_cb,
+                   scd,
+                   scd->use_mats,
+                   scd->attrs,
+                   scd->attrs_num);
 
   if (SCULPT_DEBUG_BUFFERS) {
     int debug_node_nr = 0;
diff --git a/source/blender/draw/intern/draw_pbvh.cc b/source/blender/draw/intern/draw_pbvh.cc
index 4bf88108ea8..2352f0f66cc 100644
--- a/source/blender/draw/intern/draw_pbvh.cc
+++ b/source/blender/draw/intern/draw_pbvh.cc
@@ -148,11 +148,48 @@ struct PBVHBatches {
   Map<string, PBVHBatch> batches;
   GPUIndexBuf *tri_index = nullptr;
   GPUIndexBuf *lines_index = nullptr;
+  int faces_count = 0; /* Used by PBVH_BMESH and PBVH_GRIDS */
   int tris_count = 0, lines_count = 0;
-  bool needs_tri_index = false;  // XXX
+  bool needs_tri_index = false;
 
   int material_index = 0;
 
+  PBVHBatches(PBVH_GPU_Args *args)
+  {
+    switch (args->pbvh_type) {
+      case PBVH_FACES: {
+        for (int i = 0; i < args->totprim; i++) {
+          int face_index = args->mlooptri[args->prim_indices[i]].poly;
+
+          if (args->hide_poly && args->hide_poly[face_index]) {
+            continue;
+          }
+
+          faces_count++;
+        }
+        break;
+      }
+      case PBVH_GRIDS: {
+        faces_count = BKE_pbvh_count_grid_quads((BLI_bitmap **)args->grid_hidden,
+                                                args->grid_indices,
+                                                args->totprim,
+                                                args->ccg_key.grid_size);
+
+        break;
+      }
+      case PBVH_BMESH: {
+        GSET_FOREACH_BEGIN (BMFace *, f, args->bm_faces) {
+          if (!BM_elem_flag_test(f, BM_ELEM_HIDDEN)) {
+            faces_count++;
+          }
+        }
+        GSET_FOREACH_END();
+
+        tris_count = faces_count;
+      }
+    }
+  }
+
   ATTR_NO_OPT ~PBVHBatches()
   {
     for (PBVHBatch &batch : batches.values()) {
@@ -282,9 +319,8 @@ struct PBVHBatches {
           void(std::function<void(int x, int y, int grid_index, CCGElem *elems[4], int i)>
                    func)> foreach)
   {
-    uint totgrid = args->totprim;
     uint vert_per_grid = square_i(args->ccg_key.grid_size - 1) * 4;
-    uint vert_count = totgrid * vert_per_grid;
+    uint vert_count = args->totprim * vert_per_grid;
 
     int existing_num = GPU_vertbuf_get_vertex_len(vbo.vert_buf);
     void *existing_data = GPU_vertbuf_get_data(vbo.vert_buf);
@@ -378,8 +414,6 @@ struct PBVHBatches {
     int gridsize = args->ccg_key.grid_size;
 
     uint totgrid = args->totprim;
-    uint vert_per_grid = square_i(args->ccg_key.grid_size - 1) * 4;
-    uint vert_count = totgrid * vert_per_grid;
 
     auto foreach_solid =
         [&](std::function<void(int x, int y, int grid_index, CCGElem *elems[4], int i)> func) {
@@ -410,10 +444,8 @@ struct PBVHBatches {
         [&](std::function<void(int x, int y, int grid_index, CCGElem *elems[4], int i)> func) {
           for (int i = 0; i < totgrid; i++) {
             const int grid_index = args->grid_indices[i];
-            const int grid_vert_len = gridsize * gridsize;
 
             CCGElem *grid = args->grids[grid_index];
-            const int offset = grid_index * grid_vert_len;
 
             for (int y = 0; y < gridsize; y++) {
               for (int x = 0; x < gridsize; x++) {
@@ -448,7 +480,9 @@ struct PBVHBatches {
           const MLoop *mloop = args->mloop;
 
           for (int i : IndexRange(args->totprim)) {
-            if (args->hide_poly && args->hide_poly[args->prim_indices[i]]) {
+            int face_index = args->mlooptri[args->prim_indices[i]].poly;
+
+            if (args->hide_poly && args->hide_poly[face_index]) {
               continue;
             }
 
@@ -574,6 +608,70 @@ struct PBVHBatches {
 
   void fill_vbo_bmesh(PBVHVbo &vbo, PBVH_GPU_Args *args)
   {
+    auto foreach = [&](std::function<void(BMLoop * l)> callback) {
+      GSET_FOREACH_BEGIN (BMFace *, f, args->bm_faces) {
+        if (BM_elem_flag_test(f, BM_ELEM_HIDDEN)) {
+          continue;
+        }
+
+        BMLoop *l = f->l_first;
+        do {
+          callback(l);
+        } while ((l = l->next) != f->l_first);
+      }
+      GSET_FOREACH_END();
+    };
+
+    faces_count = 0;
+    GSET_FOREACH_BEGIN (BMFace *, f, args->bm_faces) {
+      if (BM_elem_flag_test(f, BM_ELEM_HIDDEN)) {
+        continue;
+      }
+
+      BMLoop *l = f->l_first;
+      do {
+        faces_count++;
+      } while ((l = l->next) != f->l_first);
+    }
+    GSET_FOREACH_END();
+    tris_count = faces_count;
+
+    int existing_num = GPU_vertbuf_get_vertex_len(vbo.vert_buf);
+    void *existing_data = GPU_vertbuf_get_data(vbo.vert_buf);
+
+    printf("%p:%p: vbo.vert_buf: %p\n", args->node, this, vbo.vert_buf);
+
+    int vert_count = tris_count * 3;
+
+    if (existing_data == nullptr || existing_num != vert_count) {
+      /* Allocate buffer if not allocated yet or size changed. */
+      GPU_vertbuf_data_alloc(vbo.vert_buf, vert_count);
+    }
+
+    void *gpu_data = GPU_vertbuf_get_data(vbo.vert_buf);
+    GPUVertBufRaw access;
+    GPU_vertbuf_attr_get_raw_data(vbo.vert_buf, 0, &access);
+
+    if (!gpu_data || !args->totprim) {
+      printf("%s: eek!\n", __func__);
+    }
+
+    if (vbo.type == CD_PBVH_CO_TYPE) {
+      foreach (
+          [&](BMLoop *l) { *static_cast<float3 *>(GPU_vertbuf_raw_step(&access)) = l->v->co; })
+        ;
+    }
+
+    if (vbo.type == CD_PBVH_NO_TYPE) {
+      foreach ([&](BMLoop *l) {
+        short no[3];
+        bool smooth = BM_elem_flag_test(l->f, BM_ELEM_SMOOTH);
+
+        normal_float_to_short_v3(no, smooth ? l->f->no : l->v->no);
+        *static_cast<short3 *>(GPU_vertbuf_raw_step(&access)) = no;
+      })
+        ;
+    }
   }
 
   void fill_vbo(PBVHVbo &vbo, PBVH_GPU_Args *args)
@@ -698,15 +796,53 @@ struct PBVHBatches {
   {
   }
 
+  ATTR_NO_OPT void create_index_bmesh(PBVH_GPU_Args *args)
+  {
+    GPUIndexBufBuilder elb_lines;
+    GPU_indexbuf_init(&elb_lines, GPU_PRIM_LINES, tris_count * 3 * 2, INT_MAX);
+
+    int v_index = 0;
+    lines_count = 0;
+
+    GSET_FOREACH_BEGIN (BMFace *, f, args->bm_faces) {
+      if (BM_elem_flag_test(f, BM_ELEM_HIDDEN)) {
+        continue;
+      }
+
+      GPU_indexbuf_add_line_verts(&elb_lines, v_index, v_index + 1);
+      GPU_indexbuf_add_line_verts(&elb_lines, v_index + 1, v_index + 2);
+      GPU_indexbuf_add_line_verts(&elb_lines, v_index + 2, v_index);
+
+      lines_count += 3;
+      v_index += 3;
+    }
+    GSET_FOREACH_END();
+
+    lines_index = GPU_indexbuf_build(&elb_lines);
+  }
+
   ATTR_NO_OPT void create_index_grids(PBVH_GPU_Args *args)
   {
     needs_tri_index = true;
+    int gridsize = args->ccg_key.grid_size;
+    int totgrid = args->totprim;
 
     for (int i : IndexRange(args->totprim)) {
       int grid_index = args->grid_indices[i];
-      int face_index = BKE_subdiv_ccg_grid_to_face_index(args->subdiv_ccg, grid_index);
+      bool smooth = args->grid_flag_mats[grid_index].flag & ME_SMOOTH;
+      BLI_bitmap *gh = args->grid_hidden[grid_index];
+
+      for (int y = 0; y < gridsize - 1; y++) {
+        for (int x = 0; x < gridsize - 1; x++) {
+          if (gh && paint_is_grid_face_hidden(gh, gridsize, x, y)) {
+            /* Skip hidden faces by just setting smooth to true. */
+            smooth = true;
+            goto outer_loop_break;
+          }
+        }
+      }
 
-      const bool smooth = args->grid_flag_mats[args->grid_indices[0]].flag & ME_SMOOTH;
+    outer_loop_break:
 
       if (!smooth) {
         needs_tri_index = false;
@@ -718,9 +854,6 @@ struct PBVHBatche

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list