Mixed Reality systeemeigen interoperabiliteit in Unity

Elke Mixed Reality app krijgt een HolographicSpace voordat deze cameragegevens ontvangt en frames weergeeft. In Unity zorgt de engine voor deze stappen, waarbij Holographic-objecten worden verwerkt en intern worden bijgewerkt als onderdeel van de render-lus.

In geavanceerde scenario's moet u echter mogelijk toegang krijgen tot de onderliggende systeemeigen objecten, zoals holographicCamera en het huidige HolographicFrame.

WindowsMixedRealityUtilities

Naamruimte:Microsoft.MixedReality.Toolkit.WindowsMixedReality
Type:WindowsMixedRealityUtilities

MRTK biedt al marshall-typen voor zowel verouderde WSA- als XR SDK via de WindowsMixedRealityUtilities-klasse .

public static HolographicFrame CurrentHolographicFrame { get; }
public static SpatialCoordinateSystem SpatialCoordinateSystem { get; }
public static SpatialInteractionManager SpatialInteractionManager { get; }

Oorspronkelijke aanwijzers loskoppelen

Nadat u de IntPtr hebt verkregen van een van de bovenstaande methoden (niet nodig voor MRTK), gebruikt u de volgende codefragmenten om ze te marshalen naar beheerde objecten.

Als u Microsoft.Windows.MixedReality.DotNetWinRT gebruikt, kunt u een beheerd object maken op basis van een systeemeigen aanwijzer met behulp van de FromNativePtr() methode:

var worldOrigin = Microsoft.Windows.Perception.Spatial.SpatialCoordinateSystem.FromNativePtr(spatialCoordinateSystemPtr);

Marshal.GetObjectForIUnknown() Gebruik en cast anders het gewenste type:

#if ENABLE_WINMD_SUPPORT
var worldOrigin = Marshal.GetObjectForIUnknown(spatialCoordinateSystemPtr) as Windows.Perception.Spatial.SpatialCoordinateSystem;
#endif

Converteren tussen coördinaatsystemen

Unity maakt gebruik van een linkshandig coördinatensysteem, terwijl de Windows Perception-API's gebruikmaken van rechtshandige coördinatensystemen. Als u wilt converteren tussen deze twee conventies, kunt u de volgende helpers gebruiken:

namespace NumericsConversion
{
    public static class NumericsConversionExtensions
    {
        public static UnityEngine.Vector3 ToUnity(this System.Numerics.Vector3 v) => new UnityEngine.Vector3(v.X, v.Y, -v.Z);
        public static UnityEngine.Quaternion ToUnity(this System.Numerics.Quaternion q) => new UnityEngine.Quaternion(q.X, q.Y, -q.Z, -q.W);
        public static UnityEngine.Matrix4x4 ToUnity(this System.Numerics.Matrix4x4 m) => new UnityEngine.Matrix4x4(
            new Vector4( m.M11,  m.M12, -m.M13,  m.M14),
            new Vector4( m.M21,  m.M22, -m.M23,  m.M24),
            new Vector4(-m.M31, -m.M32,  m.M33, -m.M34),
            new Vector4( m.M41,  m.M42, -m.M43,  m.M44));

        public static System.Numerics.Vector3 ToSystem(this UnityEngine.Vector3 v) => new System.Numerics.Vector3(v.x, v.y, -v.z);
        public static System.Numerics.Quaternion ToSystem(this UnityEngine.Quaternion q) => new System.Numerics.Quaternion(q.x, q.y, -q.z, -q.w);
        public static System.Numerics.Matrix4x4 ToSystem(this UnityEngine.Matrix4x4 m) => new System.Numerics.Matrix4x4(
            m.m00,  m.m10, -m.m20,  m.m30,
            m.m01,  m.m11, -m.m21,  m.m31,
           -m.m02, -m.m12,  m.m22, -m.m32,
            m.m03,  m.m13, -m.m23,  m.m33);
    }
}

Systeemeigen HolographicFrame-gegevens gebruiken

Notitie

Het wijzigen van de status van de systeemeigen objecten die worden ontvangen via HolographicFrameNativeData kan onvoorspelbaar gedrag en renderingartefacten veroorzaken, met name als Unity ook redenen heeft voor dezelfde status. U moet bijvoorbeeld HolographicFrame.UpdateCurrentPrediction niet aanroepen, anders is de houdingsvoorspelling die Unity met dat frame weergeeft, niet gesynchroniseerd met de houding die Windows verwacht, waardoor de stabiliteit van het hologram wordt verminderd.

Als u toegang nodig hebt tot systeemeigen interfaces voor rendering- of foutopsporingsdoeleinden, gebruikt u gegevens van HolographicFrameNativeData in uw systeemeigen invoegtoepassingen of C#-code.

Hier volgt een voorbeeld van hoe u HolographicFrameNativeData kunt gebruiken om de voorspelling van het huidige frame voor fotontijd op te halen met behulp van de XR SDK-extensies.

using System;
using System.Runtime.InteropServices;

public static bool GetCurrentFrameDateTime(out DateTime frameDateTime)
{
#if ENABLE_WINMD_SUPPORT
    IntPtr holographicFramePtr = UnityEngine.XR.WindowsMR.WindowsMREnvironment.CurrentHolographicRenderFrame;

    if (holographicFramePtr != IntPtr.Zero)
    {
        var holographicFrame = Marshal.GetObjectForIUnknown(holographicFramePtr) as Windows.Graphics.Holographic.HolographicFrame;
        frameDateTime = holographicFrame.CurrentPrediction.Timestamp.TargetTime.DateTime;
        return true;
    }
#endif

    frameDateTime = DateTime.MinValue;
    return false;
}

Zie ook