diff options
author | Joshua Leung <aligorith@gmail.com> | 2007-11-01 14:08:07 +0300 |
---|---|---|
committer | Joshua Leung <aligorith@gmail.com> | 2007-11-01 14:08:07 +0300 |
commit | 1b4ca6d1bd301ac6a63931ef50a83cc43ee719a1 (patch) | |
tree | 2816d67adc5c0729e5292525be83fc5d7d857f24 /source/blender/src/editipo.c | |
parent | 0edb5983ecb6fcf67a7bf3de407cad19324ce94d (diff) |
Bugfix #7639: Visual Rot keyframing not working properly
When using targetless-ik, the offset in rotation of the final transform from the rest-position was being incorrectly calculated.
Now, visual-rotation keyframing uses the space-switching code I wrote for constraints, to calculate the value to keyframe. So far, it seems to work quite well.
As the constraint space-switcher correctly handles hinged bones too (I think it should!), I've also removed the restriction of only allowing visual-rotation keying on bones that didn't have hinge set.
Diffstat (limited to 'source/blender/src/editipo.c')
-rw-r--r-- | source/blender/src/editipo.c | 59 |
1 files changed, 34 insertions, 25 deletions
diff --git a/source/blender/src/editipo.c b/source/blender/src/editipo.c index 6017f8ffbde..5589dd79fb7 100644 --- a/source/blender/src/editipo.c +++ b/source/blender/src/editipo.c @@ -2289,6 +2289,8 @@ int insertmatrixkey(ID *id, int blocktype, char *actname, char *constname, int a return 1; } } else if ((adrcode==AC_QUAT_W)||(adrcode==AC_QUAT_X)||(adrcode==AC_QUAT_Y)||(adrcode==AC_QUAT_Z)) { + float tmat[4][4], trimat[3][3], localQuat[4]; + switch (adrcode) { case AC_QUAT_W: matindex=0; @@ -2303,21 +2305,18 @@ int insertmatrixkey(ID *id, int blocktype, char *actname, char *constname, int a matindex=3; break; } - if (!(pchan->bone->parent)||((pchan->bone->parent)&&!(pchan->bone->flag&BONE_HINGE))) { /* don't use for non-hinged child bones */ - float delta_mat[4][4],trimat[3][3]; - float localQuat[4]; - armature_mat_pose_to_delta(delta_mat, pchan->pose_mat, pchan->bone->arm_mat); - /* Fixed this bit up from the old "hacky" version, as it was called. - Not sure of the origin of Mat3ToQuat_is_ok or why its in there. In most cases, this - produces the same result of the "hacky" version, and in some - cases the results seem to be better. But whatever the case, this is unideal, as - we're decomposing a 3x3 rotation matrix into a quat, which is - not a discrete operation. */ - Mat3CpyMat4(trimat, delta_mat); - Mat3ToQuat_is_ok(trimat, localQuat); - insertfloatkey(id, ID_PO, pchan->name, NULL, adrcode, localQuat[matindex]); - return 1; - } + + /* it should be reasonable to assume that we are keyframing on the active object, although it is not + * strictly required for this particular space conversion, arg1 must not be null for this to work + */ + Mat4CpyMat4(tmat, pchan->pose_mat); + constraint_mat_convertspace(OBACT, pchan, tmat, CONSTRAINT_SPACE_POSE, CONSTRAINT_SPACE_LOCAL); + + Mat3CpyMat4(trimat, tmat); + Mat3ToQuat_is_ok(trimat, localQuat); + insertfloatkey(id, ID_PO, pchan->name, NULL, adrcode, localQuat[matindex]); + + return 1; } } } @@ -3090,23 +3089,33 @@ void common_insertkey(void) } } if(event==11 || event==13) { - insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_LOC_X); - insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_LOC_Y); - insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_LOC_Z); + int matok=0; + /* check one to make sure we're not trying to set visual loc keys on + bones inside of a chain, which only leads to tears. */ + matok= insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_LOC_X); + insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_LOC_Y); + insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_LOC_Z); + + if (matok == 0) { + insertkey(id, ID_PO, pchan->name, NULL, AC_LOC_X, 0); + insertkey(id, ID_PO, pchan->name, NULL, AC_LOC_Y, 0); + insertkey(id, ID_PO, pchan->name, NULL, AC_LOC_Z, 0); + } } if(event==12 || event==13) { - int matsuccess=0; + int matok=0; /* check one to make sure we're not trying to set visual rot keys on bones inside of a chain, which only leads to tears. */ - matsuccess=insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_QUAT_W); - insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_QUAT_X); - insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_QUAT_Y); - insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_QUAT_Z); - if (matsuccess==0) { + matok= insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_QUAT_W); + insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_QUAT_X); + insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_QUAT_Y); + insertmatrixkey(id, ID_PO, pchan->name, NULL, AC_QUAT_Z); + + if (matok == 0) { + insertkey(id, ID_PO, pchan->name, NULL, AC_QUAT_W, 0); insertkey(id, ID_PO, pchan->name, NULL, AC_QUAT_X, 0); insertkey(id, ID_PO, pchan->name, NULL, AC_QUAT_Y, 0); insertkey(id, ID_PO, pchan->name, NULL, AC_QUAT_Z, 0); - insertkey(id, ID_PO, pchan->name, NULL, AC_QUAT_W, 0); } } if (event==15 && ob->action) { |