[UNITY][Ruby’s Adventure]#1 UNITY導入、キャラクター移動

解説記事リスト

この記事はUNITYの公式チュートリアル『Ruby's Adventure』を日本語で解説している記事です。

↓↓記事一覧↓↓

#1 UNITY導入~キャラクター移動  ←いまここ

#2 タイルマップ~物理演算

#3 HP設定~回復とダメージ~敵の配置

#4 アニメーションの設定と適用

#5 攻撃とカメラ追従

#6 パーティクルとUI(HPゲージ)

#7 会話ダイアログ~音声~ビルド

(番外編)うまく動かない場合の対処法

UNITY公式チュートリアルとは?

UNITYはゲームエンジンと共にチュートリアルも数多く取り揃えられています。

見てのとおり英語のものが多い(元々日本語のチュートリアルもあります)ので、敬遠してしまうかたが多いと思いますが、Chromeのページ翻訳機能などを使えば意外と問題なく進めることが可能なのです。

せっかくゲーム作りの第一歩を踏み出したのだから、チュートリアルを終わらせて簡単なゲームの一本でも作れるようになりましょう!

…ということで、今回は2DRPGの作り方を学ぶチュートリアル『Ruby's Adventure』を解説したいと思います。

 

はじめに

『Ruby's Adventure』は、画像などの素材は準備されているデモ作品「Ruby's Adventure」を作りながら、2DのRPGの作り方を学ぶチュートリアルコースです。

英語のチュートリアルであり、筆者は全く英語ができませんが、Chromeのページ翻訳機能で問題なく最後まで完成させることができたので、その記録を記事にしました。

また、UNITYは日々アップデートによりバージョンが更新されるので「自分の使ってるバージョンでは記事のとおりにいかなかった!」という事があるかもしれませんのでご了承ください。

ちなみに、筆者はWindows版のUNITY「2021.1.10f1(記事執筆開始時点で最新)」を使っています。

 

各項目は実際のチュートリアルページと同じように記載しています。

また、実際のチュートリアルページへのリンクも貼りますので、不明な点は実際ページを見に行って調べてみてください(実際のページには公式のフォーラムがくっついており、英語ですが「これ、古いんじゃないのか?」など熱い議論が巻き起こっています)。

UNITYのセットアップ

実際のチュートリアルページはこちら

まずはUnityをインストールしよう

1.Unityハブをダウンロードする

2.UnityIDを新規作成するまたは既に持っているUnityIDでログインする

※UNITYをインストールしようとすると、まず「UNITY HUB」がインストールされます。これは各バージョンのUNITYや作成したプロジェクトファイルを管理するソフトです。右上の「インストール」から好きなバージョンのUNITYをインストールできます。インストールするのは最新のバージョンでOKです。

(LTS)と書かれたバージョンは「長期サポート版」でいわば安定版です。ただ、最新版でもそんなに大きなバグなどはないと思うので、最新のバージョンで大丈夫だと思います。

途中で「モジュールを加える」と聞かれるのですが、とりあえず「日本語」にだけチェックを入れて「実行」すればOKです。

いずれかのバージョンのUNITYがインストールできたら、次に進みましょう。

プロジェクトを作ろう

さて、UNITYではゲーム製作ファイルを「プロジェクト」と呼びます。UNITY HUBの「プロジェクト」タブをクリックして、

右上の「新規作成」を選び、

テンプレートは2Dを選びます。プロジェクト名はなんでもいいので、わかりやすく「Ruby's Adventure」とでもして、右下の「作成」をクリックです。

こんな画面になります。画面の各部分の説明は、チュートリアルの過程で説明していきます。

ここでひとつ注意点です。

UNITYは日本語化するべきか?

UNITYは「Edit」→「Preferences」→「Langage」から簡単に日本語化できるのですが、ゲーム開発者は英語のまま使用している方が多いです。理由としては「困ったときに海外のページを参考にすることが多い」「スクリプトを作る(プログラミングする)ときに、UNITY内の項目を英語で理解していないと必ず壁に当たる」などがあります。

日本語で開発している方もいるのでお好みで日本語化しても良いと思いますが、筆者としては英語のまま使用することをオススメします

UNITYを使い始める時点で英語は必須スキルではないですが、スクリプトを作る(プログラミング)過程で英語力が必要となります。日本語版UNITYを使っていると英語力が身につかず、そのつど英単語を調べるなどの必要が出てくるのですが、UNITYを英語のまま使っていれば、英語の勉強なんてしなくても自然と英語が身につきます

経験上、英語がわからないのは最初の一ヶ月くらいで、慣れてくればゲーム開発関連の単語などすぐに覚えられます。長らくゲーム開発をしていくつもりなら、アレルギーを起こさず頑張って英語のまま使い始めましょう。

 

Unityアセットストアを使ってみよう

UNITYアセットストア内の

2D Beginner: Tutorial Resources | 2D | Unity Asset Store
Get the 2D Beginner: Tutorial Resources package from Unity Technologies and speed up your game development process. Find this & other 2D options on the Unity As...

にアクセスし、「Ruby's Adventure」のアセットをダウンロードしましょう。もちろん無料です。

