3

我一直在尝试找到一个可以适应并用于我正在开发的游戏的防撞示例。它将用于模拟滑雪者的动作以避免山上的树木。我基于自主角色的转向行为的运动,并且有很多关于路径跟踪和聚集的好例子,但我找不到任何避免碰撞的好例子。 Nature of Code网站上有很棒的转向教程,但似乎涵盖了除避障之外的所有内容。

我从这里转换了代码,但它不能正常工作,因为碰撞是通过将障碍物中心投影到速度矢量上来找到的,而不考虑障碍物中心何时可能超出碰撞限制但圆仍然是碰撞。这是我改编的代码(用处理(基于Java)编写)。

// Method to update location
void update() {
  // Update velocity
  vel.add(acc);
  // Limit speed
  vel.limit(maxspeed);
  loc.add(vel);
  // Reset accelertion to 0 each cycle
  acc.mult(0);
}

void obstacleAvoid() {
  float checkLength = 30*vel.mag();
  PVector forward,diff,ray,projection,force;
  float dotProd,dis;
  forward = vel.get();
  forward.normalize();
  ray = forward.get();
  ray.mult(checkLength);
  for ( int i = 0; i < obs.size(); i++ ) {
    Obstacle ob = (Obstacle)obs.get(i);
    diff = ob.pos.get();
    diff.sub(loc);
    PVector temp2 = forward.get();
    temp2.mult(ob.r);
    diff.sub(temp2);
    dotProd = diff.dot(forward);
    if ( dotProd > 0 ) {
      projection = forward.get();
      projection.mult(dotProd);
      dis = PVector.dist(projection,diff);
      if ( (dis < (ob.r + r)) && (projection.mag() < ray.mag()) ) {
        ob.hit = true;
        force = forward.get();
        force.mult(maxforce);
        if ( sign(diff,vel) == -1 ) { //CCW
          force.set(force.y,-force.x,0);
        }
        else { //CW
          force.set(-force.y,force.x,0);
        }
        force.mult(1-(projection.mag())/ray.mag());
        force.limit(maxforce);
        acc.add(force);
      }
    }
  }  
}

因此,为了帮助我,我想知道是否有人知道遵循自主角色的转向行为更好地做事 的任何完整的防撞示例。这个站点是本文的示例小程序,​​也是我希望看到代码的确切示例。遗憾的是,它没有附带代码,我尝试反编译它,但它只显示了主类,所以这不是很有帮助。如果有人有这个例子的代码或类似的东西,或者教程,我会非常感激。

4

2 回答 2

1

Craig Reynolds 无法发布您感兴趣的小程序的源代码。类似的源代码在OpenSteer的 c++ 中可用,由 Reynolds 维护。Christian Schnellhammer 和 Thomas Feilkas 致力于扩展 Reynolds 的原始论文。他们的论文被翻译成英文,并包含一个关于避障的部分。他们工作的源代码在Java中可用。但是,我认为 Shiffman 的代码是一个很好的起点,听起来您已经非常接近您想要的了

我的第一个处理程序之一修改了 Boids 示例以模拟僵尸启示录。三角形追逐着避开它们的圆圈。每个幸存者在他们的视野中检查其他僵尸,并在一个函数中平均威胁的位置向量,PVector panic(ArrayList infected). 之后,就是对新向量负权重,并将其添加到幸存者的当前向量中,就像任何其他力一样。就像是:

void flock(ArrayList uninfected, ArrayList infected) {
  PVector sep = separate(uninfected);   // Separation
  PVector ali = align(uninfected);      // Alignment
  PVector coh = cohesion(uninfected);   // Cohesion
  PVector pan = panic(infected);        // Panic
  // Arbitrarily weight these forces
  sep.mult(4.0);
  ali.mult(1.0);
  coh.mult(2.0);
  pan.mult(-3.0);
  // Add the force vectors to acceleration
  acc.add(sep);
  acc.add(ali);
  acc.add(coh);
  acc.add(pan);
}

如果您的滑雪者成功地检测到障碍物,那么避免问题就是问题所在。向回避向量添加更大的权重,增加滑雪者可以“看到”以与对象交互的半径,或者甚至向对象添加一个返回与滑雪者最近点的位置的方法可以解决您的问题。您还可以根据从滑雪者到其前方最近障碍物的距离添加减速。

请记住,即使您感兴趣的小程序也不能完全避开障碍。我的解决方案可能与小程序中发生的不完全一样,但通过调整确定滑雪者方向的力量,您可以获得非常相似(并且可能更好)的效果。

于 2010-12-14T06:23:29.120 回答
0

在 NEHE 游戏开发网站上查看此链接:

在本教程中,您将学习碰撞检测、碰撞响应和基于物理的建模效果的基础知识。本教程更多地关注碰撞检测的工作原理,而不是实际代码,尽管所有重要的代码都进行了解释。

http://nehe.gamedev.net/data/lessons/lesson.asp?lesson=30

它是使用 c++ 和 win32 API 完成的。尽管您会找到使用 JOGL的Java Port链接。

尽管在 c++ 中 ,源代码http://www.red3d.com/cwr/steer/可以在此处获得。http://opensteer.sourceforge.net/你查过吗??

于 2010-11-29T04:52:16.687 回答