タワーディフェンスゲームのダイナミックパスアルゴリズム


16

私はタワーディフェンスを作っていますが、それには良いパスアルゴリズムが必要です。

私はダイクストラについて考えましたが、ダイナミックなものが必要です。1つのエッジが完全に再計算されずに削除または追加されたときに、それ自体を更新できる必要があります。

役立つ場合は、C#でコーディングしています。

回答:


8

探している重要な違いがない限り、通常はA *を使用します。


A *にそれほど詳しくない場合、動的に変化する環境にどのように対処しますか?すべてのフレームで再計算しますか?衝突時?
ジャスティンL.

1
通常、このような単純なゲームでは、各フレームのパスを変更します。マップグリッドはおそらく非常に小さく、最大で数百人のエージェントの数になります。それが何らかの形で大きなパフォーマンスの問題になった場合、必要なとき以外はツリーを再構築しないことで後で最適化できます。
coderanger

6
それが遅い場合、私の推奨事項:すべての暴徒のパスを計算しないでください。おそらく、彼らはすべて同じ道を進んでいます。新しいタワーの配置についてのみ再計算し、タワーは現在のパスにあります。その場合でも、ブロックスクエアの前のパスのポイントでのみモンスターの再計算を行います。過去のMobの場合は気にしないでください。そして、経路探索を短くするために、ブロックされた正方形の後に正方形への道を見つけるように制限することができます。そこからの経路はすでにわかっているからです。
seanmonstar

4
実際、「mob」は「モバイルオブジェクト」の業界用語(およびMMO / MUDプレーヤー)です。

3
とにかく、それはMUD1にまでさかのぼる長年にわたるものであり、多くの出版物に登場するのに十分な標準です。en.wikipedia.org/wiki/Mob_%28computer_gaming%29

19

私は同様の問題を解決する必要がありました。「迷路」と障壁が絶えず変化する大きな迷路のようなグリッド上の経路探索です。

問題は、タワーディフェンスゲームでは、パスを解決する必要があるエンティティの数は、通常、グラフ内のノードの数よりもはるかに多いということです。A *は、これを処理するための最適なアルゴリズムではありません。何かが変更されるたびに新たに解決する必要があるためです。パスを1つだけ見つける必要がある場合は適切ですが、私の場合は、さまざまな場所に表示され、それぞれに独自のパスを持つエンティティを処理できる必要がありました。

フロイド・ウォーシャル私の場合のために、私はいつでもノードの変更、それはすべての隣人からそのノードへのコストを再計算し、その独自のアルゴリズムを書いたもののアルゴリズムは、はるかに適切である場合には隣人が変更されている、それが呼び出されますそれらに対して再帰的に。

そのため、ゲームの開始時に、すべての「目標」ノードでこのアルゴリズムを起動するだけです。その後、単一のノードが変更される(たとえば、通過不能になる)たびに、そのノードで起動し、変更が影響を受けるすべてのノードに伝達され、停止されます。したがって、グローバルな再計算の必要はなく、アルゴリズムはパス検索を必要とするエンティティの数から完全に独立しています。

私のアルゴリズムは基本的に(擬似コード)のようなものでした:

update_node method in Node class:
    $old <- $my_score
    find $neighbor node among all neighbors such that
        $neighbor.score + distance_to($neighbor) is minimal
    $my_score <- $neighbor.score + distance_to($neighbor)
    $next_node <- $neighbor
    if ($my_score != $old)
        for each $neighbor
            $neighbor.update_node()

ノードがターゲットであるか、何らかのバリアであるかに応じて初期スコアが決まります。


1
また、CPU負荷の変化に応じて、これをフレームに動的に広げることも簡単です。
tenpn

使用する適切なアルゴリズムではないA *に対して+1。
リケット

5

TDで使用したルートアルゴリズムは、ゲーム内に存在するエンティティの数が原因で、通常のA *パスから逆向きでした。ゴールから悪者にルーティングする代わりに、ゴールからボード上のすべての空の広場にルーティングしました。

これにはそれほど時間がかからず、「コスト」が見つかるまでボードを繰り返し続けるだけで、ブロックされたルート(それらを実行している場合)に適切なフィードバックを提供します。Floydのアルゴリズムを使用すると、データ依存のルックアップを行わず、ストリーム内のデータを読み込んで操作するだけなので、A *と比較して高速でキャッシュフレンドリーです。

