通过HTCVive手柄发射射线控制物体的吸附效果,类似于帖在墙壁上的画框。
1.首先编写手柄上的控制类:SteamVRControllerBase。通过手柄射线获得碰撞点的位置和法线方向
using UnityEngine;
using System.Collections;
public class SteamVRControllerBase : MonoBehaviour {
public static SteamVRControllerBase getInstance;
private Transform sphere; //点的位置,使用一个小球
private Vector3 sphereNormal = Vector3.zero; //点的法线方向
private void Awake()
{
getInstance = this;
sphere = transform.Find("Sphere");
}
RaycastHit hitInfo;
private void FixedUpdate()
{
Ray ray = new Ray(transform.position, transform.forward);
if (Physics.Raycast(ray, out hitInfo, 1000f))
{
sphere.position = hitInfo.point; //复制位置
sphereNormal = hitInfo.normal; //获得法线方向
}
}
//获取位置来控制画框的位置
public Transform GetSphereTrans()
{
return sphere.transform;
}
//获取法线方向
public Vector3 GetSphereNormal()
{
return sphereNormal;
}
}
2.给画框添加吸附的控制类:AdsorbController。这样画框就能根据碰撞点的位置及时的吸附在墙壁上
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
[RequireComponent(typeof(MoveController))]
public class AdsorbController : MonoBehaviour {
private Collider col; //通过碰撞体获得大小
private Vector3 Velocity=Vector3.zero;
private float smoothTime =0.1f;
private Vector3 length; //物体长宽高
private void Start()
{
col = GetComponent<Collider>();
length = col.bounds.size;
}
private void Update()
{
Vector3 targetPos = SteamVRControllerBase.getInstance.GetSphereTrans().position;
//法线的起点需要向前移动半个物体宽度的距离,因为画框中心点在中间位置,否则会嵌入一半墙体
targetPos = new Vector3(targetPos.x- (length.x * transform.lossyScale.x)/2, targetPos.y, targetPos.z);
//使用阻尼函数平滑移动效果
transform.position = Vector3.SmoothDamp(transform.position, targetPos,ref Velocity, smoothTime);
Vector3 direction = SteamVRControllerBase.getInstance.GetSphereNormal(); //获取法线方向
Debug.DrawRay(transform.position, direction); //画出法线,用来测试
transform.forward = direction; //让画框前方与法线方向一致
}
}