Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本)

这篇具有很好参考价值的文章主要介绍了Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本)。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

持续移动是 VR 开发中的一个常用功能。一般是用户推动手柄摇杆,或者触摸手柄触摸板,来控制人物持续地移动。Unity SteamVR 插件中只提供了传送的移动功能,而没有用摇杆或触摸板控制人物持续移动的功能。因此,持续移动的功能需要我们自己开发。


📕教程说明

使用的 Unity 版本: 2021.3.5

使用的操作系统:Windows 11

使用的设备:Meta Quest 2

SteamVR 版本:2.7.3

因为我用的是 Quest 手柄,所以我会用 Quest 手柄的摇杆控制人物移动。而像 Htc Vive 手柄上只有触摸板 Touchpad,但是它的作用和摇杆是一样的。

最终实现的效果:能通过摇杆控制人物持续移动,人物能与其他物体有碰撞,能上阶梯。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎文章来源地址https://www.toymoban.com/news/detail-718281.html


📕场景搭建

我们新建一个场景,删除原本场景中的 Main Camera,在场景中放置一个平面,然后用方块制作一个阶梯,用于后续的测试。接下来,我们需要添加一个 VR 中代表玩家自己的物体。我可以打开 Assets/SteamVR/InteractionSystem/Core 文件夹,将 Player 物体拖入场景:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

也许你之前会在 Assets/SteamVR/Prefabs 文件夹下看到一个 [CameraRig] 预制体,它也能代表 VR 中的玩家自己,能够追踪头显和手柄的位置和旋转角度。但是 Player 这个预制体相当于功能更加丰富的 [CameraRig],因此,推荐大家使用 Player 这个预制体。


📕创建移动的动作

SteamVR 的输入系统是基于动作的,我们需要在代码中判断动作是否发生,或者获取动作返回的值,然后在配置文件中配置动作和设备按键的绑定关系,输入系统的详细介绍可以参考这篇教程:Unity SteamVR 开发教程:SteamVR Input 输入系统(2.x 以上版本)。

我们可以打开 Unity 编辑器菜单栏的 Windows/SteamVR Input 窗口:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

然后点击 Open Binding UI 打开动作按键绑定界面:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎
Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

我们在场景中默认会激活 default 这个动作集。然而这个动作集里并没有绑定摇杆相关的动作。因此,我们需要自己创建一个摇杆移动相关的动作,并且将它与摇杆键进行绑定。

在 VR 游戏中,经常是一只手控制移动,另一只手控制转向。转向一般是将手柄摇杆向左或者向右推动来触发。SteamVR 默认的输入配置是两只手都能转向,因此,我们需要取消其中一只手的转向绑定。那么我规定一下,在本篇教程中,我使用左摇杆进行持续移动,右摇杆进行转向。

首先,我们需要取消勾选镜像模式,这样可以为左右手柄分别绑定动作。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

然后删除左手柄上 snapturnright 和 snapturnleft 的按键绑定:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

接下来,我们要在 default 动作集下创建一个新的动作,用来表示我们的摇杆移动。回到 SteamVR Input 窗口,新键一个 Vector2 类型的动作。因为摇杆推向的位置是用一个二维向量来表示。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

然后打开 Binding UI,将 MovePlayer 动作与左摇杆位置进行绑定(记得取消镜像模式)。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

现在,我们的 Vector2 类型的动作就和左手柄摇杆绑定成功了。


📕移动脚本

我们新建一个脚本,然后挂载到 Player 物体上:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using Valve.VR;
using Valve.VR.InteractionSystem;

public class ContinousMoveController : MonoBehaviour
{
    [SerializeField] private SteamVR_Action_Vector2 moveAction;
    [SerializeField] private float speed = 1;
    [SerializeField] private float gravity = 9.81f;
    [SerializeField] private float minHeight = 0;
    [SerializeField] private float maxHeight = float.PositiveInfinity;
    [SerializeField] private CharacterController characterController;
    void Start() 
    {
        if(characterController == null)
        {
            characterController = GetComponent<CharacterController>();  
        }
    }

