通常、ゲームでは従来のタイマーを使用しません。ゲームには、ロジックと経過時間を処理するための非常に異なるメカニズムがあります。通常、ゲームはタイマーで動作しないか、期待どおりに動作しません。
ゲームには通常、ゲームループと呼ばれるものがあります。一般的に言えば、ループ内で次々に呼び出されるのは 3 つの主要な関数です。
while(running)
{
HandleUserInput();
ChangeWorld();
Render();
}
ユーザー入力を取得し、それに応じてゲームの世界を変更し、それを画面に描画します。コンピューターが高速であるほど、このループの実行速度も速くなります。これはグラフィックス (FPS を考えてください) には適していますが、ゲームには良くありません。フレームごとにブロックが動くテトリスを想像してみてください。より高速なコンピューターを購入したくはありません。そのようにすると、ゲームはより難しくなります。
そのため、コンピューターの処理能力に関係なくゲームの速度を一定に保つために、ループは経過時間を考慮します。
while(running)
{
var timePassedSinceLastLoop = CalculateTimeDelta();
HandleUserInput();
ChangeWorld(timePassedSinceLastLoop);
Render();
}
ゲーム内の何かのクールダウンを想像してみてください。プレーヤーが「a」を押すと、いくつかのクールなアクションが発生し、再び「a」を押すことはできますが、次の 5 秒間は何も起こりません。ただし、ゲームは引き続き実行され、ゲーム内で発生する可能性のある他のすべてのことを行います。これは従来のタイマーではありません。これは変数で、ActionCooldown と呼びましょう。プレイヤーがアクションをトリガーすると、5 秒に設定されます。世界が変化するたびに、timePassed がゼロになるまでその数値から差し引かれます。ゲームは常に実行され、入力とレンダリングを処理しています。ただし、ActionCooldown がゼロになると、もう一度「a」を押すと、そのアクションが再びトリガーされます。
ChangeWorld メソッドには、ワールドに対するすべての自動変更が含まれます。敵、ミサイル、プレイヤーの介入なしに動くものは何でも。そして、それは時間に基づいて移動します。敵が 1 秒間に 1 マス移動する場合、敵の座標を float にして、ループを実行するたびに 1 分の 1 のマスを追加する必要があります。
30 fps の場合、ループは 1 秒間に 30 回実行されます。敵はループごとに 1/30 の正方形を移動する必要があります。その後、最終的には 1 秒間に 1 マス移動することになります。