Merge pull request #6008 from AndrewMeadows/ik-targets-use-model-frame

IK targets specified in the skeleton's model-frame
This commit is contained in:
Brad Hefta-Gaub 2015-10-06 17:34:42 -07:00
commit 02bb372c27
8 changed files with 28 additions and 45 deletions

View file

@ -135,7 +135,7 @@ void SkeletonModel::updateRig(float deltaTime, glm::mat4 parentTransform) {
headParams.isInHMD = true;
// get HMD position from sensor space into world space, and back into model space
AnimPose avatarToWorld(glm::vec3(1), myAvatar->getOrientation(), myAvatar->getPosition());
AnimPose avatarToWorld(glm::vec3(1.0f), myAvatar->getOrientation(), myAvatar->getPosition());
glm::mat4 worldToAvatar = glm::inverse((glm::mat4)avatarToWorld);
glm::mat4 worldHMDMat = myAvatar->getSensorToWorldMatrix() * myAvatar->getHMDSensorMatrix();
glm::mat4 hmdMat = worldToAvatar * worldHMDMat;

View file

@ -78,17 +78,6 @@ void AnimInverseKinematics::setTargetVars(
}
}
static int findRootJointInSkeleton(AnimSkeleton::ConstPointer skeleton, int index) {
// walk down the skeleton hierarchy to find the joint's root
int rootIndex = -1;
int parentIndex = skeleton->getParentIndex(index);
while (parentIndex != -1) {
rootIndex = parentIndex;
parentIndex = skeleton->getParentIndex(parentIndex);
}
return rootIndex;
}
void AnimInverseKinematics::computeTargets(const AnimVariantMap& animVars, std::vector<IKTarget>& targets, const AnimPoseVec& underPoses) {
// build a list of valid targets from _targetVarVec and animVars
_maxTargetIndex = -1;
@ -100,7 +89,6 @@ void AnimInverseKinematics::computeTargets(const AnimVariantMap& animVars, std::
if (jointIndex >= 0) {
// this targetVar has a valid joint --> cache the indices
targetVar.jointIndex = jointIndex;
targetVar.rootIndex = findRootJointInSkeleton(_skeleton, jointIndex);
} else {
qCWarning(animation) << "AnimInverseKinematics could not find jointName" << targetVar.jointName << "in skeleton";
removeUnfoundJoints = true;
@ -111,7 +99,6 @@ void AnimInverseKinematics::computeTargets(const AnimVariantMap& animVars, std::
target.pose.trans = animVars.lookup(targetVar.positionVar, defaultPose.trans);
target.pose.rot = animVars.lookup(targetVar.rotationVar, defaultPose.rot);
target.setType(animVars.lookup(targetVar.typeVar, QString("")));
target.rootIndex = targetVar.rootIndex;
target.index = targetVar.jointIndex;
targets.push_back(target);
if (target.index > _maxTargetIndex) {
@ -295,7 +282,7 @@ void AnimInverseKinematics::solveWithCyclicCoordinateDescent(const std::vector<I
continue;
}
glm::vec3 tipPosition = absolutePoses[target.index].trans;
std::cout << i << " IK error = " << glm::distance(tipPosition, target.pose.trans) << std::endl; // adebug
std::cout << i << " IK error = " << glm::distance(tipPosition, target.pose.trans) << std::endl;
}
*/

View file

@ -44,7 +44,6 @@ protected:
};
AnimPose pose;
int index;
int rootIndex;
Type type = Type::RotationAndPosition;
void setType(const QString& typeVar) { type = ((typeVar == "RotationOnly") ? Type::RotationOnly : Type::RotationAndPosition); }
@ -70,15 +69,14 @@ protected:
rotationVar(rotationVarIn),
typeVar(typeVarIn),
jointName(jointNameIn),
jointIndex(-1),
rootIndex(-1) {}
jointIndex(-1)
{}
QString positionVar;
QString rotationVar;
QString typeVar;
QString jointName;
int jointIndex; // cached joint index
int rootIndex; // cached root index
};
std::map<int, RotationConstraint*> _constraints;

View file

@ -29,23 +29,6 @@ void AnimNode::setSkeleton(const AnimSkeleton::Pointer skeleton) {
}
}
const AnimPose AnimNode::getRootPose(int jointIndex) const {
AnimPose pose = AnimPose::identity;
if (_skeleton && jointIndex != -1) {
const AnimPoseVec& poses = getPosesInternal();
int numJoints = (int)(poses.size());
if (jointIndex < numJoints) {
int parentIndex = _skeleton->getParentIndex(jointIndex);
while (parentIndex != -1 && parentIndex < numJoints) {
jointIndex = parentIndex;
parentIndex = _skeleton->getParentIndex(jointIndex);
}
pose = poses[jointIndex];
}
}
return pose;
}
void AnimNode::setCurrentFrame(float frame) {
setCurrentFrameInternal(frame);
for (auto&& child : _children) {

View file

@ -75,8 +75,6 @@ public:
return evaluate(animVars, dt, triggersOut);
}
const AnimPose getRootPose(int jointIndex) const;
protected:
void setCurrentFrame(float frame);

View file

@ -93,6 +93,23 @@ const AnimPose& AnimSkeleton::getAbsoluteBindPose(int jointIndex) const {
return _absoluteBindPoses[jointIndex];
}
AnimPose AnimSkeleton::getRootAbsoluteBindPoseByChildName(const QString& childName) const {
AnimPose pose = AnimPose::identity;
int jointIndex = nameToJointIndex(childName);
if (jointIndex >= 0) {
int numJoints = (int)(_absoluteBindPoses.size());
if (jointIndex < numJoints) {
int parentIndex = getParentIndex(jointIndex);
while (parentIndex != -1 && parentIndex < numJoints) {
jointIndex = parentIndex;
parentIndex = getParentIndex(jointIndex);
}
pose = _absoluteBindPoses[jointIndex];
}
}
return pose;
}
const AnimPose& AnimSkeleton::getRelativeBindPose(int jointIndex) const {
return _relativeBindPoses[jointIndex];
}

View file

@ -57,6 +57,7 @@ public:
// absolute pose, not relative to parent
const AnimPose& getAbsoluteBindPose(int jointIndex) const;
AnimPose getRootAbsoluteBindPoseByChildName(const QString& childName) const;
// relative to parent pose
const AnimPose& getRelativeBindPose(int jointIndex) const;

View file

@ -1036,7 +1036,7 @@ void Rig::updateNeckJoint(int index, const HeadParameters& params) {
glm::vec3 headPos, neckPos;
glm::quat headRot, neckRot;
AnimPose avatarHMDPose(glm::vec3(1), params.localHeadOrientation, params.localHeadPosition);
AnimPose avatarHMDPose(glm::vec3(1.0f), params.localHeadOrientation, params.localHeadPosition);
computeHeadNeckAnimVars(_animSkeleton, avatarHMDPose, headPos, headRot, neckPos, neckRot);
// debug rendering
@ -1126,18 +1126,17 @@ void Rig::updateFromHandParameters(const HandParameters& params, float dt) {
// TODO: figure out how to obtain the yFlip from where it is actually stored
glm::quat yFlipHACK = glm::angleAxis(PI, glm::vec3(0.0f, 1.0f, 0.0f));
int leftHandIndex = _animSkeleton->nameToJointIndex("LeftHand");
AnimPose rootPose = _animNode->getRootPose(leftHandIndex);
AnimPose rootBindPose = _animSkeleton->getRootAbsoluteBindPoseByChildName("LeftHand");
if (params.isLeftEnabled) {
_animVars.set("leftHandPosition", rootPose.trans + rootPose.rot * yFlipHACK * params.leftPosition);
_animVars.set("leftHandRotation", rootPose.rot * yFlipHACK * params.leftOrientation);
_animVars.set("leftHandPosition", rootBindPose.trans + rootBindPose.rot * yFlipHACK * params.leftPosition);
_animVars.set("leftHandRotation", rootBindPose.rot * yFlipHACK * params.leftOrientation);
} else {
_animVars.unset("leftHandPosition");
_animVars.unset("leftHandRotation");
}
if (params.isRightEnabled) {
_animVars.set("rightHandPosition", rootPose.trans + rootPose.rot * yFlipHACK * params.rightPosition);
_animVars.set("rightHandRotation", rootPose.rot * yFlipHACK * params.rightOrientation);
_animVars.set("rightHandPosition", rootBindPose.trans + rootBindPose.rot * yFlipHACK * params.rightPosition);
_animVars.set("rightHandRotation", rootBindPose.rot * yFlipHACK * params.rightOrientation);
} else {
_animVars.unset("rightHandPosition");
_animVars.unset("rightHandRotation");