アセットストアってなに?
UNITYでゲーム開発に使える画像や音声素材などが無料/有料でダウンロードできるストアです。
公式が配布しているものもあれば、個人や企業が配布しているものもあります。
ゲームプロジェクトを丸ごと配布されていたりもするので、慣れてきたら作りたいゲームのジャンルをプロジェクトをダウンロードして、スクリプトの構造などを作りたいゲームの参考にすることができます。
そもそも「アセット」ってなに?
直訳すると「資産」ですが、UNITYではゲーム用の素材のことを「アセット」といいます。
ゲームを作ると、素材が全て自動的に「アセット」というフォルダに入れられます。
ゲーム開発の分野ではUNITY以外でもよく目にする単語なので、嫌でも覚えます。

ダウンロードできたらUNITYの画面に戻り、画面上の「Windows」→「Package Manager」をクリックします。

ウインドウが開くと少しロード画面になった後に項目が現れるのでウインドウの上の「Packages▼」から「My Assets」を選びましょう。ここにアセットストアで購入したものが全て表示されます。

先ほど(無料で)購入した「Ruby's Adventure」を選び、「Download」、ダウンロード完了したらウインドウ右下の「Import」をクリックします。

※「ダウンロードする?」と聞かれるので、ダウンロードしてください。

※どれをダウンロードするか聞かれるので、全てにチェック項目を入れてインポートしてください。

※「リロードする?」と聞かれるので、リロードしてください。

↑インポートが終われば準備OKです。何も変わっていないように見えますが、赤枠のなかに「Ruby's Adventure」を作るための素材がゴッソリ入れられています。とりあえず確認しなくて大丈夫です。

 

主人公と最初のスクリプト

実際のチュートリアルページはこちら

新しいシーンを作成しよう

まずはカラのシーンを作成します。

シーンってなに?
「シーン(Scene)」=ゲーム画面のことです。UNITYでのゲーム開発は、基本的にシーンごとに作業を進めます。
「なにがシーンなのか」という感覚は作るまでは飲み込みにくいと思いますが「ゲーム中に画面が変わればシーンが変わる」と理解していただければ大体合っています。
例えばドラゴンクエストのようなRPGの場合は、「オープニング映像が流れる画面」「タイトル画面」「フィールド画面」「街のなか」「家のなか」「戦闘画面」など、とにかく一度画面が暗くなって別の画面が表示されるような場合は全てシーンが区切られていると考えてください。

画面左上の「File」→「New Scene」をクリックします。

「どんな形態のシーンを作る?」と聞かれるので、「Basic 2D(Built in)」を選んでウインドウ右下の「Create」をクリックします。

「Basic 2D(Built in)」がなければ、ProjectウインドウのSceneフォルダ内の「SampleScene」を開き、そのシーンで作業を進めてください。この「SampleScene」はカラッポなので新たにシーンを作成するのと同じです。

以上で、見た目は何も変わりませんが、新たな「シーン」で作業が開始されています。ただ、まだこのシーンは保存されていない状態なので、まずは保存しましょう。

Ctrl+Sでシーンを保存します。Ctrl+Sは何度も使うことになるので覚えておきましょう。

フォルダの保存先を聞かれるので、「Scenes」というフォルダを選び、「MainScene」という名前で保存します。

ここで、画面中央あたりの「Project」というタブのなかを見てください。フォルダの階層が表示されていますね。

このなかの「Assets」→「Scenes」というフォルダのなかに、いま保存した「MainScene」が入っています。これがシーンファイルです。隣にある「SampleScene」はプロジェクト作成時に自動で作られるシーンファイルなので、削除してしまってOKです。

で、ただいま説明したとおり、この「Project」というウインドウは、パソコンの中のファイルの置き場所を見るウインドウです。保存したファイルやUNITYに取り込んだファイルは全てこの中に入りますので、フォルダの整理はこまめにしましょう。

素材をインポートしよう

まずは、チュートリアルページで提供されているこの画像をダウンロードしてください。

かわいらしいキツネちゃんですね。これが主人公Rubyです。

この画像を、「Project」ウインドウの「Assets」→「Art」フォルダにドラッグ&ドロップしてください。

こんな感じです。

この画像はファイル名が長い謎の文字列になっているので、「Art」のなかの画像を右クリック→「Rename」で名前を「Ruby」に変更しましょう。

ここで、取り込んだ画像をよく見てください。

ここに「▶」マークが付いていればOKなのですが、人によってはこの「▶」マークが付いていないことがあります。その場合は、画像をクリックしてください。

クリックすると、右側の「Inspector」ウインドウにファイルの詳細が現れますので、このウインドウ上部の「Texture Type」の「Default」となっている部分をクリックして「Sprite(2D and UI)」に切り替え、ウインドウ中央あたりの「Apply(適用)」を押せばOKです。

これは何をしてるのかというと、UNITYは画像ファイルを取り込んだだけでは「画像」として使うことができず、「どのように使うものなのか」を指定してあげる必要があります。今回選んだ「Sprite(2D and UI)」にすれば2Dの画像として使うことが可能です。

