【第14回】Colliderから衝突イベントを拾うUnityチュートリアル
- 2018.04.15
- Unityチュートリアル
- Unity, チュートリアル
前回のチュートリアルでは、ColliderコンポーネントのIsTriggerを使った落下判定用オブジェクトを配置する方法をお送りしました。
落下判定用オブジェクトの位置にボールが来た場合、跳ね返らずにすり抜けるけど、衝突したこと自体は教えてくれる状態です。
今回はその衝突イベントを拾って、飛距離測定の停止とボールを初期位置に戻す処理を実装します。
前回のチュートリアルはこちらから。
今回の目的
ボールが落下判定用オブジェクトの位置に来た場合に、飛距離測定の停止とボールを初期位置に戻す処理を実装します。
プロジェクトの準備
前回のチュートリアルで作成したプロジェクトをそのまま使います。
このページに先にたどり着いた方は、チュートリアルの初回から追っていただけるといいかもしれません。
タグを付ける
スクリプトに着手する前に、『FallChecker』オブジェクトにタグ付けしてみましょう。
なんでいきなりこんなことをするかと言うと、衝突した相手をタグで特定したいからなんです。実はこの後FallCheckerを増やして横方向の衝突も検知する(かもしれない)ので、同じタグを持っている相手は同じ処理をできるようにすると便利です。
やり方は簡単で、『Hierarchy』ウィンドウで『FallChecker』オブジェクトを選択し、Tagセレクタから付けたいタグを選ぶだけ。今回は既存のタグを選択せず、新しく追加してみましょ。[Add Tag…]を選択します。
タグとレイヤーの管理画面が開くので、Tagsの[+]を選んで名前の入力を行います。タグ名は[FallChecker]にします。
入力が終わったら[Save]を押して保存しましょう。すると、新たにFallCheckerのタグが追加されました。
もう一度『Hierarchy』ウィンドウで『FallChecker』オブジェクトを選択し、Tagセレクタを開くと、追加したFallCheckerタグが選べるようになります。これをセットしましょ。
これでOK! タグの設定ができました。
トリガーのテスト
さぁ、みんな大好きスクリプト編集のお時間です。
『FallChecker』オブジェクトのColliderにてIsTriggerを設定したので、イベントを検知できるはず……!
とは言ったものの、どのオブジェクトに知らされるんですかね?
……。
まずは実験だ!!
『Sphere』オブジェクトにアタッチされているSphereBooster.csと、新たに実験用スクリプトTriggerChecker.csを作って、両方にOnTriggerEnter()を仕込んでみましょう。
『Project』ウィンドウの『Scripts』フォルダを開き、その中で実験用スクリプトTriggerChecker.csを作ります。右クリックまたは二本指タップでコンテキストメニューを開き、[Create] -> [C# Script]を選択します。
名前はそのまま[TriggerChecker]を入力します。
新たに作成したスクリプトを『FallChecker』オブジェクトにアタッチします。『FallChecker』オブジェクトを選択し、[Add Component] -> [Scripts] -> [Trigger Checker]を選択します。
んじゃスクリプトをちょっといじりましょ。
どのオブジェクトのスクリプトでOnTriggerEnter()をキャッチできるのか確認するため、SphereBooster.csに以下を追加します。SetHighScoreText()の下にでも追加しましょうか。
続いて、新しく作ったTriggerChecker.csを以下のように。と言ってもSphereBooster.csと同様にOnTriggerEnter()を追加し、呼び出しているスクリプト名を設定するだけです。
これで、衝突時にどちらが呼ばれているのか分かります。早速ゲームを実行しましょ。
地面から落ちるように、『Sphere』オブジェクトのSphereBooster.csからForce Magnitudeを20くらいに設定していざBoost! (GIFは例のごとく2倍速)
コンソールを見ると……。
片方がIsTriggerに設定されているColliderだった場合、衝突したオブジェクトの両方でOnTriggerEnter()が呼び出されるようです。
公式のマニュアルで『Collider.OnTriggerEnter(Collider)』を見ると、「トリガーコライダーがアタッチされたオブジェクトと、トリガーコライダーに接触したオブジェクト(のRigidbody)にメッセージが送信されるよ(意訳)」とのこと。検証結果通りですね。というかマニュアルに書いてあるなら何故検証したのか……。
それはさておき、両方出るならわざわざ『FallChecker』オブジェクトの方にスクリプトをアタッチする必要もなさそうです。Removeしちゃいましょ。
一度アタッチしたコンポーネントを外すときは、コンポーネントの歯車アイコンから[Remove Component]を選択します。
今回は『FallChecker』オブジェクトのTriggerCheckerから歯車アイコンの[Remove Component]を選択。デタッチされたスクリプトファイルは、コンポーネントからは外れますが『Project』ウィンドウには残ったままなので安心です。
スクリプトの編集
さて、SphereBooster.csのOnTriggerEnter()に処理を書いていきましょ。
今回の編集の方針はこちら。
- 落下判定用オブジェクトと衝突時、相手が『FallChecker』であることを特定する
- 『FallChecker』だったら、『Sphere』オブジェクトを初期位置に戻す
- 飛距離の計測を止める
OnTriggerEnter()をいじるだけで済むのですぐにできそう。
と言う訳で、上の方針を盛り込んだものがこちら。
メンバ変数にfallCheckerTagとして『FallChecker』のタグを追加しています。文字列は今回追加したタグ名です。
OnTriggerEnter()の中身では、まず衝突した相手のタグを確認します。OnTriggerEnter()では引数に衝突相手のColliderが渡されるので、そのColliderコンポーネントがアタッチされているゲームオブジェクトのタグ、という形で参照しています。
肝心の初期位置に戻す処理ですが、現在の実装では、飛行中にBoost! ボタンを押した時と同じ処理をすれば良さそう。isBoostPressedをtrueにすると、FixedUpdate()の中でボールの飛行停止処理が呼ばれるようになっています。
ボタンの動きを変えるときはこの中身を変える必要がありますが、今回はこれで行きましょう。
スクリプトの全文はGitHub Gistにあります。
動作確認
んじゃ確認してみましょ。(例のごとく2倍速)
ゲーム実行中にも『Scene』ウィンドウに切り替えることができます。『Scene』ウィンドウで『FallChecker』オブジェクトのColliderを確認すると、この領域に『Sphere』オブジェクトが触れたタイミングで初期位置に戻っていることが分かります。
どうやら動きは良さそうですね。
この後は、横方向にも『FallChecker』を配置したいのですが、そのためにはボールがどの高さまで上がるのかを決めないといけません。また、そのためにボールの飛距離予想をしてどこまで飛ぶかをゲーム画面から視覚的に表示したいですね。あと、現在はカメラが固定されていますが、飛んでいくボールを追いかけて欲しいなぁ……。
こうしてみると、なんだかRPGのお使いイベントめいてきました。ゲーム作りはRPGそのものですね(錯乱)
次回はカメラ作成イベントからこなしましょ。
まとめ
今回はColliderから衝突イベントを拾うチュートリアルでした。
当たり判定だけ用意したい時には、メッシュ非表示+ColliderでIsTriggerの組み合わせで実現できます。スクリプトからその衝突を検知できるので、結構いろんなゲームで使うテクニックだと思います。
次回はボールの動きに合わせてカメラを移動させるチュートリアルです。
ゲーム開発の攻略チャートを作りました!
-
前の記事
【第13回】落下判定用のColliderを配置するUnityチュートリアル 2018.04.14
-
次の記事
【第15回】カメラでPlayerオブジェクトを追いかけるUnityチュートリアル 2018.04.15
コメントを書く