ゲーム作り

Unity側から変数の初期化

お疲れ様です。 せいさくしゃです。

前回は、プレイヤーの移動を実装しました。
そして、移動のためのキー入力と位置変更について説明しました。

当然ではありますが、現時点ではプレイヤーがただ移動するだけです。
なので、プレイヤーが画面外に移動してしまったら、プレイヤーが見えなくなってしまいます。
そこで、今回はカメラをいじって、プレイヤーを常に中心に映すようにしたいと思います。

今回の成果

カメラをプレイヤーに追従

リュウキ

今回は、何を作ったんだ?

今回実装した内容はこちらです。

  • プレイヤーへ追従するスクリプトをカメラに設定

以上が今回の内容です。

ケンタ

今回は、カメラにスクリプトを入れたんだな。

今回の解説

カメラに設定したスクリプト

リュウキ

カメラにプレイヤーへ追従するスクリプトを設定したって言ってたよな?
じゃあ、そのスクリプトはどうやって書けばいいんだ?

プレイヤーが動いたからと言って、カメラも同じように動かすというのは、あまり現実的ではないと思います。
そうした場合、プレイヤーと同じようなスクリプトをカメラ側にも描く事になります。
同じようなコードを複数個所に書き込むのは大変ですし、どこかで変更があった場合は全て変更しなければならないので余計大変です。

さらに、プレイヤーが壁にぶつかった等で操作をしてもプレイヤーが動けない場合もあります。
その時に、先程のようなカメラの動かし方をすると、カメラの位置がずれてしまう可能性もあります。

そこで、今回はプレイヤーの位置を常に監視して、そこから一定距離にカメラを置く、というスクリプトを書こうと思います。

カメラに設定した実際のスクリプトのコードがこちらです。

常にプレイヤーに追従させると言いましたが、実際やっていることはそこまで難しくないです。

最初に、あらかじめプレイヤーオブジェクトの情報を渡しておきます
そして、Update関数でプレイヤーの位置から一定距離離れた所に自身(カメラ)の位置を設定すれば完成です。

後は、プレイヤーにスクリプトを設定したように、カメラにもこのスクリプトを設定するだけです。

ケンタ

Update関数でプレイヤーから一定距離離れた所にカメラの位置を設定する。
これで、カメラは常にプレイヤーを追従してくれるんだな。

カメラにプレイヤーオブジェクトの情報をあらかじめ渡す方法

リュウキ

さっき、あらかじめプレイヤーオブジェクトの情報を渡しておくって言ってたよな。
コードを見ても、プレイヤーの情報がどこにも書いてないんだけど。

先程、プレイヤーに追従させるためのスクリプトを書きました。
しかし、実はこのままでプレイヤーに追従してくれるわけではありません。
何故なら、まだこのスクリプトにプレイヤーオブジェクトの情報を渡していないからです。

さて、プレイヤーの情報を渡す方法はいくつかあります。
今回は、スクリプト内ではなく、Unity側からプレイヤーの情報をスクリプトに渡してみようと思います。

まずは、Unity画面に行く前に、スクリプト側で下準備をしておきます。
対象となるコードはこちらです。

これは、追従したいプレイヤーオブジェクトを参照するための変数宣言です。
その中の先頭に、「public」(パブリック)というコードが書かれています。
今回の様に、Unity側からデータを持ってくる場合は、変数宣言の先頭に「public」というキーワードを入れておく必要があります。
また、Unity側から数値などの初期値を設定したい時等も、この「public」を付けておきます。

コード側での下準備が出来たら、Unity側で実際にプレイヤーオブジェクトを渡します。
では、実際の手順を説明します。

  1. 先程のスクリプトを設定したカメラを選択しておきます。
  2. Inspectorにある今回のスクリプトの中の変数名の部分に、プレイヤーオブジェクトをドラッグ&ドロップで設定します。

こうする事で、プレイヤーオブジェクトをカメラのスクリプトに渡し、カメラをプレイヤーに追従させることが出来ます。

