Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/blenkernel/intern/cloth.c')
-rw-r--r--source/blender/blenkernel/intern/cloth.c210
1 files changed, 105 insertions, 105 deletions
diff --git a/source/blender/blenkernel/intern/cloth.c b/source/blender/blenkernel/intern/cloth.c
index cc1c7260cbc..c5d9472ca4b 100644
--- a/source/blender/blenkernel/intern/cloth.c
+++ b/source/blender/blenkernel/intern/cloth.c
@@ -80,7 +80,7 @@ static void cloth_apply_vgroup ( ClothModifierData *clmd, Mesh *mesh );
* 2. fill object with standard values or with the GUI settings if given
*/
void cloth_init(ClothModifierData *clmd )
-{
+{
/* Initialize our new data structure to reasonable values. */
clmd->sim_parms->gravity[0] = 0.0;
clmd->sim_parms->gravity[1] = 0.0;
@@ -91,7 +91,7 @@ void cloth_init(ClothModifierData *clmd )
clmd->sim_parms->bending = 0.5;
clmd->sim_parms->max_bend = 0.5;
clmd->sim_parms->bending_damping = 0.5;
- clmd->sim_parms->Cdis = 5.0;
+ clmd->sim_parms->Cdis = 5.0;
clmd->sim_parms->Cvi = 1.0;
clmd->sim_parms->mass = 0.3f;
clmd->sim_parms->stepsPerFrame = 5;
@@ -107,7 +107,7 @@ void cloth_init(ClothModifierData *clmd )
clmd->sim_parms->time_scale = 1.0f; /* multiplies cloth speed */
clmd->sim_parms->reset = 0;
clmd->sim_parms->vel_damping = 1.0f; /* 1.0 = no damping, 0.0 = fully dampened */
-
+
clmd->coll_parms->self_friction = 5.0;
clmd->coll_parms->friction = 5.0;
clmd->coll_parms->loop_count = 2;
@@ -155,27 +155,27 @@ static BVHTree *bvhselftree_build_from_cloth (ClothModifierData *clmd, float eps
if (!cloth)
return NULL;
-
+
verts = cloth->verts;
-
+
/* in the moment, return zero if no faces there */
if (!cloth->mvert_num)
return NULL;
-
+
/* create quadtree with k=26 */
bvhtree = BLI_bvhtree_new(cloth->mvert_num, epsilon, 4, 6);
-
+
/* fill tree */
for (i = 0; i < cloth->mvert_num; i++, verts++) {
const float *co;
co = verts->xold;
-
+
BLI_bvhtree_insert(bvhtree, i, co, 1);
}
-
+
/* balance tree */
BLI_bvhtree_balance(bvhtree);
-
+
return bvhtree;
}
@@ -194,10 +194,10 @@ static BVHTree *bvhtree_build_from_cloth (ClothModifierData *clmd, float epsilon
if (!cloth)
return NULL;
-
+
verts = cloth->verts;
vt = cloth->tri;
-
+
/* in the moment, return zero if no faces there */
if (!cloth->tri_num)
return NULL;
@@ -218,23 +218,23 @@ static BVHTree *bvhtree_build_from_cloth (ClothModifierData *clmd, float epsilon
/* balance tree */
BLI_bvhtree_balance(bvhtree);
-
+
return bvhtree;
}
void bvhtree_update_from_cloth(ClothModifierData *clmd, bool moving)
-{
+{
unsigned int i = 0;
Cloth *cloth = clmd->clothObject;
BVHTree *bvhtree = cloth->bvhtree;
ClothVertex *verts = cloth->verts;
const MVertTri *vt;
-
+
if (!bvhtree)
return;
-
+
vt = cloth->tri;
-
+
/* update vertex position in bvh tree */
if (verts && vt) {
for (i = 0; i < cloth->tri_num; i++, vt++) {
@@ -257,25 +257,25 @@ void bvhtree_update_from_cloth(ClothModifierData *clmd, bool moving)
else {
ret = BLI_bvhtree_update_node(bvhtree, i, co[0], NULL, 3);
}
-
+
/* check if tree is already full */
if (ret == false) {
break;
}
}
-
+
BLI_bvhtree_update_tree(bvhtree);
}
}
void bvhselftree_update_from_cloth(ClothModifierData *clmd, bool moving)
-{
+{
unsigned int i = 0;
Cloth *cloth = clmd->clothObject;
BVHTree *bvhtree = cloth->bvhselftree;
ClothVertex *verts = cloth->verts;
const MVertTri *vt;
-
+
if (!bvhtree)
return;
@@ -304,7 +304,7 @@ void bvhselftree_update_from_cloth(ClothModifierData *clmd, bool moving)
break;
}
}
-
+
BLI_bvhtree_update_tree(bvhtree);
}
}
@@ -312,13 +312,13 @@ void bvhselftree_update_from_cloth(ClothModifierData *clmd, bool moving)
void cloth_clear_cache(Object *ob, ClothModifierData *clmd, float framenr)
{
PTCacheID pid;
-
+
BKE_ptcache_id_from_cloth(&pid, ob, clmd);
// don't do anything as long as we're in editmode!
if (pid.cache->edit && ob->mode & OB_MODE_PARTICLE_EDIT)
return;
-
+
BKE_ptcache_id_clear(&pid, PTCACHE_CLEAR_AFTER, framenr);
}
@@ -335,13 +335,13 @@ static int do_init_cloth(Object *ob, ClothModifierData *clmd, Mesh *result, int
modifier_setError(&(clmd->modifier), "Can't initialize cloth");
return 0;
}
-
+
if (clmd->clothObject == NULL) {
BKE_ptcache_invalidate(cache);
modifier_setError(&(clmd->modifier), "Null cloth object");
return 0;
}
-
+
BKE_cloth_solver_set_positions(clmd);
clmd->clothObject->last_frame= MINFRAME-1;
@@ -387,7 +387,7 @@ static int do_step_cloth(struct Depsgraph *depsgraph, Object *ob, ClothModifierD
cloth_update_spring_lengths ( clmd, result );
cloth_update_springs( clmd );
-
+
// TIMEIT_START(cloth_step)
/* call the solver. */
@@ -398,7 +398,7 @@ static int do_step_cloth(struct Depsgraph *depsgraph, Object *ob, ClothModifierD
pdEndEffectors(&effectors);
// printf ( "%f\n", ( float ) tval() );
-
+
return ret;
}
@@ -429,7 +429,7 @@ void clothModifier_do(ClothModifierData *clmd, struct Depsgraph *depsgraph, Scen
cache->last_exact= 0;
cache->flag &= ~PTCACHE_REDO_NEEDED;
}
-
+
// unused in the moment, calculated separately in implicit.c
clmd->sim_parms->dt = clmd->sim_parms->timescale / clmd->sim_parms->stepsPerFrame;
@@ -507,13 +507,13 @@ void clothModifier_do(ClothModifierData *clmd, struct Depsgraph *depsgraph, Scen
void cloth_free_modifier(ClothModifierData *clmd )
{
Cloth *cloth = NULL;
-
+
if ( !clmd )
return;
cloth = clmd->clothObject;
-
+
if ( cloth ) {
BPH_cloth_solver_free(clmd);
@@ -529,12 +529,12 @@ void cloth_free_modifier(ClothModifierData *clmd )
LinkNode *search = cloth->springs;
while (search) {
ClothSpring *spring = search->link;
-
+
MEM_freeN ( spring );
search = search->next;
}
BLI_linklist_free(cloth->springs, NULL);
-
+
cloth->springs = NULL;
}
@@ -544,7 +544,7 @@ void cloth_free_modifier(ClothModifierData *clmd )
// free BVH collision tree
if ( cloth->bvhtree )
BLI_bvhtree_free ( cloth->bvhtree );
-
+
if ( cloth->bvhselftree )
BLI_bvhtree_free ( cloth->bvhselftree );
@@ -554,8 +554,8 @@ void cloth_free_modifier(ClothModifierData *clmd )
if (cloth->edgeset)
BLI_edgeset_free(cloth->edgeset);
-
-
+
+
/*
if (clmd->clothObject->facemarks)
MEM_freeN(clmd->clothObject->facemarks);
@@ -571,12 +571,12 @@ void cloth_free_modifier_extern(ClothModifierData *clmd )
Cloth *cloth = NULL;
if (G.debug_value > 0)
printf("cloth_free_modifier_extern\n");
-
+
if ( !clmd )
return;
cloth = clmd->clothObject;
-
+
if ( cloth ) {
if (G.debug_value > 0)
printf("cloth_free_modifier_extern in\n");
@@ -610,7 +610,7 @@ void cloth_free_modifier_extern(ClothModifierData *clmd )
// free BVH collision tree
if ( cloth->bvhtree )
BLI_bvhtree_free ( cloth->bvhtree );
-
+
if ( cloth->bvhselftree )
BLI_bvhtree_free ( cloth->bvhselftree );
@@ -660,11 +660,11 @@ static void cloth_to_object (Object *ob, ClothModifierData *clmd, float (*verte
int cloth_uses_vgroup(ClothModifierData *clmd)
{
- return (((clmd->sim_parms->flags & CLOTH_SIMSETTINGS_FLAG_SCALING ) ||
+ return (((clmd->sim_parms->flags & CLOTH_SIMSETTINGS_FLAG_SCALING ) ||
(clmd->sim_parms->flags & CLOTH_SIMSETTINGS_FLAG_GOAL ) ||
(clmd->sim_parms->flags & CLOTH_SIMSETTINGS_FLAG_SEW) ||
- (clmd->coll_parms->flags & CLOTH_COLLSETTINGS_FLAG_SELF)) &&
- ((clmd->sim_parms->vgroup_mass>0) ||
+ (clmd->coll_parms->flags & CLOTH_COLLSETTINGS_FLAG_SELF)) &&
+ ((clmd->sim_parms->vgroup_mass>0) ||
(clmd->sim_parms->vgroup_struct>0)||
(clmd->sim_parms->vgroup_bend>0) ||
(clmd->sim_parms->vgroup_shrink>0) ||
@@ -693,7 +693,7 @@ static void cloth_apply_vgroup ( ClothModifierData *clmd, Mesh *mesh )
mvert_num = mesh->totvert;
verts = clothObj->verts;
-
+
if (cloth_uses_vgroup(clmd)) {
for (i = 0; i < mvert_num; i++, verts++) {
@@ -717,21 +717,21 @@ static void cloth_apply_vgroup ( ClothModifierData *clmd, Mesh *mesh )
verts->goal = dvert->dw [j].weight;
/* goalfac= 1.0f; */ /* UNUSED */
-
+
// Kicking goal factor to simplify things...who uses that anyway?
// ABS ( clmd->sim_parms->maxgoal - clmd->sim_parms->mingoal );
-
+
verts->goal = pow4f(verts->goal);
if ( verts->goal >= SOFTGOALSNAP )
verts->flags |= CLOTH_VERT_FLAG_PINNED;
}
-
+
if (clmd->sim_parms->flags & CLOTH_SIMSETTINGS_FLAG_SCALING ) {
if ( dvert->dw[j].def_nr == (clmd->sim_parms->vgroup_struct-1)) {
verts->struct_stiff = dvert->dw [j].weight;
verts->shear_stiff = dvert->dw [j].weight;
}
-
+
if ( dvert->dw[j].def_nr == (clmd->sim_parms->vgroup_bend-1)) {
verts->bend_stiff = dvert->dw [j].weight;
}
@@ -786,7 +786,7 @@ static int cloth_from_object(Object *ob, ClothModifierData *clmd, Mesh *mesh, fl
Cloth *cloth = NULL;
float maxdist = 0;
- // If we have a clothObject, free it.
+ // If we have a clothObject, free it.
if ( clmd->clothObject != NULL ) {
cloth_free_modifier ( clmd );
if (G.debug_value > 0)
@@ -837,9 +837,9 @@ static int cloth_from_object(Object *ob, ClothModifierData *clmd, Mesh *mesh, fl
else
copy_v3_v3(verts->xrest, verts->x);
}
-
+
/* no GUI interface yet */
- verts->mass = clmd->sim_parms->mass;
+ verts->mass = clmd->sim_parms->mass;
verts->impulse_count = 0;
if ( clmd->sim_parms->flags & CLOTH_SIMSETTINGS_FLAG_GOAL )
@@ -859,7 +859,7 @@ static int cloth_from_object(Object *ob, ClothModifierData *clmd, Mesh *mesh, fl
verts->impulse_count = 0;
copy_v3_v3 ( verts->impulse, tnull );
}
-
+
// apply / set vertex groups
// has to be happen before springs are build!
cloth_apply_vgroup (clmd, mesh);
@@ -870,19 +870,19 @@ static int cloth_from_object(Object *ob, ClothModifierData *clmd, Mesh *mesh, fl
printf("cloth_free_modifier cloth_build_springs\n");
return 0;
}
-
+
// init our solver
BPH_cloth_solver_init(ob, clmd);
-
+
if (!first)
BKE_cloth_solver_set_positions(clmd);
clmd->clothObject->bvhtree = bvhtree_build_from_cloth ( clmd, MAX2(clmd->coll_parms->epsilon, clmd->coll_parms->distance_repel) );
-
+
for (i = 0; i < mesh->totvert; i++) {
maxdist = MAX2(maxdist, clmd->coll_parms->selfepsilon* ( cloth->verts[i].avg_spring_len*2.0f));
}
-
+
clmd->clothObject->bvhselftree = bvhselftree_build_from_cloth ( clmd, maxdist );
return 1;
@@ -958,17 +958,17 @@ static void cloth_free_errorsprings(Cloth *cloth, LinkNodePair *edgelist)
LinkNode *search = cloth->springs;
while (search) {
ClothSpring *spring = search->link;
-
+
MEM_freeN ( spring );
search = search->next;
}
BLI_linklist_free(cloth->springs, NULL);
-
+
cloth->springs = NULL;
}
cloth_free_edgelist(edgelist, cloth->mvert_num);
-
+
if (cloth->edgeset) {
BLI_edgeset_free(cloth->edgeset);
cloth->edgeset = NULL;
@@ -981,10 +981,10 @@ static void cloth_hair_update_bending_targets(ClothModifierData *clmd)
LinkNode *search = NULL;
float hair_frame[3][3], dir_old[3], dir_new[3];
int prev_mn; /* to find hair chains */
-
+
if (!clmd->hairdata)
return;
-
+
/* XXX Note: we need to propagate frames from the root up,
* but structural hair springs are stored in reverse order.
* The bending springs however are then inserted in the same
@@ -992,17 +992,17 @@ static void cloth_hair_update_bending_targets(ClothModifierData *clmd)
* This messy situation can be resolved when solver data is
* generated directly from a dedicated hair system.
*/
-
+
prev_mn = -1;
for (search = cloth->springs; search; search = search->next) {
ClothSpring *spring = search->link;
ClothHairData *hair_ij, *hair_kl;
bool is_root = spring->kl != prev_mn;
-
+
if (spring->type != CLOTH_SPRING_TYPE_BENDING_ANG) {
continue;
}
-
+
hair_ij = &clmd->hairdata[spring->ij];
hair_kl = &clmd->hairdata[spring->kl];
if (is_root) {
@@ -1013,39 +1013,39 @@ static void cloth_hair_update_bending_targets(ClothModifierData *clmd)
*/
copy_v3_v3(dir_new, hair_frame[2]);
}
-
+
copy_v3_v3(dir_old, dir_new);
sub_v3_v3v3(dir_new, cloth->verts[spring->mn].x, cloth->verts[spring->kl].x);
normalize_v3(dir_new);
-
+
#if 0
if (clmd->debug_data && (spring->ij == 0 || spring->ij == 1)) {
float a[3], b[3];
-
+
copy_v3_v3(a, cloth->verts[spring->kl].x);
// BKE_sim_debug_data_add_dot(clmd->debug_data, cloth_vert ? cloth_vert->x : key->co, 1, 1, 0, "frames", 8246, p, k);
-
+
mul_v3_v3fl(b, hair_frame[0], clmd->sim_parms->avg_spring_len);
BKE_sim_debug_data_add_vector(clmd->debug_data, a, b, 1, 0, 0, "frames", 8247, spring->kl, spring->mn);
-
+
mul_v3_v3fl(b, hair_frame[1], clmd->sim_parms->avg_spring_len);
BKE_sim_debug_data_add_vector(clmd->debug_data, a, b, 0, 1, 0, "frames", 8248, spring->kl, spring->mn);
-
+
mul_v3_v3fl(b, hair_frame[2], clmd->sim_parms->avg_spring_len);
BKE_sim_debug_data_add_vector(clmd->debug_data, a, b, 0, 0, 1, "frames", 8249, spring->kl, spring->mn);
}
#endif
-
+
/* get local targets for kl/mn vertices by putting rest targets into the current frame,
* then multiply with the rest length to get the actual goals
*/
-
+
mul_v3_m3v3(spring->target, hair_frame, hair_kl->rest_target);
mul_v3_fl(spring->target, spring->restlen);
-
+
/* move frame to next hair segment */
cloth_parallel_transport_hair_frame(hair_frame, dir_old, dir_new);
-
+
prev_mn = spring->mn;
}
}
@@ -1056,10 +1056,10 @@ static void cloth_hair_update_bending_rest_targets(ClothModifierData *clmd)
LinkNode *search = NULL;
float hair_frame[3][3], dir_old[3], dir_new[3];
int prev_mn; /* to find hair roots */
-
+
if (!clmd->hairdata)
return;
-
+
/* XXX Note: we need to propagate frames from the root up,
* but structural hair springs are stored in reverse order.
* The bending springs however are then inserted in the same
@@ -1067,17 +1067,17 @@ static void cloth_hair_update_bending_rest_targets(ClothModifierData *clmd)
* This messy situation can be resolved when solver data is
* generated directly from a dedicated hair system.
*/
-
+
prev_mn = -1;
for (search = cloth->springs; search; search = search->next) {
ClothSpring *spring = search->link;
ClothHairData *hair_ij, *hair_kl;
bool is_root = spring->kl != prev_mn;
-
+
if (spring->type != CLOTH_SPRING_TYPE_BENDING_ANG) {
continue;
}
-
+
hair_ij = &clmd->hairdata[spring->ij];
hair_kl = &clmd->hairdata[spring->kl];
if (is_root) {
@@ -1088,18 +1088,18 @@ static void cloth_hair_update_bending_rest_targets(ClothModifierData *clmd)
*/
copy_v3_v3(dir_new, hair_frame[2]);
}
-
+
copy_v3_v3(dir_old, dir_new);
sub_v3_v3v3(dir_new, cloth->verts[spring->mn].xrest, cloth->verts[spring->kl].xrest);
normalize_v3(dir_new);
-
+
/* dir expressed in the hair frame defines the rest target direction */
copy_v3_v3(hair_kl->rest_target, dir_new);
mul_transposed_m3_v3(hair_frame, hair_kl->rest_target);
-
+
/* move frame to next hair segment */
cloth_parallel_transport_hair_frame(hair_frame, dir_old, dir_new);
-
+
prev_mn = spring->mn;
}
}
@@ -1148,10 +1148,10 @@ static void cloth_update_springs( ClothModifierData *clmd )
spring->flags |= CLOTH_SPRING_FLAG_DEACTIVATE;
}
}
-
+
search = search->next;
}
-
+
cloth_hair_update_bending_targets(clmd);
}
@@ -1243,10 +1243,10 @@ BLI_INLINE void madd_m3_m3fl(float r[3][3], float m[3][3], float f)
void cloth_parallel_transport_hair_frame(float mat[3][3], const float dir_old[3], const float dir_new[3])
{
float rot[3][3];
-
+
/* rotation between segments */
rotation_between_vecs_to_mat3(rot, dir_old, dir_new);
-
+
/* rotate the frame */
mul_m3_m3m3(mat, rot, mat);
}
@@ -1268,7 +1268,7 @@ static int cloth_build_springs ( ClothModifierData *clmd, Mesh *mesh )
LinkNodePair *edgelist;
EdgeSet *edgeset = NULL;
LinkNode *search = NULL, *search2 = NULL;
-
+
// error handling
if ( numedges==0 )
return 0;
@@ -1282,7 +1282,7 @@ static int cloth_build_springs ( ClothModifierData *clmd, Mesh *mesh )
cloth->edgeset = NULL;
edgelist = MEM_callocN(sizeof(*edgelist) * mvert_num, "cloth_edgelist_alloc" );
-
+
if (!edgelist)
return 0;
@@ -1314,7 +1314,7 @@ static int cloth_build_springs ( ClothModifierData *clmd, Mesh *mesh )
spring->flags = 0;
struct_springs++;
-
+
BLI_linklist_prepend ( &cloth->springs, spring );
}
else {
@@ -1325,7 +1325,7 @@ static int cloth_build_springs ( ClothModifierData *clmd, Mesh *mesh )
if (struct_springs_real > 0)
clmd->sim_parms->avg_spring_len /= struct_springs_real;
-
+
for (i = 0; i < mvert_num; i++) {
if (cloth->verts[i].spring_count > 0)
cloth->verts[i].avg_spring_len = cloth->verts[i].avg_spring_len * 0.49f / ((float)cloth->verts[i].spring_count);
@@ -1415,15 +1415,15 @@ static int cloth_build_springs ( ClothModifierData *clmd, Mesh *mesh )
while (search && search2) {
tspring = search->link;
tspring2 = search2->link;
-
+
if (tspring->ij == tspring2->kl) {
spring = (ClothSpring *)MEM_callocN ( sizeof ( ClothSpring ), "cloth spring" );
-
+
if (!spring) {
cloth_free_errorsprings(cloth, edgelist);
return 0;
}
-
+
spring->ij = tspring2->ij;
spring->kl = tspring->ij;
spring->mn = tspring->kl;
@@ -1431,10 +1431,10 @@ static int cloth_build_springs ( ClothModifierData *clmd, Mesh *mesh )
spring->type = CLOTH_SPRING_TYPE_BENDING_ANG;
spring->stiffness = (cloth->verts[spring->kl].bend_stiff + cloth->verts[spring->ij].bend_stiff) / 2.0f;
bend_springs++;
-
+
BLI_linklist_prepend ( &cloth->springs, spring );
}
-
+
search = search->next;
search2 = search2->next;
}
@@ -1452,33 +1452,33 @@ static int cloth_build_springs ( ClothModifierData *clmd, Mesh *mesh )
while (search && search2) {
tspring = search->link;
tspring2 = search2->link;
-
+
if (tspring->ij == tspring2->kl) {
spring = (ClothSpring *)MEM_callocN ( sizeof ( ClothSpring ), "cloth spring" );
-
+
if (!spring) {
cloth_free_errorsprings(cloth, edgelist);
return 0;
}
-
+
spring->ij = tspring2->ij;
spring->kl = tspring->kl;
spring->restlen = len_v3v3(cloth->verts[spring->kl].xrest, cloth->verts[spring->ij].xrest);
spring->type = CLOTH_SPRING_TYPE_BENDING;
spring->stiffness = (cloth->verts[spring->kl].bend_stiff + cloth->verts[spring->ij].bend_stiff) / 2.0f;
bend_springs++;
-
+
BLI_linklist_prepend ( &cloth->springs, spring );
}
-
+
search = search->next;
search2 = search2->next;
}
}
-
+
cloth_hair_update_bending_rest_targets(clmd);
}
-
+
/* note: the edges may already exist so run reinsert */
/* insert other near springs in edgeset AFTER bending springs are calculated (for selfcolls) */
@@ -1492,10 +1492,10 @@ static int cloth_build_springs ( ClothModifierData *clmd, Mesh *mesh )
BLI_edgeset_add(edgeset, mloop[mpoly[i].loopstart + 1].v, mloop[mpoly[i].loopstart + 3].v);
}
}
-
-
+
+
cloth->numsprings = struct_springs + shear_springs + bend_springs;
-
+
cloth_free_edgelist(edgelist, mvert_num);
#if 0