Unity进化模拟器:OnTriggerEnter未触发碰撞却销毁物体问题求助
问题分析与解决方案
嘿,我一眼就看出问题所在了——你在Update()方法里手动调用了OnTriggerEnter(),完全绕过了Unity的碰撞检测系统,这就导致不管生物有没有真的碰到食物,食物都会被直接销毁!
问题根源
你的Update()方法里这段代码是罪魁祸首:
void Update() { Rigidbody[] allRigidBodies = (Rigidbody[])FindObjectsOfType(typeof(Rigidbody)); foreach (Rigidbody body in allRigidBodies) { if (body.gameObject.layer == 10) { OnTriggerEnter(body.gameObject.GetComponent<CapsuleCollider>()); } } }
这段代码在每一帧都会遍历所有带Rigidbody的物体,只要发现layer是10的物体,就直接调用OnTriggerEnter()方法销毁食物——完全不管两者有没有实际触发碰撞。
修复步骤
删掉Update里的所有代码
Unity的OnTriggerEnter()是由引擎自动触发的,不需要你手动调用。只要碰撞条件满足,引擎会自动执行这个方法。确保碰撞设置正确
要让触发器正常工作,你需要满足以下条件:- 食物的
CapsuleCollider必须勾选IsTrigger选项 - 生物对象必须带有
Rigidbody组件(触发器需要至少一个参与碰撞的物体有Rigidbody) - 可以在
OnTriggerEnter()里加个判断,确保只有生物触发时才销毁食物:private void OnTriggerEnter(Collider creature) { // 检查触发的物体是否是生物(通过layer判断) if (creature.gameObject.layer == 10) { Destroy(gameObject); // 直接销毁当前挂载脚本的物体,无需额外引用 } }
- 食物的
优化冗余代码
你的脚本里FoodGO和FoodRB是多余的,直接用gameObject和GetComponent<Rigidbody>()即可,简化后的完整脚本如下:
using System.Collections; using System.Collections.Generic; using UnityEngine; public class FoodEat : MonoBehaviour { private void OnTriggerEnter(Collider creature) { // 只在生物(layer 10)触发时销毁食物 if (creature.gameObject.layer == 10) { Destroy(gameObject); } } void Start() { // 如果需要用到Rigidbody,直接在这里获取即可,无需额外赋值给字段 // Rigidbody foodRB = GetComponent<Rigidbody>(); } }
额外提示
- 如果你想用tag来区分生物和其他物体,也可以把判断改成
creature.CompareTag("Creature"),记得给生物对象设置对应的tag - 确保食物和生物的碰撞体没有被禁用,且两者的位置/大小设置合理,避免出现误触发
内容的提问来源于stack exchange,提问作者Vojtěch Vach