無限コストに設定したボードから始めて、コストがゼロになるように目標二乗を設定し、ボードのチェックを繰り返して、隣接セルのコストが現在のコストに移動コストを加えたものよりも低いかどうかを確認します 旅費はあなたがあなたの経験則を置く場所です(私の場合、斜めに旅する費用は無限でしたが、塔を通る旅の費用は高かったので、彼らは塔を通って食べることを許可されましたが、選択)

コストグリッドを取得したら、セルのコストの最も急な勾配をテストすることで、そこから「フロー」グリッドをすばやく構築できます。これは、大量の悪者に対して本当にうまく機能します。なぜなら、彼らは誰も道を見つける必要がなく、彼らは仮想の道標に従うだけだからです。

もう1つの利点は、この方法では、障害物を調整するたびに(または私のゲームでは、クリープがタワーの1つを食い尽くすたびに)このタスクを実行するだけで済むことです。クリープ/モブが毎回フィールドに入るたびに(毎秒数千のモブと数十のモブが頭痛の種になっていただろう)。


4

経路探索は高速であり、通常のタワーディフェンスゲームほどの大きさであれば、何かが変更されたときにA *またはダイクストラのフルパスを実行しても問題はありません。完全にリフレッシュするために、1ミリ秒未満で話しています。あらゆる種類の適応経路探索は、恐ろしく複雑になります。世界最大のタワーディフェンスグリ​​ッドを作成している場合を除き、簡単な方法で実行してください。


1
タワーディフェンスは、経路探索が高速ではない携帯電話で人気があることは注目に値します。特にSidekickやAndroid 1.6デバイスなどの少し古いデバイスでは。
seanmonstar

1
開発者は、A *やDijkstraなどのパスファインディングアルゴリズムを、何十年もずっと強力でないハードウェアで使用してきました(Game Boyを考えてください)。もちろん、実装が合理的に効率的であれば、ゲームに適した画面を表示するのに十分な新しい電話機には問題はありません。ここで議論されている気の利いた最適化がいくつかあります:harablog.files.wordpress.com/2009/06/beyondastar.pdf
Mike Strobel

+1。独自のDTDクローンを開発していたときにも同じ結論に達しました。パスを段階的に更新しようとしましたが、アルゴリズムが複雑になりすぎました。それに1日を費やした後、私は変更ごとに完全な再計算に切り替えました。それはうまくいきましたが、いくつかの調整を行うことで、十分に高速にすることができました。
finnw


2

これはソリューションにとってはやり過ぎかもしれませんが、前方ではなく後方へのルーティングを考えてください。

TDゲームでは、敵は一般的に特定の目標に到達しようとしています。そのゴールから最初の敵まで後方にルーティングし、そのパスをキャッシュします。後続の敵のパス生成では、最初のパスを開始点として使用します。複数の敵の進入ポイントまたは複数の目標がある場合、開始するために事前にキャッシュされたパスの範囲があります。


1

一般に、aiがダイレクトパスをたどるレベルに基づいているため、ウェイポイントパスファインディングはおそらくtdゲームに最適です。基本的に、ノードまたはウェイポイントを設定し、「ai」ポイントをウェイポイニーに向けて、そこに近づいたら、次のウェイポイントに向かい、それに向かい、それに向かって移動します。


これは、タレットをパスの横にしか配置できないTDゲームでのみ機能し、ボード上のどこにでもタワーを配置できるゲームでは機能しません。
イアン

ええ、最初は作者がどのタイプを望むかを指定しなかったので、動的ではないと仮定しました。
ロクター

1

誰かが尋ねたので、プレイヤーがタワーを配置または削除するたびにパスを再計算することにより、動的に変化する環境に対処し、その間にそのパスをメモリに保存するだけです。環境はフレームごとに変わるわけではありません。

一部のTDゲームにはパスが設定されており、タワーを配置できないので、パスをハードコーディングしてブロックしないようにすることで、パス検索を簡単に解決できることに注意してください。


1

簡単な解決策は不正行為です。

事前にマップを設計して、行き止まりがないようにします。次に、各交差点で、キャラクターにルートを選択させるトリガーを追加します(例:常に左折、常に右折、またはランダム)。


1
おそらく彼は、ユーザーがその場でマップを作成しているDesktop TDのようなものについて話しているのでしょう。それでも、「愚かな」敵にとっては良い解決策かもしれないので、より良いAIを持つ敵を少し難易度を上げることができます。
coderanger
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.