jjzjj

SteamVR 2.x 手柄射线与3D物体交互(9)

StubbrnStar 2023-04-09 原文

UI模块在前面已经讲完了,从本章开始,会着重介绍手柄与3d游戏物体之间的交互,我们平时项目开发,最常用的就是手柄射线点击物体、手柄触碰以及手柄拾取物体,先来聊聊射线点击物体。
沿用的思想我们之前有说过,利用SteamVR_LaserPointer组件的PointerIn、PointerClick、PointerOut,来监听射线进入物体、点击物体、离开物体,这样就可以实现射线与3d物体的交互,直接上干货。

一、前期准备

新建场景,删除默认相机,将Player拖拽进入场景内

新建Plane,修改为Floor,上一个黑色材质球,Transform信息如下:

场景内随意添加两个Cube,将其命名为CubeA、CubeB

二、编写游戏物体射线交互组件

using UnityEngine;
using UnityEngine.Events;

/// <summary>
/// 物体射线交互
/// </summary>
public class SteamVR_InteractRay : MonoBehaviour
{
    public UnityAction OnRayEnter { get; set; }
    public UnityAction OnRayClick { get; set; }
    public UnityAction OnRayExit { get; set; }

    private void Start()
    {
        OnRayEnter = () => Debug.Log("射线进入 " + transform.name);
        OnRayClick = () => Debug.Log("射线点击 " + transform.name);
        OnRayExit = () => Debug.Log("射线离开 " + transform.name);
    }

    /// <summary>
    /// 射线进入
    /// </summary>
    public void RayEnter() { OnRayEnter?.Invoke(); }

    /// <summary>
    /// 射线点击
    /// </summary>
    public void RayClick() { OnRayClick?.Invoke(); }

    /// <summary>
    /// 射线离开
    /// </summary>
    public void RayExit() { OnRayExit?.Invoke(); }
}

这里逻辑很简单,我们只需要定义三个回调,来触发射线进入、点击、离开即可,为了方便测试,这里直接在Start函数内部实现了Debug逻辑,实际上我们可以编写脚本来继承此组件,来实现不同游戏物体被点击后触发不同逻辑,也可以直接挂载此组件,通过外部对委托进行逻辑触发。
CubeA与CubeB上挂载此脚本。

三、编写手柄射线监听组件

using UnityEngine;
using Valve.VR.Extras;

/// <summary>
/// 物体射线交互管理
/// </summary>
public class SteamVR_RayHandler : MonoBehaviour
{
    private SteamVR_LaserPointer laserPointer;      //激光组件

    private void Awake()
    {
        laserPointer = GetComponent<SteamVR_LaserPointer>();
    }

    private void Start()
    {
        laserPointer.PointerIn += LaserPointer_PointerIn;
        laserPointer.PointerClick += LaserPointer_PointerClick;
        laserPointer.PointerOut += LaserPointer_PointerOut;
    }

    private void LaserPointer_PointerIn(object sender, PointerEventArgs e)
    {
        if (e.target.GetComponent<SteamVR_InteractRay>() != null)
        {
            e.target.GetComponent<SteamVR_InteractRay>().RayEnter();
        }
    }

    private void LaserPointer_PointerClick(object sender, PointerEventArgs e)
    {
        if (e.target.GetComponent<SteamVR_InteractRay>() != null)
        {
            e.target.GetComponent<SteamVR_InteractRay>().RayClick();
        }
    }

    private void LaserPointer_PointerOut(object sender, PointerEventArgs e)
    {
        if (e.target.GetComponent<SteamVR_InteractRay>() != null)
        {
            e.target.GetComponent<SteamVR_InteractRay>().RayExit();
        }
    }
}

该组件挂载至RightHand上,同时RightHand上要挂载SteamVR_LaserPointer组件
运行游戏,手柄射线分别与CubeA、CubeB交互,正常打印信息