で、ただいま説明したとおり、この「Inspecor」というウインドウは、選択したモノの詳細を確認したりいじったりするためのウインドウです。ファイルだけではなく、後々説明する様々なモノの詳細を見る画面になりますので、「Inspectorに何が表示されているのか」は気に掛けておくようにしましょう。

Spriteってなに?
「スプライト(Sprite)」=2Dの画像や図形のことを言います。こちらも非常によく使う単語なので覚えておきましょう。

次に、「Project」ウインドウに取り込んだ画像を左側のシーン画面にドラッグ&ドロップしてください。

シーンウインドウは、ゲーム画面の状態を表示する場所です。これでゲーム画面に主人公の2D画像を表示することができました。第一歩を踏み出しましたね!

ちなみに、画面中央あたりの「ヒエラルキー」ウインドウを見てください。

「ヒエラルキー」ウインドウでは、ゲームに追加されたモノ=オブジェクトをツリー形式で見ることができます。

オブジェクトとは、ゲームに登場させたモノのことです。ゲーム画面を捉えるカメラや当たり判定など実際には画面上に映らないものも含めて、ゲームに追加したモノは全てここに表示されることになります。

Rubyの位置をいじってみよう

ここで、ゲーム画面に登場したRubyをクリックして、Inspectorウインドウを見てみてください。

上部の「transform」という枠のなかに「position」という場所があります。ここのxとyの数値をいじると、画面上のRubyが動くのが解ると思います。

「x」と「y」=「x軸」と「y軸」のこと。つまり、そのモノの場所を意味しています。2Dの場合、xがヨコでyがタテです。

2Dでは「z軸」=「奥行き」は使わないので、動かしてもRubyに変化はありませんね。

2Dゲームは2Dで作るべきか?

このプロジェクトを作成するとき、テンプレートは2Dを選んでね、と説明しました。

さらに、このシーンを作った時、「どんな形態のシーンを作る?」と聞かれるので、「Basic 2D(Built in)」を選んでね、と説明しました。

こうして今は2Dとしてゲームを作っているわけですが、「2Dゲームを作る場合は2Dのシーンを作らなければいけない」なんてルールはありません

例えば2Dゲームでも、『聖剣伝説2』の中盤では、フィールド画面が奥(z軸)に傾いて、そのまま画面の奥に向かって移動できるようなパートがありました。

2Dゲームでも奥行きという動きを取り入れたい場合は、いつでも3Dモードで編集することが可能です。

UNITYの画面上部の「2D」というボタンを押してください。

ゲーム画面が3D表示になったことが解ります。この状態でz軸を動かすと、Rubyが動いていることが解ります。

初めにゲームプロジェクトを2Dにしても3Dにしても初期設定が色々異なるだけで大きな違いは無いのですが、途中で変えたくなった場合は画面上部の「Edit」→「Project Settings」→「Editor」内の「Default Behaviour Mode」から変更可能です。

ただし、このチュートリアルは2Dで進めますので、いじらないで大丈夫です。

 

スクリプトを作ろう

「Project」ウインドウの「Assets」フォルダを右クリックして「Create」→「Folder」を選択し、新規フォルダを作成して「Scripts」という名前にしてください。

フォルダを作成できたら、そのフォルダのなかで右クリック→「Create」→「C# Script」を選択し、スクリプトファイルを作成し、「RubyController」という名前にしてください。

「スクリプト」とか「C#」ってなに?
スクリプト」とは、皆さんがプログラミングをするファイルのことです。
UNITYはゲームを作るための作業台のようなもので、実際の作業はプログラミングによって行います。
スクリプトファイルのなかにコード(命令)を書き込むことによって、キャラクターを動かしたり、イベントを発生させたりするわけですね。
また、「C#」とは、プログラミングの種類の一つです。プログラミングは用途によって様々な言語(種類)があり、UNITYでは「C#」というプログラミング言語を使う、という感じです。

最強のVisual Studioを準備してプログラミングを楽しもう!

さて、ついにプログラミングです。ワクワクしますね!

まずはプログラミングをするためのソフト「Visual Studio 20xx」をインストールしましょう(既にインストールされている場合、このステップは飛ばして構いません)。

Visual Studio 20xx for Windows & Macのダウンロード

Windows版は色々種類がありますが「Community」版を選んでいただければ大丈夫です。

インストールができたらUNITYの画面に戻って、先ほど作成した「RubyController」のファイルをダブルクリックしてください。これでVisual Studio が立ち上がらない場合は、画面上の「Edit」→「Preference」→「External Tool」の項目から、「Visual Studio 20xx」を選択すれば立ち上がります。

こんな画面が出てきたと思います。

さて、Visual Studio 20xx は様々な機能によって使いやすくカスタムすることが可能です。

まずは基本中の基本、空白の可視化を行います。画面上の「編集」→「詳細」→「スペースの表示」を選択してください。

スペース(空白)に点が打たれて、空白部分が見えるようになりました。

次に、拡張機能を追加します。「拡張機能」とは、面倒なプログラミングを快適にするための様々な機能で、世の中の親切な人たちが作ったものを選んで追加することができます。

画面上の「拡張機能」→「拡張機能の管理」を選んでください。

こんな画面になったと思います。右上の検索窓から検索して、追加する機能を選んでいきます。

