4

私は2Dゲームプログラミングで遊んでいます。私のおもちゃのプロジェクトは、探索可能な島などを使ったセーリングゲームですが、現時点では、かなり荒れた島に「ビーチ」(つまりソフトエンド)を適用するための最良の方法を見つけようとしています。タイルサイズは64x48です。

ここに画像の説明を入力してください

私の現在の解決策は、各タイルを繰り返し処理して周囲のタイルを探し、その周囲に基づいて、水タイルを正しいテクスチャに置き換えることです。

これは、非常に欠陥のあるアプローチであることに気づきました。

  • 変更の影響を受けたタイルも含め、すべてのタイルに対してサラウンドメソッドが呼び出されるため、非常に非効率的です。
  • 実行の順序は、一部のタイルの変更が上書きされることを意味する場合があります

皆さんは、私がどのように回避してこれをより良い方法で解決できるかについての考えを持っていますか?

ありがとうございました!

編集

このアルゴリズムは、マップがロードされているときに実行されます。

4

2 に答える 2

2

少なくとも、タイルにフラグを付けるので、タイルを最初にレンダリングするときに一度これを実行してから、フラグ値を再利用する必要があります。

一度にマップの一部のみを表示すると仮定して、レンダリング時にこれを行う場合は、マップ全体に対して一度に行うよりもはるかに効率的です。

それ以外に、アルゴリズムをより効率的にする別の方法は考えられません。定義上、「ビーチ」のタイトルは、水タイルの端に土地が存在することによって定義されます。したがって、周囲のタイルを確認する以外に選択肢はありません...

于 2012-12-02T18:55:01.103 に答える
2

行/行ごとに1回のパスで境界(最初はコーナーではない)を検出するアルゴリズムは次のようになります。

for each horizontal line
  previousTag = getTag( first line pixel ) // land or water in our example
  for each pixel of the line
    currentTag = getTag( this pixel )
    if ( previousTag == currentTag ) 
       continue // not a border
    else 
       // We got a vertical border, do what is needed

    previousTag = currentTag
  endforeach
endforeach

同じことが垂直線にも当てはまります(xをインクリメントする代わりに、yをインクリメントします。ここで、垂直境界の代わりにコーナーを取得したかどうかもわかります。

for each vertical line
  previousTag = getTag( first line pixel ) // land or water in our example
  for each pixel of the line
    currentTag = getTag( this pixel )
    if ( previousTag == currentTag ) 
       continue // not a border
    else 
       if ( pixel on the right or on the left is a border )
         // we got a corner
       else
         // we got a horizontal border

    previousTag = currentTag
  endforeach
endforeach

地形が動的でない限り、これは前処理である必要があります。とにかく各フレームでそれをしないでください!

于 2012-12-02T19:20:05.357 に答える