Unity中如何获取XRRayInteractor当前悬停的UI元素引用?
解决方法
你的问题核心在于:Tracked Device Ray Caster 是Unity UI的XR输入适配组件,它的交互逻辑走的是Unity原生EventSystem,而非XR Interaction Toolkit的「Interactor-Interactable」体系。XR Ray Interactor的hoverEntered事件、interactablesHovered集合仅对继承自XRBaseInteractable的XR交互对象生效,普通UI按钮不属于这类对象,因此你之前的方法无法获取到UI元素。
以下是两种可行的解决方案:
方法一:通过EventSystem直接获取当前悬停UI
在控制器脚本中,借助Unity EventSystem的API直接查询当前被悬停的UI元素:
using UnityEngine; using UnityEngine.EventSystems; public class AccessHoveredUIElement : MonoBehaviour { void Update() { // 检查是否有UI被控制器射线命中 if (EventSystem.current.IsPointerOverGameObject()) { GameObject hoveredUI = EventSystem.current.currentSelectedGameObject; if (hoveredUI != null) { Debug.Log($"当前悬停UI:{hoveredUI.name}"); // 获取UI的自定义属性或组件,示例: // var customUIProps = hoveredUI.GetComponent<YourUIPropertiesScript>(); // if (customUIProps != null) { /* 处理逻辑 */ } } } } }
方法二:给UI添加悬停监听脚本
如果需要精准的「悬停进入/退出」回调,可以给每个目标UI按钮挂载监听脚本,通过静态变量共享当前悬停状态:
- 编写监听脚本:
using UnityEngine; using UnityEngine.EventSystems; public class UIHoverMarker : MonoBehaviour, IPointerEnterHandler, IPointerExitHandler { // 静态变量供控制器脚本访问 public static GameObject CurrentHoveredUI { get; private set; } public void OnPointerEnter(PointerEventData eventData) { CurrentHoveredUI = gameObject; Debug.Log($"进入悬停:{gameObject.name}"); } public void OnPointerExit(PointerEventData eventData) { CurrentHoveredUI = null; Debug.Log($"退出悬停:{gameObject.name}"); } }
- 在控制器脚本中直接读取:
using UnityEngine; public class ControllerUIHandler : MonoBehaviour { void Update() { if (UIHoverMarker.CurrentHoveredUI != null) { // 访问悬停UI的属性,修改控制器外观 Debug.Log($"当前悬停UI:{UIHoverMarker.CurrentHoveredUI.name}"); } } }
内容的提问来源于stack exchange,提问作者Aurélien MARCHAL
相关产品推荐
相关产品推荐

