Gesten in Unity

Es gibt zwei wichtige Möglichkeiten, den Blick in Unity zu ergreifen: Handgesten und Bewegungscontroller in HoloLens und Immersive HMD. Sie greifen über die gleichen APIs in Unity auf die Daten für beide Quellen räumlicher Eingaben zu.

Unity bietet zwei primäre Möglichkeiten für den Zugriff auf räumliche Eingabedaten für Windows Mixed Reality. Die allgemeinen Input.GetButton/Input.GetAxis-APIs funktionieren über mehrere Unity XR SDKs hinweg, während die interactionManager/GestureRecognizer-API speziell für Windows Mixed Reality den vollständigen Satz räumlicher Eingabedaten verfügbar macht.

Allgemeine zusammengesetzte Gesten-APIs (GestureRecognizer)

Namespace:UnityEngine.XR.WSA.Input
Typen: GestureRecognizer, GestureSettings, InteractionSourceKind

Ihre App kann auch zusammengesetzte Gesten höherer Ebene für räumliche Eingabequellen, Tippen, Halten, Manipulation und Navigationsgesten erkennen. Sie können diese zusammengesetzten Gesten sowohl über Hände als auch über Bewegungscontroller mithilfe von GestureRecognizer erkennen.

Jedes Gestenereignis im GestureRecognizer stellt das SourceKind für die Eingabe sowie den Zielkopfstrahl zum Zeitpunkt des Ereignisses bereit. Einige Ereignisse bieten zusätzliche kontextspezifische Informationen.

Es sind nur einige Schritte erforderlich, um Gesten mithilfe einer Gestenerkennung zu erfassen:

  1. Erstellen einer neuen Gestenerkennung
  2. Angeben, für welche Gesten watch werden sollen
  3. Abonnieren von Ereignissen für diese Gesten
  4. Beginnen der Erfassung von Gesten

Erstellen einer neuen Gestenerkennung

Um gestureRecognizer verwenden zu können, müssen Sie ein GestureRecognizer-Element erstellt haben:

GestureRecognizer recognizer = new GestureRecognizer();

Angeben, für welche Gesten watch werden sollen

Geben Sie über SetRecognizableGestures() an, welche Gesten Sie interessieren:

recognizer.SetRecognizableGestures(GestureSettings.Tap | GestureSettings.Hold);

Abonnieren von Ereignissen für diese Gesten

Abonnieren Sie Ereignisse für die Gesten, die Sie interessieren.

void Start()
{
    recognizer.Tapped += GestureRecognizer_Tapped;
    recognizer.HoldStarted += GestureRecognizer_HoldStarted;
    recognizer.HoldCompleted += GestureRecognizer_HoldCompleted;
    recognizer.HoldCanceled += GestureRecognizer_HoldCanceled;
}

Hinweis

Navigations- und Manipulationsgesten schließen sich auf einer instance eines GestureRecognizers gegenseitig aus.

Beginnen der Erfassung von Gesten

Standardmäßig überwacht ein GestureRecognizer die Eingabe erst, wenn StartCapturingGestures() aufgerufen wird. Es ist möglich, dass ein Gestenereignis generiert wird, nachdem StopCapturingGestures() aufgerufen wurde, wenn die Eingabe vor dem Frame ausgeführt wurde, in dem StopCapturingGestures() verarbeitet wurde. Der GestureRecognizer merkt sich, ob es während des vorherigen Frames aktiviert oder deaktiviert war, in dem die Geste tatsächlich aufgetreten ist. Daher ist es zuverlässig, die Gestenüberwachung basierend auf der Ausrichtung dieses Frames zu starten und zu beenden.

recognizer.StartCapturingGestures();

Beenden der Erfassung von Gesten

So beenden Sie die Gestenerkennung:

recognizer.StopCapturingGestures();

Entfernen einer Gestenerkennung

Denken Sie daran, sich von abonnierten Ereignissen abzumelden, bevor Sie ein GestureRecognizer-Objekt zerstören.

void OnDestroy()
{
    recognizer.Tapped -= GestureRecognizer_Tapped;
    recognizer.HoldStarted -= GestureRecognizer_HoldStarted;
    recognizer.HoldCompleted -= GestureRecognizer_HoldCompleted;
    recognizer.HoldCanceled -= GestureRecognizer_HoldCanceled;
}