    void Update()
    {
        HandleHeight();
        Move();
    }
    private void Move()
    {
        if(moveAction.axis.magnitude > 0.1f)
        {
            Vector3 direction = Player.instance.hmdTransform.TransformDirection(new Vector3(moveAction.axis.x, 0, moveAction.axis.y));            
            characterController.Move(speed * Time.deltaTime * Vector3.ProjectOnPlane(direction, Vector3.up) - new Vector3(0, gravity, 0) * Time.deltaTime);
        }
        
    }
    private void HandleHeight()
    {       
        float headHeight = Mathf.Clamp(Player.instance.hmdTransform.position.y, minHeight, maxHeight);
        characterController.height = headHeight;

        Vector3 newCenter = Player.instance.transform.InverseTransformPoint(Player.instance.hmdTransform.position);
        newCenter.y = characterController.height / 2 + characterController.skinWidth;
        characterController.center = newCenter;
    }
}


然后将 CharacterController 组件挂载到 Player 物体上,参数设置可以参考我的,大家也可以根据实际情况进行调整:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

⭐移动

解释一下核心方法 Move:

首先我们人物的移动选择用 CharactrrController 碰撞体的 Move 方法来移动,因为人物添加上 CharactrrController 后,可以与场景中的其他物体发生碰撞,比如碰到一堵墙会卡住,或者拥有上台阶的功能。这样身体在移动的过程中就不会穿过其他碰撞体。并且 CharacterController 组件拥有一个 Move 方法,可以用于移动身体。

Move 方法需要传入一个移动向量。因为移动相当于一段距离,所以移动的距离可以看作移动速度×移动时间×移动方向。移动方向可以通过以下代码获取:

 Vector3 direction = Player.instance.hmdTransform.TransformDirection(new Vector3(moveAction.axis.x, 0, moveAction.axis.y));  

Player 就是原本挂载在 Player 物体上的 Player 脚本:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

通过 Player.instance.hmdTransform 可以获取头部相机的位置。TransformDirection 方法可以将相对于指定对象自身坐标系的方向向量转换为相对于世界坐标系方向向量,即一个物体自己坐标系的 direction 方向,相当于世界坐标系的什么方向。我们的持续移动功能一般是相对于自己的头部移动,因为移动的输入原本是一个世界坐标系下的向量,我们需要用 TransformDirection 方法将移动输入转换为相对于玩家头部的方向,其结果是用世界坐标系下的一个向量来表示。比如头部看向右边,然后向前推动摇杆,这时候人物要朝着头部看向的右侧移动,大家可以参考下图理解。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

但是因为我们要限制玩家在水平面上前后左右移动,而头看向的方向可以是任一方向,所以我们要用以下代码对移动方向进行限制:

Vector3.ProjectOnPlane(direction, Vector3.up)

这个方法可以将将向量投影到由法线定义的平面上(法线与该平面正交),因此我们就把移动方向限制在了水平面上。ProjectOnPlane 方法的第二个参数是平面的法向量,所以用 Vector3.up 表示合适。

在 CharacterController 的 Move 方法中,我们传入的移动向量减去了一个 new Vector3(0, gravity, 0) * Time.deltaTime,这是为了模拟重力,让玩家在能够从高处落下。

脚本写完后,我们需要在 Inspector 面板中对变量进行赋值:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

⭐实时调整 CharacterController 的高度

移动脚本中还有个 HandleHeight 方法,这个方法用于实时调整 CharacterController 的高度。如果没有这个方法,我们的 CharacterController 的高度是不变的,比如游戏中有一个比较矮的洞,按照现实生活中的常识,我们可能会蹲下来走过去,但是游戏中人物的碰撞由 CharacterController 决定,如果我们在现实中蹲下而游戏中的 CharacterController 高度不变的话,我们在游戏中还是过不了洞,人物会因为 CharacterController 的高度卡在洞外。

因此我们希望比如在现实中蹲下,游戏中人物的 CharacterController 的高度会随之变低。也就是 CharacterController 的高度会随着头部相机的高度变化而变化

private void HandleHeight()
    {       
        float headHeight = Mathf.Clamp(Player.instance.hmdTransform.position.y, minHeight, maxHeight);
        characterController.height = headHeight;

        Vector3 newCenter = Player.instance.transform.InverseTransformPoint(Player.instance.hmdTransform.position);
        newCenter.y = characterController.height / 2 + characterController.skinWidth;
        characterController.center = newCenter;
    }

首先将 CharacterController 的高度设为与头部相机一样,最小高度和最大高度可以自己在 Inspector 面板定义。

