Partager via


Suivi de la main — MRTK2

Profil de suivi de la main

Le profil Suivi de la main se trouve sous le profil Système d’entrée. Il contient des paramètres pour la personnalisation de la représentation manuelle.

Profil de suivi de la main

Préfabriqués joints

Les préfabriqués joints sont visualisées à l’aide de préfabriqués simples. Les joints palm et index sont d’une importance particulière et ont leur propre préfabriqué, tandis que toutes les autres articulations partagent le même préfabriqué.

Par défaut, les préfabriqués de jointure manuelle sont des primitives géométriques simples. Ceux-ci peuvent être remplacés si vous le souhaitez. Si aucun préfabriqué n’est spécifié, des GameObjects vides sont créés à la place.

Avertissement

Évitez d’utiliser des scripts complexes ou un rendu coûteux dans les préfabriqués joints, car les objets joints sont transformés sur chaque image et peuvent avoir un coût de performances important !

Représentation par défaut de l’articulation de la main Étiquettes communes
Articulations de la main Jointures de la main d’entrée

Préfabriqué maillé à la main

Le maillage de main est utilisé si des données de maillage entièrement définies sont fournies par l’appareil de suivi de la main. Le maillage pouvant être rendu dans le préfabriqué est remplacé par les données de l’appareil, de sorte qu’un maillage factice tel qu’un cube est suffisant. Le matériau du préfabriqué est utilisé pour la maille à main.

Maillage de main d’entrée

L’affichage du maillage de main peut avoir un impact notable sur les performances. Pour cette raison, il peut être entièrement désactivé en décochant l’option Activer la visualisation du maillage de main .

Paramètres de visualisation de la main

Les visualisations du maillage de main et des articulations de main peuvent être désactivées ou activées via les paramètres Modes de visualisation du maillage de main et Modes de visualisation des articulations de main, respectivement. Ces paramètres sont spécifiques au mode application, ce qui signifie qu’il est possible d’activer certaines fonctionnalités dans l’éditeur (pour voir les jointures avec la simulation dans l’éditeur, par exemple) tout en ayant les mêmes fonctionnalités désactivées lorsqu’elles sont déployées sur l’appareil (dans les builds du lecteur).

Notez qu’il est généralement recommandé d’activer la visualisation des articulations des mains dans l’éditeur (afin que la simulation dans l’éditeur indique où se trouvent les articulations de la main), et d’avoir à la fois la visualisation des articulations de main et la visualisation du maillage de main désactivées dans le lecteur (car elles entraînent un impact sur les performances).

Scripts

La position et la rotation peuvent être demandées à partir du système d’entrée pour chaque joint de main individuelle sous la forme d’un MixedRealityPose.

Le système autorise également l’accès aux GameObjects qui suivent les articulations. Cela peut être utile si un autre GameObject doit suivre une jointure en continu.

Les joints disponibles sont répertoriés dans l’énumération TrackedHandJoint .

Remarque

Les objets joints sont détruits lorsque le suivi de la main est perdu ! Assurez-vous que tous les scripts utilisant l’objet joint gèrent correctement le null cas pour éviter les erreurs !

Accès à un contrôleur de main donné

Un contrôleur de main spécifique est souvent disponible, par exemple lors de la gestion des événements d’entrée. Dans ce cas, les données conjointes peuvent être demandées directement à partir de l’appareil, à l’aide de l’interface IMixedRealityHand .

Interrogation d’une pose commune à partir du contrôleur

La TryGetJoint fonction retourne false si l’articulation demandée n’est pas disponible pour une raison quelconque. Dans ce cas, la pose résultante sera MixedRealityPose.ZeroIdentity.