Rendern des Motion Controller-Modells in Unity

Motion Controller-Modell und Teleportierung
Motion Controller-Modell und Teleportierung

Um Motion Controller in Ihrer App zu rendern, die mit den physischen Controllern übereinstimmen, die Benutzer halten und während verschiedene Schaltflächen gedrückt werden, können Sie das MotionController-Prefab im Mixed Reality Toolkit verwenden. Dieses Prefab lädt dynamisch das richtige glTF-Modell zur Laufzeit aus dem installierten Motion Controller-Treiber des Systems. Es ist wichtig, diese Modelle dynamisch zu laden, anstatt sie manuell im Editor zu importieren, damit Ihre App physisch genaue 3D-Modelle für alle aktuellen und zukünftigen Controller zeigt, über die Ihre Benutzer möglicherweise verfügen.

  1. Befolgen Sie die Erste Schritte Anweisungen, um das Mixed Reality Toolkit herunterzuladen und ihrem Unity-Projekt hinzuzufügen.
  2. Wenn Sie Ihre Kamera im Rahmen der Erste Schritte Schritte durch das MixedRealityCameraParent Prefab ersetzt haben, können Sie losgehen! Dieses Prefab umfasst motion controller rendering. Andernfalls fügen Sie Assets/HoloToolkit/Input/Prefabs/MotionControllers.prefab aus dem Projektbereich ihrer Szene hinzu. Sie sollten dieses Prefab als untergeordnetes Element des übergeordneten Objekts hinzufügen, das Sie verwenden, um die Kamera zu bewegen, wenn der Benutzer in Ihrer Szene teleportiert, sodass die Controller mit dem Benutzer zusammenkommen. Wenn Ihre App kein Teleporting umfasst, fügen Sie einfach das Prefab am Stamm ihrer Szene hinzu.

Auslösen von Objekten

Das Auslösen von Objekten in der virtuellen Realität ist ein schwierigeres Problem, als es auf den ersten Blick erscheinen mag. Wie bei den meisten physischen Interaktionen ist das Auslösen im Spiel auf unerwartete Weise sofort offensichtlich und bricht die Immersion. Wir haben einige Zeit damit verbracht, tief darüber nachzudenken, wie wir ein physisch korrektes Wurfverhalten darstellen können, und haben einige Richtlinien erstellt, die durch Updates für unsere Plattform ermöglicht werden, die wir mit Ihnen teilen möchten.

