Commit: a3ac91da27dd80a98a1c4674c52170e84bff83a3
Author: Alexander Gavrilov
Date:   Wed Dec 28 23:39:36 2022 +0200
Branches: master
https://developer.blender.org/rBa3ac91da27dd80a98a1c4674c52170e84bff83a3

Cloth: share self and object collision BVH trees when possible.

Both cloth object collision and self collision use a BVH tree
representing the current cloth shape. The only difference between
them is the epsilon threshold value.

If these values are the same, it is possible to use the same tree
for both uses, thus easily reducing the overhead in the case when
both collision modes are used by the same cloth object.

Differential Revision: https://developer.blender.org/D16914

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

M       source/blender/blenkernel/BKE_cloth.h
M       source/blender/blenkernel/intern/cloth.cc
M       source/blender/blenkernel/intern/collision.c

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

diff --git a/source/blender/blenkernel/BKE_cloth.h 
b/source/blender/blenkernel/BKE_cloth.h
index 8185e1883a9..d26a96bea21 100644
--- a/source/blender/blenkernel/BKE_cloth.h
+++ b/source/blender/blenkernel/BKE_cloth.h
@@ -72,7 +72,7 @@ typedef struct Cloth {
   unsigned char pad2;
   short pad3;
   struct BVHTree *bvhtree;     /* collision tree for this cloth object */
-  struct BVHTree *bvhselftree; /* collision tree for this cloth object */
+  struct BVHTree *bvhselftree; /* collision tree for this cloth object (may be 
same as bvhtree) */
   struct MVertTri *tri;
   struct Implicit_Data *implicit; /* our implicit solver connects to this 
pointer */
   struct EdgeSet *edgeset;        /* used for selfcollisions */
diff --git a/source/blender/blenkernel/intern/cloth.cc 
b/source/blender/blenkernel/intern/cloth.cc
index 4f28bf5157c..fe9117b4713 100644
--- a/source/blender/blenkernel/intern/cloth.cc
+++ b/source/blender/blenkernel/intern/cloth.cc
@@ -461,7 +461,7 @@ void cloth_free_modifier(ClothModifierData *clmd)
       BLI_bvhtree_free(cloth->bvhtree);
     }
 
-    if (cloth->bvhselftree) {
+    if (cloth->bvhselftree && cloth->bvhselftree != cloth->bvhtree) {
       BLI_bvhtree_free(cloth->bvhselftree);
     }
 
@@ -538,7 +538,7 @@ void cloth_free_modifier_extern(ClothModifierData *clmd)
       BLI_bvhtree_free(cloth->bvhtree);
     }
 
-    if (cloth->bvhselftree) {
+    if (cloth->bvhselftree && cloth->bvhselftree != cloth->bvhtree) {
       BLI_bvhtree_free(cloth->bvhselftree);
     }
 
@@ -820,7 +820,14 @@ static bool cloth_from_object(
   }
 
   clmd->clothObject->bvhtree = bvhtree_build_from_cloth(clmd, 
clmd->coll_parms->epsilon);
-  clmd->clothObject->bvhselftree = bvhtree_build_from_cloth(clmd, 
clmd->coll_parms->selfepsilon);
+
+  if (compare_ff(clmd->coll_parms->selfepsilon, clmd->coll_parms->epsilon, 
1e-6f)) {
+    /* Share the BVH tree if the epsilon is the same. */
+    clmd->clothObject->bvhselftree = clmd->clothObject->bvhtree;
+  }
+  else {
+    clmd->clothObject->bvhselftree = bvhtree_build_from_cloth(clmd, 
clmd->coll_parms->selfepsilon);
+  }
 
   return true;
 }
diff --git a/source/blender/blenkernel/intern/collision.c 
b/source/blender/blenkernel/intern/collision.c
index bf814b7c595..cf0af615b6f 100644
--- a/source/blender/blenkernel/intern/collision.c
+++ b/source/blender/blenkernel/intern/collision.c
@@ -1559,6 +1559,7 @@ int cloth_bvh_collision(
   BVHTreeOverlap **overlap_obj = NULL;
   uint coll_count_self = 0;
   BVHTreeOverlap *overlap_self = NULL;
+  bool bvh_updated = false;
 
   if ((clmd->sim_parms->flags & CLOTH_SIMSETTINGS_FLAG_COLLOBJ) || cloth_bvh 
== NULL) {
     return 0;
@@ -1569,6 +1570,7 @@ int cloth_bvh_collision(
 
   if (clmd->coll_parms->flags & CLOTH_COLLSETTINGS_FLAG_ENABLED) {
     bvhtree_update_from_cloth(clmd, false, false);
+    bvh_updated = true;
 
     /* Enable self collision if this is a hair sim */
     const bool is_hair = (clmd->hairdata != NULL);
@@ -1605,7 +1607,9 @@ int cloth_bvh_collision(
   }
 
   if (clmd->coll_parms->flags & CLOTH_COLLSETTINGS_FLAG_SELF) {
-    bvhtree_update_from_cloth(clmd, false, true);
+    if (cloth->bvhselftree != cloth->bvhtree || !bvh_updated) {
+      bvhtree_update_from_cloth(clmd, false, true);
+    }
 
     overlap_self = BLI_bvhtree_overlap_self(
         cloth->bvhselftree, &coll_count_self, cloth_bvh_self_overlap_cb, clmd);

_______________________________________________
Bf-blender-cvs mailing list
Bf-blender-cvs@blender.org
List details, subscription details or unsubscribe:
https://lists.blender.org/mailman/listinfo/bf-blender-cvs

Reply via email to