基本的な情報については、 GameDev.net の Gravity FAQを確認してください。
あなたはゲームを作っているのであって、非常に正確な物理モデラーではないので、オイラーの統合を行うことで逃げることができます。精度の必要性が高まる場合、私が使用していると思われる最も一般的な統合方法は、ルンゲクッタ (RK4) 統合です。単純なゲームでは必要ない可能性が高いですが、より高度な物理シミュレーションや 3D ゲームでは確実に使用されます。RK4 を使用する場合の欠点は、複雑さがわずかに増し、速度がわずかに遅くなることです。それは非常に正確ですが、今のところ、古き良きオイラーに固執しましょう。
「弾む球技に重力を適用するにはどうすればよいですか」という同様の質問をしたところ、いくつかの適切な回答が得られました。最初に行うことは、ゲームの任意の重力定数を選択することです。私の弾むボール アプリケーションでは、デフォルトの重力定数 2000px/s を使用しています。この重力定数を使用して、特定のゲームで目的の効果を得ることができます。
次に、ゲームをレンダリングし、ゲーム オブジェクトを個別に更新していることを確認します。これは、ゲーム内のオブジェクトが高速のコンピューターでは非常に速く動き、低速のコンピューターでは遅くなるのを防ぐためです。オブジェクトが動き回る物理学と速度がコンピューターの速度に依存しないようにする必要があります。これに関する良い記事はGame Physics: Fix your timestep! です。.
では、どうすればよいのでしょうか。Update メソッドを最後に呼び出してから経過した時間を追跡します。直接必要ではありませんが、2 つのスレッドを作成しました。ゲームの更新スレッドとレンダリング スレッドがあります。更新スレッドは、ゲーム オブジェクト内の位置の更新を制御します。更新スレッドは、前回呼び出された時刻と現在の時刻を認識し、そこから update メソッドが呼び出されてからの経過時間を計算します。
重力を適用するには、オブジェクトの Y 速度に、重力定数に経過時間を掛けた値を単純に加算します。
private long previousTime = System.currentTimeMillis();
private long currentTime = previousTime;
public void updateGame()
{
currentTime = System.currentTimeMillis();
float elapsedSeconds = (currentTime - previousTime) / 1000f;
foreach(GameObject gameObject in gameObjects)
{
// Apply gravity to velocity vector
gameObject.velocity.y += (gravityConstant * elapsedSeconds);
// Move objects x/y position based off it's velocity vector
gameObject.position.x += (gameObject.velocity.x * elapsedSeconds);
gameObject.position.y += (gameObject.velocity.y * elapsedSeconds);
}
checkCollisions();
previousTime = currentTime;
}
これにより、速度ベクトルに基づいてすべてのオブジェクトが移動し、重力定数に基づいて重力が適用されます。何よりも、コンピューターの速度に関係なく実行できます。
あなたの他の質問に答えるために、はい、オブジェクトは常にyベクトルに重力の「力」を持っています。そのため、常に床に衝突します。ただし、実行したいことの 1 つは、Epsilon 値を使用して、最終的にゲームオブジェクトの速度をゼロにすることです。次に、剪定プロセスの一部としての衝突検出中に、通常、動かないオブジェクトが何かと衝突しているかどうかのチェックをスキップできます (ただし、その逆はありません!)。
私が衝突でやりたいことは、衝突している (互いに貫通している) オブジェクトを見つけたら、それらを分離する最小移動距離 (MTD) だけそれらを押し離すことです。このステップが重要です。そうしないと、オブジェクトが「くっついた」ゲームで頻繁に見られるバグが発生し、ぎくしゃくして動き回ることになります。それらが分離されたら、衝突応答を計算します。
この方法を使用すると、説明した上昇中のプラットフォームのシナリオでうまく機能します。プラットフォームは上昇し続け、gameObject はそれ自体とプラットフォームの間の MTD を使用して分離し、それに伴って自然に上昇します。
衝突応答について助けが必要な場合は、以下を参照することをお勧めします。