Ein Beispiel für die Implementierung von Throwing finden Sie hier. Dieses Beispiel folgt den folgenden vier Richtlinien:

  • Verwenden Sie die Geschwindigkeit des Controllers anstelle der Position. Im November-Update für Windows haben wir eine Änderung des Verhaltens eingeführt, wenn sich der Positionsnachverfolgungszustand "Ungefähr" befindet. In diesem Zustand werden Geschwindigkeitsinformationen über den Controller weiterhin gemeldet, solange wir glauben, dass seine hohe Genauigkeit, die oft länger als die Position ist, hohe Genauigkeit bleibt.

  • Integrieren Sie die Winkelgeschwindigkeit des Controllers. Diese Logik ist alle in der throwing.cs Datei in der GetThrownObjectVelAngVel statischen Methode im oben verknüpften Paket enthalten:

    1. Da die Winkelgeschwindigkeit beibehalten wird, muss das ausgelöste Objekt dieselbe Winkelgeschwindigkeit wie zum Zeitpunkt des Wurfs beibehalten: objectAngularVelocity = throwingControllerAngularVelocity;

    2. Da sich der Massenmittelpunkt des ausgelösten Objekts wahrscheinlich nicht am Ursprung der Griffposition befindet, hat es wahrscheinlich eine andere Geschwindigkeit als die des Controllers im Bezugsrahmen des Benutzers. Der Teil der Geschwindigkeit des Objekts, der auf diese Weise beigetragen hat, ist die sofortige Tangentialgeschwindigkeit des Massenmittelpunkts des ausgelösten Objekts um den Controllerursprung. Diese Tangentialgeschwindigkeit ist das Kreuzprodukt der Winkelgeschwindigkeit des Controllers mit dem Vektor, der den Abstand zwischen dem Controllerursprung und dem Massenmittelpunkt des ausgelösten Objekts darstellt.

      Vector3 radialVec = thrownObjectCenterOfMass - throwingControllerPos;
      Vector3 tangentialVelocity = Vector3.Cross(throwingControllerAngularVelocity, radialVec);
      
    3. Die Gesamtgeschwindigkeit des ausgelösten Objekts ist die Summe der Geschwindigkeit des Controllers und dieser Tangentialgeschwindigkeit: objectVelocity = throwingControllerVelocity + tangentialVelocity;

  • Achten Sie genau auf den Zeitpunkt , zu dem wir die Geschwindigkeit anwenden. Wenn eine Taste gedrückt wird, kann es bis zu 20 ms dauern, bis dieses Ereignis über Bluetooth an das Betriebssystem weitergeleitet wird. Wenn Sie also eine Änderung des Controllerzustands von gedrückt in nicht gedrückt oder umgekehrt abfragen, sind die Controller-Poseninformationen, die Sie damit erhalten, dieser Zustandsänderung tatsächlich voraus. Darüber hinaus wird die von unserer Abfrage-API dargestellte Controllerhaltung vorausgesagt, um eine wahrscheinliche Pose zum Zeitpunkt der Anzeige des Frames widerzuspiegeln, die in Zukunft mehr als 20 ms betragen könnte. Dies ist gut für das Rendern von gehaltenen Objekten, verschiebt jedoch unser Zeitproblem für das Zielobjekt , da wir die Flugbahn für den Moment berechnen, an dem der Benutzer den Wurf losgelassen hat. Glücklicherweise enthält der Zustand mit dem November-Update, wenn ein Unity-Ereignis wie InteractionSourcePressed oder InteractionSourceReleased gesendet wird, die historischen Posendaten von zurück, als die Schaltfläche gedrückt oder losgelassen wurde. Um das genaueste Controllerrendering und das Ziel von Controllern während der Throws zu erhalten, müssen Sie die Abruf- und Ereigniserstellung ordnungsgemäß verwenden:

    • Zum Rendern des Controllers für jeden Frame sollte Ihre App das GameObject des Controllers an der vorausgesagten Controllerposition für die Photonenzeit des aktuellen Frames positionieren. Sie erhalten diese Daten von Unity-Abruf-APIs wie XR. InputTracking.GetLocalPosition oder XR. WSA. Input.InteractionManager.GetCurrentReading.
    • Für Controller, die auf eine Pressemitteilung oder eine Veröffentlichung ausgerichtet sind, sollte Ihre App raycasten und Flugbahnen basierend auf der historischen Controllerhaltung für dieses Presse- oder Releaseereignis berechnen. Sie erhalten diese Daten von Unity-Ereignis-APIs, z . B. InteractionManager.InteractionSourcePressed.
  • Verwenden Sie die Griffposition. Angular Geschwindigkeit und Geschwindigkeit werden relativ zur Griffhaltung und nicht zur Zeigerhaltung gemeldet.

Das Auslösen wird mit zukünftigen Windows-Updates weiter verbessert, und Weitere Informationen dazu finden Sie hier.

Gesten- und Bewegungscontroller in MRTK

Sie können über den Eingabe-Manager auf gesten- und bewegungscontroller zugreifen.

Immer am Ball mit Tutorials

Schritt-für-Schritt-Tutorials mit ausführlicheren Anpassungsbeispielen finden Sie in der Mixed Reality Academy:

MR-Eingang 213 – Bewegungscontroller
MR-Eingang 213 – Bewegungscontroller

Nächster Entwicklungsprüfpunkt

Wenn Sie die von uns beschriebene Unity-Entwicklungsreise befolgen, befinden Sie sich mitten in der Erkundung der MRTK-Kernbausteine. Von hier aus können Sie mit dem nächsten Baustein fortfahren:

Oder fahren Sie mit den Funktionen und APIs der Mixed Reality-Plattform fort:

Sie können jederzeit zu den Prüfpunkten für die Unity-Entwicklung zurückkehren.

Siehe auch