Unity 射线与碰撞范围检测【踩坑记录】
射线检测
射线检测在2D和3D的区别比较大
一定要加上对应的Collider组件
对应的函数只检测对应的Collider,
Physics.Raycast
是不会检测到Collider 2D的(这个让我有一次debug了好久才发现)对应API如下
Physics.Raycast(Vector3 origin,Vector3 direction,out RaycastHit hitinfo,float distance,int LayerMask);
//origin:射线的起始点,因为是位置坐标所以使用Vector3表示
//direction:射线的方向,因为是方向坐标所以使用Vector3表示
//hitinfo:一个结构体,可以储存碰撞体的所有信息。你可以声明一个空的然后直接代入就可以
//下面是可选参数:
//distance:射线检测的距离
//LayerMask:图层,如果输入图层的序号就可以只检测这个图层的相应物体,
可以使用Debug.DrawLine(Vector3 origin,Vector3 destination,Color color)
和Debug.DrawRay(Vector3 origin,Vector3 direction,Color color)
来使射线可视化
此外因为Ray都是由两个Vector3变量构造而成的,而2D世界都是Vector2
,只能用Vector2
变量表示了。
当从物体中心点发出时,检测到的第一个碰撞体却是自己。
那我们该怎么解决这个问题呢?答案是Physics2D.queriesStartInColliders = false;
这样如果碰撞体是我们射线所在起点的内部时,我们不让它返回该碰撞体。
为什么LayerMask
是int
LayerMask
的形式是int。它表示的是你图层的序号的二次方倍
就是相当于一个二进制数,需要检测的图层的对应位置为1,其余为0
- 1 << 10 打开第10的层。 等价于
1 << LayerMask.NameToLayer(“Ground”);
也等价于LayerMask.GetMask((“Ground”);
- ~(1 << 10) 打开除了第10之外的层。(取反符号)
- ~(1 << 0) 打开所有的层。
- (1 << 10) | (1 << 8) 打开第10和第8的层。
2D碰撞检测
Unity的物理引擎是基于PhysX的,但有时候游戏需要可配置的物理效果,按帧或者是时间线的方式来产生类似的效果。
Rigidbody 2D
选用了Rigidbody 2D组件的话,不能修改transform.position
,而是要使用Rigidbody2D.position
或Rigidbody2D.rotation
Body Type
- Dynamic: 表示动态刚体,完全模拟物理效果,与任何Rigidbody 2D都会发生物理效果,但是效率最低,只适合角色使用
- Kinematic: 表示运动学,只能和Dynamic刚体碰撞,如果需要和其他类型碰撞或者是需要触发碰撞事件,需要勾选
Use Full Kinematic Contacts
. - Static: 和Dynamic发生碰撞效果,和Kinematic只能发生碰撞事件(需要勾选
Use Full Kinematic Contacts
)
碰撞事件
我们除了可以在碰撞者和被碰撞者上监听碰撞事件外,如果监听碰撞的元素比较多,还能将碰撞事件抛出去由外部统一处理。
void Start()
{CollisionLi1stener.onCollisionEnter2D.AddListener(delegace (GameObject g1, GameObject g2) {Debug.LogFormat ( "{0}开始碰撞{1}",g1.name , g2.name);});CollisionLi1stener.onCollisionStay2D.AddListener(delegace (GameObject g1, GameObject g2) {Debug.LogFormat ( "{0}碰撞中{1}",g1.name , g2.name);});CollisionLi1stener.onCollisionExit2D.AddListener(delegace (GameObject g1, GameObject g2) {Debug.LogFormat ( "{0}结束碰撞{1}",g1.name , g2.name);});}
碰撞方向
Unity2D并没有提供方法来判断方向,但是提供了碰撞发生的坐标点,需要我们自己来计算碰撞方向。
void OnCollisionStav2D(Collision2D coll){foreach (ContactPoint2D contact in coll.contacts){//绘制线Debug.DrawLine ( contact.point, transform.position, Color.red);var direction = transform.InverseTransformPoint (contact.point);if(direction.x > 0f){ print( "右碰撞");}if(direction.x < 0f){print("左碰撞");}if(direction.y > 0f){print ("上碰撞");}if(direction.y < 0f){print ("下碰撞");}}
}
Effector
unity可以给Collider 2D组件添加的额外效果
- Platform Effector 2D: 单向板地面,能从下往上跳,却掉不下来
- Surface Effector 2D: 传输带一样带摩擦移动
- Point Effector 2D: 类似炸弹,爆炸后可以把周围东西炸开
- Buoyancy Effector 2D: 模拟浮力
- Area Effector 2D: 区域力
不依赖物理引擎
我们可以不依赖物理引擎,可以极大的优化效率,比如我们可以利用射线检测实现碰撞检测
射线检测
可以看出只用一根射线检测是不行的,在2D-Epic-Controller中就使用了10个射线检测来判断地面和前提碰撞
这种方法手感非常的完美,不过实现起来有些许麻烦
Physical.Overlap
我们可以直接使用下面几种:
- Physics.OverlapBox
- Physics.OverlapCapsule
- Physics.OverlapSphere
可以在此基础上使用Gizmos 辅助线框来实现在Scence中更好的视觉效果
如果是2D则使用Physics2D.开头的一系列函数
3D碰撞检测
碰撞检测穿透
只要是跟碰撞相关的基本都是离不开Rigidbody这个组件,当中的Collision detection参数可以选择碰撞检测方式
主要用于处理高速s运动的物体,会有时候直接穿过其他物体的时候
(上图每个箭头两端均指的是两个即将碰撞的物体的Collision Detection属性的值,箭头中间的属性值所指的是这两个物体时间碰撞所用的碰撞检测模式)
Discrete(离散型检测模式)就是普通的默认状态;
Continuous(连续检测)则是更加精细的碰撞检测,但是很耗资源;
Continuous和Continuous Dynamic的共同点在于,对待没有刚体和设置为Continuous Dynamic的物体都使用连续碰撞检测,对待刚体设置为Discrete的物体都使用离散碰撞检测。
不同点在于,Continuous Dynamic在检测另一个设置为Continuous的物体使用的仍然是连续碰撞检测模式,而Continuous检测另一个Continuous的物体时使用的却是离散碰撞检测。
此两类方法由于依赖于连续(线性)扫描,所以会忽略物体的角速度,当物体迅速旋转时,仍然会有穿墙的情况发生
之后又出了一个Continuous Speculative **(基于推测式)**这里官方的API解释是要比Continuous和Dynamic的方式这两种方式更加的节省性能,是扫描方式的进行连续碰撞检测。
使用连续碰撞检测(Continuous和Continuous Dynamic)前提:
刚体和非刚体(静态碰撞器): 刚体物体的碰撞器必须是Box,Sphere,Capsule,非刚体物体的碰撞器必须是Mesh。
不使用物理引擎
不使用刚体 Rigidbody的方式,采用发射子弹之前,先发射射线,记录碰撞点(判断是否会发生碰撞),然后在发射子弹。
Unity 射线与碰撞范围检测【踩坑记录】相关推荐
- BiGCN(谣言检测)踩坑记录
BiGCN踩坑记录 论文名:Rumor Detection on Social Media with Bi-Directional Graph Convolutional Networks 作者:Ti ...
- Unity GPU Instance踩坑记录
Unity GPU Instance踩坑记录 Unity中GPUInstance主要有两种:一种是unity自动进行的,或者调用Graphics.DrawMeshInstancedIndirect等A ...
- Unity AssetBundle 踩坑记录
Unity AssetBundle 踩坑记录 editor 下选择什么平台的 ab 加载 Material doesn't have a color property '_Color' UnityEd ...
- YOLOv5在无人机/遥感场景下做旋转目标检测时进行的适应性改建详解(踩坑记录)...
作者丨略略略@知乎(已授权) 来源丨https://zhuanlan.zhihu.com/p/358441134 编辑丨极市平台 文章开头直接放上我自己的项目代码: https://github.co ...
- 日常踩坑记录-汇总版
开发踩坑记录,不定时更新 心得 RTFM 严谨的去思考问题,处理问题 严格要求自己的代码编写习惯与风格 注意 单词拼写 20200207 mybatis plus 自带insert插入异常 sql i ...
- 【学习记录】QT5界面设计的踩坑记录
学习记录:QT5 界面设计的踩坑记录 前言 一.Qlabel显示视频与图片 1. 图片显示 1.1 显示格式 1.2 label随界面缩放 1.3 界面刷新 2. 视频显示 二.常见控件的StyleS ...
- Win10+yolov5 踩坑记录
Windows10下配置yolov5环境 踩坑记录 起因随笔 基本的环境要求 yolov5各代码作用 踩坑的Package windwos下torch和torchvision的安装 windows下p ...
- AirSim学习和踩坑记录(不定时更新)
版权声明:本文为博主原创文章,遵循Creative Commons - Attribution-ShareAlike 4.0 International - CC BY-SA 4.0版权协议,转载请附 ...
- 【STM32+机智云】机智云手机APP点灯实验踩坑记录
[STM32+机智云]机智云手机APP点灯实验踩坑记录 一.实验背景 因为项目开发需要用到云平台,所以开始学习机智云平台,听说机智云比较容易入门,还有手机APP.因此开始了踩坑之旅,一切的一切开始于一 ...
最新文章
- VTK:图片之ImageWarp
- pmp每日三题(2022年2月16日)
- python策略模式包含角色_详解Python设计模式之策略模式
- yolov2训练_一文看懂YOLO v2
- php 判断不是文件类型,php 判断文件类型
- 修改 Joomla! 1.5 的 HTML 输出而不动核心文件 (附api文档)
- leetcode题解-买卖股票的最佳时机
- java输出希腊字符表,希腊字母unicode表
- django orm级联_django系列5.3--ORM数据库的多表操作
- MobaXterm 保持连接
- 南阳oj 题目127 星际之门(一)
- 远程访问linux图像桌面,在windows下远程访问linux桌面
- 2018-2019赛季多校联合新生训练赛第四场
- 走入 Cocos Creator视频教程-姜威-专题视频课程
- MyCat —— 性能最好的数据库中间件
- 暮光之城 - Eclipse的DVD发行 - 另一个重磅炸弹DVD
- 每天一个小实例——使用pdfplumber提取pdf表格及文本,并保存到excel
- Android自定义软键盘样式:字母、数字、标点三种切换
- 小毛给在一路上帮助过的人的一封感谢信
- element-ui 表格添加校验
热门文章
- 机器学习面试题之机器学习基础(一)
- 银行外包Java开发的一些感想2023.2.5
- java outputstream初始化_ByteArrayOutputStream简介和使用_动力节点Java学院整理
- 【报错记录】解决华擎J3455-ITX不插显示器无法开机的问题
- 语义分割(Semantic Segmentation)方法
- 决策树的预剪枝与后剪枝
- sql优化和索引常见的面试题(面试总结)
- powershell创建新员工AD账号
- 如何解决装修预埋网线网速过慢的问题?
- A PM2.5 concentration estimation method based on multi-feature combination of image patches文章详解