当前位置:   article > 正文

Unity在XR设备中获取手柄的按键信息_unity openxr primarybutton

unity openxr primarybutton

我们在平常的XR设备开发中,尤其适用VR设备的时候,会用到手柄的操作。

我们知道Oculus SDK提供了OVRInput,能够获取得到手柄的按键信息。

  1. // public variable that can be set to LTouch or RTouch in the Unity Inspector
  2. public Controller controller;
  3. // returns a float of the Hand Trigger’s current state on the Oculus Touch controller
  4. // specified by the controller variable.
  5. OVRInput.Get(OVRInput.Axis1D.PrimaryHandTrigger, controller);
  6. // returns true if the primary button (“A” or “X”) is pressed on the Oculus Touch controller
  7. // specified by the controller variable.
  8. OVRInput.Get(OVRInput.Button.One, controller);

因为我们开发的应用肯定不单单只在oculus上运行,如果在其他的VR设备上运行的话,那要对接各个VR设备的SDK吗?

不用慌,其实Untiy已经把这个事情帮我做了,Unity封装了一下XR Input接口,就是抽象出来一层,能够在各种VR设备上使用。

那如何使用呢?我们先看看Unity封装的各个按键的对应关系。已经支持了很多市面上的VR设备。主要还是Oculus。你可以去官网上进行参考:Unity - Manual: Unity XR Input