public void OnSourceDetected(SourceStateEventData eventData)
{
  var hand = eventData.Controller as IMixedRealityHand;
  if (hand != null)
  {
    if (hand.TryGetJoint(TrackedHandJoint.IndexTip, out MixedRealityPose jointPose)
    {
      // ...
    }
  }
}

Transformation de joint à partir du visualiseur de main

Les objets joints peuvent être demandés au visualiseur de contrôleur.

public void OnSourceDetected(SourceStateEventData eventData)
{
  var handVisualizer = eventData.Controller.Visualizer as IMixedRealityHandVisualizer;
  if (handVisualizer != null)
  {
    if (handVisualizer.TryGetJointTransform(TrackedHandJoint.IndexTip, out Transform jointTransform)
    {
      // ...
    }
  }
}

Accès simplifié aux données de jointure

Si aucun contrôleur spécifique n’est fourni, des classes utilitaires sont fournies pour un accès pratique aux données des articulations manuelles. Ces fonctions demandent des données de jointure à partir du premier appareil de main disponible actuellement suivi.

Pose commune d’interrogation à partir de HandJointUtils

HandJointUtils est une classe statique qui interroge le premier appareil actif.

if (HandJointUtils.TryGetJointPose(TrackedHandJoint.IndexTip, Handedness.Right, out MixedRealityPose pose))
{
    // ...
}

Transformation d’articulation à partir d’un service d’articulation manuelle

IMixedRealityHandJointService conserve un ensemble persistant de GameObjects pour le suivi des jointures.

var handJointService = CoreServices.GetInputSystemDataProvider<IMixedRealityHandJointService>();
if (handJointService != null)
{
    Transform jointTransform = handJointService.RequestJointTransform(TrackedHandJoint.IndexTip, Handedness.Right);
    // ...
}

Événements de suivi de la main

Le système d’entrée fournit également des événements, si l’interrogation des données directement à partir des contrôleurs n’est pas souhaitable.

Événements conjoints

IMixedRealityHandJointHandler gère les mises à jour des positions conjointes.

public class MyHandJointEventHandler : IMixedRealityHandJointHandler
{
    public Handedness myHandedness;

    void IMixedRealityHandJointHandler.OnHandJointsUpdated(InputEventData<IDictionary<TrackedHandJoint, MixedRealityPose>> eventData)
    {
        if (eventData.Handedness == myHandedness)
        {
            if (eventData.InputData.TryGetValue(TrackedHandJoint.IndexTip, out MixedRealityPose pose))
            {
                // ...
            }
        }
    }
}

Événements de maillage

IMixedRealityHandMeshHandler gère les modifications de la maille de main articulée.

Notez que les maillages de main ne sont pas activés par défaut.

public class MyHandMeshEventHandler : IMixedRealityHandMeshHandler
{
    public Handedness myHandedness;
    public Mesh myMesh;

    public void OnHandMeshUpdated(InputEventData<HandMeshInfo> eventData)
    {
        if (eventData.Handedness == myHandedness)
        {
            myMesh.vertices = eventData.InputData.vertices;
            myMesh.normals = eventData.InputData.normals;
            myMesh.triangles = eventData.InputData.triangles;

            if (eventData.InputData.uvs != null && eventData.InputData.uvs.Length > 0)
            {
                myMesh.uv = eventData.InputData.uvs;
            }

            // ...
        }
    }
}

Problèmes connus

.NET Native

Il existe actuellement un problème connu avec les builds master utilisant le back-end .NET. Dans .NET Native, IInspectable les pointeurs ne peuvent pas être marshalés du code natif vers du code managé à l’aide Marshal.GetObjectForIUnknownde . MRTK l’utilise pour obtenir le afin de recevoir les SpatialCoordinateSystem données des mains et des yeux de la plateforme.

Nous avons fourni la source DLL comme solution de contournement à ce problème, dans le dépôt natif Mixed Reality Toolkit. Suivez les instructions du FICHIER LISEZ-MOI et copiez les fichiers binaires résultants dans un dossier Plug-ins de vos ressources Unity. Après cela, le script WindowsMixedRealityUtilities fourni dans MRTK résout la solution de contournement pour vous.

Si vous souhaitez créer votre propre DLL ou inclure cette solution de contournement dans une dll existante, le cœur de la solution de contournement est :

extern "C" __declspec(dllexport) void __stdcall MarshalIInspectable(IUnknown* nativePtr, IUnknown** inspectable)
{
    *inspectable = nativePtr;
}

Et son utilisation dans votre code Unity C# :

[DllImport("DotNetNativeWorkaround.dll", EntryPoint = "MarshalIInspectable")]
private static extern void GetSpatialCoordinateSystem(IntPtr nativePtr, out SpatialCoordinateSystem coordinateSystem);

private static SpatialCoordinateSystem GetSpatialCoordinateSystem(IntPtr nativePtr)
{
    try
    {
        GetSpatialCoordinateSystem(nativePtr, out SpatialCoordinateSystem coordinateSystem);
        return coordinateSystem;
    }
    catch
    {
        UnityEngine.Debug.LogError("Call to the DotNetNativeWorkaround plug-in failed. The plug-in is required for correct behavior when using .NET Native compilation");
        return Marshal.GetObjectForIUnknown(nativePtr) as SpatialCoordinateSystem;
    }
}