赞
踩
四、添加抓取功能
上一步做完之后,如果想和物体进行交互
那么你会大失所望——什么也不会发生。
选中两个手柄,给这两个手柄添加刚性体,并且勾上 Is Kinematic,反选 Use Gravity。
然后为两个手柄添加一个盒子碰撞体并勾上 Is Trigger。
默认的碰撞体太大了,需要重新指定大小和位置。
拿起一只手柄,仔细观察。每个控制器上有这些按钮:
1 - 菜单键
6 - 系统键(按下后手柄断开连接,再次按下手柄再次连接上)
7 - 扳机键
8 - 握持键
9 - 触摸板键
现在让我们给手柄加上脚本。
新建一个文件夹,取名为Scripts。在里面新建一个C#脚本,取名为ViveControllerGrabObject
代码思路:
1、 获取手柄的引用
2、 储存与手柄碰撞的对象
3、 设置触发器碰撞时相关状态的事件(Enter、Stay、Exit)
4、 设置抓取物体建立连接和放开(投掷)物体的方法
5、 设置按下按钮时调用相关方法的事件
usingUnityEngine;
public class ViveControllerGrabObject : MonoBehaviour {
//对正在被跟踪的对象进行一个引用,这里指的是一只手柄。
privateSteamVR_TrackedObject trackedObj;
//保存与之碰撞的组件,之后通过该组件抓取该对象
privateGameObject CollidingObject;
//保存玩家抓住的对象
privateGameObject ObjectInHand;
//Device 属性能够很方便地访问到这个手柄。通过所跟踪的对象的索引来访问控制器的 input,并返回这个 input。
privateSteamVR_Controller.Device Controller
{
get { returnSteamVR_Controller.Input((int)trackedObj.index); }
}
void Awake()
{
trackedObj = GetComponent();
}
//获取对象模块
private voidSetCollidingObject(Collider col)
{
//如果该对象已被抓取或者没有刚体组件,则不将该gameObject作为可抓取目标
if (CollidingObject || !col.GetComponent())
{
//这种return的用法作用类似于break
return;
}
//将这个对象作为可抓取的目标
CollidingObject = col.gameObject;
}
//触发器模块
//当触发器碰撞体进入另一个碰撞体时将其作为可抓取目标
public void OnTriggerEnter(Collider other)
{
SetCollidingObject(other);
}
//保存那个持续停留的碰撞体(不写这个会导致异常)
public void OnTriggerStay(Collider other)
{
SetCollidingObject(other);
}
//当碰撞体退出一个对象,将 collidingObject 设为 null 以删除目标对象。
public void OnTriggerExit(Collider other)
{
if(!CollidingObject)
{
return;
}
CollidingObject = null;
}
//抓取模块
private void GrabObject()
{
//将gameObject转移到ObjectInHand中,将 collidingObject 中保存的 gameObject 移除
ObjectInHand = CollidingObject;
CollidingObject = null;
//给gameObject添加一个连接对象,并将gameObject和手柄连接起来
var joint = AddFixedJoint();
joint.connectedBody = ObjectInHand.GetComponent();
}
//创建固定连接并加到手柄中
privateFixedJoint AddFixedJoint()
{
FixedJoint fx = gameObject.AddComponent();
fx.breakForce = 20000; //固定连接的断开力
fx.breakTorque = 20000; //断开扭矩,设置断开关节所需要的转矩
return fx;
}
//释放物体模块
private void ReleaseObject()
{
//确定控制器上有一个固定连接
if(GetComponent())
{
//删除该连接所连的对象并删除该连接
GetComponent().connectedBody = null;
Destroy(GetComponent());
//将放开物体时手柄的速度和角度赋给此物体,以形成一个抛物线
ObjectInHand.GetComponent().velocity = Controller.velocity;
ObjectInHand.GetComponent().angularVelocity = Controller.angularVelocity;
}
ObjectInHand = null;
}
//最后,在Update中处理手柄的输入
void Update () {
//按下扳机时调用抓取模块
if(Controller.GetHairTriggerDown())
{
GrabObject();
}
//松开扳机时调用释放物体模块
if(Controller.GetHairTriggerUp())
{
ReleaseObject();
}
}
}
写好脚本之后,保存退出,选中两个手柄,将脚本拖给它们
好了,现在你可以打开游戏,用你的手柄,按下扳机键抓起方块或者小球,左右互抛或者扔出去~
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。