HTC Vive 开发(二)——VRTK使用

VRTK使用

参考文档:https://blog.csdn.net/qq_25601345/article/details/78497537?tdsourcetag=s_pcqq_aiomsg#_Toc31475
VRTK:3.2.1 版本  Steam VR:Assets Store下载

1、手柄发射射线

  • 手柄控制器挂载两个脚本:VRTK_Pointer 射线发射脚本 和 VRTK_Stratight Pointer Renderer 射线渲染脚本(或 VRTK_Bezier Pointer Renderer 射线脚本组件,射线的模型和目标点模型等参数可自定义),VRTK_Pointer脚本中指定Pointer Render类型;

2、手柄基本交互事件(触摸、抓取和使用)

给手柄控制器添加 VRTK_Controller_Events 脚本(手柄事件机制必需);

  • 根据需要添加以下脚本组件 :
    VRTK_Interact Touch(触碰)
    VRTK_Interact Grab(抓取 注:指定默认的抓取按键 Grab Button
    VRTK_Interact Use(使用 注:指定默认的使用按键 Use Button
    一般 Events、Touch、Grab、Use 这几个脚本都给控制器添加上
    在这里插入图片描述

抓取和使用脚本中,按钮若指定默认值,被交互物体所挂脚本中按钮可默认不更改;按钮若不指定,被交互物体所挂脚本中按钮要自定义;否则,被交互物体不能响应手柄的事件

3、物体抓取

  • 物体能够被抓取的条件*
    需要有RigidbodyCollider组件,
    挂载 VRTK_Interactable Object 脚本才可以响应手柄的交互,Touch Highlight Color 调整触碰时的高亮颜色,
    如果不给物体添加抓取方式,默认使用固定关节抓取方式:VRTK_FixedJointGrabAttach,
    挂载VRTK_ Outline Object Copy Highlighter脚本使物体 外轮廓 呈现高亮,默认整体高亮

注:

  • VRTK_Interactable Object脚本中的 Is Grabable(Is Usable) 默认是不勾选的,如果想要该物体能够被抓取,需要勾选该选项
  • 如果想点击抓取按钮之后就拿到物体,而不是一直按着按钮,取消勾选 Hold Button To Grab 即可
  • 挂载 VRTK_Swap Controller Grab Actions 脚本实现物体可以左右手交换

七种抓取方式:

VRTK_FixedJointGrabAttach 固定关节抓取(系统默认方式)
VRTK_SpringJointGrabAttach 弹簧关节抓取(手柄和被抓取物体之间弹簧链接效果,比如抽屉的弹性效果)
VRTK_CustomJointGrabAttach 自定义关节抓取(添加所需类型的Joint组件,并指定给自定义关节参数 Custom Joint)
VRTK_TrackObjectGrabAttach 对象追踪抓取(被抓取物体跟踪手柄,受外力阻挡时不会掉落)
VRTK_ClimbableGrabAttach 可攀爬抓取(实现手抓物体可攀爬效果),另外需要在场景上挂载 VRTK_Player Climb 脚本
VRTK_RotatorTrackGrabAttach 旋转体抓取 (效果和弹簧关节相似,比如门旋转的弹性效果,笔者猜测钟摆效果也可
VRTK_ChildOfControllerGrabAttach 作为控制器子物体(抓取物体成为手柄控制器模型子物体,射箭的典型例子)

4、物体使用(第25个例子未研究,一些物体的使用)

手柄控制器添加 VRTK_Interact Use 脚本,
被使用物体添加自定义脚本,继承VRTK_Interactable Object 类(勾选 Is Usable),重写该类的 StartUsing () { //自定义“使用”功能 } 和 StopUsing () 方法

注:

  • 若多个物体组成被交互对象,其中有使用对象,脚本挂在父容器上即可
  • 射线使用物体:勾选 Use Options 中的 Pointer Activates Use 实现

5、物体交互手柄震动

TriggerHapticPulse() 函数实现手柄震动:

  • 参数:
    index:手柄索引
    strength:震动强度
    duration:持续时间
    旧版本VRTK中使用的是 VRTK_Controller Action.TriggerHapticPulse(float strength);
    较新版本中使用的是 VRTK_SharedMethods.TriggerHapticPulse ( int index ,float strength,float duration);
    以上两种方法逐渐被弃用,使用 VRTK_ControllerHaptics.TriggerHapticPulse(controllerReference, 5000f);
//最简单的手柄碰撞震动脚本,脚本挂载Stick物体上,VRTK_ChildOfControllerGrabAttach 抓取方式
public class Stick :  VRTK_InteractableObject{

    //控制器引用(即 Left/RightCntroller)
    private VRTK_ControllerReference controllerReference;   

    public override void Grabbed(VRTK_InteractGrab currentGrabbingObject = null)
    {
        base.Grabbed(currentGrabbingObject);
        //获取当前抓取物体的控制器
        controllerReference = VRTK_ControllerReference.GetControllerReference(currentGrabbingObject.controllerEvents.gameObject);
    }

    public override void Ungrabbed(VRTK_InteractGrab previousGrabbingObject = null)
    {
        base.Ungrabbed(previousGrabbingObject);
        controllerReference = null;
    }

    private void OnCollisionEnter(Collision collision)
    {
        if (VRTK_ControllerReference.IsValid(controllerReference) && IsGrabbed())
        {
            //手柄震动函数
            VRTK_ControllerHaptics.TriggerHapticPulse(controllerReference, 5000f);
        }
    }
}

6、TouchPad 控制主角移动、添加自定义菜单

1、手柄控制器上挂载 VRTK_Touchpad Control 脚本组件控制圆盘

  • 参数说明:
    Device For Direction:选择哪个设备的方向为准
    Disable Other Controllers On Active:如果勾选,将其他监听TouchPad事件的函数都禁用掉
    Affect On Falling:当下落的时候可以继续控制
    Primary Activation Button:哪个按钮启动控制
    Active Modifier Button:激活控制行为的按钮
  • 真正实现圆盘控制主角移动,还需要 VRTK_SlideObjectControl Action 脚本设置轴偏移量,并且要指定 Object Controller Scripts
    Maximum Speed :触摸 TouchPad 时最大移动速度
    Speed Multilier:TouchPad 按下时速度倍乘

2、RadialMenu 预制体,VRTK_Radial Menu 菜单设置脚本 和 VRTK_Radial Menu Controller 菜单控制脚本

  • VRTK_Radial Menu 参数说明:
    Buttons:设置按钮数量,内部元素设置按钮的 图片样式 和 添加事件监听
    Button Prefab:按钮面板的样式(默认环形)
    Button Thickness:环的宽度
    Offset Distance:按钮间距
    Offset Rotation:按钮旋转的方位角
    Rotate Icons:是否旋转菜单图标来适应菜单朝向
    Icon Margin:图标到边缘距离
    Hide On Release:释放时隐藏
    Execute On Unclick:释放按钮时是否执行事件
    Base Haptic Strength:选择不同按钮时的震动

7、对象排除/包含列表 (VRTK_Policy List)

以瞬移为例,如下图

VRTK_Policy List 属性解析:

  • Operation为Ignore/Include(忽略),Types为Tag(标签)和Script(脚本)等,Element里面设置了ExcludeTeleport,这样设置,如果游戏物体上挂载有 ExcludeTeleport 这个名称的脚本或是游戏物体的标签为ExcludeTeleport,都不能瞬移到这个游戏物体上
  • 举个栗子,现在要在一个房间中实现瞬移,并且你想限制只能够在地板上瞬移,不能瞬移到高处,比如桌子、柜子上什么的;此时添加 Policy List 脚本,Operation选择 Include 地板 ground,或者 Operation 选择 Ignore 除地板之外的所有物体

8、射线与UI交互 (VRTK_UI Pointer、VRTK_UI Canvas)

注:实现射线与UI交互,需要给控制器添加 VRTK_UI Pointer 脚本
三种UI交互方式:

  • 普通UGUI:Canvas 的Render Mode设置为 World Space ;挂载脚本 VRTK_UICanvas
  • 键盘UI:添加脚本 VRTK_UICanvas 和 UI_KeyBoard ,在每个按键Button上要绑定点击事件 ClickKey
    UI_KeyBoard 脚本即控制键盘输入的代码:
public class UI_Keyboard : MonoBehaviour
    {	
        private InputField input;		//输入框
		private void Start()
        {	//获取输入框组件
            input = GetComponentInChildren<InputField>();
        }        
		//点击键盘上的字母时执行
        public void ClickKey(string character)
        {
            input.text += character;
        }
		//点击空格时执行
        public void Backspace()
        {	//如果输入文本长度不为零
            if (input.text.Length > 0)
            {	//文本分割,去掉最后一位
                input.text = input.text.Substring(0, input.text.Length - 1);
            }
        }
		//点击Enter键时执行
        public void Enter()
        {	//提示语
            VRTK_Logger.Info("You've typed [" + input.text + "]");
            //输入框文本清空
            input.text = "";
        }       
    }
  • 拖拽UI:添加脚本 VRTK_UIDropZone

9、瞬移

  • 四种瞬移方式:
    VRTK_Basic Teleport :基本的瞬移
    VRTK_Height Adjust Teleport :高度适应的瞬移,继承基本瞬移的功能
    VRTK_Dash Teleport :模拟过程的瞬移,继承基本瞬移和高度适应的瞬移
    VRTK_Transform Follow :头盔决定瞬移目标点

1、基本瞬移:场景中挂载脚本 VRTK_Basic Teleport 实现
挂载 VRTK_Dash Teleport 脚本,可以优化瞬移效果,不是硬生生的出现在目标点,而是像冲过去一样

2、适应高度的瞬移:场景中挂载脚本 VRTK_Height Adjust Teleport 实现
在这里插入图片描述
3、模拟过程的瞬移:场景中挂载脚本 VRTK_Basic Teleport 实现

4、头盔确定目标点的瞬移

  • 创建空对象,命名TransForm Follower(自定义),挂载 VRTK_SDK Object Alias 脚本,参数选择 HeadSet 也就是跟随对象选择头盔
  • 创建空对象,命名HeadSet(自定),挂载 VRTK_Pointer、VRTK_Bezier Pointer RendererVRTK_Transform Follow 脚本,前两个脚本实现发射曲射线,后者Follow实现射线跟随头盔,并且改变头盔的位置(即实现瞬移)

Pointer 要自定义手柄控制器,也就是使用哪个手柄触发头盔瞬移

笔者测试,用曲线实现此种瞬移比较好;如果选用直射线,射线有角度变化,目标点光标会变形
可以根据需要自行选择光标的形状、光标和射线路径是否显示

要特别注意 Transform Follow 中的赋值

10、双手操作

  • VRTK_MoveInPlace 脚本挂载到场景中,原地踏步就能实现移动,方向控制还需晃动头部,要是有万向走步机就更好了。

  • 双手同时操作物体
    1、VRTK_AxisScaleGrabAction 脚本实现双手缩放物体
    2、VRTK_ControlDirectionGrabAction 脚本实现双手同时拿起同一个物体,一般是长物体

11、射线作为手柄扩展

  • VRTK_Pointer 脚本组件中的 Interact With Objects 属性:如果勾选该属性,那么射线就相当于手柄控制器的扩展;已知只有当手柄接触到物体时,才会有高亮显示(如果你想),若实现手柄接触物体也能高亮显示,需勾选该选项,让射线代替手柄去接触物体即可实现,,,当然被选中物体要有Interactable Object 脚本,且勾选Pointer Active Use 的选项

12、获取手柄按键

	//获取右手手柄的引用
    rightControllerReference = VRTK_ControllerReference.GetControllerReference(VRTK_DeviceFinder.GetControllerRightHand(true));
    
    //获取手指是否触摸手柄圆盘,返回Bool值
    isTouchPadTouch = VRTK_SDK_Bridge.GetControllerButtonState(SDK_BaseController.ButtonTypes.Touchpad, SDK_BaseController.ButtonPressTypes.Touch, rightControllerReference);
    isTouchPadUp = VRTK_SDK_Bridge.GetControllerButtonState(SDK_BaseController.ButtonTypes.Touchpad, SDK_BaseController.ButtonPressTypes.TouchUp, rightControllerReference);
        
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章