ゲーム プログラミング

弾丸と壁/人の接触判定を少し真面目に実装してみる|ゲーム作成

投稿日:

フォートナイトみたいなオンラインバトロワゲームを作っています。優秀なサンプルコードから作成を開始したので早い段階で一応形にはなりました。しかし、サンプルをいじりすぎて接触判定に矛盾が生じてきてしまいました。

 ・グラフィック上は弾が当たっているのにダメージがない。
 ・建築して壁を立てているのに弾丸がすり抜けてくる。

Rayを飛ばしてぶつかるポリゴンを探すというのが一般的な手法のようですが、軽い処理でゲーム内に自由に組み込みたいので接触判定の部分を自作してみました。以下、その説明です。(数式等を使用しますが、厳密な数学的表現ではありませんがご了承ください)

接触判定方法:3次元空間での平面と線分の交点を求める

現在の建築の種類は「壁、床、階段」のみなので、建築は全て1平面で表現できます。また、プレイヤーも複数(3〜6)の平面で簡易的に表現することができます。
弾丸は現在のゲーム仕様では速度のある表現となっているので線分で表すことができます。従って、弾が建築(またはプレイヤー)に当たったかどうかは

 平面と線分の交点を求め、交点が平面の範囲内(建築の大きさ)にあるかどうかを求める

事で判別できそうです。

ベクトル、行列表記だと次のようになります。
(添字が小文字でない、その他色々、簡易的な数学表現です。お許しを)

上図にて、矢印のない太字は一座表です。
壁の位置と大きさから、P0, u, vが決まります。
弾丸の位置と進行方向から、b, dが決まります。
行列[A]は3x3です。逆行列は公式があるので{s,t,e}は一発で求まります。
det[A]が0の場合は弾丸の進行方向が壁と並行なので交点がないという事になります。実際のコードではある程度小さな値ならほぼ並行という事で交点なしとします。
det[A]が0でなく{s,t,e}が得られた場合は、その値を場合分して交点が壁の範囲(s, tが0以上、1以下)にあるかを調べます。弾丸が速度を持っている仕様なので1フレームで進む距離を弾丸の長さ(L)と考え、eは0以上、L以下であるかを調べます。
条件を満たしていたら「被弾」の処理をします。
s,tが得られると被弾場所も求めることができます。

以上、弾丸と壁の接触判定の記事でした。

-ゲーム, プログラミング

執筆者:

関連記事

Double (Multiple) pendulum simulation by Javascript

Source Code mPendulum.html <!DOCTYPE html> <html lang="en"> <head> <m …

Found an unexpected Mach-O header code: 0x72613c21 への対処 Xcode, Admob, xcframework

日々変わっていくAdmobの仕様への対応にとても苦労しています。そんな中、アプリをApple Store Connectへ提出するためXcodeにてArchiveを作成してValidateしようとした …

エピックのアップル提訴問題 じゃあフォートナイトフォン作っちゃいなよ

8月13日、フォートナイトの開発元の米エピックゲームズがスマホアプリ課金システムなどが独占に当たるとして米アップルと米グーグルを提訴したそうです。現在、多数のフォートナイトプレイヤーYouTuberの …

MacOSアプリ公開:備忘録、ライブラリLink

Web上にMacOSアプリ公開に関する情報は少なくて苦労しています。iPhoneアプリと比較した場合、MacOSアプリはAdmobで稼ぐという手段がなく有料版リリースをするしかないので開発者からは敬遠 …

How to use FFmpeg.wasm. What’s the Cross Origin Isoration?

Nowadays, I got the information that FFmpeg can be used with Javascript and I tried it immediately. …

スポンサーリンク