【发布时间】:2018-01-25 09:36:31
【问题描述】:
我正在尝试将手设置为一系列姿势中的一个。我创建了一个脚本,它捕获一个帧,序列化左手,然后将其存储为 xml 以供加载。我目前让系统通过计算实时数据中手掌位置与存储姿势之间的偏移量来将手设置为正确的姿势。我遇到的问题是让手旋转。
'hand' 参数是来自实时数据的当前手,'pose' 参数是从 xml 加载的手。
这是我创建的方法:
public static Hand SetHandInPose(Hand hand, Hand pose)
{
if(hand == null)
{
Debug.Log("Hand is null, so returning that");
return hand;
}
if(pose == null)
{
Debug.Log("The loaded pose is null, so let's just return the original hand");
return hand;
}
Hand h = pose;
Quaternion handRotOffset = pose.Rotation.ToQuaternion() * Quaternion.Inverse(hand.Rotation.ToQuaternion());
//Debug.Log("The rotational offset is: " + handRotOffset.eulerAngles);
Vector offset = hand.PalmPosition - pose.PalmPosition;
h.Rotation = hand.Rotation;//(h.Rotation.ToQuaternion() * handRotOffset).ToLeapQuaternion();
h.PalmPosition += (offset.ToVector3()).ToVector();
h.WristPosition += (offset.ToVector3()).ToVector();
for(int f = 0; f< h.Fingers.Count; f++)
{
for(int i = 0; i < h.Fingers[f].bones.Length; i++)
{
//offset = hand.Fingers[f].bones[i].Center - pose.Fingers[f].bones[i].Center;
//if (h.Fingers[f].bones[i].Type == Bone.BoneType.TYPE_METACARPAL) continue;
h.Fingers[f].bones[i].Center += (offset.ToVector3()).ToVector();
h.Fingers[f].bones[i].NextJoint += (offset.ToVector3()).ToVector();
h.Fingers[f].bones[i].PrevJoint += (offset.ToVector3()).ToVector();
h.Fingers[f].bones[i].Rotation = hand.Fingers[f].bones[i].Rotation;
//h.Fingers[f].bones[i].Rotation = (h.Fingers[f].bones[i].Rotation.ToQuaternion() * handRotOffset).ToLeapQuaternion();
h.Fingers[f].bones[i].Direction = (h.Fingers[f].bones[i].NextJoint - h.Fingers[f].bones[i].PrevJoint);
h.Fingers[f].bones[i].Center = (h.Fingers[f].bones[i].PrevJoint + h.Fingers[f].bones[i].NextJoint) / 2f;
}
h.Fingers[f].Direction = h.Fingers[f].GetBone(Bone.BoneType.TYPE_INTERMEDIATE).Direction;
}
return h;
}
任何建议/帮助将不胜感激。
更新:
这是根据收到的建议的新代码。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using Leap;
using Leap.Unity;
public class MimicHandModelDriver : MonoBehaviour
{
public Chirality whichHand = Chirality.Left;
public enum RotationMode { Inherit, Overwrite }
public RotationMode rotationMode = RotationMode.Inherit;
public MultiLeap_CapsuleHand handModelToDrive;
private bool _handModelInitialized = false;
private bool _handModelBegun = false;
private Hand mimicHand = null;
Hand sourceHand; //The current hand from the live data
Hand poseHand; //Reference to the hand we load from XML that is in the pose we want
public Hand SourceHand
{
set
{
sourceHand = value;
}
}
public Hand PoseHand
{
set
{
poseHand = value;
}
}
private void Update()
{
if (sourceHand != null)
{
// Copy data from the tracked hand into the mimic hand.
if (mimicHand == null) { mimicHand = new Hand(); }
mimicHand.CopyFrom(poseHand); //copy the stored pose in the mimic hand
mimicHand.Arm.CopyFrom(poseHand.Arm); // copy the stored pose's arm into the mimic hand
// Use the rotation from the live data
var handRotation = sourceHand.Rotation.ToQuaternion();
// Transform the copied hand so that it's centered on the current hands position and matches it's rotation.
mimicHand.SetTransform(sourceHand.PalmPosition.ToVector3(), handRotation);
}
// Drive the attached HandModel.
if (mimicHand != null && handModelToDrive != null)
{
// Initialize the handModel if it hasn't already been initialized.
if (!_handModelInitialized)
{
handModelToDrive.SetLeapHand(mimicHand); //Prevents an error with null reference exception when creating the spheres from
//the init hand call
handModelToDrive.InitHand();
_handModelInitialized = true;
}
// Set the HandModel's hand data.
handModelToDrive.SetLeapHand(mimicHand);
// "Begin" the HandModel to represent a 'newly tracked' hand.
if (!_handModelBegun)
{
handModelToDrive.BeginHand();
_handModelBegun = true;
}
Debug.Log("Updating the mimic hand");
handModelToDrive.UpdateTheHand(); //This method contains the update code, with update code commented out
//so i control when a hand is updated. I have used this throughout the rest of my project so i know this works.
}
}
}
【问题讨论】:
-
看起来这个问题得到了答案,但几天后,这个问题根据一个新问题进行了实质性修改。我不知道这会在多大程度上使您在下面已经收到的帮助无效,但是由于您在新问题中提出了新问题,所以我认为这个更好地回到原来的状态。请记住,如果您的问题变化如此之大,以至于下面的答案是错误的或令人困惑的,那么他们可能会因此而被否决 - 尽量确保问答保持良好的秩序。
-
给出的答案并不适用。
-
它发生了。不过,如果您将此问题修改为当前问题,您将获得三份而不是两份。我不知道原来的情况与你的新情况有多大不同,但总的来说,即使答案没有帮助,我也不会修改它,因为对于一个问题和一个不同意的答案来说,它仍然令人困惑。我建议您关注第二个问题,因为 +2 可能有助于获得新观点。
标签: unity3d vector rotation quaternions leap-motion