使两个物理对象不碰撞但在 Unity 中检测碰撞

Make two physics objects not collide but do detect collisions in Unity

我有一个 Unity 项目,其中有一个 2D 游戏世界,该世界由静态碰撞器组成,使几何体对于居住在其中的角色来说是实体的。玩家是一个动态对撞机(具有非运动学刚体)。还有一个敌人角色,它也是一个动态对撞机。两个角色都像我期望的那样走过地板并撞到墙上。

我想要实现的是玩家和敌人之间不是实体的,所以他们可以互相穿行。我通过将敌人和玩家放在不同的层并设置碰撞矩阵使这些层不会相互碰撞来实现这一点。然而,我现在遇到的问题是,我确实想检测敌人和玩家是否 运行 相互接触。我为敌人角色添加了一个触发碰撞器,它在敌人层上,这意味着它不会检测到与玩家的碰撞。

本来想做一个敌人的sub-gameobject,放到玩家层,加上刚体和触发碰撞器,用来检测玩家和敌人之间的碰撞,但是感觉好绕这让我想知道是否有更优雅的解决方案。

编辑 (2020-05-26): 现在你可以告诉引擎 ignore collisions between two given objects。感谢 Deepscorn 的评论。将保留其余答案不变,并牢记这一点。

是的,你需要创建一个child GameObject,带有触发碰撞器,并将其放在与播放器层交互的层中。

不,你不需要在新的GameObject上添加Rigidbody,parent的刚体已经使它成为一个动态碰撞体,所以你会得到OnTrigger 事件。

附带说明一下,为了让事情井井有条,如果您创建 child 敌人,请不要将其放在玩家层中。例如,将来您可能需要禁用播放器与自身的图层碰撞。此外,如果您的玩家以这种方式与许多 objects 交互,我会在单独的 PlayerTrigger 层上对玩家而不是敌人放置一个触发器,只是为了简单起见。

有没有更简单的方法?并不真地。你肯定需要 non-interaction 在玩家和敌人的碰撞器之间,但它们之间也需要某种交互。所以其中一个需要跨越两层,否则整个交互将由一个 bool 来描述。物理引擎一次性处理大量信息,因此您可以设置所需的所有层和碰撞,但在物理循环期间您无法进一步控制发生的事情。您不能告诉引擎忽略两个 objects 之间的碰撞。只有 32 层,并让它们以严格的方式运行实际上是 重优化 。如果您担心创建另一个层的性能,请禁用不需要的层之间的交互,例如触发层与地板和墙壁,或者甚至不接触的层。

您的替代方案是通过代码完成所有操作,这更不优雅。播放器上的单个 child 胶囊现在听起来还不错,不是吗?