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
path: root/source
diff options
context:
space:
mode:
authorLukas Stockner <lukasstockner97>2020-02-15 03:49:50 +0300
committerLukas Stockner <lukas.stockner@freenet.de>2020-02-15 05:37:20 +0300
commitf6aafd5186bd921637df755797c7ff6f3036a361 (patch)
tree8a09a244cb18e926907cfeb9df7674063b702ae0 /source
parentfa4ab69abf5750857e0b79295b13efa73aef0766 (diff)
Modifiers: Add option to directly specify a 2D transform for UVWarp
Currently the only option is to warp based on the transform of other objects, which is inconvenient if you want to e.g. control it through a driver - you need to set up a dummy object and go through that, which is clunky and should be unneccessary. Reviewed By: brecht Differential Revision: https://developer.blender.org/D6690
Diffstat (limited to 'source')
-rw-r--r--source/blender/blenlib/BLI_math_matrix.h3
-rw-r--r--source/blender/blenlib/intern/math_matrix.c10
-rw-r--r--source/blender/blenloader/intern/versioning_280.c12
-rw-r--r--source/blender/makesdna/DNA_modifier_types.h6
-rw-r--r--source/blender/makesrna/intern/rna_modifier.c15
-rw-r--r--source/blender/modifiers/intern/MOD_uvwarp.c83
6 files changed, 90 insertions, 39 deletions
diff --git a/source/blender/blenlib/BLI_math_matrix.h b/source/blender/blenlib/BLI_math_matrix.h
index ac0f5f44c74..acefe18fd40 100644
--- a/source/blender/blenlib/BLI_math_matrix.h
+++ b/source/blender/blenlib/BLI_math_matrix.h
@@ -60,6 +60,9 @@ void copy_m4d_m4(double R[4][4], const float A[4][4]);
void swap_m3m3(float A[3][3], float B[3][3]);
void swap_m4m4(float A[4][4], float B[4][4]);
+/* Build index shuffle matrix */
+void shuffle_m4(float R[4][4], int index[4]);
+
/******************************** Arithmetic *********************************/
void add_m3_m3m3(float R[3][3], const float A[3][3], const float B[3][3]);
diff --git a/source/blender/blenlib/intern/math_matrix.c b/source/blender/blenlib/intern/math_matrix.c
index 4d8a2f72eca..86a08a42247 100644
--- a/source/blender/blenlib/intern/math_matrix.c
+++ b/source/blender/blenlib/intern/math_matrix.c
@@ -210,6 +210,16 @@ void swap_m4m4(float m1[4][4], float m2[4][4])
}
}
+void shuffle_m4(float R[4][4], int index[4])
+{
+ zero_m4(R);
+ for (int k = 0; k < 4; k++) {
+ if (index[k] >= 0) {
+ R[index[k]][k] = 1.0f;
+ }
+ }
+}
+
/******************************** Arithmetic *********************************/
void mul_m4_m4m4(float R[4][4], const float A[4][4], const float B[4][4])
diff --git a/source/blender/blenloader/intern/versioning_280.c b/source/blender/blenloader/intern/versioning_280.c
index 886c7195d9e..8baea5c8c4b 100644
--- a/source/blender/blenloader/intern/versioning_280.c
+++ b/source/blender/blenloader/intern/versioning_280.c
@@ -4482,5 +4482,17 @@ void blo_do_versions_280(FileData *fd, Library *UNUSED(lib), Main *bmain)
}
}
}
+
+ /* Add 2D transform to UV Warp modifier. */
+ if (!DNA_struct_elem_find(fd->filesdna, "UVWarpModifierData", "float", "scale[2]")) {
+ for (Object *ob = bmain->objects.first; ob; ob = ob->id.next) {
+ for (ModifierData *md = ob->modifiers.first; md; md = md->next) {
+ if (md->type == eModifierType_UVWarp) {
+ UVWarpModifierData *umd = (UVWarpModifierData *)md;
+ copy_v2_fl(umd->scale, 1.0f);
+ }
+ }
+ }
+ }
}
}
diff --git a/source/blender/makesdna/DNA_modifier_types.h b/source/blender/makesdna/DNA_modifier_types.h
index 82237a10d23..7a61118921d 100644
--- a/source/blender/makesdna/DNA_modifier_types.h
+++ b/source/blender/makesdna/DNA_modifier_types.h
@@ -1742,10 +1742,14 @@ typedef struct UVWarpModifierData {
ModifierData modifier;
char axis_u, axis_v;
- char _pad[6];
+ char _pad[2];
/** Used for rotate/scale. */
float center[2];
+ float offset[2];
+ float scale[2];
+ float rotation;
+
/** Source. */
struct Object *object_src;
/** Optional name of bone target, MAX_ID_NAME-2. */
diff --git a/source/blender/makesrna/intern/rna_modifier.c b/source/blender/makesrna/intern/rna_modifier.c
index eb88f4523ab..ea0f917ca77 100644
--- a/source/blender/makesrna/intern/rna_modifier.c
+++ b/source/blender/makesrna/intern/rna_modifier.c
@@ -4599,6 +4599,21 @@ static void rna_def_modifier_uvwarp(BlenderRNA *brna)
RNA_def_property_ui_text(prop, "UV Center", "Center point for rotate/scale");
RNA_def_property_update(prop, 0, "rna_Modifier_update");
+ prop = RNA_def_property(srna, "offset", PROP_FLOAT, PROP_NONE);
+ RNA_def_property_float_sdna(prop, NULL, "offset");
+ RNA_def_property_ui_text(prop, "Offset", "2D Offset for the warp");
+ RNA_def_property_update(prop, 0, "rna_Modifier_update");
+
+ prop = RNA_def_property(srna, "scale", PROP_FLOAT, PROP_NONE);
+ RNA_def_property_float_sdna(prop, NULL, "scale");
+ RNA_def_property_ui_text(prop, "Scale", "2D Scale for the warp");
+ RNA_def_property_update(prop, 0, "rna_Modifier_update");
+
+ prop = RNA_def_property(srna, "rotation", PROP_FLOAT, PROP_ANGLE);
+ RNA_def_property_float_sdna(prop, NULL, "rotation");
+ RNA_def_property_ui_text(prop, "Rotation", "2D Rotation for the warp");
+ RNA_def_property_update(prop, 0, "rna_Modifier_update");
+
prop = RNA_def_property(srna, "object_from", PROP_POINTER, PROP_NONE);
RNA_def_property_pointer_sdna(prop, NULL, "object_src");
RNA_def_property_ui_text(prop, "Object From", "Object defining offset");
diff --git a/source/blender/modifiers/intern/MOD_uvwarp.c b/source/blender/modifiers/intern/MOD_uvwarp.c
index dd9787c3c0b..2dfb9031c38 100644
--- a/source/blender/modifiers/intern/MOD_uvwarp.c
+++ b/source/blender/modifiers/intern/MOD_uvwarp.c
@@ -38,18 +38,13 @@
#include "MOD_util.h"
-static void uv_warp_from_mat4_pair(
- float uv_dst[2], const float uv_src[2], float warp_mat[4][4], int axis_u, int axis_v)
+static void uv_warp_from_mat4_pair(float uv_dst[2], const float uv_src[2], float warp_mat[4][4])
{
float tuv[3] = {0.0f};
- tuv[axis_u] = uv_src[0];
- tuv[axis_v] = uv_src[1];
-
+ copy_v2_v2(tuv, uv_src);
mul_m4_v3(warp_mat, tuv);
-
- uv_dst[0] = tuv[axis_u];
- uv_dst[1] = tuv[axis_v];
+ copy_v2_v2(uv_dst, tuv);
}
static void initData(ModifierData *md)
@@ -58,6 +53,7 @@ static void initData(ModifierData *md)
umd->axis_u = 0;
umd->axis_v = 1;
copy_v2_fl(umd->center, 0.5f);
+ copy_v2_fl(umd->scale, 1.0f);
}
static void requiredDataMask(Object *UNUSED(ob),
@@ -92,8 +88,6 @@ typedef struct UVWarpData {
int defgrp_index;
float (*warp_mat)[4];
- int axis_u;
- int axis_v;
} UVWarpData;
static void uv_warp_compute(void *__restrict userdata,
@@ -110,8 +104,6 @@ static void uv_warp_compute(void *__restrict userdata,
const int defgrp_index = data->defgrp_index;
float(*warp_mat)[4] = data->warp_mat;
- const int axis_u = data->axis_u;
- const int axis_v = data->axis_v;
int l;
@@ -120,13 +112,13 @@ static void uv_warp_compute(void *__restrict userdata,
float uv[2];
const float weight = defvert_find_weight(&dvert[ml->v], defgrp_index);
- uv_warp_from_mat4_pair(uv, mluv->uv, warp_mat, axis_u, axis_v);
+ uv_warp_from_mat4_pair(uv, mluv->uv, warp_mat);
interp_v2_v2v2(mluv->uv, mluv->uv, uv, weight);
}
}
else {
for (l = 0; l < mp->totloop; l++, ml++, mluv++) {
- uv_warp_from_mat4_pair(mluv->uv, mluv->uv, warp_mat, axis_u, axis_v);
+ uv_warp_from_mat4_pair(mluv->uv, mluv->uv, warp_mat);
}
}
}
@@ -141,9 +133,6 @@ static Mesh *applyModifier(ModifierData *md, const ModifierEvalContext *ctx, Mes
MDeformVert *dvert;
int defgrp_index;
char uvname[MAX_CUSTOMDATA_LAYER_NAME];
- float mat_src[4][4];
- float mat_dst[4][4];
- float imat_dst[4][4];
float warp_mat[4][4];
const int axis_u = umd->axis_u;
const int axis_v = umd->axis_v;
@@ -152,32 +141,52 @@ static Mesh *applyModifier(ModifierData *md, const ModifierEvalContext *ctx, Mes
if (!CustomData_has_layer(&mesh->ldata, CD_MLOOPUV)) {
return mesh;
}
- else if (ELEM(NULL, umd->object_src, umd->object_dst)) {
- modifier_setError(md, "From/To objects must be set");
- return mesh;
- }
- /* make sure anything moving UVs is available */
- matrix_from_obj_pchan(mat_src, umd->object_src, umd->bone_src);
- matrix_from_obj_pchan(mat_dst, umd->object_dst, umd->bone_dst);
+ if (!ELEM(NULL, umd->object_src, umd->object_dst)) {
+ float mat_src[4][4];
+ float mat_dst[4][4];
+ float imat_dst[4][4];
+ float shuf_mat[4][4];
+
+ /* make sure anything moving UVs is available */
+ matrix_from_obj_pchan(mat_src, umd->object_src, umd->bone_src);
+ matrix_from_obj_pchan(mat_dst, umd->object_dst, umd->bone_dst);
- invert_m4_m4(imat_dst, mat_dst);
- mul_m4_m4m4(warp_mat, imat_dst, mat_src);
+ invert_m4_m4(imat_dst, mat_dst);
+ mul_m4_m4m4(warp_mat, imat_dst, mat_src);
- /* apply warp */
- if (!is_zero_v2(umd->center)) {
- float mat_cent[4][4];
- float imat_cent[4][4];
+ /* apply warp */
+ if (!is_zero_v2(umd->center)) {
+ float mat_cent[4][4];
+ float imat_cent[4][4];
- unit_m4(mat_cent);
- mat_cent[3][axis_u] = umd->center[0];
- mat_cent[3][axis_v] = umd->center[1];
+ unit_m4(mat_cent);
+ mat_cent[3][axis_u] = umd->center[0];
+ mat_cent[3][axis_v] = umd->center[1];
- invert_m4_m4(imat_cent, mat_cent);
+ invert_m4_m4(imat_cent, mat_cent);
- mul_m4_m4m4(warp_mat, warp_mat, imat_cent);
- mul_m4_m4m4(warp_mat, mat_cent, warp_mat);
+ mul_m4_m4m4(warp_mat, warp_mat, imat_cent);
+ mul_m4_m4m4(warp_mat, mat_cent, warp_mat);
+ }
+
+ int shuf_indices[4] = {axis_u, axis_v, -1, 3};
+ shuffle_m4(shuf_mat, shuf_indices);
+ mul_m4_m4m4(warp_mat, shuf_mat, warp_mat);
+ transpose_m4(shuf_mat);
+ mul_m4_m4m4(warp_mat, warp_mat, shuf_mat);
}
+ else {
+ unit_m4(warp_mat);
+ }
+
+ /* Apply direct 2d transform. */
+ translate_m4(warp_mat, umd->center[0], umd->center[1], 0.0f);
+ const float scale[3] = {umd->scale[0], umd->scale[1], 1.0f};
+ rescale_m4(warp_mat, scale);
+ rotate_m4(warp_mat, 'Z', umd->rotation);
+ translate_m4(warp_mat, umd->offset[0], umd->offset[1], 0.0f);
+ translate_m4(warp_mat, -umd->center[0], -umd->center[1], 0.0f);
/* make sure we're using an existing layer */
CustomData_validate_layer_name(&mesh->ldata, CD_MLOOPUV, umd->uvlayer_name, uvname);
@@ -199,8 +208,6 @@ static Mesh *applyModifier(ModifierData *md, const ModifierEvalContext *ctx, Mes
.dvert = dvert,
.defgrp_index = defgrp_index,
.warp_mat = warp_mat,
- .axis_u = axis_u,
- .axis_v = axis_v,
};
TaskParallelSettings settings;
BLI_parallel_range_settings_defaults(&settings);