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:
authorJagannadhan Ravi <easythrees>2021-04-23 11:06:46 +0300
committerJeroen Bakker <jeroen@blender.org>2021-04-23 11:07:06 +0300
commit425e19bc1fca91116d5fceb7e994bdbf7656acc2 (patch)
treef3304a68874395cb8b3cb1d6517c6769117f799b
parentcfa20ff03bdeb87b1625196d58a1dbe0e22cc2f9 (diff)
Modifiers: Performance Simple Deformation
Use multiprocessing with simple deform modifiers. Master 2.92 fps this patch 3.13 fps on Ryzen 1700X With Vega 64 GPU. 3970X: 2.85 fps -> 2.95 fps 3990X: 3.15 fps -> 3.41 fps 3995WX: 3.21 fps -> 3.38 fps Reviewed By: jbakker Differential Revision: https://developer.blender.org/D10609
m---------release/scripts/addons0
-rw-r--r--source/blender/blenlib/BLI_compiler_attrs.h7
-rw-r--r--source/blender/modifiers/intern/MOD_simpledeform.c183
3 files changed, 120 insertions, 70 deletions
diff --git a/release/scripts/addons b/release/scripts/addons
-Subproject 81815ea92c2071a08566dc66d4a871b6e2f5c86
+Subproject 4cb833e84acfd2be5fa08ce75118ce9cb60643b
diff --git a/source/blender/blenlib/BLI_compiler_attrs.h b/source/blender/blenlib/BLI_compiler_attrs.h
index 680c4bc78da..4b5a7d671f2 100644
--- a/source/blender/blenlib/BLI_compiler_attrs.h
+++ b/source/blender/blenlib/BLI_compiler_attrs.h
@@ -98,3 +98,10 @@
#else
# define ATTR_ALIGN(x) __attribute__((aligned(x)))
#endif
+
+/* Alignment directive */
+#ifdef _WIN64
+# define ALIGN_STRUCT __declspec(align(64))
+#else
+# define ALIGN_STRUCT
+#endif
diff --git a/source/blender/modifiers/intern/MOD_simpledeform.c b/source/blender/modifiers/intern/MOD_simpledeform.c
index ea31bdc6e31..f9d1d5ae566 100644
--- a/source/blender/modifiers/intern/MOD_simpledeform.c
+++ b/source/blender/modifiers/intern/MOD_simpledeform.c
@@ -22,9 +22,8 @@
*/
#include "BLI_utildefines.h"
-
#include "BLI_math.h"
-
+#include "BLI_task.h"
#include "BLT_translation.h"
#include "DNA_defaults.h"
@@ -57,6 +56,21 @@
#define BEND_EPS 0.000001f
+ALIGN_STRUCT struct DeformUserData {
+ bool invert_vgroup;
+ char mode;
+ char deform_axis;
+ int lock_axis;
+ int vgroup;
+ int limit_axis;
+ float weight;
+ float smd_factor;
+ float smd_limit[2];
+ float (*vertexCos)[3];
+ SpaceTransform *transf;
+ MDeformVert *dvert;
+};
+
/* Re-maps the indices for X Y Z by shifting them up and wrapping, such that
* X = Y, Y = Z, Z = X (for X axis), and X = Z, Y = X, Z = Y (for Y axis). This
* exists because the deformations (excluding bend) are based on the Z axis.
@@ -203,6 +217,86 @@ static void simpleDeform_bend(const float factor,
}
}
+static void simple_helper(void *__restrict userdata,
+ const int iter,
+ const TaskParallelTLS *__restrict UNUSED(tls))
+{
+ struct DeformUserData *curr_deform_data = userdata;
+ float weight = BKE_defvert_array_find_weight_safe(curr_deform_data->dvert, iter, curr_deform_data->vgroup);
+ const uint *axis_map = axis_map_table[(curr_deform_data->mode != MOD_SIMPLEDEFORM_MODE_BEND) ?
+ curr_deform_data->deform_axis :
+ 2];
+ const float base_limit[2] = {0.0f, 0.0f};
+
+ if (curr_deform_data->invert_vgroup) {
+ weight = 1.0f - weight;
+ }
+
+ if (weight != 0.0f) {
+ float co[3], dcut[3] = {0.0f, 0.0f, 0.0f};
+
+ if (curr_deform_data->transf) {
+ BLI_space_transform_apply(curr_deform_data->transf, curr_deform_data->vertexCos[iter]);
+ }
+
+ copy_v3_v3(co, curr_deform_data->vertexCos[iter]);
+
+ /* Apply axis limits, and axis mappings */
+ if (curr_deform_data->lock_axis & MOD_SIMPLEDEFORM_LOCK_AXIS_X) {
+ axis_limit(0, base_limit, co, dcut);
+ }
+ if (curr_deform_data->lock_axis & MOD_SIMPLEDEFORM_LOCK_AXIS_Y) {
+ axis_limit(1, base_limit, co, dcut);
+ }
+ if (curr_deform_data->lock_axis & MOD_SIMPLEDEFORM_LOCK_AXIS_Z) {
+ axis_limit(2, base_limit, co, dcut);
+ }
+ axis_limit(curr_deform_data->limit_axis, curr_deform_data->smd_limit, co, dcut);
+
+ /* apply the deform to a mapped copy of the vertex, and then re-map it back. */
+ float co_remap[3];
+ float dcut_remap[3];
+ copy_v3_v3_map(co_remap, co, axis_map);
+ copy_v3_v3_map(dcut_remap, dcut, axis_map);
+ switch (curr_deform_data->mode) {
+ case MOD_SIMPLEDEFORM_MODE_TWIST:
+ simpleDeform_twist(curr_deform_data->smd_factor,
+ curr_deform_data->deform_axis,
+ dcut_remap,
+ co_remap); /* apply deform */
+ break;
+ case MOD_SIMPLEDEFORM_MODE_BEND:
+ simpleDeform_bend(curr_deform_data->smd_factor,
+ curr_deform_data->deform_axis,
+ dcut_remap,
+ co_remap); /* apply deform */
+ break;
+ case MOD_SIMPLEDEFORM_MODE_TAPER:
+ simpleDeform_taper(curr_deform_data->smd_factor,
+ curr_deform_data->deform_axis,
+ dcut_remap,
+ co_remap); /* apply deform */
+ break;
+ case MOD_SIMPLEDEFORM_MODE_STRETCH:
+ simpleDeform_stretch(curr_deform_data->smd_factor,
+ curr_deform_data->deform_axis,
+ dcut_remap,
+ co_remap); /* apply deform */
+ break;
+ default:
+ return; /* No simple-deform mode? */
+ }
+ copy_v3_v3_unmap(co, co_remap, axis_map);
+
+ /* Use vertex weight has coef of linear interpolation */
+ interp_v3_v3v3(curr_deform_data->vertexCos[iter], curr_deform_data->vertexCos[iter], co, weight);
+
+ if (curr_deform_data->transf) {
+ BLI_space_transform_invert(curr_deform_data->transf, curr_deform_data->vertexCos[iter]);
+ }
+ }
+}
+
/* simple deform modifier */
static void SimpleDeformModifier_do(SimpleDeformModifierData *smd,
const ModifierEvalContext *UNUSED(ctx),
@@ -211,14 +305,9 @@ static void SimpleDeformModifier_do(SimpleDeformModifierData *smd,
float (*vertexCos)[3],
int numVerts)
{
- const float base_limit[2] = {0.0f, 0.0f};
int i;
float smd_limit[2], smd_factor;
SpaceTransform *transf = NULL, tmp_transf;
- void (*simpleDeform_callback)(const float factor,
- const int axis,
- const float dcut[3],
- float co[3]) = NULL; /* Mode callback */
int vgroup;
MDeformVert *dvert;
@@ -300,23 +389,6 @@ static void SimpleDeformModifier_do(SimpleDeformModifierData *smd,
smd_factor = smd->factor / max_ff(FLT_EPSILON, smd_limit[1] - smd_limit[0]);
}
- switch (smd->mode) {
- case MOD_SIMPLEDEFORM_MODE_TWIST:
- simpleDeform_callback = simpleDeform_twist;
- break;
- case MOD_SIMPLEDEFORM_MODE_BEND:
- simpleDeform_callback = simpleDeform_bend;
- break;
- case MOD_SIMPLEDEFORM_MODE_TAPER:
- simpleDeform_callback = simpleDeform_taper;
- break;
- case MOD_SIMPLEDEFORM_MODE_STRETCH:
- simpleDeform_callback = simpleDeform_stretch;
- break;
- default:
- return; /* No simple-deform mode? */
- }
-
if (smd->mode == MOD_SIMPLEDEFORM_MODE_BEND) {
if (fabsf(smd_factor) < BEND_EPS) {
return;
@@ -325,53 +397,24 @@ static void SimpleDeformModifier_do(SimpleDeformModifierData *smd,
MOD_get_vgroup(ob, mesh, smd->vgroup_name, &dvert, &vgroup);
const bool invert_vgroup = (smd->flag & MOD_SIMPLEDEFORM_FLAG_INVERT_VGROUP) != 0;
- const uint *axis_map =
- axis_map_table[(smd->mode != MOD_SIMPLEDEFORM_MODE_BEND) ? deform_axis : 2];
-
- for (i = 0; i < numVerts; i++) {
- float weight = BKE_defvert_array_find_weight_safe(dvert, i, vgroup);
-
- if (invert_vgroup) {
- weight = 1.0f - weight;
- }
-
- if (weight != 0.0f) {
- float co[3], dcut[3] = {0.0f, 0.0f, 0.0f};
- if (transf) {
- BLI_space_transform_apply(transf, vertexCos[i]);
- }
-
- copy_v3_v3(co, vertexCos[i]);
-
- /* Apply axis limits, and axis mappings */
- if (lock_axis & MOD_SIMPLEDEFORM_LOCK_AXIS_X) {
- axis_limit(0, base_limit, co, dcut);
- }
- if (lock_axis & MOD_SIMPLEDEFORM_LOCK_AXIS_Y) {
- axis_limit(1, base_limit, co, dcut);
- }
- if (lock_axis & MOD_SIMPLEDEFORM_LOCK_AXIS_Z) {
- axis_limit(2, base_limit, co, dcut);
- }
- axis_limit(limit_axis, smd_limit, co, dcut);
-
- /* apply the deform to a mapped copy of the vertex, and then re-map it back. */
- float co_remap[3];
- float dcut_remap[3];
- copy_v3_v3_map(co_remap, co, axis_map);
- copy_v3_v3_map(dcut_remap, dcut, axis_map);
- simpleDeform_callback(smd_factor, deform_axis, dcut_remap, co_remap); /* apply deform */
- copy_v3_v3_unmap(co, co_remap, axis_map);
-
- /* Use vertex weight has coef of linear interpolation */
- interp_v3_v3v3(vertexCos[i], vertexCos[i], co, weight);
-
- if (transf) {
- BLI_space_transform_invert(transf, vertexCos[i]);
- }
- }
- }
+ // build our data
+ struct DeformUserData deform_pool_data = {.mode = smd->mode,
+ .smd_factor = smd_factor,
+ .deform_axis = deform_axis,
+ .transf = transf,
+ .vertexCos = vertexCos,
+ .invert_vgroup = invert_vgroup,
+ .lock_axis = lock_axis,
+ .vgroup = vgroup,
+ .smd_limit[0] = smd_limit[0],
+ .smd_limit[1] = smd_limit[1],
+ .dvert = dvert,
+ .limit_axis = limit_axis};
+ /* Do deformation. */
+ TaskParallelSettings settings;
+ BLI_parallel_range_settings_defaults(&settings);
+ BLI_task_parallel_range(0, numVerts, &deform_pool_data, simple_helper, &settings);
}
/* SimpleDeform */