💊IK Controller

This page is about a beta feature, that may not be stable yet

Introduction

Our SDK allows inverse kinematic control when playing a kinetix animation. The IK has multiple features such as :

  • Hint (or "Pole Vector"): These are positions like "left knee" or "right elbow" used by the IK to orient the elbow or knee in the correct direction.

  • Target: These are, as their name suggest, the target position and rotation for a hand or foot.

  • Auto-retargeted hand and foot rotation : Our IK ensure that if you have multiple rigs in your virtual world, the IK rotation will be the same for both characters.

  • Adjust Hips : This feature let you lock hands or foots into place by moving the hips

The entire IK api ask for global rotations and positions.

The IK target rotation is described as follow : For the hands, the forward vector points toward the fingers (we average each finger to get a forward direction). The down vector points toward the palm of the hand.

For the feet, the forward vector points toward the toes, parallel to the ground. The down vector points toward the knee. (based on the T-Pose)

The IK target position use the root game object you provide us when registering your avatar in order to convert from global context to the avatar context.

IK Event

Registering the OnBeforeIkEffect allows you bind to the Update of the Kinetix Animator before any IK is computed. This allows you to check for collisions or grounding and use IK methods.

void RegisterIkEventOnLocalPlayer(
    IKEffect.DelegateBeforeIkEffect _OnBeforeIkEffect
)

void UnregisterIkEventOnLocalPlayer(
    IKEffect.DelegateBeforeIkEffect _OnBeforeIkEffect
)

Example:

using Kinetix;
using UnityEngine;

public class MyIkTestClass : MonoBehaviour 
{
    [SerializeField] private Animator myAnimator;

    
    //This code is from the Quickstart example
    private void Awake() 
    {
        KinetixCore.OnInitialized += OnInitialize;
        KinetixCore.Initialize(new KinetixCoreConfiguration()
        {
            GameAPIKey = "yourGameAPIKey",
            PlayAutomaticallyAnimationOnAnimators = true,
            EnableAnalytics = true
        });
    }
    	
    private void OnInitialize()
    {
        KinetixCore.OnInitialized -= OnInitialize;
    
        //Register local Player
        KinetixCore.Animation.RegisterLocalPlayerAnimator(myAnimator);
        
        //Register IK event
        KinetixCore.Animation.RegisterIkEventOnLocalPlayer(Kinetix_OnBeforeIK);
    }
    
    private void OnDestroy() 
    {
        //"Try" in case the sdk is disposed before us.
        //Unregister the event
        try 
        {
            KinetixCore.Animation.UnregisterIkEventOnLocalPlayer(Kinetix_OnBeforeIK);
        }
        finally {}
    }
    
    private void Kinetix_OnBeforeIK(IKInfo currentPose) 
    {
        //In this example, every position and locations
        //depends on the scene and on the character.
        
        //We can use IK methods here.
        //We set the Elbow hint at the left foot position.
        KinetixCore.Animation.SetIKHintPositionOnLocalPlayer(AvatarIKHint.LeftElbow, Vector3.left);

        //Set target position for the left hand
        KinetixCore.Animation.SetIKPositionOnLocalPlayer(AvatarIKGoal.LeftHand, Vector3.left + 2*Vector3.up);
        //Set weight between the Animation pose and the IK pose.
        KinetixCore.Animation.SetIKPositionWeightOnLocalPlayer(AvatarIKGoal.LeftHand, 1); //1 = full ik
        
        //Make the palm look at the forward (= hand's back look at the back) and make the fingers look up
        KinetixCore.Animation.SetIKRotationOnLocalPlayer(AvatarIKGoal.LeftHand, Quaternion.LookRotation(Vector3.up, Vector3.back));        
        //Set weight between the Animation pose and the IK pose.
        KinetixCore.Animation.SetIKRotationWeightOnLocalPlayer(AvatarIKGoal.LeftHand, 1); //1 = full ik
    }
}

Target Position

//==============================//
// Set value                    //
//==============================//

//Position
void SetIKPositionOnLocalPlayer(
    AvatarIKGoal _Goal,
    Vector3 _Value
)

//Position + Weight
void SetIKPositionAndWeightOnLocalPlayer(
    AvatarIKGoal _Goal,
    Vector3 _Position,
    float _Weight
)

//Weight
void SetIKPositionWeightOnLocalPlayer(
    AvatarIKGoal _Goal, 
    float _Value
)

//==============================//
// Get value                    //
//==============================//

//Position
Vector3 GetIKPositionOnLocalPlayer(
    AvatarIKGoal _Goal
)

//Weight
float GetIKPositionWeightOnLocalPlayer(
    AvatarIKGoal _Goal
)

Position weight showcase :

Hint Position

These are positions like "left knee" or "right elbow" used by the IK to orient the elbow or knee in the correct direction.

void SetIKHintPositionOnLocalPlayer(
    AvatarIKHint _Hint,
    Vector3 _Value
)

Vector3 GetIKHintPositionOnLocalPlayer(
    AvatarIKHint _Hint
)

Global Target Rotation

Our IK ensure that if you have multiple rigs in your virtual world, the IK rotation will be the same for both characters. The global rotations are described as follow :

//==============================//
// Set value                    //
//==============================//

//Rotation
void SetIKRotationOnLocalPlayer(
    AvatarIKGoal _Goal,
    Quaternion _Value
)

//Rotation + Weight
void SetIKRotationAndWeightOnLocalPlayer(
    AvatarIKGoal _Goal,
    Quaternion _Rotation,
    float _Weight
)

//Weight
void SetIKRotationWeightOnLocalPlayer(
    AvatarIKGoal _Goal, 
    float _Value
)

//==============================//
// Get value                    //
//==============================//

//Rotation
Quaternion GetIKRotationOnLocalPlayer(
    AvatarIKGoal _Goal
)

//Weight
float GetIKRotationWeightOnLocalPlayer(
    AvatarIKGoal _Goal
)

Rotation (and position) weight showcase :

IK Weight

//==============================//
// Set value                    //
//==============================//

void SetIKPositionWeightOnLocalPlayer(
    AvatarIKGoal _Goal,
    float _Value
)

void SetIKRotationWeightOnLocalPlayer(
    AvatarIKGoal _Goal, 
    float _Value
)

//==============================//
// Get value                    //
//==============================//

float GetIKPositionWeightOnLocalPlayer(
    AvatarIKGoal _Goal
)

float GetIKRotationWeightOnLocalPlayer(
    AvatarIKGoal _Goal
)

Adjust Hips

This feature let you lock hands or foots into place by moving the hips

//==============================//
// Set value                    //
//==============================//

void SetIKAdjustHipsOnLocalPlayer(
    AvatarIKGoal _Goal,
    bool _Value
)

//==============================//
// Get value                    //
//==============================//

bool GetIKAdjustHipsOnLocalPlayer(
    AvatarIKGoal _Goal
)

Last updated