Dyntopo: avoid mask layer lookups while adding/removing verts
authorCampbell Barton <ideasman42@gmail.com>
Mon, 7 Apr 2014 03:05:39 +0000 (13:05 +1000)
committerCampbell Barton <ideasman42@gmail.com>
Mon, 7 Apr 2014 03:05:39 +0000 (13:05 +1000)
source/blender/blenkernel/intern/pbvh_bmesh.c
source/blender/bmesh/intern/bmesh_log.c
source/blender/bmesh/intern/bmesh_log.h
source/blender/editors/sculpt_paint/sculpt_undo.c

index 98efc112125061dedc4753c104cc9b001d57bcf5..6e481b761d61b17ff835b4f4b38c97bb89067398 100644 (file)
@@ -285,7 +285,8 @@ static PBVHNode *pbvh_bmesh_node_lookup(PBVH *bvh, GHash *map, void *key)
 
 static BMVert *pbvh_bmesh_vert_create(PBVH *bvh, int node_index,
                                       const float co[3],
-                                      const BMVert *example)
+                                      const BMVert *example,
+                                      const int cd_vert_mask_offset)
 {
        BMVert *v = BM_vert_create(bvh->bm, co, example, BM_CREATE_NOP);
        void *val = SET_INT_IN_POINTER(node_index);
@@ -296,7 +297,7 @@ static BMVert *pbvh_bmesh_vert_create(PBVH *bvh, int node_index,
        BLI_ghash_insert(bvh->bm_vert_to_node, v, val);
 
        /* Log the new vertex */
-       BM_log_vert_added(bvh->bm, bvh->bm_log, v);
+       BM_log_vert_added(bvh->bm_log, v, cd_vert_mask_offset);
 
        return v;
 }
@@ -695,7 +696,7 @@ static void pbvh_bmesh_split_edge(EdgeQueueContext *eq_ctx, PBVH *bvh,
 
        node_index = GET_INT_FROM_POINTER(BLI_ghash_lookup(bvh->bm_vert_to_node,
                                                           e->v1));
-       v_new = pbvh_bmesh_vert_create(bvh, node_index, mid, e->v1);
+       v_new = pbvh_bmesh_vert_create(bvh, node_index, mid, e->v1, eq_ctx->cd_vert_mask_offset);
 
        /* update paint mask */
        if (eq_ctx->cd_vert_mask_offset != -1) {
@@ -942,7 +943,7 @@ static void pbvh_bmesh_collapse_edge(PBVH *bvh, BMEdge *e, BMVert *v1,
                /* Delete unused vertices */
                for (j = 0; j < 3; j++) {
                        if (v_tri[j]) {
-                               BM_log_vert_removed(bvh->bm, bvh->bm_log, v_tri[j]);
+                               BM_log_vert_removed(bvh->bm_log, v_tri[j], cd_vert_mask_offset);
                                BM_vert_kill(bvh->bm, v_tri[j]);
                        }
                }
@@ -951,14 +952,14 @@ static void pbvh_bmesh_collapse_edge(PBVH *bvh, BMEdge *e, BMVert *v1,
        /* Move v_conn to the midpoint of v_conn and v_del (if v_conn still exists, it
         * may have been deleted above) */
        if (!BLI_ghash_haskey(deleted_verts, v_conn)) {
-               BM_log_vert_before_modified(bvh->bm, bvh->bm_log, v_conn);
+               BM_log_vert_before_modified(bvh->bm_log, v_conn, cd_vert_mask_offset);
                mid_v3_v3v3(v_conn->co, v_conn->co, v_del->co);
        }
 
        /* Delete v_del */
        BLI_assert(BM_vert_face_count(v_del) == 0);
        BLI_ghash_insert(deleted_verts, v_del, NULL);
-       BM_log_vert_removed(bvh->bm, bvh->bm_log, v_del);
+       BM_log_vert_removed(bvh->bm_log, v_del, cd_vert_mask_offset);
        BM_vert_kill(bvh->bm, v_del);
 }
 
index 372252db8fe7aaf006fbd344073bb3b8ee01fbcb..5f0c11d1d069b451ed93f657ec61738085eaf4e0 100644 (file)
@@ -178,12 +178,10 @@ static BMFace *bm_log_face_from_id(BMLog *log, unsigned int id)
 /* Get a vertex's paint-mask value
  *
  * Returns zero if no paint-mask layer is present */
-static float vert_mask_get(BMesh *bm, BMVert *v)
+static float vert_mask_get(BMVert *v, const int cd_vert_mask_offset)
 {
-       float *mask = CustomData_bmesh_get(&bm->vdata, v->head.data, CD_PAINT_MASK);
-       BLI_assert((CustomData_has_layer(&bm->vdata, CD_PAINT_MASK) == 0) == (mask == NULL));
-       if (mask) {
-               return *mask;
+       if (cd_vert_mask_offset != -1) {
+               return BM_ELEM_CD_GET_FLOAT(v, cd_vert_mask_offset);
        }
        else {
                return 0.0f;
@@ -193,31 +191,29 @@ static float vert_mask_get(BMesh *bm, BMVert *v)
 /* Set a vertex's paint-mask value
  *
  * Has no effect is no paint-mask layer is present */
-static void vert_mask_set(BMesh *bm, BMVert *v, float new_mask)
+static void vert_mask_set(BMVert *v, const float new_mask, const int cd_vert_mask_offset)
 {
-       float *mask = CustomData_bmesh_get(&bm->vdata, v->head.data, CD_PAINT_MASK);
-       BLI_assert((CustomData_has_layer(&bm->vdata, CD_PAINT_MASK) == 0) == (mask == NULL));
-       if (*mask) {
-               *mask = new_mask;
+       if (cd_vert_mask_offset != -1) {
+               BM_ELEM_CD_SET_FLOAT(v, cd_vert_mask_offset, new_mask);
        }
 }
 
 /* Update a BMLogVert with data from a BMVert */
-static void bm_log_vert_bmvert_copy(BMesh *bm, BMLogVert *lv, BMVert *v)
+static void bm_log_vert_bmvert_copy(BMLogVert *lv, BMVert *v, const int cd_vert_mask_offset)
 {
        copy_v3_v3(lv->co, v->co);
        normal_float_to_short_v3(lv->no, v->no);
-       lv->mask = vert_mask_get(bm, v);
+       lv->mask = vert_mask_get(v, cd_vert_mask_offset);
        lv->hflag = v->head.hflag;
 }
 
 /* Allocate and initialize a BMLogVert */
-static BMLogVert *bm_log_vert_alloc(BMesh *bm, BMLog *log, BMVert *v)
+static BMLogVert *bm_log_vert_alloc(BMLog *log, BMVert *v, const int cd_vert_mask_offset)
 {
        BMLogEntry *entry = log->current_entry;
        BMLogVert *lv = BLI_mempool_alloc(entry->pool_verts);
 
-       bm_log_vert_bmvert_copy(bm, lv, v);
+       bm_log_vert_bmvert_copy(lv, v, cd_vert_mask_offset);
 
        return lv;
 }
@@ -246,6 +242,8 @@ static BMLogFace *bm_log_face_alloc(BMLog *log, BMFace *f)
 
 static void bm_log_verts_unmake(BMesh *bm, BMLog *log, GHash *verts)
 {
+       const int cd_vert_mask_offset = CustomData_get_offset(&bm->vdata, CD_PAINT_MASK);
+
        GHashIterator gh_iter;
        GHASH_ITER (gh_iter, verts) {
                void *key = BLI_ghashIterator_getKey(&gh_iter);
@@ -255,7 +253,7 @@ static void bm_log_verts_unmake(BMesh *bm, BMLog *log, GHash *verts)
 
                /* Ensure the log has the final values of the vertex before
                 * deleting it */
-               bm_log_vert_bmvert_copy(bm, lv, v);
+               bm_log_vert_bmvert_copy(lv, v, cd_vert_mask_offset);
 
                BM_vert_kill(bm, v);
        }
@@ -289,13 +287,15 @@ static void bm_log_faces_unmake(BMesh *bm, BMLog *log, GHash *faces)
 
 static void bm_log_verts_restore(BMesh *bm, BMLog *log, GHash *verts)
 {
+       const int cd_vert_mask_offset = CustomData_get_offset(&bm->vdata, CD_PAINT_MASK);
+
        GHashIterator gh_iter;
        GHASH_ITER (gh_iter, verts) {
                void *key = BLI_ghashIterator_getKey(&gh_iter);
                BMLogVert *lv = BLI_ghashIterator_getValue(&gh_iter);
                BMVert *v = BM_vert_create(bm, lv->co, NULL, BM_CREATE_NOP);
+               vert_mask_set(v, lv->mask, cd_vert_mask_offset);
                v->head.hflag = lv->hflag;
-               vert_mask_set(bm, v, lv->mask);
                normal_short_to_float_v3(v->no, lv->no);
                bm_log_vert_id_set(log, v, GET_UINT_FROM_POINTER(key));
        }
@@ -319,6 +319,8 @@ static void bm_log_faces_restore(BMesh *bm, BMLog *log, GHash *faces)
 
 static void bm_log_vert_values_swap(BMesh *bm, BMLog *log, GHash *verts)
 {
+       const int cd_vert_mask_offset = CustomData_get_offset(&bm->vdata, CD_PAINT_MASK);
+
        GHashIterator gh_iter;
        GHASH_ITER (gh_iter, verts) {
                void *key = BLI_ghashIterator_getKey(&gh_iter);
@@ -334,8 +336,8 @@ static void bm_log_vert_values_swap(BMesh *bm, BMLog *log, GHash *verts)
                normal_short_to_float_v3(v->no, normal);
                SWAP(char, v->head.hflag, lv->hflag);
                mask = lv->mask;
-               lv->mask = vert_mask_get(bm, v);
-               vert_mask_set(bm, v, mask);
+               lv->mask = vert_mask_get(v, cd_vert_mask_offset);
+               vert_mask_set(v, mask, cd_vert_mask_offset);
        }
 }
 
@@ -766,7 +768,7 @@ void BM_log_redo(BMesh *bm, BMLog *log)
  * state so that a subsequent redo operation will restore the newer
  * vertex state.
  */
-void BM_log_vert_before_modified(BMesh *bm, BMLog *log, BMVert *v)
+void BM_log_vert_before_modified(BMLog *log, BMVert *v, const int cd_vert_mask_offset)
 {
        BMLogEntry *entry = log->current_entry;
        BMLogVert *lv;
@@ -775,10 +777,10 @@ void BM_log_vert_before_modified(BMesh *bm, BMLog *log, BMVert *v)
 
        /* Find or create the BMLogVert entry */
        if ((lv = BLI_ghash_lookup(entry->added_verts, key))) {
-               bm_log_vert_bmvert_copy(bm, lv, v);
+               bm_log_vert_bmvert_copy(lv, v, cd_vert_mask_offset);
        }
        else if (!BLI_ghash_haskey(entry->modified_verts, key)) {
-               lv = bm_log_vert_alloc(bm, log, v);
+               lv = bm_log_vert_alloc(log, v, cd_vert_mask_offset);
                BLI_ghash_insert(entry->modified_verts, key, lv);
        }
 }
@@ -789,14 +791,14 @@ void BM_log_vert_before_modified(BMesh *bm, BMLog *log, BMVert *v)
  * of added vertices, with the key being its ID and the value
  * containing everything needed to reconstruct that vertex.
  */
-void BM_log_vert_added(BMesh *bm, BMLog *log, BMVert *v)
+void BM_log_vert_added(BMLog *log, BMVert *v, const int cd_vert_mask_offset)
 {
        BMLogVert *lv;
        unsigned int v_id = range_tree_uint_take_any(log->unused_ids);
        void *key = SET_UINT_IN_POINTER(v_id);
 
        bm_log_vert_id_set(log, v, v_id);
-       lv = bm_log_vert_alloc(bm, log, v);
+       lv = bm_log_vert_alloc(log, v, cd_vert_mask_offset);
        BLI_ghash_insert(log->current_entry->added_verts, key, lv);
 }
 
@@ -836,7 +838,7 @@ void BM_log_face_added(BMLog *log, BMFace *f)
  * If there's a move record for the vertex, that's used as the
  * vertices original location, then the move record is deleted.
  */
-void BM_log_vert_removed(BMesh *bm, BMLog *log, BMVert *v)
+void BM_log_vert_removed(BMLog *log, BMVert *v, const int cd_vert_mask_offset)
 {
        BMLogEntry *entry = log->current_entry;
        unsigned int v_id = bm_log_vert_id_get(log, v);
@@ -852,7 +854,7 @@ void BM_log_vert_removed(BMesh *bm, BMLog *log, BMVert *v)
        else {
                BMLogVert *lv, *lv_mod;
 
-               lv = bm_log_vert_alloc(bm, log, v);
+               lv = bm_log_vert_alloc(log, v, cd_vert_mask_offset);
                BLI_ghash_insert(entry->deleted_verts, key, lv);
 
                /* If the vertex was modified before deletion, ensure that the
@@ -901,13 +903,14 @@ void BM_log_face_removed(BMLog *log, BMFace *f)
 /* Log all vertices/faces in the BMesh as added */
 void BM_log_all_added(BMesh *bm, BMLog *log)
 {
+       const int cd_vert_mask_offset = CustomData_get_offset(&bm->vdata, CD_PAINT_MASK);
        BMIter bm_iter;
        BMVert *v;
        BMFace *f;
 
        /* Log all vertices as newly created */
        BM_ITER_MESH (v, &bm_iter, bm, BM_VERTS_OF_MESH) {
-               BM_log_vert_added(bm, log, v);
+               BM_log_vert_added(log, v, cd_vert_mask_offset);
        }
 
        /* Log all faces as newly created */
@@ -919,6 +922,7 @@ void BM_log_all_added(BMesh *bm, BMLog *log)
 /* Log all vertices/faces in the BMesh as removed */
 void BM_log_before_all_removed(BMesh *bm, BMLog *log)
 {
+       const int cd_vert_mask_offset = CustomData_get_offset(&bm->vdata, CD_PAINT_MASK);
        BMIter bm_iter;
        BMVert *v;
        BMFace *f;
@@ -930,7 +934,7 @@ void BM_log_before_all_removed(BMesh *bm, BMLog *log)
 
        /* Log deletion of all vertices */
        BM_ITER_MESH (v, &bm_iter, bm, BM_VERTS_OF_MESH) {
-               BM_log_vert_removed(bm, log, v);
+               BM_log_vert_removed(log, v, cd_vert_mask_offset);
        }
 }
 
index 3cd2fd7008131e8c71d16c0ab5277e0b95dffeb1..dab17268d969003d3d975826f9d3a5d22e122657 100644 (file)
@@ -61,16 +61,16 @@ void BM_log_undo(BMesh *bm, BMLog *log);
 void BM_log_redo(BMesh *bm, BMLog *log);
 
 /* Log a vertex before it is modified */
-void BM_log_vert_before_modified(BMesh *bm, BMLog *log, struct BMVert *v);
+void BM_log_vert_before_modified(BMLog *log, struct BMVert *v, const int cd_vert_mask_offset);
 
 /* Log a new vertex as added to the BMesh */
-void BM_log_vert_added(BMesh *bm, BMLog *log, struct BMVert *v);
+void BM_log_vert_added(BMLog *log, struct BMVert *v, const int cd_vert_mask_offset);
 
 /* Log a new face as added to the BMesh */
 void BM_log_face_added(BMLog *log, struct BMFace *f);
 
 /* Log a vertex as removed from the BMesh */
-void BM_log_vert_removed(BMesh *bm, BMLog *log, struct BMVert *v);
+void BM_log_vert_removed(BMLog *log, struct BMVert *v, const int cd_vert_mask_offset);
 
 /* Log a face as removed from the BMesh */
 void BM_log_face_removed(BMLog *log, struct BMFace *f);
index b086bff1ba787315af4eae89b7706b9d23e8118e..90e26f03b2e97bb17ac6435ca1a577f533e79b69 100644 (file)
@@ -761,7 +761,7 @@ static SculptUndoNode *sculpt_undo_bmesh_push(Object *ob,
                                /* Before any vertex values get modified, ensure their
                                 * original positions are logged */
                                BKE_pbvh_vertex_iter_begin(ss->pbvh, node, vd, PBVH_ITER_ALL) {
-                                       BM_log_vert_before_modified(ss->bm, ss->bm_log, vd.bm_vert);
+                                       BM_log_vert_before_modified(ss->bm_log, vd.bm_vert, vd.cd_vert_mask_offset);
                                }
                                BKE_pbvh_vertex_iter_end;
                                break;