実は、この時プレイヤーオブジェクトではなく、他のオブジェクトを渡すこともできます
その場合は、そのオブジェクトに対して同じように追従させることが出来ます。
今回、Unity側から渡す方法を採用したのも、この様に汎用性が高いからです。
同じような方法でも、汎用性の高さを少し意識して作ってみると、便利な事があるのでお勧めです。

ケンタ

Unity側から初期値を設定したい変数には「public」を付ける。
そして、UnityでスクリプトのInspectorに初期値を設定する。
こうする事で、Unityで初期値を設定して、カメラをプレイヤーに追従させることが出来るんだな。

ソウバ

今回使った「public」の様なキーワードを「アクセス修飾子」と言います。
アクセス修飾子とは、他のクラスからその変数等を使うことが出来るかどうかを決めるためのキーワードです。

当然「public」以外のアクセス修飾子もある訳ですが、初心者のうちに使うであろう主な種類は次の2つです。

1つ目は、先程使った「public」というアクセス修飾子です。
これを付けると、他のクラスから自由に使うことが出来ます。
主な使い方としては、他のクラスから呼び出したい関数を作る時に使います。
また、今回の様にUnity側から初期値を変更したい場合に使うこともできます。

2つ目は、「private」(プライベート)というアクセス修飾子です。
これを付けると、他のクラスから直接使うことが一切できなくなります
主な使い方としては、他のクラスから使う必要のない時は、基本的に全てこのprivateを付けておきます。

他のクラスから使う関数や、Unity側から初期値を変更する変数には「public」を付ける。
それ以外の関数や変数等には、全て「private」を付けておく、と覚えておけば最初のうちは大丈夫だと思います。

ソウバ

気付いた方もいるかもしれませんが、実はこの「public」を使ってUnity側から初期値をいじる方法はあまりいい方法ではありません。
なぜなら、publicを付ける事により他のクラスから自由に使えてしまうという副作用もあるからです。

これを避ける為の方法として、「[SerializeField]」 ([シリアライズフィールド])という属性を使うというものがあります。
具体的には[SerializeField]を変数宣言の前に書きます。(文字の前後の[]も一緒に書いてください。)
この時、アクセス修飾子はprivateにしておきましょう。
こうする事で、Unity側からアクセスでき、なおかつ他のクラスから自由に使わせない事が出来ます。

せいさくしゃが、このキーワードを使っていない理由は、publicの方が慣れていて、なおかつコードを書くのが早いからです。
また、せいさくしゃは一人で制作しているので、事故が起きにくいという理由もあります。

チームで制作したり、一人でも厳密に書いておきたいという方もいると思います。
そういう方は、この[SerializeField]を使ってみるといいと思います。

因みに、せいさくしゃ自身はこのキーワードを使ったことがないので、使うなら今回の記事以外でも調べてみる事を推奨します。
もし、間違っている等あれば、コメント等で報告していただけると助かります。

他の方のやり方を紹介

直感的にカメラの位置をいじる方法

リュウキ

確かに、カメラをプレイヤーに追従させられたな。
でも、これだとカメラの位置を細かく調節するのが面倒なんだけど。

今回の私のやり方では、プレイヤーからのカメラの位置を指定するのに定数を使っていました。
私の場合は、偶然すぐにしっくりくる位置に置けましたが、最終的にはもう少し細かく調整する事も出てくるかもしれません。
その時、定数で指定すると確認する際にいちいち起動する必要がありますし、直感的ではありません

そこで、他の方がより良い方法でカメラを追従させていたので、その方法を紹介したいと思います。

こちらは、YouTubeの「ずっくん ch.」というチャンネルで扱われている、ゲーム制作の解説動画です。
(ずっくん ch.で公開されているゲームの制作者さんの事は、以降「ずっくんさん」と呼ばせていただきます。)

なお、今回参考にさせていただいた部分は、3:00辺りから解説されています。
一応、動画は全て載せてありますが、今回の部分だけ見る場合はお手数ですが3:00辺りから再生してください。

