You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Unity UI Toolkit点击按钮时Raycast穿透到世界空间问题咨询

UI Toolkit 射线穿透UI问题标准解决方法

UI Toolkit 有独立的事件检测体系,旧版UGUI使用的EventSystem.current.IsPointerOverGameObject接口无法识别UI Toolkit元素命中,不要用加碰撞体、手动改射线层级这类临时方案,直接用官方原生方案即可:


方案1:代码判定拦截(灵活度最高,适配所有场景)

在执行世界空间瓦片射线检测逻辑前,调用UI Toolkit原生接口判定指针是否在UI元素上方,命中则直接终止后续世界交互逻辑:

using UnityEngine;
using UnityEngine.UIElements;

public class TileInputHandler : MonoBehaviour
{
    void Update()
    {
        // 监听鼠标左键点击
        if (Input.GetMouseButtonDown(0))
        {
            // 检测鼠标指针是否悬停在UI Toolkit元素上
            if (RuntimePanelUtils.PointerOverScreenUI(PointerId.mousePointerId))
            {
                // 命中UI,拦截后续世界射线逻辑
                return;
            }

            // 下方写原有六边形瓦片的射线检测、交互逻辑
            // Ray tileRay = Camera.main.ScreenPointToRay(Input.mousePosition);
            // if (Physics.Raycast(tileRay, out RaycastHit hit)) { ... }
        }
    }
}
  • 多触摸场景下,将传入的指针ID替换为对应触摸事件的fingerId即可,不要硬编码鼠标指针ID。

方案2:全局配置拦截(配置即可生效,零代码)

打开场景中UI Document引用的Panel Settings配置资产,找到Input分组下的Send Events to World选项,取消勾选即可。

该配置会让UI Toolkit直接消费掉所有落在UI区域的指针输入事件,从输入层阻断事件向下透传到世界空间,适合不需要UI和下层世界同时响应点击的场景。如果有半透明UI需要同时触发下层交互,优先用方案1的代码判定做灵活控制。


避坑提示

  • 不要通过给UI加3D/2D碰撞体、调整物理射线LayerMask的方式做拦截,这类方案会额外产生物理开销,且在UI缩放、分辨率适配时容易出现判定区域和UI实际显示范围不匹配的问题。
  • 不要在纯UI Toolkit项目里依赖EventSystem.current.IsPointerOverGameObject做判定,该接口只能识别旧版UGUI的元素命中,对UI Toolkit元素无效。

内容的提问来源于stack exchange,提问作者Wolfik

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.29 06:24:24