当然、皆さんが自分で選んだ便利だと思う拡張機能を追加していけばよいのですが、今回は筆者の思うオススメの拡張機能を紹介します。
※記事執筆当時の「Visual Strudio 2019」に対応した拡張機能です。最新版のVisual Studioには対応していない可能性があるため注意!

  • Viasfora …括弧に色づけ
  • Semantic Colorizer …コードを色分け
  • Indent Rainbow …インデントを色分け(これ要らないかも)
  • Code Alignment …コードを整列するボタンを追加
  • RockMargin …スクロールバーに全体のミニマップを表示
  • Pronama-chan IDE …背景に動くプロ生ちゃんを表示

以上を検索してインストールしてください。

インストール完了後、一度Visual Studio 2019を閉じてから、もう一度「RubyController」を開いてみてください。

色々変わりましたね。追加した機能については後々調べていただき、もし不要なものがあれば、同じく画面上の「拡張機能」から「無効化」できますが、不便なものは入っていないと思うので安心してください。

プログラミングが初めての方は緊張すると思いますが、このように楽しく便利な環境を整え、一つ一つ学べば必ずマスターできますよ!

スクリプトの構造を理解しよう

それでは、作成した「RubyController」の編集に入ります。まず、ファイルを開くとこのような記述が現れると思います。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class RubyController : MonoBehaviour
{
 // Start is called before the first frame update
 void Start()
 {

 }
 // Update is called once per frame
 void Update()
 {

 }
}

「わけわからん!!もうダメだ!!」

と投げ出すのは早いです。順番に説明します。

まず、上記の記述はUNITY内でスクリプトファイルを作ると自動的に生成されます。これらはほとんどの場合必要となる記述なので、先に書いてくれてるわけですね。

まずは最初の三行から。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

using」と書かれた記述が3行あります。これは、「このファイルのなかでは、この機能を使うよ」という意味です。

ドット「.」は「~の中の」という意味です。つまり、

using System.Collections;

は、「Systemの中の、Collectionsという機能を使うよ」という意味です。

まあ、この辺をいじることはまずないので覚えなくても大丈夫です。

 

次に、

public class RubyController : MonoBehaviour
{

この「RubyController」の部分には、ファイル作成時のファイル名が入ります。もしファイル作成後にファイル名を変更した場合は、この部分の記述も変更する必要があります。これは重要です。

また、ここで言っているのは「次の { } 内ではMonoBehaviourという機能を使うよ」という意味なのですが、ここもいじることはまずないので、とりあえず今は覚えなくて大丈夫です。

 

次に、

  // Start is called before the first frame update
  void Start()
  {

  }
  // Update is called once per frame
  void Update()
  {
 
  }

まず段落の初めの空白ですが、空白に意味はありません。見た目がわかりやすいようにインデントしているだけです。

次に「//」と書かれた部分ですが、これはメモ書きです。「//」と書くと、以降の記述は一切機能しなくなるので、メモ書きとして使うことができます。

それぞれに書かれている

Start is called before the first frame update(Startは最初のフレームに呼び出されます)
Update is called once per frame(Updateは毎フレーム呼び出されます)

は、すぐ下にある「void Start()」と「void Update()」の意味を解説するメモ書きです。初心者のために説明してくれているのですね。

 

次にこの部分。

  void Start()
  {

  }

まず、「void」は「このメソッドを呼んでも、何も返さないよ」という意味です。…といっても今は難しいので、とりあえずなんか最初に書いとくやつくらいの認識でOKです。

次に、「Start」は「ここはシーン開始時に呼び出されるコードを書く場所だよ」という意味です。先ほどメモ書きに書いてあったとおりですね。例えばタイトル画面なら「タイトル画像を表示する」といったものです。

さきほど「void」=「このメソッドはなにも返さないよ」と説明しましたが、「Start」は自動的に呼び出されるメソッドなので、「Start」は「呼ぶことで何かを受け取るようなタイプのメソッドではない」、という意味で「void」が使われていたわけですね。

次に、「括弧()」について。このカッコは、実はすごく便利なものなのですが、「Start」の括弧()にはなにも書かなくていいのです。なので、何も書かれていないカラの括弧()が置かれています。カラでも括弧()自体は書く決まりなので、一応置いてあるのです。どう便利なのかは、複雑なのでいまは説明しません。

次に、「波括弧{}」について。先ほど「Start」=「ここはシーン開始時に呼び出されるコードを書く場所だよ」と説明しましたが、波括弧{}はそのコードを書く場所です。

で、次は構造の名前について。これも必ず必要な知識となるので重要です。上記の記述の場合、それぞれの部分に名前が付いています。

void」は「Startというメソッドを呼んでも、何も返さないよ」という意味。
Start()」は「波括弧{}の中にシーン開始時に呼び出されるコードを書くよ」という意味の「メソッド」。

となります。…これ、最初は「???」となるかもしれませんが、ゲームを作っていると、ある日突然「あ、こういう意味か」と腑に落ちたように理解できるので、今はとりあえずこういうものだと思っておいてください。

 

…以上がわかれば、次は簡単です。

  void Update() 
  {
   
  }

さっきと違うのは「Update」だけですね。「Update」は、「毎フレーム呼び出されるコードを書くよ」という意味です。

フレーム」とは「パラパラ漫画のひとコマ」です。ゲームは無数のパラパラ漫画によってできています。
マリオに例えると、マリオが走っているとき、1ドット動けば1フレームです。その1フレーム毎に呼び出したいコードを書くのが「Update」です。

 

以上です。…あら! もうスクリプトの構造を理解できてしまいましたね!

 

「RubyController」を編集してRubyを動かそう

さて、スクリプトの構造がわかったところでUNITYに戻ります。先ほど作った「RubyController」は、Rubyを動かすためのスクリプトです。

まずはUNITY内で作った「RubyController」をダブルクリックして開いてください。

次に、「void Update() 」の後の波括弧 {} の中に、以下のように記述を追加してください。

void Update()
{
 Vector2 position = transform.position;
 position.x = position.x + 0.1f;
 transform.position = position;
}

「もうダメだ!!わからん!!諦めまーす!!」

落ち着いてください。きちんと説明します。

 

まずここ。

Vector2 position = transform.position;

先に「position」について解説します。

position」は適当に名前を決めた入れ物だと思ってください。適当に名前を決められる入れ物のことを「変数」といいます。自由に名前を決められるので、ここを「unko」とかにしても動きます。しかし、この変数には「Rubyの動き」を入れる予定なので、解りやすく「position」と名付けているわけです。

また、「(見た目で区別しやすくするために)変数の頭文字は小文字にする」という業界内のルールがあるため、Positionではなくpositionとなっています。

次に、「Vector2」は型の一種です。「Vector」は「ベクトル」=「方向」のこと。「2」は方向の数=タテとヨコのこと。

つまり「Vector2」は「この次に書く変数(→position)にはx軸とy軸の場所を入れるよ」という意味の「型」です。

次に「=」について。算数なら「等しい」という意味ですが、スクリプトでは「左に書いたものに右に書いたものを入れる」という意味になります。

次に「transform.position」について。

以前、「ドット.」=「~の中の」と説明しました。つまり、「transform.position」は、「transformのなかのposition」という意味です。

transform」についてですが、このスクリプト「RubyController」は後で「Ruby」に貼り付ける予定です。つまり、「Rubyのtransformをいじる」という意味です。以前、Rubyの位置をいじってみようの項で、transformのなかのpositionの値をいじればRubyの位置を変えられることを説明しました。

つまり、「transform.position」は「Rubyの位置(transuformの中のposition)」のことです。

最後に、「セミコロン;」はそのコードの終わりを示す記号です。ちなみに、セミコロン;は「改行するとき」ではなく「コードが終わった時」に書くものなので、波括弧{}によるメソッドが始まる場合などは「まだコードが終わっていない」=セミコロン;を書いてはいけませんので注意です。

まとめると、「Vector2 position = transform.position;」は「positionという変数に、Rubyの位置を入れるよ」という意味になります。

 

次にここ。

