Skip to content

Instantly share code, notes, and snippets.

@vshotarov
Last active August 30, 2022 16:50
Show Gist options
  • Star 3 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save vshotarov/5f28441fab335ccf1ee65d2563f02488 to your computer and use it in GitHub Desktop.
Save vshotarov/5f28441fab335ccf1ee65d2563f02488 to your computer and use it in GitHub Desktop.
Functions for switching between IK and FK setups, matching the existing pose.
'''File containing simple commands for switching between IK and FK and keeping the pose.
This file is used for demonstration purposes, to be followed along with in this blog post
http://bindpose.com/seamless-ik-fk-switch-maya-python/
'''
import maya.cmds as mc
def ikFkSwitch_sameOrient():
'''This command should be used in the cases where all the controls and joints, including the
ik control are oriented in the exact same way.'''
if mc.getAttr("L_armIkFk_CTL.fkIk"):
# From IK to FK
mc.delete(mc.orientConstraint("L_armIk01_JNT", "L_armFk01_CTL"))
mc.delete(mc.orientConstraint("L_armIk02_JNT", "L_armFk02_CTL"))
mc.delete(mc.orientConstraint("L_handIk01_JNT", "L_handFk01_CTL"))
mc.setAttr("L_armIkFk_CTL.fkIk", 0)
else:
# From FK to IK
mc.delete(mc.parentConstraint("L_handFk01_JNT", "L_armIk_CTL"))
arm01Vec = [mc.xform("L_armFk02_JNT", t=1, ws=1, q=1)[i] - mc.xform("L_armFk01_JNT", t=1, ws=1, q=1)[i] for i in range(3)]
arm02Vec = [mc.xform("L_armFk02_JNT", t=1, ws=1, q=1)[i] - mc.xform("L_armFk03_JNT", t=1, ws=1, q=1)[i] for i in range(3)]
mc.xform("L_armPv_CTL", t=[mc.xform("L_armFk02_JNT", t=1, q=1, ws=1)[i] + arm01Vec[i] * .75 + arm02Vec[i] * .75 for i in range(3)], ws=1)
mc.setAttr("L_armIkFk_CTL.fkIk", 1)
def ikFkSwitch_ikWorld():
'''This command should be uses in the cases where everything except the ik control is oriented
in the same way. Usually it is used when we want the ik control to be oriented in world space.
This function relies on the "L_hand01IkOfs_LOC" locator, which is a dummy object underneath
"L_handFk01_JNT", but is oriented in the same way as L_armIk_CTL.
Additionally, if we want to have the "L_handIk01_JNT", oriented the same way as the IK control,
we run this piece of code to apply an additional transformation to the "L_hand01IkOfs_LOC" in
order to adjust for that difference.
ikRot = [-1 * mc.xform("L_handIk01_JNT", ro=1 ,q=1)[i] for i in range(3)]
mc.xform("L_hand01IkOfs_LOC", ro=ikRot, r=1)
'''
if mc.getAttr("L_armIkFk_CTL.fkIk"):
# From IK to FK
mc.delete(mc.orientConstraint("L_armIk01_JNT", "L_armFk01_CTL"))
mc.delete(mc.orientConstraint("L_armIk02_JNT", "L_armFk02_CTL"))
mc.delete(mc.orientConstraint("L_handIk01_JNT", "L_handFk01_CTL"))
mc.setAttr("L_armIkFk_CTL.fkIk", 0)
else:
# From FK to IK
mc.delete(mc.parentConstraint("L_hand01IkOfs_LOC", "L_armIk_CTL"))
arm01Vec = [mc.xform("L_armFk02_JNT", t=1, ws=1, q=1)[i] - mc.xform("L_armFk01_JNT", t=1, ws=1, q=1)[i] for i in range(3)]
arm02Vec = [mc.xform("L_armFk02_JNT", t=1, ws=1, q=1)[i] - mc.xform("L_armFk03_JNT", t=1, ws=1, q=1)[i] for i in range(3)]
mc.xform("L_armPv_CTL", t=[mc.xform("L_armFk02_JNT", t=1, q=1, ws=1)[i] + arm01Vec[i] * .75 + arm02Vec[i] * .75 for i in range(3)], ws=1)
mc.setAttr("L_armIkFk_CTL.fkIk", 1)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment