[Bf-blender-cvs] [8a1860bd9ae] master: BMesh: support face-normal calculation in normal & looptri functions
Campbell Barton
noreply at git.blender.org
Mon Jun 14 15:04:27 CEST 2021
Commit: 8a1860bd9aecddf611b64e3e842bdc8c76f15cc6
Author: Campbell Barton
Date: Mon Jun 14 22:56:03 2021 +1000
Branches: master
https://developer.blender.org/rB8a1860bd9aecddf611b64e3e842bdc8c76f15cc6
BMesh: support face-normal calculation in normal & looptri functions
Support calculating face normals when tessellating. When this is done
before updating vertex normals it gives ~20% performance improvement.
Now vertex normal calculation only needs to perform a single pass on the
mesh vertices when called after tessellation.
Extended versions of normal & looptri update functions have been added:
- BM_mesh_calc_tessellation_ex
- BM_mesh_normals_update_ex
Most callers don't need to be aware of this detail by using:
- BKE_editmesh_looptri_and_normals_calc
- BKE_editmesh_looptri_and_normals_calc_with_partial
- EDBM_update also takes advantage of this,
where calling EDBM_update with calc_looptri & calc_normals
enabled uses the faster normal updating logic.
===================================================================
M source/blender/blenkernel/BKE_editmesh.h
M source/blender/blenkernel/intern/editmesh.c
M source/blender/bmesh/intern/bmesh_mesh_normals.c
M source/blender/bmesh/intern/bmesh_mesh_normals.h
M source/blender/bmesh/intern/bmesh_mesh_tessellate.c
M source/blender/bmesh/intern/bmesh_mesh_tessellate.h
M source/blender/editors/include/ED_mesh.h
M source/blender/editors/mesh/editmesh_utils.c
M source/blender/editors/object/object_edit.c
M source/blender/editors/object/object_hook.c
M source/blender/editors/object/object_relations.c
M source/blender/editors/transform/transform_convert_mesh.c
M source/blender/editors/transform/transform_convert_mesh_skin.c
M source/blender/makesrna/intern/rna_object.c
===================================================================
diff --git a/source/blender/blenkernel/BKE_editmesh.h b/source/blender/blenkernel/BKE_editmesh.h
index 3a1eedfd807..075a9bc0eac 100644
--- a/source/blender/blenkernel/BKE_editmesh.h
+++ b/source/blender/blenkernel/BKE_editmesh.h
@@ -34,6 +34,7 @@ extern "C" {
struct BMLoop;
struct BMesh;
struct BMPartialUpdate;
+struct BMeshCalcTessellation_Params;
struct BoundBox;
struct Depsgraph;
struct Mesh;
@@ -85,8 +86,17 @@ typedef struct BMEditMesh {
} BMEditMesh;
/* editmesh.c */
+void BKE_editmesh_looptri_calc_ex(BMEditMesh *em,
+ const struct BMeshCalcTessellation_Params *params);
void BKE_editmesh_looptri_calc(BMEditMesh *em);
+void BKE_editmesh_looptri_calc_with_partial_ex(BMEditMesh *em,
+ struct BMPartialUpdate *bmpinfo,
+ const struct BMeshCalcTessellation_Params *params);
void BKE_editmesh_looptri_calc_with_partial(BMEditMesh *em, struct BMPartialUpdate *bmpinfo);
+void BKE_editmesh_looptri_and_normals_calc_with_partial(BMEditMesh *em,
+ struct BMPartialUpdate *bmpinfo);
+
+void BKE_editmesh_looptri_and_normals_calc(BMEditMesh *em);
BMEditMesh *BKE_editmesh_create(BMesh *bm, const bool do_tessellate);
BMEditMesh *BKE_editmesh_copy(BMEditMesh *em);
diff --git a/source/blender/blenkernel/intern/editmesh.c b/source/blender/blenkernel/intern/editmesh.c
index 472de1f3c77..b908df267c4 100644
--- a/source/blender/blenkernel/intern/editmesh.c
+++ b/source/blender/blenkernel/intern/editmesh.c
@@ -96,7 +96,8 @@ BMEditMesh *BKE_editmesh_from_object(Object *ob)
return ((Mesh *)ob->data)->edit_mesh;
}
-static void editmesh_tessface_calc_intern(BMEditMesh *em)
+static void editmesh_tessface_calc_intern(BMEditMesh *em,
+ const struct BMeshCalcTessellation_Params *params)
{
/* allocating space before calculating the tessellation */
@@ -130,12 +131,13 @@ static void editmesh_tessface_calc_intern(BMEditMesh *em)
em->tottri = looptris_tot;
/* after allocating the em->looptris, we're ready to tessellate */
- BM_mesh_calc_tessellation(em->bm, em->looptris);
+ BM_mesh_calc_tessellation_ex(em->bm, em->looptris, params);
}
-void BKE_editmesh_looptri_calc(BMEditMesh *em)
+void BKE_editmesh_looptri_calc_ex(BMEditMesh *em,
+ const struct BMeshCalcTessellation_Params *params)
{
- editmesh_tessface_calc_intern(em);
+ editmesh_tessface_calc_intern(em, params);
/* commented because editbmesh_build_data() ensures we get tessfaces */
#if 0
@@ -149,12 +151,58 @@ void BKE_editmesh_looptri_calc(BMEditMesh *em)
#endif
}
-void BKE_editmesh_looptri_calc_with_partial(BMEditMesh *em, struct BMPartialUpdate *bmpinfo)
+void BKE_editmesh_looptri_calc(BMEditMesh *em)
+{
+ BKE_editmesh_looptri_calc_ex(em,
+ &(const struct BMeshCalcTessellation_Params){
+ .face_normals = false,
+ });
+}
+
+/**
+ * Performing the face normal calculation at the same time as tessellation
+ * gives a reasonable performance boost (approx ~20% faster).
+ */
+void BKE_editmesh_looptri_and_normals_calc(BMEditMesh *em)
+{
+ BKE_editmesh_looptri_calc_ex(em,
+ &(const struct BMeshCalcTessellation_Params){
+ .face_normals = true,
+ });
+ BM_mesh_normals_update_ex(em->bm,
+ &(const struct BMeshNormalsUpdate_Params){
+ .face_normals = false,
+ });
+}
+
+void BKE_editmesh_looptri_calc_with_partial_ex(BMEditMesh *em,
+ struct BMPartialUpdate *bmpinfo,
+ const struct BMeshCalcTessellation_Params *params)
{
BLI_assert(em->tottri == poly_to_tri_count(em->bm->totface, em->bm->totloop));
BLI_assert(em->looptris != NULL);
- BM_mesh_calc_tessellation_with_partial(em->bm, em->looptris, bmpinfo);
+ BM_mesh_calc_tessellation_with_partial_ex(em->bm, em->looptris, bmpinfo, params);
+}
+
+void BKE_editmesh_looptri_calc_with_partial(BMEditMesh *em, struct BMPartialUpdate *bmpinfo)
+{
+ BKE_editmesh_looptri_calc_with_partial_ex(em, bmpinfo, false);
+}
+
+void BKE_editmesh_looptri_and_normals_calc_with_partial(BMEditMesh *em,
+ struct BMPartialUpdate *bmpinfo)
+{
+ BKE_editmesh_looptri_calc_with_partial_ex(em,
+ bmpinfo,
+ &(const struct BMeshCalcTessellation_Params){
+ .face_normals = true,
+ });
+ BM_mesh_normals_update_with_partial_ex(em->bm,
+ bmpinfo,
+ &(const struct BMeshNormalsUpdate_Params){
+ .face_normals = false,
+ });
}
void BKE_editmesh_free_derivedmesh(BMEditMesh *em)
diff --git a/source/blender/bmesh/intern/bmesh_mesh_normals.c b/source/blender/bmesh/intern/bmesh_mesh_normals.c
index bf30f3a52e1..bddd3da98b7 100644
--- a/source/blender/bmesh/intern/bmesh_mesh_normals.c
+++ b/source/blender/bmesh/intern/bmesh_mesh_normals.c
@@ -240,19 +240,29 @@ static void bm_face_calc_normals_cb(void *UNUSED(userdata),
*
* Updates the normals of a mesh.
*/
-void BM_mesh_normals_update(BMesh *bm)
+void BM_mesh_normals_update_ex(BMesh *bm, const struct BMeshNormalsUpdate_Params *params)
{
- /* Calculate all face normals. */
- TaskParallelSettings settings;
- BLI_parallel_mempool_settings_defaults(&settings);
- settings.use_threading = bm->totedge >= BM_OMP_LIMIT;
+ if (params->face_normals) {
+ /* Calculate all face normals. */
+ TaskParallelSettings settings;
+ BLI_parallel_mempool_settings_defaults(&settings);
+ settings.use_threading = bm->totedge >= BM_OMP_LIMIT;
- BM_iter_parallel(bm, BM_FACES_OF_MESH, bm_face_calc_normals_cb, NULL, &settings);
+ BM_iter_parallel(bm, BM_FACES_OF_MESH, bm_face_calc_normals_cb, NULL, &settings);
+ }
/* Add weighted face normals to vertices, and normalize vert normals. */
bm_mesh_verts_calc_normals(bm, NULL, NULL, NULL);
}
+void BM_mesh_normals_update(BMesh *bm)
+{
+ BM_mesh_normals_update_ex(bm,
+ &(const struct BMeshNormalsUpdate_Params){
+ .face_normals = true,
+ });
+}
+
/** \} */
/* -------------------------------------------------------------------- */
@@ -277,7 +287,9 @@ static void bm_partial_verts_parallel_range_calc_normal_cb(
* A version of #BM_mesh_normals_update that updates a subset of geometry,
* used to avoid the overhead of updating everything.
*/
-void BM_mesh_normals_update_with_partial(BMesh *UNUSED(bm), const BMPartialUpdate *bmpinfo)
+void BM_mesh_normals_update_with_partial_ex(BMesh *UNUSED(bm),
+ const BMPartialUpdate *bmpinfo,
+ const struct BMeshNormalsUpdate_Params *params)
{
BLI_assert(bmpinfo->params.do_normals);
@@ -290,14 +302,25 @@ void BM_mesh_normals_update_with_partial(BMesh *UNUSED(bm), const BMPartialUpdat
BLI_parallel_range_settings_defaults(&settings);
/* Faces. */
- BLI_task_parallel_range(
- 0, faces_len, faces, bm_partial_faces_parallel_range_calc_normals_cb, &settings);
+ if (params->face_normals) {
+ BLI_task_parallel_range(
+ 0, faces_len, faces, bm_partial_faces_parallel_range_calc_normals_cb, &settings);
+ }
/* Verts. */
BLI_task_parallel_range(
0, verts_len, verts, bm_partial_verts_parallel_range_calc_normal_cb, &settings);
}
+void BM_mesh_normals_update_with_partial(BMesh *bm, const BMPartialUpdate *bmpinfo)
+{
+ BM_mesh_normals_update_with_partial_ex(bm,
+ bmpinfo,
+ &(const struct BMeshNormalsUpdate_Params){
+ .face_normals = true,
+ });
+}
+
/** \} */
/* -------------------------------------------------------------------- */
diff --git a/source/blender/bmesh/intern/bmesh_mesh_normals.h b/source/blender/bmesh/intern/bmesh_mesh_normals.h
index 41191340e9e..ecd627d4bfe 100644
--- a/source/blender/bmesh/intern/bmesh_mesh_normals.h
+++ b/source/blender/bmesh/intern/bmesh_mesh_normals.h
@@ -22,7 +22,19 @@
#include "bmesh_class.h"
+struct BMeshNormalsUpdate_Params {
+ /**
+ * When calculating tessellation as well as normals, tessellate & calculate face normals
+ * for improved performance. See #BMeshCalcTessellation_Params
+ */
+ bool face_normals;
+};
+
+void BM_mesh_normals_update_ex(BMesh *bm, const struct BMeshNormalsUpdate_Params *param);
void BM_mesh_normals_update(BMesh *bm);
+void BM_mesh_normals_update_with_partial_ex(BMesh *bm,
+ const struct BMPartialUpdate *bmpinfo,
+ const struct BMeshNormalsUpdate_Params *param);
void BM_mesh_normals_update_with_partial(BMesh *bm, const struct BMPartialUpdate *bmpinfo);
void BM_verts_calc_normal_vcos(BMesh *bm,
diff --git a/source/blender/bmesh/intern/bmesh_mesh_tessellate.c b/source/blender/bmesh/intern/bmesh_mesh_tessellate.c
index 7a95e52ce25..4092ad22ef9 100644
--- a/source/blender/bmesh/intern/bmesh_mesh_tessellate.c
+++ b/source/blender/bmesh/intern/bmesh_mesh_tessellate.c
@@ -50,9 +50,13 @@
/** \name Default Mesh Tessellation
* \{ */
-static int mesh_calc_tessellation_for_face(BMLoop *(*looptris)[3],
- BMFace *efa,
- MemArena **pf_arena_p)
+/**
+ * \param face_normal: This will be optimized out as a constant.
+ */
+BLI_INLINE int mesh_calc_tessellation_for_face_impl(BMLoop *(*looptris)[3],
+
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list