 position.x = position.x + 0.1f;

position.x」ですが、もう解りますね。「ドット.」が「~のなかの」という意味なので、「positionのなかのx」、つまり「x軸」のことです。

次に「+」ですが、これは見たままの意味です。足す(加える)という意味です。

次に「0.1f」ですが、0.1は見たまま、数値です。

では「」はなんでしょうか? これは「float」の略です。小数点を含む数値の後に「f」と書くのはゲームを作る上で非常に頻繁に登場するので、嫌でも覚えます。

float」とは、小数点を含む数値のことを言います。「0.1」のように小数点を含む数値を書く場合は、必ず「」を付けます。

つまり、「position.x + 0.1f」は「x軸の値に0.1を加えるよ」という意味になります。

さらに、初めの「position.x =(x軸に入れるよ)」と意味を繋げると、「x軸に、x軸の値に0.1を加えた値を入れるよ」という意味になります。

まとめると、「position.x = position.x + 0.1f;」は、「x軸の値を0.1増やすよ」という意味になります。

 

次にここです。

transform.position = position;

見てのとおり「transform.positionに、変数positionを入れるよ」という意味です。

変数「position」には何が入っていたかというと、「x軸の値に0.1加えた値」が入っていましたね。

つまりここで、先ほど計算した「x軸の値に0.1加えた値」を「Rubyの位置(transformのなかのposition)」に入れるわけです。

で、この記述は「Update」メソッドのなかに書きましたね。つまり、この計算が毎フレーム処理されるわけです。

 

以上を全てまとめると、

void Update()
{
 Vector2 position = transform.position;
 position.x = position.x + 0.1f;
 transform.position = position;
}

は、「x軸の値を毎フレーム0.1ずつ増やす」という意味になります。

あら!最初はわからなかったのに、きちんと理解できましたね!

編集が終わったスクリプトは忘れずに保存しよう

編集が終わったら、スクリプトを保存しましょう。

「…いや、言われなくても解ってるよ!」

と思うかもしれませんが、「スクリプトを保存してなかった」というミスは超多いです。

わざわざチュートリアルの一つの項として書くくらい、超マジメチャクチャ多いです

あれ?なんでエラー?あれ?…と思って右往左往していると、「あ、保存してないだけだった…」ということがよくあります。

スクリプトをVisual Studio 2019で編集したら、必ず Ctrl+S を押して保存してからUNITY画面に戻りましょう。

 

スクリプトを動かしてみよう

さて、編集したスクリプトを保存してUNITY画面に戻ると、少し読み込みを挟んでから元の画面に戻ります。

スクリプト「RubyController」でRubyを動かすためには、スクリプトとRubyを紐付ける必要があります。

ここでいう「Ruby」は、元の画像ファイルではなく、オブジェクトのRubyです。

つまり、オブジェクトにスクリプトを紐付ける、ということを今からするのですが、これには2通りの方法があります。

スクリプトをオブジェクトに取り込む方法 ①

ProjectウインドウでScriptsフォルダを開いた状態で、ゲーム画面上のRubyをクリックするとInspector画面にRubyのInspectorが表示されるので、そこにProjectウインドウからスクリプトをドラッグ&ドロップする。

スクリプトをオブジェクトに取り込む方法 ②

ゲーム画面上のRubyをクリックするとInspector画面にRubyのInspectorが表示されるので、Inspectorウインドウの下部にある「Add Component」をクリックし、表示されたウインドウから「Ruby」と検索、検索結果に出てきたスクリプトをダブルクリックする。

どちらでも結構です。

2通りの方法を動画で説明すると、↑こんな感じです。

さて、スクリプトが正常に動くかどうか試すために、これまでに作ったゲームを試しに起動させてみます

そうです。皆さんは既にゲームを作り終えているのです。

スタート画面もなければキャラクターの操作もできませんが、紛れもなくゲームが完成しています。

このゲームを起動するためには、UNITYの画面上部の▶ボタンを押します。

これを押してみると…

ルビィィーーーーーーーーーー!!!!

博士!落ち着いてください!成功です!

何が起きているかというと、先ほどのスクリプトで「xの値を毎フレーム増やす」ということをしましたよね。

xの値が増えるということは、オブジェクトの位置が右方向に動くことになります。

つまり、「スクリプトを貼り付けたオブジェクト(Ruby)が、毎フレーム右に動く」というのが今作ったスクリプトだったわけです。

そして、それに成功したのです。おめでとうございます!

確認が終わったら再度「▶」ボタンを押して試動から抜けてくださいね。

うまく動かなかったかたはこちらの記事を参照してください。

 

主人公をキー入力で移動させよう

実際のチュートリアルページはコチラ

さて、主人公を自動で動かすことに成功したので、今後はプレイヤーが移動を制御できるようにしてみましょう。

まずはUNITYのキー入力を確認しよう

まずはUNITY上にキー入力がどう反映されているのかみてみましょう。

画面上部の「Edit」→「Project Settings」→「Input」→「Axes(軸)」→「Horizontal」をクリックしてみてください。↓

恐らく↓のようになっているかと思います。

まず「Horizontal」とは、その名のとおり「横軸」のことで、UNITYではx軸のキー入力を表します。

まず、「Name」欄が「Horizontal」となってますね。つまり、スクリプトで横軸を呼び出したければ「Horizontal」と打てば良いわけです。

次に、「Negative Button」「Positive Button」がそれぞれ「left(矢印キー左)」「right(矢印キー→)」となっています。

Negative” Positive”はそれぞれx軸の数値の増減のことを表しています。

UNITYでゲームを開発する際、例えば画面が回転したときやカメラが3D的な動きをした時など、x軸がヨコにならない場合があり、どちらが「右」かも場合によって異なります。

そのため、x軸の数値として方向を司り、その数値が「増えるか減るか」で軸の移動を制御しているわけですね。

次に、「Alt Negative Button」の「Alt」は「Alternative」、つまりこのキーでも動くという意味です。

同じことが「Vertical」でも設定されていることが確認いただけるかと思います。

移動制御のスクリプトを書こう

次に、スクリプト「RubyController」を開いてください。

前回追加した「Update()」内の記述を一旦消して、下記の記述を追加してください。

