Index: release/scripts/startup/bl_ui/properties_data_modifier.py =================================================================== --- release/scripts/startup/bl_ui/properties_data_modifier.py (revision 58165) +++ release/scripts/startup/bl_ui/properties_data_modifier.py (working copy) @@ -725,10 +725,21 @@ col.prop(md, "factor") else: col.prop(md, "angle") - col.prop(md, "limits", slider=True) + + split = layout.split() + col = split.column() + col.label(text="Deform axis:") + col.prop(md, "deform_axis", expand=True) + + col = split.column() if md.deform_method in {'TAPER', 'STRETCH', 'TWIST'}: + col.label("Lock axis:") col.prop(md, "lock_x") col.prop(md, "lock_y") + col.prop(md, "lock_z") + + col = split.column() + col.prop(md, "limits", slider=True) def SMOKE(self, layout, ob, md): layout.label(text="Settings can be found inside the Physics context") Index: source/blender/makesdna/DNA_modifier_types.h =================================================================== --- source/blender/makesdna/DNA_modifier_types.h (revision 58165) +++ source/blender/makesdna/DNA_modifier_types.h (working copy) @@ -714,7 +714,7 @@ char mode; /* deform function */ char axis; /* lock axis (for taper and strech) */ char originOpts; /* originOptions */ - char pad; + char defaxis; /* axis along wich modifier will work */ } SimpleDeformModifierData; @@ -725,7 +725,12 @@ #define MOD_SIMPLEDEFORM_LOCK_AXIS_X (1<<0) #define MOD_SIMPLEDEFORM_LOCK_AXIS_Y (1<<1) +#define MOD_SIMPLEDEFORM_LOCK_AXIS_Z (1<<2) +#define MOD_SIMPLEDEFORM_ALONG_X 1 +#define MOD_SIMPLEDEFORM_ALONG_Y 2 +#define MOD_SIMPLEDEFORM_ALONG_Z 3 + /* indicates whether simple deform should use the local * coordinates or global coordinates of origin */ /* XXX, this should have never been an option, all other modifiers work relatively Index: source/blender/makesrna/intern/rna_modifier.c =================================================================== --- source/blender/makesrna/intern/rna_modifier.c (revision 58165) +++ source/blender/makesrna/intern/rna_modifier.c (working copy) @@ -2569,6 +2569,13 @@ {0, NULL, 0, NULL, NULL} }; + static EnumPropertyItem prop_deform_axis_items[] = { + {MOD_CURVE_POSX, "X", 0, "X", ""}, + {MOD_CURVE_POSY, "Y", 0, "Y", ""}, + {MOD_CURVE_POSZ, "Z", 0, "Z", ""}, + {0, NULL, 0, NULL, NULL} + }; + srna = RNA_def_struct(brna, "SimpleDeformModifier", "Modifier"); RNA_def_struct_ui_text(srna, "SimpleDeform Modifier", "Simple deformation modifier to apply effects such as twisting and bending"); @@ -2620,13 +2627,24 @@ prop = RNA_def_property(srna, "lock_x", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "axis", MOD_SIMPLEDEFORM_LOCK_AXIS_X); - RNA_def_property_ui_text(prop, "Lock X Axis", "Do not allow deformation along the X axis"); + RNA_def_property_ui_text(prop, "X", "Do not allow deformation along the X axis"); RNA_def_property_update(prop, 0, "rna_Modifier_update"); prop = RNA_def_property(srna, "lock_y", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, NULL, "axis", MOD_SIMPLEDEFORM_LOCK_AXIS_Y); - RNA_def_property_ui_text(prop, "Lock Y Axis", "Do not allow deformation along the Y axis"); + RNA_def_property_ui_text(prop, "Y", "Do not allow deformation along the Y axis"); RNA_def_property_update(prop, 0, "rna_Modifier_update"); + + prop = RNA_def_property(srna, "lock_z", PROP_BOOLEAN, PROP_NONE); + RNA_def_property_boolean_sdna(prop, NULL, "axis", MOD_SIMPLEDEFORM_LOCK_AXIS_Z); + RNA_def_property_ui_text(prop, "Z", "Do not allow deformation along the Z axis"); + RNA_def_property_update(prop, 0, "rna_Modifier_update"); + + prop = RNA_def_property(srna, "deform_axis", PROP_ENUM, PROP_NONE); + RNA_def_property_enum_sdna(prop, NULL, "defaxis"); + RNA_def_property_enum_items(prop, prop_deform_axis_items); + RNA_def_property_ui_text(prop, "Deform Axis", "The axis that the object deforms along"); + RNA_def_property_update(prop, 0, "rna_Modifier_update"); } static void rna_def_modifier_surface(BlenderRNA *brna) Index: source/blender/modifiers/intern/MOD_simpledeform.c =================================================================== --- source/blender/modifiers/intern/MOD_simpledeform.c (revision 58165) +++ source/blender/modifiers/intern/MOD_simpledeform.c (working copy) @@ -140,7 +140,36 @@ } +/* swaps axis values deepend on modifier mode, + * this allow to change deform axis (that is Z by default) */ +static void swap_defaxis(SimpleDeformModifierData *smd, float co[3]) { + if (smd->defaxis == MOD_SIMPLEDEFORM_ALONG_X) { + SWAP(float, co[2], co[0]); + } else if (smd->defaxis == MOD_SIMPLEDEFORM_ALONG_Y) { + SWAP(float, co[2], co[1]); + } +} +/* coordinate locks must be also swapped so lockX must lock x always */ +static int convert_axis(SimpleDeformModifierData *smd, int axis) { + if (smd->defaxis == MOD_SIMPLEDEFORM_ALONG_X) { + if (axis == 0) { + return 2; + } + else if (axis == 2) { + return 0; + } + } else if (smd->defaxis == MOD_SIMPLEDEFORM_ALONG_Y) { + if (axis == 1) { + return 2; + } + else if (axis == 2) { + return 1; + } + } + return axis; +} + /* simple deform modifier */ static void SimpleDeformModifier_do(SimpleDeformModifierData *smd, struct Object *ob, struct DerivedMesh *dm, float (*vertexCos)[3], int numVerts) @@ -188,6 +217,7 @@ for (i = 0; i < numVerts; i++) { float tmp[3]; copy_v3_v3(tmp, vertexCos[i]); + swap_defaxis(smd, tmp); if (transf) space_transform_apply(transf, tmp); @@ -220,6 +250,8 @@ if (weight != 0.0f) { float co[3], dcut[3] = {0.0f, 0.0f, 0.0f}; + swap_defaxis(smd, vertexCos[i]); + if (transf) { space_transform_apply(transf, vertexCos[i]); } @@ -228,17 +260,29 @@ /* Apply axis limits */ if (smd->mode != MOD_SIMPLEDEFORM_MODE_BEND) { /* Bend mode shoulnt have any lock axis */ - if (smd->axis & MOD_SIMPLEDEFORM_LOCK_AXIS_X) axis_limit(0, lock_axis, co, dcut); - if (smd->axis & MOD_SIMPLEDEFORM_LOCK_AXIS_Y) axis_limit(1, lock_axis, co, dcut); + if ((smd->axis & MOD_SIMPLEDEFORM_LOCK_AXIS_X) && smd->defaxis != MOD_SIMPLEDEFORM_ALONG_X) { + axis_limit(convert_axis(smd, 0), lock_axis, co, dcut); + } + if ((smd->axis & MOD_SIMPLEDEFORM_LOCK_AXIS_Y) && smd->defaxis != MOD_SIMPLEDEFORM_ALONG_Y) { + axis_limit(convert_axis(smd, 1), lock_axis, co, dcut); + } + if ((smd->axis & MOD_SIMPLEDEFORM_LOCK_AXIS_Z) && smd->defaxis != MOD_SIMPLEDEFORM_ALONG_Z) { + axis_limit(convert_axis(smd, 2), lock_axis, co, dcut); + } } axis_limit(limit_axis, smd_limit, co, dcut); + simpleDeform_callback(smd_factor, dcut, co); /* apply deform */ + + interp_v3_v3v3(vertexCos[i], vertexCos[i], co, weight); /* Use vertex weight has coef of linear interpolation */ if (transf) { space_transform_invert(transf, vertexCos[i]); } + + swap_defaxis(smd, vertexCos[i]); } } } @@ -259,6 +303,7 @@ smd->factor = 0.35f; smd->limit[0] = 0.0f; smd->limit[1] = 1.0f; + smd->defaxis = MOD_SIMPLEDEFORM_ALONG_Z; } static void copyData(ModifierData *md, ModifierData *target) @@ -271,6 +316,7 @@ tsmd->origin = smd->origin; tsmd->originOpts = smd->originOpts; tsmd->factor = smd->factor; + tsmd->defaxis = smd->defaxis; memcpy(tsmd->limit, smd->limit, sizeof(tsmd->limit)); BLI_strncpy(tsmd->vgroup_name, smd->vgroup_name, sizeof(tsmd->vgroup_name)); }