[Bf-blender-cvs] [31fda0363d5] temp-angavrilov-constraints: Add Custom Space to Constraints
Henrik Dick
noreply at git.blender.org
Wed Dec 2 18:25:37 CET 2020
Commit: 31fda0363d55f9b451427b6693591a1be062e905
Author: Henrik Dick
Date: Mon Nov 23 19:26:53 2020 +0300
Branches: temp-angavrilov-constraints
https://developer.blender.org/rB31fda0363d55f9b451427b6693591a1be062e905
Add Custom Space to Constraints
Constraints can currently only use World Space, Local Space, Pose Space, Local with Parent.
This patch adds Custom Space with a custom object to define the evaluation space.
The Custom Space option uses the Local Space of an other object/bone/vertex group.
If selected on owner or target it will show a box for object selection.
If an armature is selected, then it will also show a box for bone selection.
If a mesh object is selected it will show the option for using the local space of a vertex group.
It looks like this in the UI:
{F8731291}
The motivation for this patch is the following situation.
If you have a copy location constraint in your armature you are already limited when you want to use a specific axis. It can be done, but its unneccessarily difficult (as far as I know). But the situation is close to impossible as soon as you have a root bone in your armature (which I was told you always want). I need to only copy the location along a custom axis for a lot of things. The same goes for copy rotation/scale and all the limit constraints because I need to make that axis relat [...]
Here is a demo video:
{F8498960}
This is the file of that video:
{F8647541}
This is the file for the tests included in this patch:
{F8699677}
File intended for acceptance test:
{F8879818}
Reviewed By: #animation_rigging, sybren, Severin, angavrilov
Differential Revision: https://developer.blender.org/D7437
===================================================================
M release/scripts/startup/bl_ui/properties_constraint.py
M source/blender/blenkernel/BKE_constraint.h
M source/blender/blenkernel/intern/constraint.c
M source/blender/blenkernel/intern/fcurve_driver.c
M source/blender/editors/armature/armature_add.c
M source/blender/makesdna/DNA_constraint_types.h
M source/blender/makesrna/intern/rna_constraint.c
M source/blender/makesrna/intern/rna_object_api.c
M tests/python/bl_constraints.py
===================================================================
diff --git a/release/scripts/startup/bl_ui/properties_constraint.py b/release/scripts/startup/bl_ui/properties_constraint.py
index f46e9f9727f..71a7b056d07 100644
--- a/release/scripts/startup/bl_ui/properties_constraint.py
+++ b/release/scripts/startup/bl_ui/properties_constraint.py
@@ -85,14 +85,23 @@ class ConstraintButtonsPanel(Panel):
row.operator("constraint.disable_keep_transform", text="", icon='CANCEL')
@staticmethod
- def space_template(layout, con, target=True, owner=True):
+ def space_template(layout, con, target=True, owner=True, separator=True):
if target or owner:
- layout.separator()
+ if separator:
+ layout.separator()
if target:
layout.prop(con, "target_space", text="Target")
if owner:
layout.prop(con, "owner_space", text="Owner")
+ if con.target_space == 'CUSTOM' or con.owner_space == 'CUSTOM':
+ col = layout.column()
+ col.prop(con, "space_object")
+ if con.space_object and con.space_object.type == 'ARMATURE':
+ col.prop_search(con, "space_subtarget", con.space_object.data, "bones", text="Bone")
+ elif con.space_object and con.space_object.type in {'MESH', 'LATTICE'}:
+ col.prop_search(con, "space_subtarget", con.space_object, "vertex_groups", text="Vertex Group")
+
@staticmethod
def target_template(layout, con, subtargets=True):
col = layout.column()
@@ -237,7 +246,7 @@ class ConstraintButtonsPanel(Panel):
row.label(icon="BLANK1")
layout.prop(con, "use_transform_limit")
- layout.prop(con, "owner_space")
+ self.space_template(layout, con, target=False, owner=True)
self.draw_influence(layout, con)
@@ -306,7 +315,7 @@ class ConstraintButtonsPanel(Panel):
row.prop_decorator(con, "max_z")
layout.prop(con, "use_transform_limit")
- layout.prop(con, "owner_space")
+ self.space_template(layout, con, target=False, owner=True)
self.draw_influence(layout, con)
@@ -375,7 +384,7 @@ class ConstraintButtonsPanel(Panel):
row.prop_decorator(con, "max_z")
layout.prop(con, "use_transform_limit")
- layout.prop(con, "owner_space")
+ self.space_template(layout, con, target=False, owner=True)
self.draw_influence(layout, con)
@@ -483,7 +492,7 @@ class ConstraintButtonsPanel(Panel):
layout.prop(con, "volume")
- layout.prop(con, "owner_space")
+ self.space_template(layout, con, target=False, owner=True)
self.draw_influence(layout, con)
@@ -1117,7 +1126,7 @@ class ConstraintButtonsSubPanel(Panel):
col = layout.column()
col.active = not con.use_eval_time
col.prop(con, "transform_channel", text="Channel")
- col.prop(con, "target_space")
+ ConstraintButtonsPanel.space_template(col, con, target=True, owner=False, separator=False)
sub = col.column(align=True)
sub.prop(con, "min", text="Range Min")
diff --git a/source/blender/blenkernel/BKE_constraint.h b/source/blender/blenkernel/BKE_constraint.h
index e5c4535560d..4b9f480e091 100644
--- a/source/blender/blenkernel/BKE_constraint.h
+++ b/source/blender/blenkernel/BKE_constraint.h
@@ -56,6 +56,8 @@ typedef struct bConstraintOb {
float matrix[4][4];
/** original matrix (before constraint solving) */
float startmat[4][4];
+ /** space matrix for custom object space */
+ float space_obj_world_matrix[4][4];
/** type of owner */
short type;
@@ -203,6 +205,7 @@ void BKE_constraints_clear_evalob(struct bConstraintOb *cob);
void BKE_constraint_mat_convertspace(struct Object *ob,
struct bPoseChannel *pchan,
+ struct bConstraintOb *cob,
float mat[4][4],
short from,
short to,
@@ -221,6 +224,7 @@ void BKE_constraint_targets_for_solving_get(struct Depsgraph *depsgraph,
struct bConstraintOb *ob,
struct ListBase *targets,
float ctime);
+void BKE_constraint_custom_object_space_get(float r_mat[4][4], struct bConstraint *con);
void BKE_constraints_solve(struct Depsgraph *depsgraph,
struct ListBase *conlist,
struct bConstraintOb *cob,
diff --git a/source/blender/blenkernel/intern/constraint.c b/source/blender/blenkernel/intern/constraint.c
index 5497065bb34..1a16f1d3c6e 100644
--- a/source/blender/blenkernel/intern/constraint.c
+++ b/source/blender/blenkernel/intern/constraint.c
@@ -261,8 +261,13 @@ void BKE_constraints_clear_evalob(bConstraintOb *cob)
* of a matrix from one space to another for constraint evaluation.
* For now, this is only implemented for Objects and PoseChannels.
*/
-void BKE_constraint_mat_convertspace(
- Object *ob, bPoseChannel *pchan, float mat[4][4], short from, short to, const bool keep_scale)
+void BKE_constraint_mat_convertspace(Object *ob,
+ bPoseChannel *pchan,
+ bConstraintOb *cob,
+ float mat[4][4],
+ short from,
+ short to,
+ const bool keep_scale)
{
float diff_mat[4][4];
float imat[4][4];
@@ -282,25 +287,30 @@ void BKE_constraint_mat_convertspace(
switch (from) {
case CONSTRAINT_SPACE_WORLD: /* ---------- FROM WORLDSPACE ---------- */
{
- /* world to pose */
- invert_m4_m4(imat, ob->obmat);
- mul_m4_m4m4(mat, imat, mat);
-
- /* use pose-space as stepping stone for other spaces... */
- if (ELEM(to, CONSTRAINT_SPACE_LOCAL, CONSTRAINT_SPACE_PARLOCAL)) {
- /* call self with slightly different values */
- BKE_constraint_mat_convertspace(ob, pchan, mat, CONSTRAINT_SPACE_POSE, to, keep_scale);
+ if (to == CONSTRAINT_SPACE_CUSTOM) {
+ /* World to custom. */
+ BLI_assert(cob);
+ invert_m4_m4(imat, cob->space_obj_world_matrix);
+ mul_m4_m4m4(mat, imat, mat);
+ }
+ else {
+ /* World to pose. */
+ invert_m4_m4(imat, ob->obmat);
+ mul_m4_m4m4(mat, imat, mat);
+
+ /* Use pose-space as stepping stone for other spaces. */
+ if (ELEM(to, CONSTRAINT_SPACE_LOCAL, CONSTRAINT_SPACE_PARLOCAL)) {
+ /* Call self with slightly different values. */
+ BKE_constraint_mat_convertspace(
+ ob, pchan, cob, mat, CONSTRAINT_SPACE_POSE, to, keep_scale);
+ }
}
break;
}
case CONSTRAINT_SPACE_POSE: /* ---------- FROM POSESPACE ---------- */
{
- /* pose to world */
- if (to == CONSTRAINT_SPACE_WORLD) {
- mul_m4_m4m4(mat, ob->obmat, mat);
- }
/* pose to local */
- else if (to == CONSTRAINT_SPACE_LOCAL) {
+ if (to == CONSTRAINT_SPACE_LOCAL) {
if (pchan->bone) {
BKE_armature_mat_pose_to_bone(pchan, mat, mat);
}
@@ -312,6 +322,16 @@ void BKE_constraint_mat_convertspace(
mul_m4_m4m4(mat, imat, mat);
}
}
+ else {
+ /* Pose to world. */
+ mul_m4_m4m4(mat, ob->obmat, mat);
+ /* Use world-space as stepping stone for other spaces. */
+ if (to != CONSTRAINT_SPACE_WORLD) {
+ /* Call self with slightly different values. */
+ BKE_constraint_mat_convertspace(
+ ob, pchan, cob, mat, CONSTRAINT_SPACE_WORLD, to, keep_scale);
+ }
+ }
break;
}
case CONSTRAINT_SPACE_LOCAL: /* ------------ FROM LOCALSPACE --------- */
@@ -323,9 +343,10 @@ void BKE_constraint_mat_convertspace(
}
/* use pose-space as stepping stone for other spaces */
- if (ELEM(to, CONSTRAINT_SPACE_WORLD, CONSTRAINT_SPACE_PARLOCAL)) {
+ if (ELEM(to, CONSTRAINT_SPACE_WORLD, CONSTRAINT_SPACE_PARLOCAL, CONSTRAINT_SPACE_CUSTOM)) {
/* call self with slightly different values */
- BKE_constraint_mat_convertspace(ob, pchan, mat, CONSTRAINT_SPACE_POSE, to, keep_scale);
+ BKE_constraint_mat_convertspace(
+ ob, pchan, cob, mat, CONSTRAINT_SPACE_POSE, to, keep_scale);
}
break;
}
@@ -337,9 +358,24 @@ void BKE_constraint_mat_convertspace(
}
/* use pose-space as stepping stone for other spaces */
- if (ELEM(to, CONSTRAINT_SPACE_WORLD, CONSTRAINT_SPACE_LOCAL)) {
+ if (ELEM(to, CONSTRAINT_SPACE_WORLD, CONSTRAINT_SPACE_LOCAL, CONSTRAINT_SPACE_CUSTOM)) {
/* call self with slightly different values */
- BKE_constraint_mat_convertspace(ob, pchan, mat, CONSTRAINT_SPACE_POSE, to, keep_scale);
+ BKE_constraint_mat_convertspace(
+ ob, pchan, cob, mat, CONSTRAINT_SPACE_POSE, to, keep_scale);
+ }
+ break;
+ }
+ case CONSTRAINT_SPACE_CUSTOM: /* -------------- FROM CUSTOM SPACE ---------- */
+ {
+ /* Custom to world. */
+ BLI_assert(cob);
+ mul_m4_m4m4(mat, cob->space_obj_world_matrix, mat);
+
+ /* Use world-space as stepping stone for other spaces. */
+ if (to != CONSTRAINT_SPACE_WORLD) {
+ /* Call self with slightly different values. */
+ BKE_constraint_mat_convertspace(
+ ob, pchan, cob, mat, CONSTRAINT_SPACE_WORLD, to, keep_scale);
}
break;
}
@@ -347,37 +383,44 @@ void BKE_constraint_mat_convertspace(
}
else {
/* objects */
- if (from == CONSTRAINT_SPACE_WORLD && to == CONSTRAINT_SPACE_LOCAL) {
- /* check if object has a parent */
- if (ob->parent) {
- /* 'subtract' parent's effects from owner */
- mul_m4_m4m4(diff_mat, ob->parent->obmat, ob->parentinv);
- invert_m4_m4_
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list