 void Update()
{
float horizontal = Input.GetAxis("Horizontal");
Debug.Log(horizontal);
Vector2 position = transform.position;
position.x = position.x + 0.1f * horizontal;
transform.position = position;
}

順番に説明します。

まずここ。

float horizontal = Input.GetAxis("Horizontal");

float」は、変数に「小数点を含む数値」を入れるためのです。

horizontal」は変数ですね。x軸を制御するための変数を作っています。ちなみに、変数を作ることを「定義する」と言います。

「Input.GetAxis("Horizontal")」ですが、まず「Input」は先ほどみたキー入力のことを表しています。UNITYでは「Input」と書くとキー入力の情報を呼び出すことができるのです。

GetAxis」は直訳のとおり「軸(Axis)を受け取る(Get)」こと。つまり、括弧()内の軸を受け取るための命令です。

("Horizontal")」は、先ほど見たキー入力画面のx軸の「Name」欄の記述をここに書いています。「GetAxis」のあとの「("")」にはNeme欄を入れればよいわけですね。

以上をまとめると、「float horizontal = Input.GetAxis("Horizontal");」は、「horizontalという変数には、x軸のキー入力を入れるよ」という意味になります。

ちなみに、方向キーを入力した場合、数値は「-1」~「1」として入力されます。
例えば、→キーを押すとx軸に「1」が入力されます。で、このキー入力の定義は「float horizontal」というように、小数点を含む数値=float型を使っています。
整数を入れる変数を定義する場合は「int」という型を使います。それでは、なぜキー入力に「float」を使って小数点以下の数値を含む必要があるのでしょうか?
それは、ジョイスティックに対応するためですね。キー入力は「押せば1(または-1)になる」ものですが、ジョイスティックは傾き加減で「0.568」みたいな微妙な数値を入力することが可能です。
そのため、移動制御の変数はfloat型で定義するのが一般的なのです。

 

次にここです。

Debug.Log(horizontal);

これはゲーム完成時には必要なコードではないのですが、ゲーム開発時には重要なコードです。

Debug.Log()」は「括弧()内を(デバッグのために)コンソールウインドウのログに表示するよ」という意味です。

コンソールウインドウとは、↓ここのことです。赤い矢印がコンソールウインドウ、エラーがあれば黄色い矢印のボタンを押すと表示されます。

このウインドウが表示されていない場合は、UNITY画面上部の「Window」→「General」→「Console」で表示できます。

「Console」ウインドウは「Debug.Log()」で指定した情報のほか、警告やエラーなど様々な情報が表示される重要な場所なので、必ず表示させてておきましょう。

先ほどのコードに戻ると、「Debug.Log(horizontal);」と書かれていました。「horizontal」は先ほど定義した変数で、x軸のキー入力が入っています。

つまり、「Debug.Log(horizontal);」は「Consoleウインドウにx軸のキー入力を表示させるよ」という意味です。x軸を動かすコードが正常に通っているか確認するために、このようなコードを挟めているわけですね。

 

次にここです。

Vector2 position = transform.position;
position.x = position.x + 0.1f * horizontal;
transform.position = position;

Vector2 position = transform.position;」は変わっていません。

次に、「position.x = position.x + 0.1f」の後に「* horizontal;」が加えられています。「*」は見た目の通り、算数の「×(かける)」、乗算の意味です。「horizontal」はx軸のキー入力でしたね。

つまり、元々「x軸を毎フレーム0.1ずつ増やす」というコードだったのが、「x軸を(キー入力×0.1)だけ毎フレーム動かす」という風に変わっているわけです。乗算なので、マイナスの値を掛ければ「-0.1」となり、逆方向に動くわけですね。

transform.position = position;」は変わっていません。

 

以上をまとめると、「(毎フレーム)キー入力を監視してデバッグログを表示させ、入力があればx軸を動かす」という意味になります。

だんだん解るようになってきましたね。その調子です!

さて、スクリプトの編集が終わったら忘れずに保存して、UNITYに戻ります。

再生ボタンからゲームを試動してみてください。

コンソールウインドウにログが表示され、キー入力していないときはゼロ、入力すると-1から1の値が表示されていれば成功です!

演習:Rubyがタテにも動けるようにできるかな?

さて、主人公Rubyにx軸(横方向)の動きを与えることには成功しました。

ここまでくれば、Rubyにy軸(縦方向)の動きを与えることもできそうですね。

ここで演習です。

何も見ずに、Rubyを縦方向に動くようスクリプトを編集してみましょう!

え、「自分にはまだ早い」

そんなことはありません。ここまでの情報だけでRubyをタテに動かすことは可能です。

え、「めんどくさいから答えを見ちゃう」

それはやめたほうがいいです。

なぜなら、あなたが実際に独創的なアイデアでゲームを作るとき、そこにヒントは無いからです。

チュートリアルは学びの場です。学びの場では、マネして覚えるだけではなく、実際に自分で考えてみなければ身につくものも身につきません。

もう一度言いますが、ここまでの情報だけでRubyをタテに動かすことは可能なのです。

ここまで真面目に勉強してきたあなた自身の力を信じて、アイデアを具現化してみましょう。

 

(コーヒーブレイク)…

 

…さて、うまく動かせたでしょうか?

うまく動かせたあなた。素晴らしい!

あなたはゲーム開発の第一歩を非常に幸先の良い形で踏み出しました。その感覚を忘れずに進み続けましょう!

うまく動かせなかったあなた。全然OKです!!!

私もそうでした笑。この演習は元のチュートリアルにも載っているのですが、メチャクチャ難易度高いし全然初心者向けじゃないと思います。

先ほどあなたが実際に独創的なアイデアでゲームを作るとき、そこにヒントは無いなんて言いましたが、あれは嘘です。どんなゲームを作るとしてもヒントはUNITYのAssets Storeに山ほどあります

迷ったら答えを見て学ぶのは全然アリなので、演習も大事だけど、ネットで正しいヒントを探し出すのも大事ということを覚えていただければ全く問題ありません。

答え:Rubyをタテに動かしてみよう

さて、難易度:Inferno の演習が終わったところで正解をみてみましょう。

Rubyをタテに動かすためには、Update()内を次のように書き換えます。

void Update()
{
float horizontal = Input.GetAxis("Horizontal");
float vertical = Input.GetAxis("Vertical"); //←ここ

Vector2 position = transform.position;
position.x = position.x + 0.1f * horizontal;
position.y = position.y + 0.1f * vertical; //←ここ
transform.position = position;
}

2行追加するだけでよかったのですね。

それぞれ、「Horizontal」を「Vertical」に、「」を「」に変えてコピペしてるのが解ると思います。

また、「Vector2 position = transform.position;」と「transform.position = position;」はposition全体に影響するので書き換えなくてもよいわけですね。

フレームレートと移動速度を調整しよう

さて、Unityのデフォルト設定では、動作環境によってFPSが自動で調整されるようになっています。

FPSとは「Frame Per Second」、つまり「1秒間にフレーム(パラパラ漫画のひとコマ)を描写する回数」のことです。

そのため、低スペックのPCなら動きが遅く、高スペックのPCなら動きが速くなってしまいます。恐らく、Rubyの動きはすごく速くなっているかたが多いのではないでしょうか?

これを防ぐためには画面上部の「Edit」→「Project Settings」→「Quality」→「VSync Count」の項目を選び直す必要があります。

デフォルトでは「Every VBlankモニターのリフレッシュレートと同期)」が設定されているため、60Hzのモニタを使用なら60FPS、90Hzのモニタを使用なら90FPSとなります。他には「Every Second VBlankEvery VBlankの半分)」という選択項目もありますね。

