MCPcopy Create free account
hub / github.com/FlaxEngine/FlaxEngine / SolveTwoBoneIK

Method SolveTwoBoneIK

Source/Engine/Animations/InverseKinematics.cpp:13–179  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

11}
12
13void InverseKinematics::SolveTwoBoneIK(Transform& rootTransform, Transform& midJointTransform, Transform& endEffectorTransform, const Vector3& targetPosition, const Vector3& poleVector, bool allowStretching, float maxStretchScale)
14{
15 // Calculate limb segment lengths
16 Real lowerLimbLength = (endEffectorTransform.Translation - midJointTransform.Translation).Length();
17 Real upperLimbLength = (midJointTransform.Translation - rootTransform.Translation).Length();
18 Vector3 midJointPos = midJointTransform.Translation;
19
20 // Calculate the direction and length towards the target
21 Vector3 toTargetVector = targetPosition - rootTransform.Translation;
22 Real toTargetLength = toTargetVector.Length();
23 Real totalLimbLength = lowerLimbLength + upperLimbLength;
24
25 // Normalize the direction vector or set a default direction if too small
26 Vector3 toTargetDir;
27 if (toTargetLength < ZeroTolerance)
28 {
29 toTargetLength = ZeroTolerance;
30 toTargetDir = Vector3(1, 0, 0);
31 }
32 else
33 {
34 toTargetDir = toTargetVector.GetNormalized();
35 }
36
37 // Calculate the pole vector direction
38 Vector3 poleVectorDelta = poleVector - rootTransform.Translation;
39 const Real poleVectorLengthSqr = poleVectorDelta.LengthSquared();
40
41 Vector3 jointPlaneNormal, bendDirection;
42 if (poleVectorLengthSqr < ZeroTolerance * ZeroTolerance)
43 {
44 bendDirection = Vector3::Forward;
45 jointPlaneNormal = Vector3::Up;
46 }
47 else
48 {
49 jointPlaneNormal = toTargetDir ^ poleVectorDelta;
50 if (jointPlaneNormal.LengthSquared() < ZeroTolerance * ZeroTolerance)
51 {
52 toTargetDir.FindBestAxisVectors(jointPlaneNormal, bendDirection);
53 }
54 else
55 {
56 jointPlaneNormal.Normalize();
57 bendDirection = poleVectorDelta - (poleVectorDelta | toTargetDir) * toTargetDir;
58 bendDirection.Normalize();
59 }
60 }
61
62 // Handle limb stretching if allowed
63 if (allowStretching)
64 {
65 const Real initialStretchRatio = 1.0f;
66 const Real stretchRange = maxStretchScale - initialStretchRatio;
67 if (stretchRange > ZeroTolerance && totalLimbLength > ZeroTolerance)
68 {
69 const Real reachRatio = toTargetLength / totalLimbLength;
70 const Real scalingFactor = (maxStretchScale - 1.0f) * Math::Saturate((reachRatio - initialStretchRatio) / stretchRange);

Callers

nothing calls this directly

Calls 12

SaturateFunction · 0.85
FindBetweenFunction · 0.85
LookRotationFunction · 0.85
FindBestAxisVectorsMethod · 0.80
Vector3Class · 0.50
AcosFunction · 0.50
SinFunction · 0.50
SqrtFunction · 0.50
LengthMethod · 0.45
GetNormalizedMethod · 0.45
LengthSquaredMethod · 0.45
NormalizeMethod · 0.45

Tested by

no test coverage detected