Sculpt: Fix creation of repeated constraints in the Cloth Brush
Previously, constraints were added multiple times from different vertices. This adds a GSet to check that the same constraint is not being added twice when iterating over the neighbors of two different vertices. Reviewed By: zeddb Differential Revision: https://developer.blender.org/D8007
This commit is contained in:
parent
fe3ca3f6ce
commit
23d0361b30
|
@ -24,6 +24,7 @@
|
|||
* \ingroup bke
|
||||
*/
|
||||
|
||||
#include "BLI_ghash.h"
|
||||
#include "BLI_utildefines.h"
|
||||
#include "DNA_object_enums.h"
|
||||
|
||||
|
@ -268,6 +269,7 @@ typedef struct SculptClothLengthConstraint {
|
|||
typedef struct SculptClothSimulation {
|
||||
SculptClothLengthConstraint *length_constraints;
|
||||
int tot_length_constraints;
|
||||
GSet *created_length_constraints;
|
||||
int capacity_length_constraints;
|
||||
float *length_constraint_tweak;
|
||||
|
||||
|
|
|
@ -106,6 +106,27 @@
|
|||
#define CLOTH_MAX_CONSTRAINTS_PER_VERTEX 1024
|
||||
#define CLOTH_SIMULATION_TIME_STEP 0.01f
|
||||
|
||||
static void cloth_brush_constraint_key_get(int r_key[2], const int v1, const int v2)
|
||||
{
|
||||
if (v1 < v2) {
|
||||
r_key[0] = v1;
|
||||
r_key[1] = v2;
|
||||
}
|
||||
else {
|
||||
r_key[0] = v2;
|
||||
r_key[1] = v1;
|
||||
}
|
||||
}
|
||||
|
||||
static bool cloth_brush_sim_has_length_constraint(SculptClothSimulation *cloth_sim,
|
||||
const int v1,
|
||||
const int v2)
|
||||
{
|
||||
int constraint[2];
|
||||
cloth_brush_constraint_key_get(constraint, v1, v2);
|
||||
return BLI_gset_haskey(cloth_sim->created_length_constraints, constraint);
|
||||
}
|
||||
|
||||
static void cloth_brush_add_length_constraint(SculptSession *ss,
|
||||
SculptClothSimulation *cloth_sim,
|
||||
const int v1,
|
||||
|
@ -126,6 +147,11 @@ static void cloth_brush_add_length_constraint(SculptSession *ss,
|
|||
sizeof(SculptClothLengthConstraint),
|
||||
"length constraints");
|
||||
}
|
||||
|
||||
/* Add the constraint to the GSet to avoid creating it again. */
|
||||
int constraint[2];
|
||||
cloth_brush_constraint_key_get(constraint, v1, v2);
|
||||
BLI_gset_add(cloth_sim->created_length_constraints, constraint);
|
||||
}
|
||||
|
||||
static void do_cloth_brush_build_constraints_task_cb_ex(
|
||||
|
@ -159,7 +185,8 @@ static void do_cloth_brush_build_constraints_task_cb_ex(
|
|||
|
||||
for (int c_i = 0; c_i < tot_indices; c_i++) {
|
||||
for (int c_j = 0; c_j < tot_indices; c_j++) {
|
||||
if (c_i != c_j) {
|
||||
if (c_i != c_j && !cloth_brush_sim_has_length_constraint(
|
||||
data->cloth_sim, build_indices[c_i], build_indices[c_j])) {
|
||||
cloth_brush_add_length_constraint(
|
||||
ss, data->cloth_sim, build_indices[c_i], build_indices[c_j]);
|
||||
}
|
||||
|
@ -445,6 +472,9 @@ static void cloth_brush_build_nodes_constraints(Sculpt *sd,
|
|||
TaskParallelSettings settings;
|
||||
BKE_pbvh_parallel_range_settings(&settings, false, totnode);
|
||||
|
||||
cloth_sim->created_length_constraints = BLI_gset_new(
|
||||
BLI_ghashutil_inthash_v2_p, BLI_ghashutil_inthash_v2_cmp, "created length constraints");
|
||||
|
||||
SculptThreadedTaskData build_constraints_data = {
|
||||
.sd = sd,
|
||||
.ob = ob,
|
||||
|
@ -456,6 +486,8 @@ static void cloth_brush_build_nodes_constraints(Sculpt *sd,
|
|||
};
|
||||
BLI_task_parallel_range(
|
||||
0, totnode, &build_constraints_data, do_cloth_brush_build_constraints_task_cb_ex, &settings);
|
||||
|
||||
BLI_gset_free(cloth_sim->created_length_constraints, NULL);
|
||||
}
|
||||
|
||||
static void cloth_brush_satisfy_constraints(SculptSession *ss,
|
||||
|
|
Loading…
Reference in New Issue