但是因为调整 CharacterController 的高度会让 CharacterController 的两头都进行伸缩,所以还要调整它的 center 让它与人物匹配。

首先我们要让 CharacterController 的中心位置和头部相机位置匹配。因为此时的 CharacterController 的 center 是相对于玩家角色的局部坐标,所以我们也要得到头部相机相对于玩家角色的局部坐标,利用 InverseTransformPoint 方法将头部相机的位置从世界坐标系转换为相对于玩家角色的局部坐标系。然后调整 center 的高度,相当于头部相机高度的一半加上 CharacterController 的 skinWidth。skinWidth表示角色控制器的皮肤宽度。皮肤宽度是一个用于处理碰撞的边界区域,加上后 center 的高度更加准确。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

可以看到 CharacterController 的高度和中心位置会在游戏运行过程中根据头部相机的位置而改变。


📕取消手部和 CharacterController 的碰撞

如果这时候运行代码,你会发现手部和身体(CharacterController)产生了碰撞。为了解决这个问题,我们可以把 Player 这个物体的 Layer 设为 Player(或者任意一个你喜欢的名字)

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

只需要将挂载了 CharacterController 的物体的 Layer 设为 Player 就行。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

然后在 Assets/SteamVR/InteractionSystem/Core/Prefabs 文件夹下找到 HandColliderLeft 和 HandColliderRight 预制体。这两个物体会在游戏运行的时候自动创建,作为手部的碰撞体。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

游戏运行时自动添加:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

这两个物体的实例化是在什么时候进行的呢?我们可以找到 Player 物体的子物体 LeftHand 或者 RightHand,这两个物体上挂载了 HandPhysics 脚本:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

我们可以打开 HandPhysics 脚本,看看源码:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

可以看到在 Start 方法中就通过 Instantiate 方法实例化了 Hand Collider 的 Prefab 预制体。

现在,我们将手部碰撞体的预制体(HandColliderLeft 和 HandColliderRight)的 Layer 设为 Hand(随便取一个名字就行),这次需要选择 Yes,因为手部碰撞体所有的子物体都不能与 CharacterController 发生碰撞。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎
Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

然后打开编辑器菜单栏的 Edit/Project Settings:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

找到 Physics,取消勾选 Player 和 Hand 之间的交叉点:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

这样,Layer 是 Player 的物体和 Layer 是 Hand 的物体就不会发生碰撞,也就是我们手部的碰撞体不会与 CharacterController 发生碰撞。我们为手部碰撞体单独设置一个 Hand Layer 是因为我们希望手与手之间可以发生碰撞,但是手和 CharacterController 不能发生碰撞。

📕取消手部模型的抖动

但是这个时候如果运行程序,你可能会发现一个问题:有时候移动或者转向时手部模型会有抖动的现象。

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

这个时候我们需要找到 HandColliderLeft 和 HandColliderRight 预制体,取消勾选 Rigidbody 组件上的 Use gravity,然后将 Interpolate 选项设为 Interpolate

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

重要的是这个 Interpolate 插值选项。它可以平滑消除固定帧率运行物理导致的现象。因为在 Unity 中,物理的计算通常是以固定的时间步长进行更新,然后应用的实际帧率是不一定的。当物理计算和应用实际帧率不同步时,可能会导致对象出现视觉抖动。而 Interpolate 插值运算可以一定程度上解决抖动问题。(Unity 官方说明:https://docs.unity.cn/2023.2/Documentation/Manual/rigidbody-interpolation.html)

最终效果:

Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本),# Unity SteamVR,unity,游戏引擎

