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

Unity 6.1下基于MetaQuestXRSimulator的自动化PlayMode测试困境

基于Meta Quest XR Simulator的Unity PlayMode自动化抓取测试实现

前提配置确认

先完成项目基础配置校验:

  • 已在Project Settings > XR Plug-in Management中启用OpenXR作为XR插件提供商
  • 已在OpenXR Settings > Interaction Profiles中勾选Meta Quest Controller Profile
  • 场景内已配置XR Origin (XR SDK),并挂载Meta Quest XR Simulator组件(通常作为XR Origin的子物体,或在Camera Offset节点下)

核心实现步骤

1. 获取模拟器实例

Meta Quest XR Simulator的控制API封装在Meta.XR.Simulator命名空间下,直接通过代码获取实例即可:

using Meta.XR.Simulator;

private MetaXRSimulator _simulator;

void Awake()
{
    _simulator = FindObjectOfType<MetaXRSimulator>();
    if (_simulator == null)
    {
        Debug.LogError("场景中未找到MetaXRSimulator组件,请检查配置");
    }
}

2. 模拟手柄抓取动作

通过模拟器API直接控制手柄姿态与按键输入,实现自动抓取逻辑:

using UnityEngine;
using UnityEngine.XR.OpenXR.Input;

/// <summary>
/// 模拟指定手柄抓取目标物体
/// </summary>
/// <param name="target">待抓取的立方体</param>
/// <param name="handIndex">0=左手,1=右手</param>
public IEnumerator SimulateGrabAction(GameObject target, int handIndex = 1)
{
    if (_simulator == null || target == null) yield break;

    // 将手柄移动到立方体前方(避免模型穿透)
    Vector3 targetPos = target.transform.position + Vector3.forward * 0.1f;
    _simulator.SetControllerPosition(handIndex, targetPos);
    _simulator.SetControllerRotation(handIndex, Quaternion.LookRotation(-Vector3.forward));
    yield return null;

    // 按下扳机键(对应OpenXR的Trigger输入)
    string triggerInput = OpenXRInputUtility.ToInputString(OpenXRInput.Button.Trigger);
    _simulator.SetControllerButton(handIndex, triggerInput, true);
    yield return new WaitForSeconds(0.3f);

    // 保持抓取状态
    yield return new WaitForSeconds(2f);

    // 释放扳机键
    _simulator.SetControllerButton(handIndex, triggerInput, false);
}

3. 编写PlayMode自动化测试

结合Unity Test Framework编写可自动运行的测试用例:

using NUnit.Framework;
using UnityEngine;
using UnityEngine.TestTools;
using Meta.XR.Simulator;
using UnityEngine.XR.OpenXR.Input;
using UnityEngine.XR.Interaction.Toolkit;

public class CubeGrabAutomationTest
{
    private GameObject _testCube;
    private MetaXRSimulator _simulator;
    private XRController _rightController;

    [SetUp]
    public void TestSetup()
    {
        // 加载目标测试场景
        UnityEngine.SceneManagement.SceneManager.LoadScene("YourTestScene");

        // 获取测试所需对象
        _testCube = GameObject.Find("GrabCube");
        _simulator = FindObjectOfType<MetaXRSimulator>();
        _rightController = FindObjectOfType<XRController>(true);
    }

    [UnityTest]
    public IEnumerator TestAutoGrabAndRelease()
    {
        // 等待场景初始化完成
        yield return new WaitForSeconds(1f);

        // 执行模拟抓取逻辑
        yield return SimulateGrabAction(_testCube, 1);

        // 验证抓取状态(假设抓取后立方体成为控制器子物体)
        Assert.IsTrue(_testCube.transform.parent == _rightController.transform, "立方体未被成功抓取");

        // 等待释放动作完成
        yield return new WaitForSeconds(0.5f);

        // 验证释放状态
        Assert.IsNull(_testCube.transform.parent, "立方体未被成功释放");
    }
}

关键注意事项

  • 确保立方体已挂载XR Grab Interactable组件,并将场景中的XR Controller设置为其交互器
  • 若使用自定义抓取逻辑,需调整测试中的验证条件(比如检查Rigidbody约束状态、自定义抓取标记等)
  • PlayMode测试启动时,可手动初始化XR子系统避免异常:
    XRGeneralSettings.Instance.Manager.InitializeLoader();
    XRGeneralSettings.Instance.Manager.StartSubsystems();
    

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.13 05:37:47