8.1 Collider 组件
Collider 定义物体的物理形状,用于碰撞检测。
3D Collider 类型
| 类型 |
用途 |
| BoxCollider |
盒型碰撞体(箱子、墙壁) |
| SphereCollider |
球型碰撞体(球、检测范围) |
| CapsuleCollider |
胶囊碰撞体(角色) |
| MeshCollider |
网格碰撞体(复杂形状,性能消耗大) |
| TerrainCollider |
地形碰撞体 |
2D Collider 类型
- BoxCollider2D / CircleCollider2D / CapsuleCollider2D
- PolygonCollider2D(多边形)
- EdgeCollider2D(边缘线)
8.2 碰撞事件
碰撞需要两个物体都带有 Collider,且至少一个有 Rigidbody。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
| public class CollisionEvents : MonoBehaviour { private void OnCollisionEnter(Collision collision) { Debug.Log($"撞到了:{collision.gameObject.name}"); Debug.Log($"碰撞点数量:{collision.contactCount}"); ContactPoint contact = collision.GetContact(0); Debug.Log($"碰撞点位置:{contact.point}"); Debug.Log($"碰撞法线:{contact.normal}"); }
private void OnCollisionStay(Collision collision) { }
private void OnCollisionExit(Collision collision) { Debug.Log($"离开碰撞:{collision.gameObject.name}"); } }
|
碰撞力计算
1 2 3 4 5 6 7 8 9
| private void OnCollisionEnter(Collision collision) { float impactForce = collision.impulse.magnitude; if (impactForce > 10f) { TakeDamage(impactForce); } }
|
8.3 触发器事件
将 Collider 的 IsTrigger 勾选后,变为触发器,不产生物理碰撞,仅触发事件。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25
| public class TriggerEvents : MonoBehaviour { private void OnTriggerEnter(Collider other) { Debug.Log($"进入区域:{other.gameObject.name}"); if (other.CompareTag("Player")) { CollectItem(); } }
private void OnTriggerStay(Collider other) { }
private void OnTriggerExit(Collider other) { Debug.Log($"离开区域:{other.gameObject.name}"); } }
|
触发器的典型应用
| 场景 |
实现 |
| 拾取道具 |
道具设为 Trigger,玩家进入触发拾取 |
| 伤害区域 |
岩浆/毒气区域,对进入者持续造成伤害 |
| 机关触发 |
玩家走到特定位置激活门/电梯 |
| 检测范围 |
AI 发现玩家的检测区域 |
| 关卡边界 |
检测物体是否掉出地图 |
8.4 Layer 与碰撞矩阵
通过 Layer 控制哪些层之间可以碰撞。
设置步骤
- 选中 GameObject,在 Inspector 顶部选择 Layer
- 点击 Layer 下拉菜单 → Add Layer… 添加自定义层级
- Edit → Project Settings → Physics → Layer Collision Matrix
1 2 3 4 5 6 7 8 9
| gameObject.layer = LayerMask.NameToLayer("Player");
Physics.IgnoreLayerCollision( LayerMask.NameToLayer("Player"), LayerMask.NameToLayer("Enemy"), true );
|
LayerMask 过滤器
1 2 3 4 5 6
| int layerMask = LayerMask.GetMask("Player", "Ground"); if (Physics.Raycast(ray, out hit, 100f, layerMask)) { }
|
8.5 碰撞与触发的选择
|
碰撞 |
触发器 |
| 物理阻挡 |
是(物体不能穿过) |
否(可穿过) |
| 回调方法 |
OnCollision 系列 |
OnTrigger 系列 |
| 性能 |
较高(需计算物理反馈) |
较低 |
| 典型用途 |
墙壁、地板、角色碰撞 |
拾取区、检测区、伤害区 |
8.6 本章小结
- Collider 定义物理形状,Rigidbody + Collider 产生真实碰撞
OnCollisionEnter/Stay/Exit 处理碰撞事件
- Trigger 不产生物理力,适合检测区域
- Layer 和碰撞矩阵控制哪些层可以碰撞
- 合理选择碰撞 vs 触发器以优化性能
练习题
- 创建两个球体,一个设定为 Trigger(作为拾取物品),玩家触碰后收集并销毁
- 实现一个伤害区域触发器:玩家进入后持续扣血
- 使用 Layer 让敌人物体之间不互相碰撞
- 用
Physics.Raycast 实现射击检测,区分不同 Layer 的物体