到了这里,关于Unity SteamVR 开发教程:用摇杆/触摸板控制人物持续移动(2.x 以上版本)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【Unity游戏开发教程】零基础带你从小白到超神16——四种方法控制人物移动之角色控制器

    直接修改组件位置 去资源商城下载角色控制系统成品直接拿来用 unity提供的角色控制器组件 通过物理系统自己做

    2024年02月08日
    浏览(47)
  • Unity SteamVR 开发教程:SteamVR Input 输入系统(2.x 以上版本)

    输入系统是 VR 开发中非常重要的一部分。我们通常需要获取 VR 手柄上某个按键的输入,然后将其作用到应用中,比如按下手柄的 Grip 键进行抓取,就需要在检测到“按下手柄 Grip 键”的输入操作时,执行抓取的行为。 SteamVR 插件是 Valve 提供给 Unity 开发者的用于开发 PCVR (头

    2024年02月08日
    浏览(55)
  • Unity教程3:使用BlendTree控制人物移动动画切换

    目录 创建动画文件 移动动画逻辑以及BlendTree的使用方法  创建移动变量 了解并使用混合树 实现保持移动方向的动画切换 手册链接在这:Unity User Manual (2019.3) - Unity 手册 实现了基本的人物移动代码后,为了使得我们的人物更加的生动有趣,我们还需要实现人物的动画效果。

    2024年02月13日
    浏览(45)
  • Unity教程2:保姆级教程.几行代码实现输入控制2D人物的移动

    目录 人物的创建以及刚体的设置 图层渲染层级设置 角色碰撞箱设置 使用代码控制人物移动 创建脚本文件  初始函数解释 控制移动代码 初始化变量  获得键盘输入  调用函数 手册链接在这:Unity User Manual (2019.3) - Unity 手册 没有控制人物移动的2D游戏就太说不过去了!那么接

    2024年02月06日
    浏览(42)
  • 【unity游戏开发教程】Unity+Umotion Pro+VRoid+Blender制作人物模型和动画,在unity中简单制作二次元人物动画

    大家好!本期教程教大家在unity中制作二次元人物模型和动画 1.下载VRoid Studio 1.搜索VRoid Studio下载即可,或者前往官网VRoid官网 VRoid Studio是由pixiv开发的一款3D人物建模软件,VRoid的主要特征就是通过类似绘画的方式进行人物的建模,使人们更为轻松地创造自己的虚拟人物。

    2024年02月10日
    浏览(53)
  • 【Unity】【Pico】手柄摇杆控制第一人称移动和旋转

    背景:开发影院系统 环境:Unity2021.3、PicoNeo3ProEye 描述 :已经在Unity项目中实现第一人称WASD移动和鼠标旋转(代码见我的其他博文) 需求 :希望项目在Pico一体机运行时可以通过手柄摇杆控制(unityxr的基础配置见我的其他博文) 解决 : Locomotion System XR Origin Continuous Move Pr

    2024年01月18日
    浏览(87)
  • Unity开发之SteamVR---VRTK简介

    一、什么是VRTK VRTK全称是Virtual Reality Toolkit,前身是SteamVR Toolkit,由于后续版本开始支持其他VR平台的SDK,如Oculus、Daydream、GearVR等,故改名为VRTK,它是使用Unity进行VR交互开发的利器,以二八原则来看,开发者可以使用20%的时间完成80%的VR交互开发内容。 在Unity Asset Store上搜索

    2024年02月12日
    浏览(56)
  • Unity VR 开发教程 OpenXR+XR Interaction Toolkit (六)手与物品交互(触摸、抓取)

    往期回顾: Unity VR 开发教程 OpenXR+XR Interaction Toolkit (一) 安装和配置 Unity VR 开发教程 OpenXR+XR Interaction Toolkit (二) 手部动画 Unity VR 开发教程 OpenXR+XR Interaction Toolkit (三) 转向和移动 Unity VR 开发教程 OpenXR+XR Interaction Toolkit (四) 传送 Unity VR 开发教程 OpenXR+XR Interaction Toolkit (五) UI

    2024年02月11日
    浏览(52)
  • unity开发笔记#230821-手搓一个虚拟摇杆

    做unity游戏时,如果是做手机端则需要加一个虚拟摇杆以便玩家控制角色移动(做pc端则直接获取键值即可较方便)。原理就是用Image制作一个大圆圈住一个Image小圆,玩家拖拽小圆控制角色移动。 中心思想是,以小圆中心为(0,0),获取拖拽的偏移量即可。 首先将图片资源拉入

    2024年02月12日
    浏览(45)
  • Unity中人物控制器

       在Unity中控制器是很常见的功能,一般的人物控制器有两种方法,一种是通过代码实现,另外一种就是通过Unity中的API实现。   这里主要介绍第一种方法。   首先对控制器步骤进行分析。 步骤1:通过方向键控制人物移动。 步骤2:控制摄像机跟随人物 步骤1:通过方

    2024年02月13日
    浏览(46)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包