首页 > 编程语言 >【Unity】碰撞检测算法及框架实现

【Unity】碰撞检测算法及框架实现

时间:2024-07-12 19:42:35浏览次数:16  
标签:两者 多边形 凸多边形 算法 碰撞检测 Unity SAT

背景

硕士期间研究课题是海洋生物数字孪生,基于各类Boids改进的算法里会有大量的海洋鱼类在三维空间中运动,鱼类之间会有互相感知的过程,同一帧里需要对许多行为进行决策判定,例如同伴鱼、食物、捕食者、栖息地等等。因此打算研究下有什么空间加速算法能够避免暴力迭代,减少开销。既然研究了这个,顺便也把碰撞检测也给弄懂了,想一次性弄的透彻一些,所以基于各个算法实现了一套碰撞检测框架。文章大纲和[1]这篇类似,包含了碰撞检测和空间加速算法。但是对各个算法的原理会简单概括,不对细节进行冗余介绍,但是会对各个算法的优缺点进行总结,并且主要侧重于框架的搭建

碰撞检测

各种碰撞体

  • BoxCollider
  • SphereCollider

各种碰撞检测算法

AABB算法(Axis-Aligned Bounding Box)

图片名称

OBB/SAT算法(Oriented Bounding Box / Seperating Axis Theorem)

OBB不赘述了,是简化成了四条边的SAT

  • 分离轴定理:两个凸多边形之间如果不相交,那么必定存在一条线可以将两者进行分割。这条线称之为分割线(Seperating Line)
  • 分离轴定理推论:两个凸多边形之间如果不相交,那么必定存在一条轴,让两多边形落在上面的投影线段不相交。这条轴称之为分离轴(Seperating Axis)

所以只要找到了那一条分离轴,就必定可以判断出两个凸多边形不相交。

