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:
authorPablo Dobarro <pablodp606@gmail.com>2020-08-17 23:18:26 +0300
committerPablo Dobarro <pablodp606@gmail.com>2020-08-18 13:17:14 +0300
commitdb4e08dfdc9c90680e4722e02a3c6f35d51f124f (patch)
tree2791ce20d576054b2c6e140cecd225d82917e1f3 /source/blender/editors/sculpt_paint
parentc82166ffcd88dcb5fe5b694faa33043f1a4979b4 (diff)
Sculpt: Expose the functions to create and init a SculptClothSimulation
This will be used for new features like supporting cloth deformation in other brushes and tools outside of the cloth brush code. No functional changes. Reviewed By: sergey Differential Revision: https://developer.blender.org/D8602
Diffstat (limited to 'source/blender/editors/sculpt_paint')
-rw-r--r--source/blender/editors/sculpt_paint/sculpt_cloth.c218
-rw-r--r--source/blender/editors/sculpt_paint/sculpt_intern.h24
2 files changed, 137 insertions, 105 deletions
diff --git a/source/blender/editors/sculpt_paint/sculpt_cloth.c b/source/blender/editors/sculpt_paint/sculpt_cloth.c
index 4070822a0a8..bdc7d7520ea 100644
--- a/source/blender/editors/sculpt_paint/sculpt_cloth.c
+++ b/source/blender/editors/sculpt_paint/sculpt_cloth.c
@@ -505,49 +505,6 @@ static ListBase *cloth_brush_collider_cache_create(Depsgraph *depsgraph)
return cache;
}
-static SculptClothSimulation *cloth_brush_simulation_create(SculptSession *ss,
- Brush *brush,
- const float cloth_mass,
- const float cloth_damping,
- const bool use_collisions)
-{
- const int totverts = SCULPT_vertex_count_get(ss);
- SculptClothSimulation *cloth_sim;
-
- cloth_sim = MEM_callocN(sizeof(SculptClothSimulation), "cloth constraints");
-
- cloth_sim->length_constraints = MEM_callocN(sizeof(SculptClothLengthConstraint) *
- CLOTH_LENGTH_CONSTRAINTS_BLOCK,
- "cloth length constraints");
- cloth_sim->capacity_length_constraints = CLOTH_LENGTH_CONSTRAINTS_BLOCK;
-
- cloth_sim->acceleration = MEM_calloc_arrayN(
- totverts, sizeof(float[3]), "cloth sim acceleration");
- cloth_sim->pos = MEM_calloc_arrayN(totverts, sizeof(float[3]), "cloth sim pos");
- cloth_sim->prev_pos = MEM_calloc_arrayN(totverts, sizeof(float[3]), "cloth sim prev pos");
- cloth_sim->last_iteration_pos = MEM_calloc_arrayN(
- totverts, sizeof(float[3]), "cloth sim last iteration pos");
- cloth_sim->init_pos = MEM_calloc_arrayN(totverts, sizeof(float[3]), "cloth sim init pos");
- cloth_sim->length_constraint_tweak = MEM_calloc_arrayN(
- totverts, sizeof(float), "cloth sim length tweak");
-
- /* Brush can be NULL for tools that need the solver but don't rely on constraint to deformation
- * positions. */
- if (brush && SCULPT_is_cloth_deform_brush(brush)) {
- cloth_sim->deformation_pos = MEM_calloc_arrayN(
- totverts, sizeof(float[3]), "cloth sim deformation positions");
- }
-
- cloth_sim->mass = cloth_mass;
- cloth_sim->damping = cloth_damping;
-
- if (use_collisions) {
- cloth_sim->collider_list = cloth_brush_collider_cache_create(ss->depsgraph);
- }
-
- return cloth_sim;
-}
-
typedef struct ClothBrushCollision {
CollisionModifierData *col_data;
struct IsectRayPrecalc isect_precalc;
@@ -699,43 +656,6 @@ static void do_cloth_brush_solve_simulation_task_cb_ex(
BKE_pbvh_vertex_iter_end;
}
-static void cloth_brush_build_nodes_constraints(
- Sculpt *sd,
- Object *ob,
- PBVHNode **nodes,
- int totnode,
- SculptClothSimulation *cloth_sim,
- /* Cannot be const, because it is assigned to a non-const variable.
- * NOLINTNEXTLINE: readability-non-const-parameter. */
- float initial_location[3],
- const float radius)
-{
- Brush *brush = BKE_paint_brush(&sd->paint);
-
- /* TODO: Multi-threaded needs to be disabled for this task until implementing the optimization of
- * storing the constraints per node. */
- /* Currently all constrains are added to the same global array which can't be accessed from
- * different threads. */
- TaskParallelSettings settings;
- BKE_pbvh_parallel_range_settings(&settings, false, totnode);
-
- cloth_sim->created_length_constraints = BLI_edgeset_new("created length constraints");
-
- SculptThreadedTaskData build_constraints_data = {
- .sd = sd,
- .ob = ob,
- .brush = brush,
- .nodes = nodes,
- .cloth_sim = cloth_sim,
- .cloth_sim_initial_location = initial_location,
- .cloth_sim_radius = radius,
- };
- BLI_task_parallel_range(
- 0, totnode, &build_constraints_data, do_cloth_brush_build_constraints_task_cb_ex, &settings);
-
- BLI_edgeset_free(cloth_sim->created_length_constraints);
-}
-
static void cloth_brush_satisfy_constraints(SculptSession *ss,
Brush *brush,
SculptClothSimulation *cloth_sim)
@@ -897,6 +817,107 @@ static void cloth_brush_apply_brush_foces(Sculpt *sd, Object *ob, PBVHNode **nod
}
/* Public functions. */
+SculptClothSimulation *SCULPT_cloth_brush_simulation_create(SculptSession *ss,
+ Brush *brush,
+ const float cloth_mass,
+ const float cloth_damping,
+ const bool use_collisions)
+{
+ const int totverts = SCULPT_vertex_count_get(ss);
+ SculptClothSimulation *cloth_sim;
+
+ cloth_sim = MEM_callocN(sizeof(SculptClothSimulation), "cloth constraints");
+
+ cloth_sim->length_constraints = MEM_callocN(sizeof(SculptClothLengthConstraint) *
+ CLOTH_LENGTH_CONSTRAINTS_BLOCK,
+ "cloth length constraints");
+ cloth_sim->capacity_length_constraints = CLOTH_LENGTH_CONSTRAINTS_BLOCK;
+
+ cloth_sim->acceleration = MEM_calloc_arrayN(
+ totverts, sizeof(float[3]), "cloth sim acceleration");
+ cloth_sim->pos = MEM_calloc_arrayN(totverts, sizeof(float[3]), "cloth sim pos");
+ cloth_sim->prev_pos = MEM_calloc_arrayN(totverts, sizeof(float[3]), "cloth sim prev pos");
+ cloth_sim->last_iteration_pos = MEM_calloc_arrayN(
+ totverts, sizeof(float[3]), "cloth sim last iteration pos");
+ cloth_sim->init_pos = MEM_calloc_arrayN(totverts, sizeof(float[3]), "cloth sim init pos");
+ cloth_sim->length_constraint_tweak = MEM_calloc_arrayN(
+ totverts, sizeof(float), "cloth sim length tweak");
+
+ /* Brush can be NULL for tools that need the solver but don't rely on constraint to deformation
+ * positions. */
+ if (brush && SCULPT_is_cloth_deform_brush(brush)) {
+ cloth_sim->deformation_pos = MEM_calloc_arrayN(
+ totverts, sizeof(float[3]), "cloth sim deformation positions");
+ }
+
+ cloth_sim->mass = cloth_mass;
+ cloth_sim->damping = cloth_damping;
+
+ if (use_collisions) {
+ cloth_sim->collider_list = cloth_brush_collider_cache_create(ss->depsgraph);
+ }
+
+ return cloth_sim;
+}
+
+void SCULPT_cloth_brush_build_nodes_constraints(
+ Sculpt *sd,
+ Object *ob,
+ PBVHNode **nodes,
+ int totnode,
+ SculptClothSimulation *cloth_sim,
+ /* Cannot be const, because it is assigned to a non-const variable.
+ * NOLINTNEXTLINE: readability-non-const-parameter. */
+ float initial_location[3],
+ const float radius)
+{
+ Brush *brush = BKE_paint_brush(&sd->paint);
+
+ /* TODO: Multi-threaded needs to be disabled for this task until implementing the optimization of
+ * storing the constraints per node. */
+ /* Currently all constrains are added to the same global array which can't be accessed from
+ * different threads. */
+ TaskParallelSettings settings;
+ BKE_pbvh_parallel_range_settings(&settings, false, totnode);
+
+ cloth_sim->created_length_constraints = BLI_edgeset_new("created length constraints");
+
+ SculptThreadedTaskData build_constraints_data = {
+ .sd = sd,
+ .ob = ob,
+ .brush = brush,
+ .nodes = nodes,
+ .cloth_sim = cloth_sim,
+ .cloth_sim_initial_location = initial_location,
+ .cloth_sim_radius = radius,
+ };
+ BLI_task_parallel_range(
+ 0, totnode, &build_constraints_data, do_cloth_brush_build_constraints_task_cb_ex, &settings);
+
+ BLI_edgeset_free(cloth_sim->created_length_constraints);
+}
+
+void SCULPT_cloth_brush_simulation_init(SculptSession *ss, SculptClothSimulation *cloth_sim)
+{
+ const int totverts = SCULPT_vertex_count_get(ss);
+ const bool has_deformation_pos = cloth_sim->deformation_pos != NULL;
+ for (int i = 0; i < totverts; i++) {
+ copy_v3_v3(cloth_sim->last_iteration_pos[i], SCULPT_vertex_co_get(ss, i));
+ copy_v3_v3(cloth_sim->init_pos[i], SCULPT_vertex_co_get(ss, i));
+ copy_v3_v3(cloth_sim->prev_pos[i], SCULPT_vertex_co_get(ss, i));
+ if (has_deformation_pos) {
+ copy_v3_v3(cloth_sim->deformation_pos[i], SCULPT_vertex_co_get(ss, i));
+ }
+ }
+}
+
+void SCULPT_cloth_brush_store_simulation_state(SculptSession *ss, SculptClothSimulation *cloth_sim)
+{
+ const int totverts = SCULPT_vertex_count_get(ss);
+ for (int i = 0; i < totverts; i++) {
+ copy_v3_v3(cloth_sim->pos[i], SCULPT_vertex_co_get(ss, i));
+ }
+}
/* Main Brush Function. */
void SCULPT_do_cloth_brush(Sculpt *sd, Object *ob, PBVHNode **nodes, int totnode)
@@ -914,27 +935,19 @@ void SCULPT_do_cloth_brush(Sculpt *sd, Object *ob, PBVHNode **nodes, int totnode
/* The simulation structure only needs to be created on the first symmetry pass. */
if (SCULPT_stroke_is_first_brush_step(ss->cache) || !ss->cache->cloth_sim) {
- const bool is_cloth_deform_brush = SCULPT_is_cloth_deform_brush(brush);
- ss->cache->cloth_sim = cloth_brush_simulation_create(
+ ss->cache->cloth_sim = SCULPT_cloth_brush_simulation_create(
ss,
brush,
brush->cloth_mass,
brush->cloth_damping,
(brush->flag2 & BRUSH_CLOTH_USE_COLLISION));
- for (int i = 0; i < totverts; i++) {
- copy_v3_v3(ss->cache->cloth_sim->last_iteration_pos[i], SCULPT_vertex_co_get(ss, i));
- copy_v3_v3(ss->cache->cloth_sim->init_pos[i], SCULPT_vertex_co_get(ss, i));
- copy_v3_v3(ss->cache->cloth_sim->prev_pos[i], SCULPT_vertex_co_get(ss, i));
- if (is_cloth_deform_brush) {
- copy_v3_v3(ss->cache->cloth_sim->deformation_pos[i], SCULPT_vertex_co_get(ss, i));
- }
- }
+ SCULPT_cloth_brush_simulation_init(ss, ss->cache->cloth_sim);
}
/* Build the constraints. */
const float radius = ss->cache->initial_radius;
const float limit = radius + (radius * brush->cloth_sim_limit);
- cloth_brush_build_nodes_constraints(
+ SCULPT_cloth_brush_build_nodes_constraints(
sd, ob, nodes, totnode, ss->cache->cloth_sim, ss->cache->location, limit);
return;
@@ -1192,26 +1205,21 @@ static int sculpt_cloth_filter_invoke(bContext *C, wmOperator *op, const wmEvent
const float cloth_mass = RNA_float_get(op->ptr, "cloth_mass");
const float cloth_damping = RNA_float_get(op->ptr, "cloth_damping");
const bool use_collisions = RNA_boolean_get(op->ptr, "use_collisions");
- ss->filter_cache->cloth_sim = cloth_brush_simulation_create(
+ ss->filter_cache->cloth_sim = SCULPT_cloth_brush_simulation_create(
ss, NULL, cloth_mass, cloth_damping, use_collisions);
copy_v3_v3(ss->filter_cache->cloth_sim_pinch_point, SCULPT_active_vertex_co_get(ss));
- const int totverts = SCULPT_vertex_count_get(ss);
- for (int i = 0; i < totverts; i++) {
- copy_v3_v3(ss->filter_cache->cloth_sim->last_iteration_pos[i], SCULPT_vertex_co_get(ss, i));
- copy_v3_v3(ss->filter_cache->cloth_sim->prev_pos[i], SCULPT_vertex_co_get(ss, i));
- copy_v3_v3(ss->filter_cache->cloth_sim->init_pos[i], SCULPT_vertex_co_get(ss, i));
- }
+ SCULPT_cloth_brush_simulation_init(ss, ss->filter_cache->cloth_sim);
float origin[3] = {0.0f, 0.0f, 0.0f};
- cloth_brush_build_nodes_constraints(sd,
- ob,
- ss->filter_cache->nodes,
- ss->filter_cache->totnode,
- ss->filter_cache->cloth_sim,
- origin,
- FLT_MAX);
+ SCULPT_cloth_brush_build_nodes_constraints(sd,
+ ob,
+ ss->filter_cache->nodes,
+ ss->filter_cache->totnode,
+ ss->filter_cache->cloth_sim,
+ origin,
+ FLT_MAX);
const bool use_face_sets = RNA_boolean_get(op->ptr, "use_face_sets");
if (use_face_sets) {
diff --git a/source/blender/editors/sculpt_paint/sculpt_intern.h b/source/blender/editors/sculpt_paint/sculpt_intern.h
index ee0eaeb28f3..4ac7c79e839 100644
--- a/source/blender/editors/sculpt_paint/sculpt_intern.h
+++ b/source/blender/editors/sculpt_paint/sculpt_intern.h
@@ -352,6 +352,30 @@ void SCULPT_do_cloth_brush(struct Sculpt *sd,
int totnode);
void SCULPT_cloth_simulation_free(struct SculptClothSimulation *cloth_sim);
+struct SculptClothSimulation *SCULPT_cloth_brush_simulation_create(struct SculptSession *ss,
+ struct Brush *brush,
+ const float cloth_mass,
+ const float cloth_damping,
+ const bool use_collisions);
+void SCULPT_cloth_brush_simulation_init(struct SculptSession *ss,
+ struct SculptClothSimulation *cloth_sim);
+void SCULPT_cloth_brush_store_simulation_state(struct SculptSession *ss,
+ struct SculptClothSimulation *cloth_sim);
+
+void SCULPT_cloth_brush_do_simulation_step(struct Sculpt *sd,
+ struct Object *ob,
+ struct SculptClothSimulation *cloth_sim,
+ struct PBVHNode **nodes,
+ int totnode);
+
+void SCULPT_cloth_brush_build_nodes_constraints(struct Sculpt *sd,
+ struct Object *ob,
+ struct PBVHNode **nodes,
+ int totnode,
+ struct SculptClothSimulation *cloth_sim,
+ float initial_location[3],
+ const float radius);
+
void SCULPT_cloth_simulation_limits_draw(const uint gpuattr,
const struct Brush *brush,
const float location[3],