私のやり方では、カメラに直接プレイヤーを追従させるスクリプトを設定しました。
対して、ずっくんさんのやり方では、プレイヤーに追従する空オブジェクトを作り、カメラをそのオブジェクトの子に設定しています。
この方法について、もう少し詳しく見ていきたいと思います。
(ここからの解説はあくまでも私の考察であり、実際のやり方とは異なる可能性があります。
私の理解できる範囲での考察なので、間違っている所もある可能性がある事はご了承ください。
もし、指摘等がある場合は、コメント等で報告していただけると助かります。)

ソウバ

ずっくんさんのやり方では、本格的に親子関係の技術を駆使しています。
せいさくしゃとしても、そろそろ親子関係を無視して解説していくことが難しくなってきました。

今回も、他の解説で手一杯なので、申し訳ございませんがここで解説する事は出来ません。
しかし、近いうちにこの親子関係について解説しようと思うので、ご容赦願います。

まず、オブジェクトの構成は恐らく次の通りです。

この中で、「Player_Pos」がプレイヤーに追従する空オブジェクトです。
この時、Player_PosはPlayerと同じ位置に置いておくと分かりやすくなります。
そして、その子にカメラオブジェクトを置いています。

因みに、オブジェクトの子にオブジェクトを配置する方法は次の通りです。

  1. 子にしたいオブジェクトを、親のオブジェクトにドラッグ&ドロップします。

これで、オブジェクトの親子関係を設定する事が出来ます。

プレイヤー追従オブジェクトとカメラの親子関係が設定出来たら、次はプレイヤー追従のスクリプトを設定します。
プレイヤー追従のスクリプトは、私がカメラに設定したスクリプトとほぼ同じです。
但し、オフセット(プレイヤーからのカメラの位置)は必要ないので、この部分を削除してプレイヤーに直接追従させます。
後は、このスクリプトをPlayer_Posオブジェクトに設定するだけです。

一応、この時のスクリプトも紹介します。

この方法で実装した場合、カメラの位置の調整はUnity上の画面で直接位置を調整すればそのまま反映されるので直感的に調節できます。
また、カメラ位置を調節しながら見え方を確認できるので、調節がスムーズにできます。

この様に、ずっくんさんのやり方の方が圧倒的に直感的で便利なので、実装するならこちらの方法がお勧めです。

ケンタ

カメラを直接プレイヤーに追従させずに、プレイヤーに追従するオブジェクトの子にカメラを設定する。
これで、直感的に追従カメラの調整が出来るんだな。

せいさくしゃもこっちの方がお勧めだから、やるならこの方法で実装すると良さそうだな。

今回のまとめ

今回は、カメラをプレイヤーに追従させました。
その際、カメラのスクリプトにプレイヤーをUnity側から設定する方法を解説しました。

その時、主に組んだコードは、以下の通りです。

また、より良い方法として、ずっくんさんのやり方を紹介しました。

こちらの方法で、主に組んだコードは、以下の通りです。

そして、今回の解説を端的にまとめると、以下の通りです。

今回のまとめ
  • Updateでカメラを常にプレイヤーから一定距離離れたところに置く
  • publicに設定した変数は、Unity側から直接初期値をいじることが出来る。
  • プレイヤーに追従するオブジェクトを作り、そのオブジェクトの子にカメラを設定するとより良い。

これで、カメラをプレイヤーに追従させることが出来ます。

今回紹介したカメラを追従させる方法は、あくまでも一例です。
ゲームによってカメラに必要な機能は異なります。
なので、実際に作る時はコード等を改変してみて自分に合ったカメラを作ってみるといいと思います。
そのままコピーしてもいいですが、1から組み直してみるとより理解しやすくなると思うのでお勧めです。

ずっくんさん、動画を拝借してすみません。
ですが、私自身勉強になりました。
ありがとうございました。

また、今回は親子関係について触れたにも関わらず、肝心の親子関係の説明が出来ませんでした。
親子関係の解説については、近いうちに行おうと思うので、ご容赦ください。

それでは、今回はここまでにしたいと思います。
お疲れ様でした。

COMMENT

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

CAPTCHA