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:
-rw-r--r--source/blender/blenkernel/intern/constraint.c57
-rw-r--r--source/blender/blenkernel/intern/depsgraph.c4
2 files changed, 43 insertions, 18 deletions
diff --git a/source/blender/blenkernel/intern/constraint.c b/source/blender/blenkernel/intern/constraint.c
index 651b8a102e9..7f736a644f9 100644
--- a/source/blender/blenkernel/intern/constraint.c
+++ b/source/blender/blenkernel/intern/constraint.c
@@ -1116,6 +1116,8 @@ static void contarget_get_mesh_mat (Object *ob, char *substring, float mat[][4])
{
DerivedMesh *dm = (DerivedMesh *)ob->derivedFinal;
float vec[3] = {0.0f, 0.0f, 0.0f}, tvec[3];
+ float normal[3] = {0.0f, 0.0f, 0.0f}, plane[3];
+ float imat[3][3], tmat[3][3];
int dgroup;
/* initialize target matrix using target matrix */
@@ -1131,7 +1133,8 @@ static void contarget_get_mesh_mat (Object *ob, char *substring, float mat[][4])
int *index = (int *)dm->getVertDataArray(dm, CD_ORIGINDEX);
int numVerts = dm->getNumVerts(dm);
int i, j, count = 0;
- float co[3];
+ float co[3], nor[3];
+
/* get the average of all verts with that are in the vertex-group */
for (i = 0; i < numVerts; i++, index++) {
@@ -1139,7 +1142,9 @@ static void contarget_get_mesh_mat (Object *ob, char *substring, float mat[][4])
/* does this vertex belong to nominated vertex group? */
if (dvert[i].dw[j].def_nr == dgroup) {
dm->getVertCo(dm, i, co);
+ dm->getVertNo(dm, i, nor);
VecAddf(vec, vec, co);
+ VecAddf(normal, normal, nor);
count++;
break;
}
@@ -1147,12 +1152,38 @@ static void contarget_get_mesh_mat (Object *ob, char *substring, float mat[][4])
}
}
- /* calculate average, and apply as new location for matrix */
- if (count > 0)
+
+ /* calculate averages of normal and coordinates */
+ if (count > 0) {
VecMulf(vec, 1.0f / count);
- VecMat4MulVecfl(tvec, ob->obmat, vec);
+ VecMulf(normal, 1.0f / count);
+ }
- /* copy new location to matrix */
+
+ /* derive the rotation from the average normal:
+ * - code taken from transform_manipulator.c,
+ * calc_manipulator_stats, V3D_MANIP_NORMAL case
+ */
+ /* we need the transpose of the inverse for a normal... */
+ Mat3CpyMat4(imat, ob->obmat);
+
+ Mat3Inv(tmat, imat);
+ Mat3Transp(tmat);
+ Mat3MulVecfl(tmat, normal);
+
+ Normalize(normal);
+ VECCOPY(plane, tmat[1]);
+
+ VECCOPY(tmat[2], normal);
+ Crossf(tmat[0], normal, plane);
+ Crossf(tmat[1], tmat[2], tmat[0]);
+
+ Mat4CpyMat3(mat, tmat);
+ Mat4Ortho(mat);
+
+
+ /* apply the average coordinate as the new location */
+ VecMat4MulVecfl(tvec, ob->obmat, vec);
VECCOPY(mat[3], tvec);
}
}
@@ -1224,25 +1255,19 @@ static void constraint_target_to_mat4 (Object *ob, char *substring, float mat[][
}
/* Case VERTEXGROUP */
/* Current method just takes the average location of all the points in the
- * VertexGroup, and uses that as the location value of the target's matrix
- * instead.
+ * VertexGroup, and uses that as the location value of the targets. Where
+ * possible, the orientation will also be calculated, by calculating an
+ * 'average' vertex normal, and deriving the rotaation from that.
*
- * TODO: figure out a way to find 3-points to define a rotation plane based
- * on the normal of the triangle formed by those three points.
- * NOTE: editmode is not currently taken into consideration when doing this
+ * NOTE: EditMode is not currently supported, and will most likely remain that
+ * way as constraints can only really affect things on object/bone level.
*/
else if (ob->type == OB_MESH) {
- /* devise a matrix from the vertices in the vertexgroup */
contarget_get_mesh_mat(ob, substring, mat);
-
- /* make sure it's in the right space for evaluation */
constraint_mat_convertspace(ob, NULL, mat, from, to);
}
else if (ob->type == OB_LATTICE) {
- /* devise a matrix from the vertices in the vertexgroup */
contarget_get_lattice_mat(ob, substring, mat);
-
- /* make sure it's in the right space for evaluation */
constraint_mat_convertspace(ob, NULL, mat, from, to);
}
/* Case BONE */
diff --git a/source/blender/blenkernel/intern/depsgraph.c b/source/blender/blenkernel/intern/depsgraph.c
index abb0dce0ca2..f72db559197 100644
--- a/source/blender/blenkernel/intern/depsgraph.c
+++ b/source/blender/blenkernel/intern/depsgraph.c
@@ -569,7 +569,7 @@ static void build_dag_object(DagForest *dag, DagNode *scenenode, Object *ob, int
}
}
- for (con = ob->constraints.first; con; con=con->next){
+ for (con = ob->constraints.first; con; con=con->next) {
if (constraint_has_target(con)) {
char *str;
Object *obt= get_constraint_target(con, &str);
@@ -578,7 +578,7 @@ static void build_dag_object(DagForest *dag, DagNode *scenenode, Object *ob, int
if(ELEM(con->type, CONSTRAINT_TYPE_FOLLOWPATH, CONSTRAINT_TYPE_CLAMPTO))
dag_add_relation(dag, node2, node, DAG_RL_DATA_OB|DAG_RL_OB_OB);
else {
- if(obt->type==OB_ARMATURE && str[0])
+ if(ELEM3(obt->type, OB_ARMATURE, OB_MESH, OB_LATTICE) && str[0])
dag_add_relation(dag, node2, node, DAG_RL_DATA_OB|DAG_RL_OB_OB);
else
dag_add_relation(dag, node2, node, DAG_RL_OB_OB);