ここでは「Don't Sync同期させない)」を選ぶことでFPSが固定されます。

 

…が、これをスクリプト側で制御することもできます。

一旦「VSync Count」の項目を「Every VBlank」のままにしておいてください。

次に、「RubyController」のStart()内に次のように書き加えます。

QualitySettings.vSyncCount = 0;
Application.targetFrameRate = 10;

QualitySettings.vSyncCount = 0;」で、「Vsync Countをゼロにする」=「Don't Sync(同期させない)」と同じにしているわけです。

また、「Application.targetFrameRate = 10;」と設定することで、最大FPSを10(毎秒10フレーム描写)に固定することができます。

Rubyがメチャメチャ遅くなったよ…

…さて、この状態で試動してみると、Rubyの動きが遅くなってしまいましたね。なぜでしょう?

「RubyController」の移動制御コードを思い出してください。

position.x = position.x + 0.1f * horizontal;
position.y = position.y + 0.1f * vertical;

これは「Update()」内に記述されています。「Update()」は「毎フレーム処理することを書く場所」。

で、いまは毎秒10フレーム描写に固定しています。

つまり、Rubyは「毎フレーム0.11秒間に1」しか動けないわけです。

これを解決するために、次のように書き換えてみてください。

position.x = position.x + 0.1f * horizontal * Time.deltaTime;
position.y = position.y + 0.1f * vertical * Time.deltaTime;

末尾に「* Time.deltaTime」と書き加えました。この「Time.deltaTime」は非常に頻回に使用するコードなので覚えておきましょう。

Time.deltaTime」は「直前のフレームからの経過秒数を返すコード」です。

…あれ? ということは…

実際に動かしてみると、Rubyがさらに遅くなったことがわかると思います。

毎フレーム0.11秒間に1」に経過秒数を乗じたことで、「1秒間に0.1」しか動けなくなったのです。

つまり、「0.1f」の数値を増やせばよさそうですね。

ということで、0.1fを次のように書き換えてみてください。

position.x = position.x + 3.0f * horizontal * Time.deltaTime;
position.y = position.y + 3.0f * vertical * Time.deltaTime;

「0.1f」を「3.0f」にしたので、Rubyは30倍の速度で動けるようになりました。

この状態で試動してみると…

うーん、速度はいい感じだけど、なんか動きがガクガクしてますね。

これは、「* Time.deltaTime」によって速度は改善されたものの、「QualitySettings.vSyncCount = 0;」とApplication.targetFrameRate = 10;」によってFPSが低く固定されているためです。

 

以上をまとめると、速度を「時間毎」に固定すればFPSを固定する必要はないという答えが導き出されます。

ということで、Start()内を削除してしまいましょう。

 void Start()
{
}

これで試動してみると…

…なんか良い感じですね!

ということで、遠回りしましたが無事にRubyの移動速度を正常に調整することができました。

うまく動かなかったかたはこちらの記事を参照してください。

(ちょっと寄り道)移動速度をpublicにしてみよう

さて、ちょっと寄り道をして、移動速度をInspectorウインドウで編集できるように書き換えてみましょう。

RubyControllerスクリプトを2カ所、こんなふうに書き換えてみてください。

public class RubyController : MonoBehaviour
{
public float speed = 3.0f; //←ここ
position.x = position.x + speed * horizontal * Time.deltaTime; //←ここ
position.y = position.y + speed * vertical * Time.deltaTime; //←ここ

//の部分が書き換えたところです。

変更前は単純に移動速度を「3.0f」としていましたが、冒頭で変数「speed」として定義することで、移動速度をInspectorウインドウで編集できるようにしました。定義の後ろに「= 3.0f」と書くことで、初期値を「3.0f」にすることができます。

保存してUNITYに戻り、Rubyオブジェクトを見てみると…

このとおり、移動速度をInspectorウインドウで編集できるようになりました

 

次の記事はこちらです

#2 タイルマップ~物理演算