但是这样找很难找,遍历的范围是无穷的,所以就有了简化的证明方法,来缩小搜索范围(重要推论

  • 重要推论:两个凸多边形之间如果不相交,那么必定存在一条平行于这两个多边形中的某一条边的分割线同时有一条垂直于该分割线的分割轴,让两多边形落在上面的投影线段不相交。
图片名称

其实AABB、OBB、SAT我认为都有个共同点,它们都是:只要寻找到一个轴,落在上面的投影没有交叉(Amin > Bmax || Amax < Bmin),则整体都不会有相交。

GJK算法(Gilbert–Johnson–Keerthi 人名缩写)

结论

两个多边形相交 <=> 则它们的闵可夫斯基差集必然包括原点(零向量)

Support函数

输入为方向d,输出是该方向上凸多边形的最远顶点的位置。

图片名称

闵可夫斯基差集

图形A和图形B中的所有(xx的)点坐标相减,得到的新集合叫闵可夫斯基差集。

碰撞检测算法的切换条件

加粗代表已实现

  • Sphere:两者都是Sphere时。
  • AABB(可被OBB代替):两者都是未发生旋转的Box,或者本身就是限制旋转的AABBBox。
  • ABBB-圆[3,4]:两者其中一者是未发生旋转的Box,或者本身就是限制旋转的AABBBox,另一者是Sphere。
  • OBB(可被SAT代替):两者都是Box,且其中任意一者存在旋转。
  • SAT-多边形-多边形:两者都是凸多边形,且两者都不是Sphere。
  • SAT-多边形-圆:两者中其中一者是凸多边形,另一者是圆形。
  • GJK:两者中其中一者是凸多边形,且两者都不是Sphere。
  • EPA:两者中其中一者是凸多边形,且两者都不是Sphere。
    以上SAT、GJK、EPA三选一
  • 圆框与AABB矩形框(矩形框不旋转):其中一者是未发生旋转的Box,或者本身就是限制旋转的AABBBox。另一者是Sphere。
  • 分割SAT:两者其中一者是凹多边形,且两者都不是Sphere。

相关算法

判断一个点在一条线的顺时针侧(右)还是逆时针侧(左)

图片名称

判断一个点是否在一个三角形内

面积法

图片名称

向量法

无论三角形的连线方向是顺逆时针。只要点在三条边的同侧,就代表点在三角形内部。

判断一个图形是凹是凸

定义:凸多边形是指如果一个多边形的所有边中,任意一条边向两方无限延长成为一直线时,其他各边都在此直线的同旁,那么这个多边形就叫做凸多边形。

实现过程:① 从凸多边形的一个点开始,顺序选择第二个点,连成一条直线。 ②判断剩下所有点是否都在该直线的同一侧。 ③ 反复①过程,遍历完每一条边,如果每条边都满足②,则为凸多边形。

图片名称

Unity的碰撞检测介绍

在Unity 5.5之前,Unity使用SAT来进行碰撞检测。之后Unity推出了PCM(持久接触流形,Persistent Contacts Manifold)方法,会更高效,无用的碰撞点信息会更少。

现在的项目默认都是PCM了,但是也可以在Project Settings里修改:

图片名称

空间划分加速算法

BSP,BHV,八叉树,四叉树

框架设计及搭建

参考

[1] https://blog.csdn.net/weixin_42186870/article/details/136147295
[2] https://zhuanlan.zhihu.com/p/177006015
[3] https://www.zhihu.com/question/266499219/answers/updated
[4] https://www.cnblogs.com/zhjblogs/p/16737750.html

标签:两者,多边形,凸多边形,算法,碰撞检测,Unity,SAT
From: https://www.cnblogs.com/JimmyZou/p/18296317

相关文章

  • 「代码随想录算法训练营」第九天 | 栈与队列 part1
    232.用栈实现队列题目链接:https://leetcode.cn/problems/implement-queue-using-stacks/题目难度:简单文章讲解:https://programmercarl.com/0232.用栈实现队列.html视频讲解:https://www.bilibili.com/video/BV1nY4y1w7VC题目状态:看视频讲解后通过思路:通过两个栈来实现队......
  • 课程设计——基于matlab仿真的puma560机械臂RRT路径规划算法
    本项目适合做计算机相关专业的毕业设计,课程设计,技术难度适中、工作量比较充实。完整资源获取点击下载完整资源1、资源项目源码均已通过严格测试验证,保证能够正常运行;2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通;3、本项目比较适合计算......
  • UWA学堂上新|服务器AOI(Area Of Interest)算法和功能实现
    课程是《基于.NetCore开发MMORPG分布式游戏服务器》系列课程第6节,本系列课程旨在帮助大家从零开始搭建商业化MMORPG的分布式服务器框架,包括不同种类服务器的线程模型,如中心服务器、网关服务器、游戏服务器、寻路服务器等,并讲解了这些服务器该如何根据各自的职责进行业务模块分工......
  • 课程设计——基于Matlab的LDPC编解码算法实现及LDPC码性能测试
    本项目适合做计算机相关专业的毕业设计,课程设计,技术难度适中、工作量比较充实。完整资源获取点击下载完整资源1、资源项目源码均已通过严格测试验证,保证能够正常运行;2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通;3、本项目比较适合计算......
  • ARC算法实现
    1.概述AdaptiveReplacementCache(ARC)是一种缓存替换算法,用于提高缓存的命中率。ARC动态调整缓存策略,以适应实际的访问模式,从而在不确定的工作负载下表现良好。它通过同时维护两个缓存列表来追踪最近使用和频繁使用的数据块,并根据访问模式在这两个列表之间动态分配缓存空间。2......
  • 代码随想录算法训练营第10天 | 复习队列和栈
    2024年7月12日题232.用栈实现队列两边倒即可,要出队列就倒到右边去,然后再回来。classMyQueue{Stack<Integer>s1;Stack<Integer>s2;intsize;publicMyQueue(){s1=newStack<>();s2=newStack<>();size=0;}......
  • 算法力扣刷题记录 四十三【最大、最小深度问题】
    前言本文学习树的深度问题:二叉树(N叉树)最大深度、最小深度;记录三十九【层序遍历模版应用二】中解决过二叉树的最大深度和最小深度题目。思路是按层遍历:最大深度,相当于层序遍历结束;最小深度,相当于层序遍历过程中判断节点是不是叶子节点。那么此处的深度,还有什么知识点?......
  • 【unity开发】怎么下载国际版的unity编辑器版本
    有一天从公司那接手了一个项目,然后发现那个项目的版本我没有,我就去unity官网下载。下载完了发现还是版本不对。仔细一看发现,他们用的版本号末尾少了个"c1"。c1的意思是中国特供版,好像是说有微信api的支持。那么我应该怎么做呢?下面随便一个版本为例子1.点击按钮下载。2.......
  • 代码随想录算法训练营Day22 | Leetcode 77. 组合 | 216.组合总和III | 17.电话号码的
    今日任务77.组合题目链接:https://leetcode.cn/problems/combinations/description/题目描述:CodeclassSolution{vector<vector<int>>ans;vector<int>path;public:vector<vector<int>>combine(intn,intk){//intst......
  • 如何使用 Unity 的 ScriptableObjects 和 Resources 系统来创建一个简易的数据库系统,
    1.引言问题:如何在Unity中存储数据?解决方案:使用ScriptableObjects和Resources系统创建一个易于使用和管理的数据库。优势:自动读写数据自动处理资源实例化和更改无需额外插件使用用户定义键进行访问可扩展性强2.实现2.1项目结构四个主要的脚本:Item......