Commit: 887dfc298d14b994cfc3adba55f6f9a149ad31d9
Author: Luca Rood
Date:   Thu Jan 5 20:48:48 2017 -0200
Branches: cloth-improvements
https://developer.blender.org/rB887dfc298d14b994cfc3adba55f6f9a149ad31d9

Refactor/Optimization: Integrate bend springs into struct/shear

A bending spring runs along each structural and shearing spring. Taking
advantage of that, this integrates the required data for both into the
same spring struct instance. This greatly simplifies bending spring
generation code, and also reduces the memory usage for spring storage
in about 40-50%.

This change also fixes minor memory management issues.

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

M       source/blender/blenkernel/BKE_cloth.h
M       source/blender/blenkernel/intern/cloth.c
M       source/blender/physics/intern/BPH_mass_spring.cpp

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

diff --git a/source/blender/blenkernel/BKE_cloth.h 
b/source/blender/blenkernel/BKE_cloth.h
index 53c2f27..b9507a7 100644
--- a/source/blender/blenkernel/BKE_cloth.h
+++ b/source/blender/blenkernel/BKE_cloth.h
@@ -143,7 +143,8 @@ typedef struct ClothSpring {
        float angoffset;        /* Offset of restang used for plasticity */
        int     type;           /* types defined in BKE_cloth.h ("springType") 
*/
        int     flags;          /* defined in BKE_cloth.h, e.g. deactivated due 
to tearing */
-       float   stiffness;      /* stiffness factor from the vertex groups */
+       float lin_stiffness;    /* linear stiffness factor from the vertex 
groups */
+       float ang_stiffness;    /* angular stiffness factor from the vertex 
groups */
        
        /* angular bending spring target and derivatives */
        float target[3];
diff --git a/source/blender/blenkernel/intern/cloth.c 
b/source/blender/blenkernel/intern/cloth.c
index 70b0359..9a35e52 100644
--- a/source/blender/blenkernel/intern/cloth.c
+++ b/source/blender/blenkernel/intern/cloth.c
@@ -65,9 +65,8 @@ static int cloth_build_springs ( ClothModifierData *clmd, 
DerivedMesh *dm );
 static void cloth_apply_vgroup ( ClothModifierData *clmd, DerivedMesh *dm );
 
 typedef struct BendSpringRef {
-       int set;
-       int index;
-       LinkNode **spring;
+       int index, polys;
+       ClothSpring *spring;
 } BendSpringRef;
 
 /******************************************************************************
@@ -543,8 +542,10 @@ void cloth_free_modifier(ClothModifierData *clmd )
                        while (search) {
                                ClothSpring *spring = search->link;
 
-                               if (spring->type == CLOTH_SPRING_TYPE_BENDING) {
+                               if (spring->pa != NULL) {
                                        MEM_freeN(spring->pa);
+                               }
+                               if (spring->pb != NULL) {
                                        MEM_freeN(spring->pb);
                                }
 
@@ -614,7 +615,7 @@ void cloth_free_modifier_extern(ClothModifierData *clmd )
                        while (search) {
                                ClothSpring *spring = search->link;
 
-                               if (spring->type == CLOTH_SPRING_TYPE_BENDING) {
+                               if (spring->type & CLOTH_SPRING_TYPE_BENDING) {
                                        MEM_freeN(spring->pa);
                                        MEM_freeN(spring->pb);
                                }
@@ -993,7 +994,7 @@ int cloth_add_spring(ClothModifierData *clmd, unsigned int 
indexA, unsigned int
                spring->restlen =  restlength;
                spring->type = spring_type;
                spring->flags = 0;
-               spring->stiffness = 0;
+               spring->lin_stiffness = 0.0f;
                
                cloth->numsprings++;
        
@@ -1023,7 +1024,7 @@ static void cloth_free_errorsprings(Cloth *cloth, 
LinkNodePair *edgelist)
                while (search) {
                        ClothSpring *spring = search->link;
 
-                       if (spring->type == CLOTH_SPRING_TYPE_BENDING) {
+                       if (spring->type & CLOTH_SPRING_TYPE_BENDING) {
                                MEM_freeN(spring->pa);
                                MEM_freeN(spring->pb);
                        }
@@ -1235,16 +1236,17 @@ static void cloth_update_springs( ClothModifierData 
*clmd )
        while (search) {
                ClothSpring *spring = search->link;
 
-               spring->stiffness = 0.0f;
+               spring->lin_stiffness = 0.0f;
 
-               if (spring->type == CLOTH_SPRING_TYPE_STRUCTURAL) {
-                       spring->stiffness = 
(cloth->verts[spring->kl].struct_stiff + cloth->verts[spring->ij].struct_stiff) 
/ 2.0f;
+               if (spring->type & CLOTH_SPRING_TYPE_BENDING) {
+                       spring->ang_stiffness = 
(cloth->verts[spring->kl].bend_stiff + cloth->verts[spring->ij].bend_stiff) / 
2.0f;
                }
-               else if (spring->type == CLOTH_SPRING_TYPE_SHEAR) {
-                       spring->stiffness = 
(cloth->verts[spring->kl].shear_stiff + cloth->verts[spring->ij].shear_stiff) / 
2.0f;
+
+               if (spring->type & CLOTH_SPRING_TYPE_STRUCTURAL) {
+                       spring->lin_stiffness = 
(cloth->verts[spring->kl].struct_stiff + cloth->verts[spring->ij].struct_stiff) 
/ 2.0f;
                }
-               else if (spring->type == CLOTH_SPRING_TYPE_BENDING) {
-                       spring->stiffness = 
(cloth->verts[spring->kl].bend_stiff + cloth->verts[spring->ij].bend_stiff) / 
2.0f;
+               else if (spring->type & CLOTH_SPRING_TYPE_SHEAR) {
+                       spring->lin_stiffness = 
(cloth->verts[spring->kl].shear_stiff + cloth->verts[spring->ij].shear_stiff) / 
2.0f;
                }
                else if (spring->type == CLOTH_SPRING_TYPE_BENDING_HAIR) {
                        ClothVertex *v1 = &cloth->verts[spring->ij];
@@ -1254,7 +1256,7 @@ static void cloth_update_springs( ClothModifierData *clmd 
)
                                v1->bend_stiff = 
clmd->hairdata[spring->ij].bending_stiffness;
                                v2->bend_stiff = 
clmd->hairdata[spring->kl].bending_stiffness;
                        }
-                       spring->stiffness = (v1->bend_stiff + v2->bend_stiff) / 
2.0f;
+                       spring->lin_stiffness = (v1->bend_stiff + 
v2->bend_stiff) / 2.0f;
                }
                else if (spring->type == CLOTH_SPRING_TYPE_GOAL) {
                        /* Warning: Appending NEW goal springs does not work 
because implicit solver would need reset! */
@@ -1319,12 +1321,12 @@ static void cloth_update_spring_lengths( 
ClothModifierData *clmd, DerivedMesh *d
 
                        spring->restlen = 
len_v3v3(cloth->verts[spring->kl].xrest, cloth->verts[spring->ij].xrest) * 
shrink_factor;
 
-                       if ( spring->type == CLOTH_SPRING_TYPE_BENDING ) {
+                       if ( spring->type & CLOTH_SPRING_TYPE_BENDING ) {
                                spring->restang = spring_angle(cloth->verts, 
spring->ij, spring->kl, spring->pa, spring->pb, spring->la, spring->lb);
                        }
                }
 
-               if ( spring->type == CLOTH_SPRING_TYPE_STRUCTURAL ) {
+               if ( spring->type & CLOTH_SPRING_TYPE_STRUCTURAL ) {
                        clmd->sim_parms->avg_spring_len += spring->restlen;
                        cloth->verts[spring->ij].avg_spring_len += 
spring->restlen;
                        cloth->verts[spring->kl].avg_spring_len += 
spring->restlen;
@@ -1381,7 +1383,7 @@ void cloth_parallel_transport_hair_frame(float mat[3][3], 
const float dir_old[3]
 }
 
 /* add a shear and a bend spring between two verts within a poly */
-BLI_INLINE bool add_shear_bend_spring(ClothModifierData *clmd, LinkNodePair 
*edgelist, BendSpringRef *spring_ref,
+BLI_INLINE bool add_shear_bend_spring(ClothModifierData *clmd, LinkNodePair 
*edgelist,
                                       const MLoop *mloop, const MPoly *mpoly, 
int i, int j, int k)
 {
        Cloth *cloth = clmd->clothObject;
@@ -1390,7 +1392,7 @@ BLI_INLINE bool add_shear_bend_spring(ClothModifierData 
*clmd, LinkNodePair *edg
        float shrink_factor;
        int x, y;
 
-       /* shear spring */
+       /* Combined shear/bend properties */
 
        spring = (ClothSpring *)MEM_callocN(sizeof(ClothSpring), "cloth 
spring");
 
@@ -1406,35 +1408,28 @@ BLI_INLINE bool add_shear_bend_spring(ClothModifierData 
*clmd, LinkNodePair *edg
        shrink_factor = cloth_shrink_factor(clmd, cloth->verts, spring->ij, 
spring->kl);
        spring->restlen = len_v3v3(cloth->verts[spring->kl].xrest, 
cloth->verts[spring->ij].xrest) * shrink_factor;
        spring->lenfact = 1.0f;
-       spring->type = CLOTH_SPRING_TYPE_SHEAR;
-       spring->stiffness = (cloth->verts[spring->kl].shear_stiff + 
cloth->verts[spring->ij].shear_stiff) / 2.0f;
+       spring->type |= CLOTH_SPRING_TYPE_SHEAR;
+       spring->lin_stiffness = (cloth->verts[spring->kl].shear_stiff + 
cloth->verts[spring->ij].shear_stiff) / 2.0f;
 
        BLI_linklist_append(&edgelist[spring->ij], spring);
        BLI_linklist_append(&edgelist[spring->kl], spring);
 
-       BLI_linklist_prepend(&cloth->springs, spring);
-
-       spring = cloth->springs->next->link;
-
-       if (spring->type == CLOTH_SPRING_TYPE_BENDING && spring->mn != -1) {
-               spring_ref[spring->mn].spring = &cloth->springs->next;
-       }
-
-       /* bending spring */
+       /* Bending specific spring */
 
-       spring = MEM_callocN(sizeof(ClothSpring), "cloth spring");
-
-       if (!spring) {
-               return false;
-       }
-
-       spring->type = CLOTH_SPRING_TYPE_BENDING;
+       spring->type |= CLOTH_SPRING_TYPE_BENDING;
 
        spring->la = k - j + 1;
        spring->lb = mpoly[i].totloop - k + j + 1;
 
        spring->pa = MEM_mallocN(sizeof(*spring->pa) * spring->la, "spring 
poly");
+       if (!spring->pa) {
+               return false;
+       }
+
        spring->pb = MEM_mallocN(sizeof(*spring->pb) * spring->lb, "spring 
poly");
+       if (!spring->pb) {
+               return false;
+       }
 
        tmp_loop = mloop + mpoly[i].loopstart;
 
@@ -1450,17 +1445,11 @@ BLI_INLINE bool add_shear_bend_spring(ClothModifierData 
*clmd, LinkNodePair *edg
                spring->pb[x] = tmp_loop[y].v;
        }
 
-       spring->ij = tmp_loop[j].v;
-       spring->kl = tmp_loop[k].v;
        spring->mn = -1;
 
-       shrink_factor = cloth_shrink_factor(clmd, cloth->verts, spring->ij, 
spring->kl);
-       spring->restlen = len_v3v3(cloth->verts[spring->ij].xrest, 
cloth->verts[spring->kl].xrest) * shrink_factor;
-       spring->lenfact = 1.0f;
-
        spring->restang = spring_angle(cloth->verts, spring->ij, spring->kl, 
spring->pa, spring->pb, spring->la, spring->lb);
 
-       spring->stiffness = (cloth->verts[spring->ij].bend_stiff + 
cloth->verts[spring->kl].bend_stiff) / 2.0f;
+       spring->ang_stiffness = (cloth->verts[spring->ij].bend_stiff + 
cloth->verts[spring->kl].bend_stiff) / 2.0f;
 
        BLI_linklist_prepend(&cloth->springs, spring);
 
@@ -1484,6 +1473,8 @@ static int cloth_build_springs ( ClothModifierData *clmd, 
DerivedMesh *dm )
        LinkNodePair *edgelist;
        EdgeSet *edgeset = NULL;
        LinkNode *search = NULL, *search2 = NULL;
+       BendSpringRef *spring_ref;
+       BendSpringRef *curr_ref;
 
        // error handling
        if ( numedges==0 )
@@ -1497,29 +1488,37 @@ static int cloth_build_springs ( ClothModifierData 
*clmd, DerivedMesh *dm )
        cloth->springs = NULL;
        cloth->edgeset = NULL;
 
+       spring_ref = MEM_callocN(sizeof(*spring_ref) * numedges, "temp bend 
spring reference");
+
+       if (!spring_ref) {
+               return 0;
+       }
+
        edgelist = MEM_callocN(sizeof(*edgelist) * mvert_num, 
"cloth_edgelist_alloc" );
-       
-       if (!edgelist)
+
+       if (!edgelist) {
+               MEM_freeN(spring_ref);
                return 0;
+       }
 
        /* structural springs */
        for ( i = 0; i < numedges; i++ ) {
-               spring = (ClothSpring *)MEM_callocN ( sizeof ( ClothSpring ), 
"cloth spring" );
+               spring = MEM_callocN ( sizeof ( ClothSpring ), "cloth spring" );
 
                if ( spring ) {
                        spring_verts_ordered_set(spring, medge[i].v1, 
medge[i].v2);
                        if (clmd->sim_parms->flags & CLOTH_SIMSETTINGS_FLAG_SEW 
&& medge[i].flag & ME_LOOSEEDGE) {
                                // handle sewing (loose edges will be pulled 
together)
                                spring->restlen = 0.0f;
-                               spring->stiffness = 1.0f;
+                               spring->lin_stiffness = 1.0f;
                                spring->type = CLOTH_SPRING_TYPE_SEWING;
                        }
                        else {
                                shrink_factor = cloth_shrink_factor(clmd, 
cloth->verts, spring->ij, spring->kl);
                                spring->restlen = 
len_v3v3(cloth->verts[spring->kl].xrest, cloth->verts[spring->ij].xrest) * 
shrink_factor;
                                spring->lenfact = 1.0f;
-                               spring->stiffness = 
(cloth->verts[spring->kl].struct_stiff + cloth->verts[spring->ij].struct_stiff) 
/ 2.0f;
-                               spring->type = CLOTH_SPRING_TYPE_STRUCTURAL;
+                               spring->lin_stiffness = (cloth->verts[

@@ Diff output truncated at 10240 characters. @@

_______________________________________________
Bf-blender-cvs mailing list
[email protected]
https://lists.blender.org/mailman/listinfo/bf-blender-cvs

Reply via email to