1. 理解AABB与OBB:Unity中的两种包围盒
在游戏开发中,碰撞检测是核心功能之一。想象一下,当你玩射击游戏时,子弹能否击中敌人;在平台跳跃游戏中,角色能否站在平台上——这些都依赖于碰撞检测。而包围盒(Bounding Box)就是碰撞检测中最基础也最高效的工具之一。
Unity中主要有两种包围盒:AABB(Axis-Aligned Bounding Box,轴对齐包围盒)和OBB(Oriented Bounding Box,方向包围盒)。简单来说,AABB是一个始终与世界坐标轴对齐的长方体,而OBB则是可以随着物体旋转而改变方向的长方体。理解这两种包围盒的区别和使用场景,对于优化游戏性能、实现精确碰撞检测至关重要。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. AABB详解:表示方法与Unity实现
2.1 AABB的基本概念
AABB是最简单的包围盒形式,它的六个面始终与世界坐标系的X、Y、Z轴平行。这种对齐特性使得AABB的计算非常高效,但也带来了一个限制:当物体旋转时,AABB不会随之旋转,而是会"膨胀"以包含旋转后的物体。
举个例子,想象一个长条形的木棍。当它平放时,AABB紧贴木棍;但当木棍旋转45度后,AABB会变成一个更大的正方体,完全包含旋转后的木棍。这就是AABB的"轴对齐"特性带来的结果。
2.2 AABB的两种表示方法
2.2.1 最小-最大表示法
这是最直观的表示方法:
- Pmin:物体所有顶点中最小的x、y、z坐标值
- Pmax:物体所有顶点中最大的x、y、z坐标值
这种表示法的优点是计算简单,直接给出了包围盒的边界。在代码中,我们可以这样表示:
csharp复制Vector3 pMin = new Vector3(xMin, yMin, zMin);
Vector3 pMax = new Vector3(xMax, yMax, zMax);
2.2.2 中心-范围表示法
这是Unity采用的表示方法:
- center:包围盒的中心点 (pMin + pMax)/2
- extents:从中心点到各面的距离 (pMax - pMin)/2
- size:包围盒的长宽高 extents * 2
Unity中使用Bounds结构体来表示AABB:
csharp复制Bounds bounds = new Bounds(center, size);
// 或者
Bounds bounds = new Bounds();
bounds.center = center;
bounds.extents = extents;
提示:在Unity编辑器中,选中物体后显示的白色线框就是该物体的AABB包围盒。
2.3 Unity中获取AABB
在Unity中,可以通过Renderer组件的bounds属性获取物体的AABB:
csharp复制Renderer renderer = GetComponent<Renderer>();
Bounds aabb = renderer.bounds;
这个bounds属性返回的是物体在世界空间中的AABB。值得注意的是,即使物体有复杂的形状或子物体,这个AABB也会包含整个物体。
3. OBB详解:更精确的碰撞表示
3.1 OBB的基本概念
与AABB不同,OBB的方向是与物体的本地坐标系对齐的。这意味着当物体旋转时,OBB也会随之旋转,始终保持与物体相同的方向。这使得OBB能够更紧密地包裹物体,特别是在物体有旋转的情况下。
继续用木棍的例子:当木棍旋转45度时,OBB也会旋转45度,仍然紧贴木棍,而不会像AABB那样膨胀。这使得OBB在旋转物体的碰撞检测中更加精确。
3.2 Unity中的OBB实现
在Unity中,BoxCollider实际上就是一个OBB。但是要注意,BoxCollider的bounds属性返回的仍然是AABB(因为Unity的