我对使用方法进行了封装,挂载GameObject上就可以使用了。大家可以自行使用啊。

  1. using System.Collections.Generic;
  2. using UnityEngine;
  3. using UnityEngine.Events;
  4. using UnityEngine.XR;
  5. [System.Serializable]
  6. public enum InputFeature
  7. {
  8. //
  9. // ժҪ:
  10. // The primary face button being pressed on a device, or sole button if only one
  11. // is available.
  12. primaryButton,
  13. //
  14. // ժҪ:
  15. // The primary face button being touched on a device.
  16. primaryTouch,
  17. //
  18. // ժҪ:
  19. // The secondary face button being pressed on a device.
  20. secondaryButton,
  21. //
  22. // ժҪ:
  23. // The secondary face button being touched on a device.
  24. secondaryTouch,
  25. //
  26. // ժҪ:
  27. // A binary measure of whether the device is being gripped.
  28. gripButton,
  29. //
  30. // ժҪ:
  31. // A binary measure of whether the index finger is activating the trigger.
  32. triggerButton,
  33. //
  34. // ժҪ:
  35. // Represents a menu button, used to pause, go back, or otherwise exit gameplay.
  36. menuButton,
  37. //
  38. // ժҪ:
  39. // Represents the primary 2D axis being clicked or otherwise depressed.
  40. primary2DAxisClick,
  41. //
  42. // ժҪ:
  43. // Represents the primary 2D axis being touched.
  44. primary2DAxisTouch,
  45. //
  46. // ժҪ:
  47. // Represents the secondary 2D axis being clicked or otherwise depressed.
  48. secondary2DAxisClick,
  49. //
  50. // ժҪ:
  51. // Represents the secondary 2D axis being touched.
  52. secondary2DAxisTouch,
  53. //
  54. // ժҪ:
  55. // Use this property to test whether the user is currently wearing and/or interacting
  56. // with the XR device. The exact behavior of this property varies with each type
  57. // of device: some devices have a sensor specifically to detect user proximity,
  58. // however you can reasonably infer that a user is present with the device when
  59. // the property is UserPresenceState.Present.
  60. userPresence
  61. }
  62. public class XRControllerButtonWatcher : MonoBehaviour
  63. {
  64. private Dictionary<InputFeature, InputFeatureUsage<bool>> inputFeatureUsageMap = new Dictionary<InputFeature, InputFeatureUsage<bool>>() {
  65. { InputFeature.primaryButton, CommonUsages.primaryButton },
  66. { InputFeature.primaryTouch, CommonUsages.primaryTouch },
  67. { InputFeature.secondaryButton, CommonUsages.secondaryButton },
  68. { InputFeature.secondaryTouch, CommonUsages.secondaryTouch },
  69. { InputFeature.gripButton, CommonUsages.gripButton },
  70. { InputFeature.triggerButton, CommonUsages.triggerButton },
  71. { InputFeature.menuButton, CommonUsages.menuButton },
  72. { InputFeature.primary2DAxisClick, CommonUsages.primary2DAxisClick },
  73. { InputFeature.primary2DAxisTouch, CommonUsages.primary2DAxisTouch },
  74. { InputFeature.secondary2DAxisClick, CommonUsages.secondary2DAxisClick },
  75. { InputFeature.secondary2DAxisTouch, CommonUsages.secondary2DAxisTouch },
  76. { InputFeature.userPresence, CommonUsages.userPresence }
  77. };
  78. [SerializeField]
  79. public InputFeature ButtonInputFeature;
  80. [SerializeField]
  81. public InputDeviceCharacteristics inputDeviceType = InputDeviceCharacteristics.None;
  82. [SerializeField]
  83. public UnityEvent OnInputDown;
  84. [SerializeField]
  85. public UnityEvent OnInputUp;
  86. private InputFeatureUsage<bool> buttonInputFeatureUsage;
  87. private bool lastButtonState = false;
  88. private List<InputDevice> devicesButton;
  89. private void Awake()
  90. {
  91. if (OnInputDown == null)
  92. OnInputDown = new UnityEvent();
  93. if (OnInputUp == null)
  94. OnInputUp = new UnityEvent();
  95. devicesButton = new List<InputDevice>();
  96. if (!inputFeatureUsageMap.TryGetValue(ButtonInputFeature, out buttonInputFeatureUsage))
  97. {
  98. Debug.LogError("not found inputFeature: " + ButtonInputFeature);
  99. }
  100. }
  101. private void OnEnable()
  102. {
  103. Init();
  104. }
  105. private void OnDisable()
  106. {
  107. InputDevices.deviceConnected -= InputDevices_deviceConnected;
  108. InputDevices.deviceDisconnected -= InputDevices_deviceDisconnected;
  109. devicesButton.Clear();
  110. }
  111. private void InputDevices_deviceConnected(InputDevice device)
  112. {
  113. bool discardedValue;
  114. if (device.TryGetFeatureValue(buttonInputFeatureUsage, out discardedValue))
  115. {
  116. Debug.Log($"add device: {device.name}");
  117. devicesButton.Add(device); // Add any devices that have a primary button.
  118. }
  119. }
  120. private void InputDevices_deviceDisconnected(InputDevice device)
  121. {
  122. if (devicesButton.Contains(device))
  123. devicesButton.Remove(device);
  124. }
  125. private void Update()
  126. {
  127. bool tempState = false;
  128. foreach (var device in devicesButton)
  129. {
  130. bool primaryButtonState = false;
  131. tempState = device.TryGetFeatureValue(buttonInputFeatureUsage, out primaryButtonState) // did get a value
  132. && primaryButtonState // the value we got
  133. || tempState; // cumulative result from other controllers
  134. }
  135. if (tempState != lastButtonState) // Button state changed since last frame
  136. {
  137. if (tempState)
  138. OnInputDown?.Invoke();
  139. else
  140. OnInputUp?.Invoke();
  141. lastButtonState = tempState;
  142. }
  143. }
  144. public void Init()
  145. {
  146. List<InputDevice> allDevices = new List<InputDevice>();
  147. if (inputDeviceType == InputDeviceCharacteristics.None)
  148. InputDevices.GetDevices(allDevices);
  149. else
  150. InputDevices.GetDevicesWithCharacteristics(inputDeviceType, allDevices);
  151. foreach (InputDevice device in allDevices)
  152. InputDevices_deviceConnected(device);
  153. InputDevices.deviceConnected += InputDevices_deviceConnected;
  154. InputDevices.deviceDisconnected += InputDevices_deviceDisconnected;
  155. }
  156. }

使用Unity自带的XR Input可以很好的支持多种设备。不需要再一个一个对接各个VR设备的SDK中的Input了。

参考文档:

Unity - Manual: Unity XR Input

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/菜鸟追梦旅行/article/detail/89656
推荐阅读
相关标签
  

闽ICP备14008679号