// --------------------------------------------------------------------------------------------------------------------
//
// Copyright (c) VRMADA, All rights reserved.
//
// --------------------------------------------------------------------------------------------------------------------
using System;
using UltimateXR.Core;
using UltimateXR.Manipulation.HandPoses;
namespace UltimateXR.Avatar.Rig
{
///
/// Runtime, lightweight version of . It is used to describe the local orientations of
/// finger bones of a for a given .
/// objects contain orientations in a well-known space. They are used to adapt hand
/// poses independently of the coordinate system used by each avatar. This means an additional transformation needs to
/// be performed to get to each avatar's coordinate system. is used
/// to have a high performant version that already contains the bone orientations in each avatar's coordinate system
/// so that hand pose blending can be computed using much less processing power.
///
public class UxrRuntimeHandPose
{
#region Public Types & Data
public string PoseName { get; }
public UxrHandPoseType PoseType { get; }
#endregion
#region Constructors & Finalizer
///
/// Constructor.
///
/// Avatar to compute the runtime hand pose for
/// Hand pose in a well-known coordinate system
public UxrRuntimeHandPose(UxrAvatar avatar, UxrHandPoseAsset handPoseAsset)
{
PoseName = handPoseAsset.name;
PoseType = handPoseAsset.PoseType;
HandDescriptorLeft = new UxrRuntimeHandDescriptor(avatar, UxrHandSide.Left, handPoseAsset, UxrHandPoseType.Fixed, UxrBlendPoseType.None);
HandDescriptorRight = new UxrRuntimeHandDescriptor(avatar, UxrHandSide.Right, handPoseAsset, UxrHandPoseType.Fixed, UxrBlendPoseType.None);
HandDescriptorOpenLeft = new UxrRuntimeHandDescriptor(avatar, UxrHandSide.Left, handPoseAsset, UxrHandPoseType.Blend, UxrBlendPoseType.OpenGrip);
HandDescriptorOpenRight = new UxrRuntimeHandDescriptor(avatar, UxrHandSide.Right, handPoseAsset, UxrHandPoseType.Blend, UxrBlendPoseType.OpenGrip);
HandDescriptorClosedLeft = new UxrRuntimeHandDescriptor(avatar, UxrHandSide.Left, handPoseAsset, UxrHandPoseType.Blend, UxrBlendPoseType.ClosedGrip);
HandDescriptorClosedRight = new UxrRuntimeHandDescriptor(avatar, UxrHandSide.Right, handPoseAsset, UxrHandPoseType.Blend, UxrBlendPoseType.ClosedGrip);
}
#endregion
#region Public Methods
///
/// Gets the given hand descriptor, based on the .
///
/// Hand to get the descriptor for
///
/// If is , whether to get the open or
/// closed pose descriptor.
///
/// Hand descriptor
public UxrRuntimeHandDescriptor GetHandDescriptor(UxrHandSide handSide, UxrBlendPoseType blendPoseType = UxrBlendPoseType.None)
{
return PoseType switch
{
UxrHandPoseType.Fixed => handSide == UxrHandSide.Left ? HandDescriptorLeft : HandDescriptorRight,
UxrHandPoseType.Blend when blendPoseType == UxrBlendPoseType.OpenGrip => handSide == UxrHandSide.Left ? HandDescriptorOpenLeft : HandDescriptorOpenRight,
UxrHandPoseType.Blend when blendPoseType == UxrBlendPoseType.ClosedGrip => handSide == UxrHandSide.Left ? HandDescriptorClosedLeft : HandDescriptorClosedRight,
_ => throw new ArgumentOutOfRangeException(nameof(blendPoseType), blendPoseType, null)
};
}
#endregion
#region Private Types & Data
private UxrRuntimeHandDescriptor HandDescriptorLeft { get; }
private UxrRuntimeHandDescriptor HandDescriptorRight { get; }
private UxrRuntimeHandDescriptor HandDescriptorOpenLeft { get; }
private UxrRuntimeHandDescriptor HandDescriptorOpenRight { get; }
private UxrRuntimeHandDescriptor HandDescriptorClosedLeft { get; }
private UxrRuntimeHandDescriptor HandDescriptorClosedRight { get; }
#endregion
}
}