【问题标题】:What is a good way to identify which specific gameObjects are colliding?什么是识别哪些特定游戏对象正在碰撞的好方法?
【发布时间】:2011-01-30 00:57:18
【问题描述】:

这是关于物理引擎的。一旦发生碰撞,它会返回两个游戏对象正在碰撞的信息。所有实体,如玩家、怪物、子弹等都是从 GameObject 派生(继承)的。

什么是识别哪些特定游戏对象正在碰撞的好方法?

枚举:我曾考虑过使用枚举,但是一旦您开始添加更多实体,就无法跟踪所有可能的组合。

编辑:我在这里找到了 C# 的潜在解决方案:http://blogs.msdn.com/b/laurionb/archive/2009/08/13/multimethods-in-c-4-0-with-dynamic.aspx

但是,如果我必须在 C++ 中执行此操作,我该怎么做?

【问题讨论】:

  • 好吧,我现在正在用 c# 做这个,但最终,我会将它移植到 c++,这样我就可以在不同的平台上使用它。

标签: architecture software-design multiple-dispatch dynamic-dispatch


【解决方案1】:

典型的解决方案是像这样进行两级调度:

class Thing
{
    public abstract void Collide(Thing other);
    public abstract void CollideWithSpaceship(Spaceship spaceship);
    public abstract void CollideWithAsteroid(Asteroid asteroid);
};

class Spaceship : Thing
{
    public override void Collide(Thing other) {
        other.CollideWithSpaceship(this);
    }

    public abstract void CollideWithSpaceship(Spaceship spaceship)
    {
        // Handle Spaceship -> Spaceship collision...
    }

    public abstract void CollideWithAsteroid(Asteroid asteroid)
    {
        // Handle Spaceship -> Asteroid collision...
    }
}

class Asteroid : Thing
{
    public override void Collide(Thing other) {
        other.CollideWithAsteroid(this);
    }

    public abstract void CollideWithSpaceship(Spaceship spaceship)
    {
        // Handle Asteroid -> Spaceship collision...
    }

    public abstract void CollideWithAsteroid(Asteroid asteroid)
    {
        // Handle Asteroid -> Asteroid collision...
    }
}

随着不同类别的数量增加,它变得有点麻烦,但它有一些事情要做:

  1. 速度很快。它依赖于语言的内置动态调度,即 优化得很好。
  2. 它是类型安全的。您会注意到没有进行投射。

缺点是:

  1. 它不是对扩展开放的。添加新课程需要您触摸 所有其他人。

一个更具扩展性的解决方案是构建一个 2D 调度表,其中每个单元格标识一对冲突类。在每个单元格中,放置一个处理这两种类类型之间冲突的函数。这也很有效,但它有点欺骗类型系统。您最终会进行一些强制转换,并且必须想出一种识别类的好方法。

不会使用 C# 的 dynamic 支持。我强烈的预感是它对于物理引擎来说太慢了。

我还要指出,Game Development Stack Exchange 更擅长回答此类问题。那里见!

【讨论】:

  • 这不是类似于访问者模式吗?我在更有效的书中读到了这个和动态调度。但是,感谢您如此详尽的回复。正如你所提到的,我不喜欢在调度表上欺骗类型系统。我仍在寻找一个解决方案,如果我添加一个新类并且添加所有相应的函数以完成实体之间关系的笛卡尔积,我将不必重新编译所有内容。
  • 另外,我很想了解动态系统如何在后台工作以解析对象并使用正确的参数类型正确映射到正确的函数调用。
  • 与访客模式非常相似。它基本上是一个折叠起来的访问者,其中被访问的类和进行访问的类是同一类 (Thing)。在其他访问者实现中,情况并非总是如此。
  • 如果你对多方法感兴趣,看看 CLOS,Common Lisp 中的对象系统。这是最著名的多方法语言。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-02-24
  • 1970-01-01
  • 2016-09-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多