mixedreality/com.microsoft.mixedreality..../Runtime/API/EyeLevelSceneOrigin.cs

102 lines
4.1 KiB
C#
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using UnityEngine;
using UnityEngine.XR;
using UnityEngine.XR.Management;
namespace Microsoft.MixedReality.OpenXR
{
/// <summary>
/// Add the EyeLevelSceneOrigin component to the scene, it will automatically
/// switch the Unity's scene origin to an eye level experiences.
/// It will try to use "Unbounded" origin mode when it's supported.
/// </summary>
[System.Obsolete("Obsolete and will be removed in future releases. " +
"Use MRTK3 Microsoft.MixedReality.Toolkit.Input.UnboundedTrackingMode instead for HoloLens 2 application using Unbounded space." +
"Or use Unity.XR.CoreUtils.XROrigin for other XR applications.", false)]
public class EyeLevelSceneOrigin : MonoBehaviour
{
private XRInputSubsystem m_inputSubsystem;
private ulong m_currentSession = 0;
private static XRInputSubsystem GetXRInputSubsystem()
{
XRGeneralSettings xrSettings = XRGeneralSettings.Instance;
if (xrSettings != null)
{
XRManagerSettings xrManager = xrSettings.Manager;
if (xrManager != null)
{
XRLoader xrLoader = xrManager.activeLoader;
if (xrLoader != null)
{
return xrLoader.GetLoadedSubsystem<XRInputSubsystem>();
}
}
}
return null;
}
private void Update()
{
if (m_currentSession != OpenXRContext.Current.Session)
{
m_currentSession = OpenXRContext.Current.Session;
if (m_inputSubsystem != null)
{
m_inputSubsystem.trackingOriginUpdated -= XrInputSubsystem_trackingOriginUpdated;
m_inputSubsystem = null; // reset input subsystem reference on a new OpenXR session.
}
}
// Lazy initialize input subsystem.
if (m_inputSubsystem == null && OpenXRContext.Current.IsSessionRunning)
{
m_inputSubsystem = GetXRInputSubsystem();
if (m_inputSubsystem != null)
{
EnsureSceneOriginAtEyeLevel(m_inputSubsystem);
m_inputSubsystem.trackingOriginUpdated += XrInputSubsystem_trackingOriginUpdated;
}
}
}
private void XrInputSubsystem_trackingOriginUpdated(XRInputSubsystem xrInputSubsystem)
{
if (OpenXRContext.Current.IsSessionRunning && xrInputSubsystem == m_inputSubsystem)
{
EnsureSceneOriginAtEyeLevel(m_inputSubsystem);
}
}
private static void EnsureSceneOriginAtEyeLevel(XRInputSubsystem xrInputSubsystem)
{
TrackingOriginModeFlags currentMode = xrInputSubsystem.GetTrackingOriginMode();
TrackingOriginModeFlags desiredMode = GetDesiredTrackingOriginMode(xrInputSubsystem);
bool isEyeLevel = currentMode == TrackingOriginModeFlags.Device || currentMode == TrackingOriginModeFlags.Unbounded;
if (!isEyeLevel || currentMode != desiredMode)
{
Debug.Log($"EyeLevelSceneOrigin: TrySetTrackingOriginMode to {desiredMode}");
if (!xrInputSubsystem.TrySetTrackingOriginMode(desiredMode))
{
Debug.LogWarning($"EyeLevelSceneOrigin: Failed to set tracking origin to {desiredMode}.");
}
}
}
private static TrackingOriginModeFlags GetDesiredTrackingOriginMode(XRInputSubsystem xrInputSubsystem)
{
TrackingOriginModeFlags supportedFlags = xrInputSubsystem.GetSupportedTrackingOriginModes();
TrackingOriginModeFlags targetFlag = TrackingOriginModeFlags.Device; // All OpenXR runtime must support LOCAL space
if (supportedFlags.HasFlag(TrackingOriginModeFlags.Unbounded))
{
targetFlag = TrackingOriginModeFlags.Unbounded;
}
return targetFlag;
}
}
}