有关SteamVR 2.x 手柄射线与3D物体交互(9)的更多相关文章

  1. ruby-on-rails - 如何在 ruby​​ 交互式 shell 中有多行? - 2

    这可能是个愚蠢的问题。但是,我是一个新手......你怎么能在交互式ruby​​shell中有多行代码?好像你只能有一条长线。按回车键运行代码。无论如何我可以在不运行代码的情况下跳到下一行吗?再次抱歉,如果这是一个愚蠢的问题。谢谢。 最佳答案 这是一个例子:2.1.2:053>a=1=>12.1.2:054>b=2=>22.1.2:055>a+b=>32.1.2:056>ifa>b#Thecode‘if..."startsthedefinitionoftheconditionalstatement.2.1.2:057?>puts"f

  2. 世界前沿3D开发引擎HOOPS全面讲解——集3D数据读取、3D图形渲染、3D数据发布于一体的全新3D应用开发工具 - 2

    无论您是想搭建桌面端、WEB端或者移动端APP应用,HOOPSPlatform组件都可以为您提供弹性的3D集成架构,同时,由工业领域3D技术专家组成的HOOPS技术团队也能为您提供技术支持服务。如果您的客户期望有一种在多个平台(桌面/WEB/APP,而且某些客户端是“瘦”客户端)快速、方便地将数据接入到3D应用系统的解决方案,并且当访问数据时,在各个平台上的性能和用户体验保持一致,HOOPSPlatform将帮助您完成。利用HOOPSPlatform,您可以开发在任何环境下的3D基础应用架构。HOOPSPlatform可以帮您打造3D创新型产品,HOOPSSDK包含的技术有:快速且准确的CAD

  3. FOHEART H1数据手套驱动Optitrack光学动捕双手运动(Unity3D) - 2

    本教程将在Unity3D中混合Optitrack与数据手套的数据流,在人体运动的基础上,添加双手手指部分的运动。双手手背的角度仍由Optitrack提供,数据手套提供双手手指的角度。 01  客户端软件分别安装MotiveBody与MotionVenus并校准人体与数据手套。MotiveBodyMotionVenus数据手套使用、校准流程参照:https://gitee.com/foheart_1/foheart-h1-data-summary.git02  数据转发打开MotiveBody软件的Streaming,开始向Unity3D广播数据;MotionVenus中设置->选项选择Unit

  4. Unity 3D 制作开关门动画,旋转门制作,推拉门制作,门把手动画制作 - 2

    Unity自动旋转动画1.开门需要门把手先动,门再动2.关门需要门先动,门把手再动3.中途播放过程中不可以再次进行操作觉得太复杂?查看我的文章开关门简易进阶版效果:如果这个门可以直接打开的话,就不需要放置"门把手"如果门把手还有钥匙需要旋转,那就可以把钥匙放在门把手的"门把手",理论上是可以无限套娃的可调整参数有:角度,反向,轴向,速度运行时点击Test进行测试自己写的代码比较垃圾,命名与结构比较拉,高手轻点喷,新手有类似的需求可以拿去做参考上代码usingSystem.Collections;usingSystem.Collections.Generic;usingUnityEngine;u

  5. [Vuforia]二.3D物体识别 - 2

    之前说过10之后的版本没有3dScan了,所以还是9.8的版本或者之前更早的版本。 3d物体扫描需要先下载扫描的APK进行扫面。首先要在手机上装一个扫描程序,扫描现实中的三维物体,然后上传高通官网,在下载成UnityPackage类型让Unity能够使用这个扫描程序可以从高通官网上进行下载,是一个安卓程序。点到Tools往下滑,找到VuforiaObjectScanner下载后解压数据线连接手机,将apk文件拷入手机安装然后刚才解压文件中的Media文件夹打开,两个PDF图打印第一张A4-ObjectScanningTarget.pdf,主要是用来辅助扫描的。好了,接下来就是扫描三维物体。将瓶

  6. python - Ruby 或 Python 的 3d 游戏引擎? - 2

    关闭。这个问题不符合StackOverflowguidelines.它目前不接受答案。要求我们推荐或查找工具、库或最喜欢的场外资源的问题对于StackOverflow来说是偏离主题的,因为它们往往会吸引自以为是的答案和垃圾邮件。相反,describetheproblem以及迄今为止为解决该问题所做的工作。关闭9年前。Improvethisquestion是否有适用于这些的3d游戏引擎?

  7. 【自动驾驶环境感知项目】——基于Paddle3D的点云障碍物检测 - 2

    文章目录1.自动驾驶实战:基于Paddle3D的点云障碍物检测1.1环境信息1.2准备点云数据1.3安装Paddle3D1.4模型训练1.5模型评估1.6模型导出1.7模型部署效果附录show_lidar_pred_on_image.py1.自动驾驶实战:基于Paddle3D的点云障碍物检测项目地址——自动驾驶实战:基于Paddle3D的点云障碍物检测课程地址——自动驾驶感知系统揭秘1.1环境信息硬件信息CPU:2核AI加速卡:v100总显存:16GB总内存:16GB总硬盘:100GB环境配置Python:3.7.4框架信息框架版本:PaddlePaddle2.4.0(项目默认框架版本为2.3

  8. ruby - 如何与 Ruby 中的 Perl 程序交互? - 2

    据我了解,在Ruby和Perl之间没有“桥梁”可以让您直接从Ruby调用Perl函数。据我了解,要从Ruby调用Perl程序,只需将其放在反引号中(即result=`./helloWorld.pl`)。但是,这不允许与Perl程序交互(即您不能与提示交互或提供输入)。我的问题如下:有没有什么方法可以从Ruby向Perl程序提供输入(除了参数)?Ruby和Perl之间没有桥梁,我错了吗?在导航提示时与程序的标准输入交互似乎是错误的方式,我正在处理的程序设计良好,并且具有包含适当Perl函数的库。 最佳答案 有Inline::Ruby模

  9. ruby - IRb:如何使用预加载类启动交互式 ruby​​ session - 2

    在我采用Ruby语言的过程中,我花了很多时间在IRb中。太棒了!但是,由于我不是很清楚它的功能,并且对Ruby仍然是个“笨蛋”,所以我想知道以下内容:如何在不重新启动IRb的情况下“刷新”session(或者这是不可能的)。如何配置IRb加载一堆源文件“hello.rb”和“hello_objects.rb”,即在启动时?我在这些方面投入了大量工作,如果知道加载这些类的速记,而无需再次为每个类手动键入“加载”,那就太好了。 最佳答案 我不确定是否可以“刷新”session。但是,您可以像这样加载您的类:irb-r'hello.rb'

  10. ruby - Lisp - 是否适合网络编程/应用程序(交互式)? ruby 的方式是? php的方式是? - 2

    Lisp是否适合Web编程/应用程序(交互式),就像ruby​​和php一样?需要考虑的事情是:易于使用可部署性难度(尤其是对于编程初学者而言)(编辑)在阅读PaulGraham'sessay之后,我特别提到了CommonLisp.将是我的第一门编程语言。在这方面。这样做合适吗?我听说Clojure的宏功能不如CommonLisp的强大,这就是我尝试学习Clojure的原因。它教授编程并且非常强大。 最佳答案 Lisp是一个语系,而不是单一的语言。为了稍微回答您的问题,是的,存在用于各种Lisp方言的Web框架,例如用于Common

随机推荐