Unity的射线
Ray射线
今天我要总结的使Unity有关射线的相关东西,如有某些地方理解错误还望指正,谢谢!
1.什么Ray射线
首先,我们要知道射线构成的两大要素:起点和方向,所以实例化一条射线需要这两个参数。
射线的实例化:
(关键字)Ray 变量名 = new (关键字)Ray(Vector3 origin,Vector3 direction);
第一个参数origin表示射线的起点,第二个参数direction表示射线的方向。
特殊的Camera.main.ScreenPointToRay(Vector3 targetPosition)
表示摄像机向目标位置发射射线其中targetPosition通常会使用屏幕坐标
Input.mousePosition,表示摄像机向鼠标位置发射射线。
2. RaycastHit类的介绍
作用:用于储存发射射线产生的碰撞信息。
常用的成员变量有:
point:射线与碰撞器的交点坐标
collider:与射线发生碰撞的物体的碰撞器
distance:射线起点到与碰撞物体交点的坐标
3.射线的调试(显示)
Debug.DrawRay(Vector3 start, Vector3 dir, Color color, float duration)
参数start:射线的起点
参数dir:射线的方向
参数color:调试中射线的颜色
参数duration:调试中射线的存在的时间
当然Debug.DrawRay函数有很多重载,比如我们可以不写Color color, float duration,那么我们的射线在编辑模式下,射线的颜色就默认是白色,存在时间默认是一帧;
把下面这个脚本放在一个物体,然后运行,在编辑模式就可看到以(0,0,0)为起点,方向为沿X轴正方向的红色 射线。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Shoot : MonoBehaviour
{
void Update()
{
Vector3 origin = new Vector3(0, 0, 0);
Vector3 direction = new Vector3(1f, 0, 0);
Ray ray = new Ray(origin, direction);
Debug.DrawRay(ray.origin, ray.direction * 100f, Color.red, 1f);
}
}
4.射线的发射:bool Physics.Raycast(Ray ray, out RaycastHit hitInfo, float maxDistance, int layerMask,QueryTriggerInteraction );
参数start:射线的起点
参数ray:射线
参数hitInfo:储存被射线碰撞到的物体信息
参数maxDistance:射线的最大距离
参数layerMask:射线检测的图层,用int 十进制转化为二进制判断,(十进制)2->(二进制)10,表示 检 测第一层TransparentFX;
参数QueryTriggerInteraction :查询是否忽略is Trigger(触发器),忽略使用QueryTriggerInteraction.Ignore,检测使用QueryTriggerInteraction.Collide
函数描述:发射一条射线ray,这条射线的长度为maxDistance,如果这条射线在指定图层碰到了其它带有碰撞器的物体,则把该物体信息储存在hitInfo中,且返回true,如果没碰到物体就返回false;
当然这个函数还有其它重载,比如我们可以不写 float maxDistance, int layerMask,QueryTriggerInteraction 这三个参数,那么发射射线的最大距离默认为无限大,图层就默认检测除了2 图层Ignore Raycast外的其它图层,参数QueryTriggerInteraction 就为QueryTriggerInteraction.UseGlobal,也就是我们项目设置里面的默认设置。如果勾了就默认检测,否则就忽略;
然后我们在一个物体上添加如下脚本,并在射线经过的地方摆一个盒形碰撞器。然后运行并点击一下鼠标左键,然后你就会在控制台上发现射线碰撞到的物体的碰撞器的种类。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Rayshoot : MonoBehaviour
{
bool isnoShoot;
public Vector3 Direction;
// Update is called once per frame
void Update()
{
// Input.GetMouseButtonDown(0)点击鼠标左键返回true,否则返回false
isnoShoot = Input.GetMouseButtonDown(0);
// Shoot();
if (isnoShoot)
{
Vector3 origin = new Vector3(0, 0, 0);
Vector3 direction = new Vector3(1f, 0, 0);
Ray ray = new Ray(origin, direction);
//实例了一条以(0,0,0)为起点,方向为沿X轴正方向的射线
Debug.DrawRay(ray.origin, ray.direction * 100f, Color.red, 1f);
RaycastHit hit;
Physics.Raycast(ray, out hit, 100f, 1, QueryTriggerInteraction.Collide);
Debug.Log(hit.collider);
}
}
}
射线的应用场景
射线的应用场景有很多,由于篇幅有限,我们就模拟一下人物射击。
首先我们需要在场景中创建一个球形碰撞器,然后通过拖动把它变成预制体,然后删除场景中的球形碰撞器,然后在在预制体上增加以下脚本。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class bullet : MonoBehaviour
{
Vector3 shootdirection;
float speed;
// Start is called before the first frame update
void Start()
{
speed = 6f;
}
// Update is called once per frame
void Update()
{
transform.Translate(shootdirection*speed*Time.deltaTime,Space.World);
}
/// <summary>
/// 初始化子弹移动的方向
/// </summary>
/// <param name="shoot"></param>
public void startState(Ray shoot)
{
shootdirection = shoot.direction;
}
}
然后我们在场景中再创键一个球形碰撞器模拟人物,并在上面添加如下脚本。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class roleshoot : MonoBehaviour
{
bool isnoShoot;
public bullet bullets;
// Update is called once per frame
void Update()
{
isnoShoot = Input.GetMouseButtonDown(0);
if(isnoShoot)
{
RoleShoot();
}
}
void RoleShoot()
{
//摄像机向鼠标所在的地方发射射线
Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
RaycastHit hit;//定义一个RaycastHit接受被碰撞物体的信息
//发射射线
Physics.Raycast(ray, out hit, 100f, 1, QueryTriggerInteraction.Collide);
Vector3 shootdirection = hit.point - transform.position;
//实例主角应该发射的射线
Ray roleray = new Ray(transform.position, shootdirection);
//让射线在编辑模式中可见
Debug.DrawRay(roleray.origin, roleray.direction*1000f, Color.red, 2f);
//生成子弹,
bullet bullet = Instantiate(bullets, transform.position, bullets.gameObject.transform.rotation);
//初始化子弹方向
bullet.startState(roleray);
}
}
然后手动添加预制体.
然后点击地面就可以发射子弹了。
本文地址:https://blog.csdn.net/a15970673567/article/details/109273600