【Unity初心者向け】C#スクリプトの書き方・使い方を基礎からサンプル付きで解説
はじめに
Unityでゲームやアプリを作るとき、見た目の配置だけではなく「プレイヤーを動かす」「敵を出す」「ボタンを押したら処理を実行する」といった動きを作るために必要になるのがC#スクリプトです。
Unity初心者にとって、C#やscriptという言葉は難しく感じるかもしれません。しかし、基本の書き方と使い方を順番に理解すれば、シンプルな処理から少しずつ作れるようになります。
この記事では、UnityにおけるC#スクリプトの役割、作成方法、基本構造、GameObjectへのアタッチ方法、よく使う文法、サンプルコード、エラー対処法までを初心者向けに解説します。Unityで初めてscriptを書く方でも理解しやすいように、できるだけ基礎から説明していきます。
1. UnityのC#スクリプトとは?
UnityのC#スクリプトとは、Unity上のGameObjectに動きや処理を与えるためのプログラムです。
Unityでは、画面上に配置したキャラクター、カメラ、ライト、アイテム、敵、UIボタンなどをGameObjectとして扱います。これらにC#スクリプトを追加することで、プレイヤーの入力に反応したり、時間経過で動いたり、当たり判定を行ったりできます。
たとえば、次のような処理はC#スクリプトで作成します。
C#using UnityEngine;
public class SampleScript : MonoBehaviour
{
void Start()
{
Debug.Log("UnityでC#スクリプトを実行しました");
}
}
このscriptをGameObjectにアタッチしてゲームを再生すると、Consoleウィンドウに文字が表示されます。とても簡単な例ですが、UnityのC#スクリプトはこのような小さな処理の積み重ねで作られています。
1-1. Unityにおけるスクリプトの役割
Unityにおけるスクリプトの役割は、GameObjectに「どう動くか」「いつ処理するか」「何に反応するか」を指示することです。
Unity Editor上では、オブジェクトの位置や見た目を設定できます。しかし、ゲーム中にキャラクターを動かしたり、敵を追いかけさせたり、スコアを加算したりするには、C#スクリプトが必要です。
たとえば、次のような処理を作るときにscriptを使います。
プレイヤーをキーボードで移動させる、ジャンプさせる、弾を発射する、敵が一定時間ごとに出現する、アイテムを取ったらスコアを増やす、ボタンを押したら画面を切り替える、HPが0になったらゲームオーバーにする、などです。
Unityでは、GameObjectにコンポーネントを追加して機能を持たせます。C#スクリプトもコンポーネントの一種として扱われます。そのため、作成したスクリプトをGameObjectにアタッチすることで、そのGameObjectに独自の機能を追加できます。
1-2. C#スクリプトでできること
UnityのC#スクリプトでは、ゲーム制作に必要なさまざまな処理を実装できます。
代表的なものは、オブジェクトの移動、回転、拡大縮小、キーボードやマウス入力の取得、物理演算の制御、当たり判定、オブジェクトの生成と削除、UIの操作、アニメーションの制御、サウンド再生、シーン切り替えなどです。
たとえば、オブジェクトを右方向に移動させる場合は、次のように書けます。
C#using UnityEngine;
public class MoveObject : MonoBehaviour
{
public float speed = 3f;
void Update()
{
transform.position += Vector3.right * speed * Time.deltaTime;
}
}
このC#スクリプトをCubeなどのGameObjectにアタッチすると、ゲーム再生中にオブジェクトが右方向へ移動します。
Unityのscriptでは、C#の基本文法に加えて、Unityが用意しているTransform、Rigidbody、Collider、Input、Timeなどの機能を使うことが重要です。
1-3. Unity初心者が最初に覚えるべき基本用語
UnityでC#スクリプトを書く前に、いくつかの基本用語を理解しておくと学習が進めやすくなります。
GameObjectは、Unityのシーン上に存在する基本的なオブジェクトです。キャラクター、カメラ、ライト、UI、空のオブジェクトなど、ほとんどのものがGameObjectとして扱われます。
Componentは、GameObjectに追加する機能です。Transform、Rigidbody、Collider、AudioSource、C#スクリプトなどがコンポーネントです。
Transformは、GameObjectの位置、回転、大きさを管理するコンポーネントです。すべてのGameObjectに必ず付いています。
Inspectorは、選択したGameObjectやコンポーネントの設定を確認・変更できるウィンドウです。C#スクリプトでpublic変数を作ると、Inspectorから値を変更できる場合があります。
Projectウィンドウは、Assetsフォルダ内のファイルを管理する場所です。C#スクリプト、画像、音声、Prefab、Sceneなどを確認できます。
Consoleウィンドウは、エラーメッセージやDebug.Logの出力を確認する場所です。C#スクリプトを書いていて問題が起きたときは、まずConsoleを確認します。
1-4. C#とUnityスクリプトの違い
C#はプログラミング言語の名前です。一方で、UnityスクリプトはUnity上で使うC#のプログラムを指すことが多いです。
C#そのものは、Unity以外にもアプリ開発、Web開発、業務システムなどで使われます。変数、条件分岐、繰り返し、クラス、メソッドなどの基本文法はUnityでも同じです。
ただし、Unityで使うC#スクリプトには、Unity特有の書き方があります。代表的なのがMonoBehaviour、Start、Update、Transform、Rigidbody、Colliderなどです。
通常のC#では、StartメソッドやUpdateメソッドが自動的に呼ばれるわけではありません。しかし、UnityのC#スクリプトではMonoBehaviourを継承することで、Unityのライフサイクルに合わせた処理を書けるようになります。
つまり、Unity初心者は「C#の基本文法」と「Unity独自の機能」の両方を少しずつ覚えていくことが大切です。
2. UnityでC#スクリプトを作成する準備
UnityでC#スクリプトを書くには、Unity Editorとコードエディタを準備する必要があります。
基本的には、Unity Hubをインストールし、そこからUnity Editorを追加します。さらに、C#スクリプトを編集するためにVisual StudioやVisual Studio Codeなどのエディタを用意します。
Unity初心者の場合は、まずUnity Hub、Unity Editor、コードエディタの3つを準備しておけば問題ありません。
2-1. Unity HubとUnity Editorのインストール
Unity Hubは、UnityのプロジェクトやEditorのバージョンを管理するためのアプリです。Unityで開発する場合、まずUnity Hubをインストールします。
Unity Hubを起動したら、Unity Editorをインストールします。初心者の場合は、特別な理由がなければ推奨バージョンやLTS版を選ぶと安心です。LTS版は長期サポート版で、安定性を重視したバージョンです。
インストール時には、開発環境に合わせて必要なモジュールを追加できます。たとえば、Windows向け、Mac向け、Android向け、iOS向けなど、作りたいアプリの出力先に応じてモジュールを選択します。
最初はPC上で動く簡単なUnityプロジェクトを作るだけでも十分です。慣れてからAndroidやiOSなどのビルド環境を追加しても問題ありません。
2-2. Visual StudioまたはVisual Studio Codeの準備
UnityのC#スクリプトは、Unity Editor上で作成できますが、実際のコード編集には外部エディタを使います。代表的なのはVisual StudioとVisual Studio Codeです。
Visual Studioは、Unityとの連携がしやすく、C#の補完機能やエラー表示が充実しています。初心者がUnityでC#を学ぶ場合にも使いやすいエディタです。
Visual Studio Codeは軽量で拡張機能が豊富です。Unityと連携するためには、C#関連の拡張機能やUnity向けの設定を行うと便利です。
Unity側では、外部スクリプトエディタを設定できます。Unity Editorの設定画面から、C#スクリプトを開くときに使うエディタを指定しておきましょう。
2-3. Unityプロジェクトの作成方法
Unity Hubを開いたら、新しいプロジェクトを作成します。初心者の場合は、まず2Dまたは3Dのテンプレートを選ぶとよいでしょう。
2Dゲームを作りたい場合は2Dテンプレート、3D空間でCubeやキャラクターを動かしたい場合は3Dテンプレートを選びます。学習目的であれば、3Dテンプレートを選び、Cubeを動かすところから始めるとC#スクリプトの動きがわかりやすいです。
プロジェクト名は、内容がわかる名前にします。たとえば「UnityScriptPractice」「CSharpSampleProject」などです。
プロジェクトを作成すると、Unity Editorが起動し、Sceneビュー、Gameビュー、Hierarchy、Project、Inspectorなどのウィンドウが表示されます。
C#スクリプトはProjectウィンドウ内のAssetsフォルダに作成します。
2-4. スクリプトを保存するフォルダ構成の基本
Unityプロジェクトでは、Assetsフォルダの中にさまざまなファイルを保存します。C#スクリプトもAssetsフォルダ内に保存します。
初心者のうちは、Assetsフォルダ直下にスクリプトを置いても動作します。しかし、ファイルが増えてくると管理しづらくなるため、Scriptsフォルダを作ってまとめるのがおすすめです。
一般的なフォルダ構成の例は次のとおりです。
Assets
├── Scenes
├── Scripts
├── Prefabs
├── Materials
├── Textures
└── Audio
Scriptsフォルダの中にPlayer、Enemy、UI、Systemなどのサブフォルダを作ると、さらに管理しやすくなります。
Assets
└── Scripts
├── Player
├── Enemy
├── UI
└── System
C#スクリプトはどこに置いても基本的には動きますが、整理されたフォルダ構成にしておくことで、後から修正しやすくなります。
3. UnityでC#スクリプトを作成する方法
UnityでC#スクリプトを作成する方法は簡単です。Projectウィンドウから新しいC# Scriptを作成し、名前を付けて、コードエディタで開いて編集します。
ただし、UnityのC#スクリプトでは「ファイル名」と「クラス名」の関係が重要です。ここを間違えると、GameObjectにアタッチできない原因になることがあります。
3-1. Projectウィンドウから新規スクリプトを作成する手順
Unity EditorでC#スクリプトを作成する基本手順は次のとおりです。
ProjectウィンドウでAssetsフォルダ、またはScriptsフォルダを開きます。何もない場所で右クリックし、「Create」から「C# Script」を選びます。作成されたスクリプトに名前を付けます。
たとえば、プレイヤーを動かすスクリプトなら「PlayerController」、敵を制御するスクリプトなら「EnemyController」のように名前を付けます。
作成したスクリプトをダブルクリックすると、Visual StudioやVisual Studio Codeなどのコードエディタで開けます。
新規作成したC#スクリプトには、通常、次のような基本構造が用意されています。
C#using UnityEngine;
public class PlayerController : MonoBehaviour
{
void Start()
{
}
void Update()
{
}
}
この状態から、StartやUpdateの中に処理を書いていきます。
3-2. C#スクリプトの名前を付けるときの注意点
UnityのC#スクリプト名には、いくつか注意点があります。
まず、スクリプト名は内容がわかる名前にしましょう。「Script1」「Test」「NewBehaviourScript」のような名前のままだと、後から何の処理かわかりにくくなります。
たとえば、次のような名前がおすすめです。
PlayerController
EnemyController
CameraFollow
GameManager
ScoreManager
ItemController
また、C#ではクラス名の先頭を大文字にするのが一般的です。単語をつなげる場合は、PlayerControllerのように各単語の先頭を大文字にする書き方がよく使われます。
ファイル名にはスペースや記号を使わないようにしましょう。日本語名も避けた方が安全です。Unityや外部ツールとの連携で問題が起きにくくするため、英数字でわかりやすい名前にするのがおすすめです。
3-3. 作成したスクリプトを開いて編集する方法
作成したC#スクリプトは、Projectウィンドウでダブルクリックするとコードエディタで開けます。
もし別のエディタで開きたい場合は、Unityの設定から外部スクリプトエディタを変更します。設定後、スクリプトを開き直すと指定したエディタが起動します。
コードを編集したら保存します。Unity Editorに戻ると、Unityが自動的にスクリプトをコンパイルします。コンパイルに成功すれば、スクリプトをGameObjectにアタッチしたり、実行したりできます。
コードに文法ミスがある場合は、Consoleウィンドウにエラーが表示されます。C#スクリプトを編集した後にUnityで動かない場合は、まずConsoleを確認しましょう。
3-4. スクリプトファイルとクラス名の関係
UnityのC#スクリプトでは、ファイル名とクラス名を一致させることが重要です。
たとえば、ファイル名が「PlayerController.cs」の場合、クラス名も次のように「PlayerController」にします。
C#using UnityEngine;
public class PlayerController : MonoBehaviour
{
void Start()
{
}
void Update()
{
}
}
ファイル名がPlayerController.csなのに、クラス名がPlayerMoveになっていると、Unity上で正しく認識されなかったり、GameObjectにアタッチできなかったりすることがあります。
特に、スクリプト作成後にファイル名だけを変更した場合は注意が必要です。ファイル名を変更しても、コード内のクラス名は自動で変わらないことがあります。名前を変更したときは、ファイル名とクラス名の両方を確認しましょう。
4. UnityのC#スクリプトの基本構造
Unityで新しくC#スクリプトを作成すると、using文、class、MonoBehaviour、Startメソッド、Updateメソッドなどが含まれています。
最初は難しく見えますが、それぞれの役割を理解すれば、Unity scriptの基本構造がわかるようになります。
基本形は次のとおりです。
C#using UnityEngine;
public class SampleScript : MonoBehaviour
{
void Start()
{
Debug.Log("開始時に1回だけ実行");
}
void Update()
{
Debug.Log("毎フレーム実行");
}
}
4-1. using文とは
using文は、C#スクリプト内で使う機能を読み込むための記述です。
Unityの基本機能を使う場合は、次のように書きます。
C#using UnityEngine;
UnityEngineには、Transform、GameObject、MonoBehaviour、Debug、Rigidbody、Colliderなど、Unityでよく使う機能が含まれています。
たとえばDebug.Logを使えるのは、UnityEngineを読み込んでいるからです。
C#using UnityEngine;
public class LogSample : MonoBehaviour
{
void Start()
{
Debug.Log("ログを表示します");
}
}
UIを扱う場合や、リストを使う場合など、必要に応じて別のusing文を追加することもあります。
C#using UnityEngine;
using UnityEngine.UI;
using System.Collections.Generic;
初心者のうちは、まずusing UnityEngine;の役割を覚えておけば十分です。
4-2. classとは
classは、C#で処理をまとめるための設計図のようなものです。
UnityのC#スクリプトでは、基本的に1つのスクリプトファイルに1つのclassを作ります。
C#public class PlayerController : MonoBehaviour
{
}
この例では、PlayerControllerというクラスを作っています。Unityでは、このクラスがGameObjectにアタッチできるコンポーネントになります。
classの中には、変数やメソッドを書きます。
C#using UnityEngine;
public class PlayerController : MonoBehaviour
{
public float speed = 5f;
void Move()
{
transform.position += Vector3.right * speed * Time.deltaTime;
}
}
このように、関連するデータや処理を1つのclassにまとめることで、スクリプトを整理できます。
4-3. MonoBehaviourとは
MonoBehaviourは、UnityのC#スクリプトで非常によく使われる基本クラスです。
C#public class SampleScript : MonoBehaviour
{
}
: MonoBehaviourと書くことで、そのクラスはUnityのコンポーネントとしてGameObjectにアタッチできるようになります。
また、MonoBehaviourを継承すると、Start、Update、OnCollisionEnter、OnTriggerEnterなど、Unityが特定のタイミングで自動的に呼び出すメソッドを使えるようになります。
初心者のうちは、「GameObjectにアタッチして使うUnity scriptにはMonoBehaviourを書く」と覚えておくとよいでしょう。
ただし、すべてのC#クラスにMonoBehaviourが必要なわけではありません。データ管理用の普通のC#クラスを作る場合などは、MonoBehaviourを使わないこともあります。
4-4. Startメソッドとは
Startメソッドは、ゲーム開始時やスクリプトが有効になった最初のタイミングで1回だけ実行されるメソッドです。
C#void Start()
{
Debug.Log("Startが実行されました");
}
Startは、初期設定に使われることが多いです。
たとえば、最初のHPを設定する、初期位置を保存する、スコアを0にする、必要なコンポーネントを取得する、といった処理に使います。
C#using UnityEngine;
public class PlayerStatus : MonoBehaviour
{
public int hp;
void Start()
{
hp = 100;
Debug.Log("HPを初期化しました");
}
}
Startは最初に1回だけ実行されるため、毎フレーム行う必要がない処理を書くのに向いています。
4-5. Updateメソッドとは
Updateメソッドは、ゲーム実行中に毎フレーム呼び出されるメソッドです。
C#void Update()
{
Debug.Log("Updateが実行されています");
}
毎フレーム実行されるため、プレイヤー入力の確認や、オブジェクトの移動、時間経過の処理などに使われます。
たとえば、右キーを押している間だけオブジェクトを動かす処理はUpdateに書けます。
C#using UnityEngine;
public class MoveRight : MonoBehaviour
{
public float speed = 5f;
void Update()
{
if (Input.GetKey(KeyCode.RightArrow))
{
transform.position += Vector3.right * speed * Time.deltaTime;
}
}
}
Updateは便利ですが、毎フレーム実行されるため、重い処理を書きすぎるとゲームの動作が遅くなる原因になります。
4-6. コメントの書き方
コメントは、C#スクリプト内に説明を書き残すための機能です。コメントはプログラムとして実行されません。
1行コメントは//を使います。
C#// プレイヤーの移動速度
public float speed = 5f;
複数行コメントは/* */を使います。
C#/*
このメソッドは
プレイヤーを右方向に移動させます
*/
void MoveRight()
{
transform.position += Vector3.right;
}
コメントは、処理の意図を説明するために使います。ただし、すべての行にコメントを書く必要はありません。コードを見ただけでは意図がわかりにくい部分に、簡潔なコメントを書くのがおすすめです。
5. C#スクリプトをGameObjectにアタッチして使う方法
UnityのC#スクリプトは、作成しただけでは基本的に動きません。GameObjectにアタッチして初めて、そのオブジェクトのコンポーネントとして動作します。
たとえば、Cubeを動かしたい場合は、移動用のC#スクリプトをCubeにアタッチします。プレイヤーを操作したい場合は、PlayerオブジェクトにPlayerController scriptをアタッチします。
5-1. GameObjectとは
GameObjectとは、Unityのシーン内に配置される基本単位です。
Cube、Sphere、Camera、Light、Canvas、Button、空のオブジェクトなど、Unity上で扱う多くのものはGameObjectです。
GameObject自体は入れ物のような存在で、具体的な機能はComponentによって追加されます。
たとえば、CubeにはTransform、Mesh Renderer、Colliderなどのコンポーネントが付いています。ここにC#スクリプトを追加すれば、Cubeに独自の動きを持たせることができます。
5-2. スクリプトをアタッチする手順
C#スクリプトをGameObjectにアタッチする手順は簡単です。
まず、Hierarchyウィンドウでスクリプトを付けたいGameObjectを選択します。次に、ProjectウィンドウにあるC#スクリプトをInspectorへドラッグ&ドロップします。
または、Inspectorの「Add Component」ボタンを押し、スクリプト名を検索して追加することもできます。
たとえば、PlayerControllerというC#スクリプトをPlayerオブジェクトにアタッチすると、PlayerのInspectorにPlayerControllerコンポーネントが表示されます。
アタッチ後にゲームを再生すると、そのGameObject上でスクリプトのStartやUpdateが実行されます。
5-3. Inspectorでスクリプトを確認する方法
スクリプトをGameObjectにアタッチすると、Inspectorウィンドウにそのスクリプトがコンポーネントとして表示されます。
C#スクリプト内にpublic変数がある場合、Inspectorから値を変更できます。
C#using UnityEngine;
public class SpeedSample : MonoBehaviour
{
public float speed = 5f;
void Update()
{
transform.position += Vector3.forward * speed * Time.deltaTime;
}
}
このスクリプトをGameObjectにアタッチすると、Inspectorにspeedという項目が表示されます。コードを変更しなくても、Unity Editor上で移動速度を調整できます。
Inspectorで値を変更できる仕組みは、UnityのC#スクリプトを使ううえで非常に便利です。
5-4. アタッチできないときの主な原因
C#スクリプトをGameObjectにアタッチできない場合、主な原因はいくつかあります。
よくあるのは、スクリプトにコンパイルエラーがある場合です。Consoleウィンドウに赤いエラーが出ていると、Unityはスクリプトを正しく読み込めません。
また、ファイル名とクラス名が一致していない場合もアタッチできない原因になります。
C#// ファイル名が PlayerController.cs なのに
// クラス名が PlayerMove になっている例
public class PlayerMove : MonoBehaviour
{
}
このような場合は、ファイル名とクラス名を同じにしましょう。
さらに、MonoBehaviourを継承していない場合も、通常のコンポーネントとしてGameObjectにアタッチできません。
C#// MonoBehaviourがないため、通常はGameObjectにアタッチする用途ではない
public class PlayerController
{
}
アタッチできないときは、Consoleのエラー、ファイル名とクラス名、MonoBehaviourの有無を確認しましょう。
5-5. スクリプトを外す・削除する方法
GameObjectにアタッチしたC#スクリプトを外したい場合は、Inspectorで対象のスクリプトコンポーネントを確認します。
コンポーネント右上のメニューから「Remove Component」を選ぶと、そのGameObjectからスクリプトを外せます。
これはGameObjectからコンポーネントを外すだけで、Projectウィンドウ内のC#スクリプトファイル自体は削除されません。
スクリプトファイルそのものを削除したい場合は、Projectウィンドウで対象の.csファイルを選択し、削除します。ただし、他のGameObjectに同じスクリプトを使っている場合は影響が出るため注意しましょう。
6. Unity C#スクリプトの基本文法
Unityでscriptを書くには、C#の基本文法を理解する必要があります。
最初からすべてを覚える必要はありません。まずは、変数、データ型、if文、for文、メソッド、publicとprivateの違いを理解しましょう。
これらを使えるようになると、Unityで簡単なゲーム処理を作れるようになります。
6-1. 変数の書き方
変数とは、数値や文字などのデータを入れておく箱のようなものです。
C#では、変数を作るときにデータ型と名前を書きます。
C#int score = 0;
float speed = 5.0f;
string playerName = "Player";
bool isGameOver = false;
UnityのC#スクリプトでは、プレイヤーの速度、HP、スコア、ジャンプ力、ゲームの状態などを変数で管理します。
C#using UnityEngine;
public class VariableSample : MonoBehaviour
{
public int hp = 100;
public float speed = 5f;
public string playerName = "Hero";
public bool isAlive = true;
void Start()
{
Debug.Log(playerName + "のHPは" + hp);
}
}
変数を使うことで、値を変更しながら処理を作れます。
6-2. データ型の種類
C#にはさまざまなデータ型があります。Unity初心者が最初に覚えるべき代表的な型は次のとおりです。
C#int score = 10; // 整数
float speed = 3.5f; // 小数
string message = "Hello"; // 文字列
bool isClear = false; // trueまたはfalse
Vector3 position; // 3D座標
GameObject player; // GameObject
intは整数を扱います。スコア、残機、レベルなどに使います。
floatは小数を扱います。移動速度、時間、ジャンプ力などに使います。C#でfloatの値を書くときは、5fや3.5fのように最後にfを付けます。
stringは文字列を扱います。名前やメッセージなどに使います。
boolはtrueまたはfalseを扱います。ゲームオーバーかどうか、ジャンプ中かどうか、アイテムを持っているかどうかなどの判定に使います。
Vector3はUnityでよく使う型で、3D空間の位置、方向、大きさなどを表します。
6-3. 条件分岐 if文の使い方
if文は、条件によって処理を分けるために使います。
C#if (条件)
{
条件がtrueのときの処理
}
たとえば、HPが0以下になったらゲームオーバーにする処理は次のように書けます。
C#using UnityEngine;
public class IfSample : MonoBehaviour
{
public int hp = 100;
void Update()
{
if (hp <= 0)
{
Debug.Log("ゲームオーバー");
}
}
}
elseを使うと、条件に当てはまらない場合の処理も書けます。
C#if (hp > 0)
{
Debug.Log("プレイヤーは生きています");
}
else
{
Debug.Log("プレイヤーは倒れました");
}
Unityのscriptでは、キーが押されたか、敵に当たったか、スコアが一定以上かなど、さまざまな判定にif文を使います。
6-4. 繰り返し for文の使い方
for文は、同じ処理を繰り返すために使います。
C#for (int i = 0; i < 5; i++)
{
Debug.Log(i);
}
この例では、0から4までの数字がConsoleに表示されます。
Unityでは、複数の敵を生成したり、配列の中身を順番に処理したりするときにfor文を使います。
C#using UnityEngine;
public class ForSample : MonoBehaviour
{
public GameObject enemyPrefab;
void Start()
{
for (int i = 0; i < 5; i++)
{
Vector3 position = new Vector3(i * 2, 0, 0);
Instantiate(enemyPrefab, position, Quaternion.identity);
}
}
}
このscriptでは、enemyPrefabを横方向に5体生成します。
6-5. メソッドの作り方
メソッドとは、処理をまとめたものです。何度も使う処理や、意味のある処理のまとまりをメソッドに分けることで、C#スクリプトが読みやすくなります。
C#void メソッド名()
{
処理
}
たとえば、プレイヤーを移動させる処理をMoveメソッドに分けると、次のようになります。
C#using UnityEngine;
public class MethodSample : MonoBehaviour
{
public float speed = 5f;
void Update()
{
Move();
}
void Move()
{
float x = Input.GetAxis("Horizontal");
float z = Input.GetAxis("Vertical");
Vector3 direction = new Vector3(x, 0, z);
transform.position += direction * speed * Time.deltaTime;
}
}
Updateの中にすべて書くよりも、Moveというメソッドに分けた方が、何をしている処理なのかわかりやすくなります。
6-6. publicとprivateの違い
publicとprivateは、変数やメソッドにアクセスできる範囲を指定するためのキーワードです。
publicを付けた変数は、他のクラスからアクセスでき、UnityのInspectorにも表示されます。
C#public float speed = 5f;
privateを付けた変数は、そのクラスの中だけで使えます。
C#private int score = 0;
初心者のうちは、Inspectorで調整したい値はpublicにし、外から変更されたくない値はprivateにすると考えるとわかりやすいです。
ただし、何でもpublicにすると、どこからでも変更できて管理が難しくなります。基本的にはprivateを使い、必要なものだけpublicにする意識を持つとよいでしょう。
6-7. Inspectorに変数を表示する方法
Unityでは、public変数を作るとInspectorに表示されます。
C#using UnityEngine;
public class InspectorSample : MonoBehaviour
{
public float speed = 5f;
public int hp = 100;
}
このC#スクリプトをGameObjectにアタッチすると、Inspectorにspeedとhpが表示されます。ゲームを再生する前に値を変更できるため、移動速度やHPの調整が簡単になります。
private変数をInspectorに表示したい場合は、[SerializeField]を使います。
C#using UnityEngine;
public class SerializeSample : MonoBehaviour
{
[SerializeField]
private float speed = 5f;
}
この書き方を使うと、変数はprivateのままInspectorに表示できます。UnityのC#スクリプトではよく使われる書き方です。
7. Unity初心者向けC#スクリプトのサンプル
ここからは、Unity初心者向けに実際に使えるC#スクリプトのサンプルを紹介します。
サンプルは、GameObjectにアタッチして動かすことを想定しています。まずはCubeやSphereなどの簡単なオブジェクトにアタッチして、動きを確認してみましょう。
7-1. Debug.Logで文字を表示するサンプル
Debug.Logは、Consoleウィンドウに文字や値を表示するために使います。C#スクリプトが実行されているか確認するときに便利です。
C#using UnityEngine;
public class DebugLogSample : MonoBehaviour
{
void Start()
{
Debug.Log("ゲーム開始");
}
void Update()
{
if (Input.GetKeyDown(KeyCode.Space))
{
Debug.Log("スペースキーが押されました");
}
}
}
このscriptをGameObjectにアタッチして再生すると、開始時に「ゲーム開始」と表示されます。さらに、スペースキーを押すと「スペースキーが押されました」と表示されます。
処理が動いているか確認したいときは、Debug.Logを活用しましょう。
7-2. オブジェクトを移動させるサンプル
次のC#スクリプトは、GameObjectを右方向に移動させるサンプルです。
C#using UnityEngine;
public class MoveSample : MonoBehaviour
{
public float speed = 3f;
void Update()
{
transform.position += Vector3.right * speed * Time.deltaTime;
}
}
Vector3.rightは右方向を表します。speedは移動速度です。Time.deltaTimeを掛けることで、フレームレートの違いによる移動量の差を抑えられます。
このscriptをCubeにアタッチして再生すると、Cubeが右に移動します。
7-3. キー入力でキャラクターを動かすサンプル
次のサンプルでは、矢印キーやWASDキーでGameObjectを動かします。
C#using UnityEngine;
public class PlayerMoveSample : MonoBehaviour
{
public float speed = 5f;
void Update()
{
float x = Input.GetAxis("Horizontal");
float z = Input.GetAxis("Vertical");
Vector3 direction = new Vector3(x, 0, z);
transform.position += direction * speed * Time.deltaTime;
}
}
Input.GetAxis("Horizontal")は左右入力、Input.GetAxis("Vertical")は上下入力を取得します。
3Dゲームの場合、x方向とz方向に移動させることが多いため、new Vector3(x, 0, z)のように書きます。
このC#スクリプトをPlayer用のGameObjectにアタッチすると、キーボード入力で移動できます。
7-4. マウスクリックで処理を実行するサンプル
マウスクリックを検出するには、Input.GetMouseButtonDownを使います。
C#using UnityEngine;
public class MouseClickSample : MonoBehaviour
{
void Update()
{
if (Input.GetMouseButtonDown(0))
{
Debug.Log("左クリックされました");
}
if (Input.GetMouseButtonDown(1))
{
Debug.Log("右クリックされました");
}
}
}
Input.GetMouseButtonDown(0)は左クリック、Input.GetMouseButtonDown(1)は右クリックを表します。
クリックで弾を発射する、UIを操作する、オブジェクトを選択するなど、Unityのゲーム制作ではマウス入力を使う場面が多くあります。
7-5. オブジェクトを回転させるサンプル
GameObjectを回転させるには、TransformのRotateを使います。
C#using UnityEngine;
public class RotateSample : MonoBehaviour
{
public float rotateSpeed = 90f;
void Update()
{
transform.Rotate(0, rotateSpeed * Time.deltaTime, 0);
}
}
このscriptをCubeにアタッチすると、Y軸を中心に回転します。
transform.Rotate(x, y, z)では、x軸、y軸、z軸に対する回転量を指定できます。アイテムを回転させたり、敵を向かせたり、演出を作ったりするときに使えます。
7-6. 当たり判定を使うサンプル
Unityで当たり判定を使うには、ColliderやRigidbodyが関係します。
次のサンプルは、他のオブジェクトに衝突したときにログを表示するC#スクリプトです。
C#using UnityEngine;
public class CollisionSample : MonoBehaviour
{
void OnCollisionEnter(Collision collision)
{
Debug.Log(collision.gameObject.name + "にぶつかりました");
}
}
この処理を動かすには、衝突するGameObjectにColliderが必要です。また、物理演算による衝突を扱う場合は、どちらかのGameObjectにRigidbodyを付ける必要があります。
Triggerを使う場合は、次のようにOnTriggerEnterを使います。
C#using UnityEngine;
public class TriggerSample : MonoBehaviour
{
void OnTriggerEnter(Collider other)
{
Debug.Log(other.gameObject.name + "が入りました");
}
}
Triggerを使うには、Colliderの「Is Trigger」をオンにします。アイテム取得やエリア侵入の判定によく使われます。
8. Unity C#スクリプトでよく使う基本機能
UnityのC#スクリプトでは、UnityEngineが提供するさまざまな機能を使います。
特に初心者がよく使うのは、Transform、Input、Rigidbody、Collider、Instantiate、Destroy、Time.deltaTimeです。これらを理解すると、基本的なゲームの動きを作りやすくなります。
8-1. Transformで位置・回転・大きさを操作する
Transformは、GameObjectの位置、回転、大きさを管理するコンポーネントです。
位置はtransform.positionで操作できます。
C#transform.position = new Vector3(0, 1, 0);
現在の位置に加算して移動させることもできます。
C#transform.position += Vector3.forward * 3f * Time.deltaTime;
回転はtransform.rotationやtransform.Rotateを使います。
C#transform.Rotate(0, 90f * Time.deltaTime, 0);
大きさはtransform.localScaleで変更できます。
C#transform.localScale = new Vector3(2, 2, 2);
TransformはUnity scriptの中でも非常によく使う機能なので、最初に慣れておきましょう。
8-2. Inputでキーボードやマウス入力を取得する
Inputは、キーボードやマウスなどの入力を取得するために使います。
キーが押されている間の処理にはInput.GetKeyを使います。
C#if (Input.GetKey(KeyCode.Space))
{
Debug.Log("スペースキーを押しています");
}
キーが押された瞬間だけ処理したい場合はInput.GetKeyDownを使います。
C#if (Input.GetKeyDown(KeyCode.Space))
{
Debug.Log("スペースキーが押されました");
}
マウスクリックはInput.GetMouseButtonDownで取得できます。
C#if (Input.GetMouseButtonDown(0))
{
Debug.Log("左クリック");
}
Unityでは新しいInput Systemを使う方法もありますが、初心者が基本を学ぶ段階では、まず従来のInputの使い方を理解するとよいでしょう。
8-3. Rigidbodyで物理演算を扱う
Rigidbodyは、GameObjectに物理演算を適用するためのコンポーネントです。
Rigidbodyを付けると、重力の影響を受けたり、力を加えて動かしたり、衝突判定を扱いやすくなります。
次のサンプルは、スペースキーで上方向に力を加える例です。
C#using UnityEngine;
public class RigidbodyJumpSample : MonoBehaviour
{
public float jumpPower = 5f;
private Rigidbody rb;
void Start()
{
rb = GetComponent<Rigidbody>();
}
void Update()
{
if (Input.GetKeyDown(KeyCode.Space))
{
rb.AddForce(Vector3.up * jumpPower, ForceMode.Impulse);
}
}
}
このscriptを使うには、同じGameObjectにRigidbodyを追加しておく必要があります。
物理演算で動かす場合は、Transformを直接変更するよりも、Rigidbodyの機能を使う方が自然に動かせることがあります。
8-4. Colliderで当たり判定を設定する
Colliderは、GameObjectの当たり判定の形を決めるコンポーネントです。
代表的なColliderには、Box Collider、Sphere Collider、Capsule Collider、Mesh Colliderなどがあります。
CubeにはBox Collider、SphereにはSphere Colliderが付いていることが多いです。キャラクターにはCapsule Colliderが使われることがあります。
Colliderが付いているオブジェクト同士がぶつかると、OnCollisionEnterなどのメソッドで衝突を検出できます。
C#void OnCollisionEnter(Collision collision)
{
Debug.Log("衝突しました");
}
ColliderのIs Triggerをオンにすると、物理的にぶつからず、通過を検出できます。
C#void OnTriggerEnter(Collider other)
{
Debug.Log("通過しました");
}
アイテム取得やエリア判定ではTriggerを使うことが多いです。
8-5. Instantiateでオブジェクトを生成する
Instantiateは、ゲーム中にGameObjectを生成するために使います。
弾、敵、アイテム、エフェクトなどを生成するときによく使います。
C#using UnityEngine;
public class InstantiateSample : MonoBehaviour
{
public GameObject bulletPrefab;
void Update()
{
if (Input.GetKeyDown(KeyCode.Space))
{
Instantiate(bulletPrefab, transform.position, Quaternion.identity);
}
}
}
このscriptでは、スペースキーを押したときにbulletPrefabを現在位置に生成します。
Prefabを使う場合は、ProjectウィンドウにあるPrefabをInspectorのbulletPrefabに設定します。
Instantiateは便利ですが、何度も大量に生成すると負荷が高くなることがあります。大量の弾や敵を扱う場合は、オブジェクトプールという方法を使うこともあります。
8-6. Destroyでオブジェクトを削除する
Destroyは、GameObjectを削除するために使います。
C#Destroy(gameObject);
このコードを書くと、そのscriptが付いているGameObjectを削除します。
一定時間後に削除したい場合は、第2引数に秒数を指定します。
C#Destroy(gameObject, 3f);
次のサンプルは、生成された弾を3秒後に削除する例です。
C#using UnityEngine;
public class BulletSample : MonoBehaviour
{
void Start()
{
Destroy(gameObject, 3f);
}
}
弾やエフェクトなど、使い終わったオブジェクトを削除しないと、シーン上にどんどん残って処理が重くなる原因になります。
8-7. Time.deltaTimeで動きを安定させる
Time.deltaTimeは、前のフレームから現在のフレームまでにかかった時間を表します。
Unityでは、Updateが毎フレーム呼ばれますが、フレームレートは環境によって変わります。Time.deltaTimeを使わずに移動処理を書くと、フレームレートが高い環境ほど速く動いてしまうことがあります。
悪い例は次のような書き方です。
C#transform.position += Vector3.forward * speed;
この場合、毎フレームspeed分だけ移動します。
Time.deltaTimeを使うと、秒単位で安定した移動になります。
C#transform.position += Vector3.forward * speed * Time.deltaTime;
UnityのC#スクリプトで移動や回転をUpdate内に書く場合は、基本的にTime.deltaTimeを使うと覚えておきましょう。
9. Unity C#スクリプトでよくあるエラーと対処法
UnityでC#スクリプトを書いていると、エラーは必ず出ます。初心者のうちはエラーが出ると不安になりますが、エラーは原因を教えてくれる重要なヒントです。
まずはConsoleウィンドウを確認し、エラーメッセージの内容、発生しているスクリプト名、行番号を見ましょう。
9-1. コンパイルエラーが出る原因
コンパイルエラーとは、C#スクリプトの文法に問題があり、Unityがコードを読み込めない状態です。
よくある原因は、セミコロンの付け忘れ、波括弧の閉じ忘れ、変数名の間違い、クラス名の間違い、全角文字の混入などです。
たとえば、次のコードはセミコロンがないためエラーになります。
C#int score = 0
正しくは次のように書きます。
C#int score = 0;
また、波括弧{}の数が合っていない場合もエラーになります。
C#void Start()
{
Debug.Log("Hello");
この場合、閉じる波括弧が足りません。
C#void Start()
{
Debug.Log("Hello");
}
コンパイルエラーが1つでもあると、他のC#スクリプトも正しく動かないことがあります。まずはConsoleの一番上のエラーから順番に直しましょう。
9-2. NullReferenceExceptionの原因と直し方
NullReferenceExceptionは、参照しているオブジェクトやコンポーネントが存在しないときによく出るエラーです。
たとえば、次のようなコードでtargetが設定されていない場合、エラーになります。
C#using UnityEngine;
public class NullSample : MonoBehaviour
{
public GameObject target;
void Start()
{
target.SetActive(false);
}
}
targetに何も入っていない状態でtarget.SetActive(false);を実行すると、NullReferenceExceptionが発生します。
対処法としては、InspectorでtargetにGameObjectを設定する、StartでGetComponentする、nullチェックを行うなどがあります。
C#void Start()
{
if (target != null)
{
target.SetActive(false);
}
else
{
Debug.LogWarning("targetが設定されていません");
}
}
NullReferenceExceptionが出た場合は、「どの変数が空なのか」を確認することが大切です。
9-3. スクリプトが動かないときの確認ポイント
C#スクリプトが動かないときは、次のポイントを確認しましょう。
まず、Consoleにエラーが出ていないか確認します。コンパイルエラーがあると、スクリプトが実行されません。
次に、スクリプトがGameObjectにアタッチされているか確認します。Projectにscriptを作っただけでは動きません。
また、GameObjectがアクティブになっているか、スクリプトコンポーネントのチェックがオンになっているかも確認しましょう。
StartやUpdateの名前を間違えていないかも重要です。
C#// 間違い
void start()
{
}
// 正しい
void Start()
{
}
C#は大文字と小文字を区別します。Start、Update、OnCollisionEnterなどは正しい大文字小文字で書く必要があります。
9-4. クラス名とファイル名が違う場合のエラー
Unityでは、MonoBehaviourを継承したC#スクリプトのファイル名とクラス名が違うと、アタッチできない原因になることがあります。
たとえば、ファイル名がEnemyController.csなのに、クラス名がEnemyMoveになっている場合です。
C#using UnityEngine;
public class EnemyMove : MonoBehaviour
{
}
この場合は、ファイル名かクラス名のどちらかを修正して一致させます。
C#using UnityEngine;
public class EnemyController : MonoBehaviour
{
}
スクリプト名を変更したときは、Projectウィンドウ上のファイル名だけでなく、コード内のclass名も必ず確認しましょう。
9-5. Inspectorに変数が表示されない原因
C#スクリプトの変数がInspectorに表示されない場合、いくつかの原因が考えられます。
まず、変数がprivateになっている場合は、そのままではInspectorに表示されません。
C#private float speed = 5f;
Inspectorに表示したい場合はpublicにします。
C#public float speed = 5f;
または、privateのまま表示したい場合は[SerializeField]を付けます。
C#[SerializeField]
private float speed = 5f;
ただし、static変数やプロパティなどは通常の変数と同じようにはInspectorに表示されません。
C#public static int score;
public int Hp { get; set; }
Inspectorに表示したい場合は、基本的なフィールドとして定義しましょう。
9-6. Consoleウィンドウの見方
Consoleウィンドウは、Unityでエラーやログを確認するための重要な場所です。
赤いアイコンはエラー、黄色いアイコンは警告、白いアイコンは通常ログです。
Debug.Logで出力した内容もConsoleに表示されます。
C#Debug.Log("確認用ログ");
Debug.LogWarning("警告ログ");
Debug.LogError("エラーログ");
エラーをクリックすると、どのC#スクリプトの何行目で問題が起きているか確認できます。ダブルクリックすると、コードエディタで該当箇所を開けることもあります。
Unity初心者は、エラー文をすべて理解できなくても構いません。まずはスクリプト名、行番号、エラーの種類を見る習慣を付けましょう。
10. Unity C#スクリプトを書くときのコツ
UnityでC#スクリプトを書くときは、ただ動けばよいというだけでなく、後から読みやすく修正しやすいコードにすることが大切です。
初心者のうちから、変数名の付け方、メソッド分け、コメント、Updateの使い方、スクリプトの役割分担を意識すると、学習が進んだときに大きな差が出ます。
10-1. 変数名・メソッド名をわかりやすくする
変数名やメソッド名は、何を表しているのかがわかる名前にしましょう。
悪い例は次のような名前です。
C#public float a;
public int x;
void Do()
{
}
これでは、何の値なのか、何をする処理なのかわかりません。
よい例は次のような名前です。
C#public float moveSpeed;
public int playerHp;
void MovePlayer()
{
}
名前を見ただけで意味がわかるようにすると、後からC#スクリプトを見返したときに理解しやすくなります。
Unityのscriptは、プロジェクトが大きくなるほど数が増えます。わかりやすい名前を付けることは、エラーを減らすことにもつながります。
10-2. 処理をメソッドに分ける
Updateの中にすべての処理を書くと、コードが長くなり、何をしているのかわかりにくくなります。
たとえば、移動、ジャンプ、攻撃をそれぞれメソッドに分けると読みやすくなります。
C#using UnityEngine;
public class PlayerController : MonoBehaviour
{
void Update()
{
Move();
Jump();
Attack();
}
void Move()
{
// 移動処理
}
void Jump()
{
// ジャンプ処理
}
void Attack()
{
// 攻撃処理
}
}
このように分けると、Updateを見るだけで「毎フレーム何をしているのか」がわかります。
また、不具合が起きたときも、どの処理を確認すればよいか判断しやすくなります。
10-3. コメントを適切に書く
コメントは、処理の意図を説明するために使います。
ただし、コードをそのまま説明するだけのコメントは多すぎると読みにくくなります。
C#// speedに5を入れる
public float speed = 5f;
このようなコメントは、コードを見ればわかるため不要なことが多いです。
一方で、なぜその処理をしているのかを説明するコメントは役立ちます。
C#// フレームレートに関係なく一定速度で移動させるため、Time.deltaTimeを掛ける
transform.position += direction * speed * Time.deltaTime;
コメントは「何をしているか」よりも「なぜそうしているか」を書くと、後から役立つことが多いです。
10-4. Updateに重い処理を書きすぎない
Updateは毎フレーム呼び出されるため、重い処理を書きすぎるとゲームの動作が遅くなる原因になります。
たとえば、大量のオブジェクト検索、毎フレームのInstantiate、複雑な計算、大量のDebug.Logなどは注意が必要です。
特に、次のような処理をUpdateに何度も書くのは避けた方がよい場合があります。
C#void Update()
{
GameObject player = GameObject.Find("Player");
}
毎フレームGameObject.Findを実行すると負荷が高くなることがあります。必要な参照はStartで取得して変数に保存する方がよいです。
C#private GameObject player;
void Start()
{
player = GameObject.Find("Player");
}
Updateには、毎フレーム本当に必要な処理だけを書くようにしましょう。
10-5. スクリプトを役割ごとに分ける
1つのC#スクリプトにすべての処理を詰め込むと、コードが長くなりすぎて管理が難しくなります。
たとえば、プレイヤーの移動、HP管理、攻撃、スコア管理、UI更新をすべて1つのscriptに書くと、修正しづらくなります。
役割ごとにスクリプトを分けると管理しやすくなります。
PlayerController // プレイヤーの移動
PlayerHealth // プレイヤーのHP管理
PlayerAttack // 攻撃処理
ScoreManager // スコア管理
UIManager // UI表示
GameManager // ゲーム全体の管理
Unityでは、GameObjectに複数のコンポーネントを追加できます。そのため、役割ごとにC#スクリプトを分けてアタッチする設計がしやすいです。
10-6. 公式ドキュメントを活用する
UnityのC#スクリプトを学ぶときは、公式ドキュメントを活用することも大切です。
Transform、Rigidbody、Collider、Input、Instantiate、Destroyなど、Unityの機能には多くのプロパティやメソッドがあります。すべてを暗記する必要はありません。
わからない機能が出てきたら、公式ドキュメントで使い方やサンプルを確認しましょう。
また、C#の基本文法については、MicrosoftのC#ドキュメントも参考になります。Unity特有の機能とC#の言語仕様を分けて学ぶと、理解が深まりやすくなります。
11. Unity C#スクリプトの学習方法
UnityのC#スクリプトは、読むだけではなかなか身に付きません。小さなサンプルを作り、自分で値を変え、エラーを直しながら学ぶことが大切です。
最初から大きなゲームを作ろうとすると難しく感じます。まずは、Cubeを動かす、キー入力を取る、当たり判定を使うなど、小さな練習から始めましょう。
11-1. まず覚えるべきC#文法
Unity初心者が最初に覚えるべきC#文法は、変数、データ型、if文、for文、メソッド、クラス、publicとprivateです。
これらを理解すれば、基本的なUnity scriptは読めるようになります。
次に、配列、List、プロパティ、継承、インターフェース、イベントなどを少しずつ学ぶとよいでしょう。
ただし、最初からC#を完璧に覚える必要はありません。Unityで実際に使いながら、必要になった文法を覚えていく方法でも問題ありません。
11-2. 小さなサンプルを作りながら学ぶ
C#スクリプトを学ぶときは、小さなサンプルを作るのが効果的です。
たとえば、次のような練習がおすすめです。
Cubeを左右に動かす、スペースキーでジャンプする、クリックでCubeを消す、敵を一定間隔で生成する、アイテムを取ったらスコアを増やす、時間制限を作る、HPを減らす、ゲームオーバー画面を表示する、などです。
小さなサンプルを作ると、Unityの基本機能を実際に使いながら理解できます。
1つのサンプルを作ったら、値を変えたり、条件を追加したりして改造してみましょう。自分で試すことで、C#スクリプトの理解が深まります。
11-3. Unity公式チュートリアルを活用する
Unityには初心者向けのチュートリアルが用意されています。公式チュートリアルでは、Unity Editorの使い方、C#スクリプトの基本、2Dや3Dゲーム制作の流れを実践的に学べます。
動画やサンプルプロジェクトを見ながら学ぶと、文章だけではわかりにくい部分も理解しやすくなります。
特に初心者は、完成したサンプルをただ見るだけでなく、自分のUnityプロジェクトで同じように作ってみることが大切です。
手を動かして作ることで、スクリプトをどのGameObjectにアタッチするのか、Inspectorで何を設定するのか、Consoleのエラーをどう読むのかが自然に身に付きます。
11-4. エラーを調べながら理解を深める
UnityでC#スクリプトを書いていると、エラーは必ず出ます。エラーを避けるのではなく、エラーから学ぶことが大切です。
エラーが出たら、まずConsoleを確認します。エラーメッセージ、スクリプト名、行番号を見て、どこで問題が起きているか調べます。
よくあるエラーには、セミコロン忘れ、変数名の間違い、NullReferenceException、ファイル名とクラス名の不一致などがあります。
エラー文を検索すると、同じ問題で困っている人の解決例が見つかることもあります。ただし、コードをそのままコピーするだけでなく、なぜ直るのかを理解するようにしましょう。
エラーを1つずつ解決する経験が、Unity C#スクリプトの理解につながります。
11-5. 初心者におすすめの練習課題
Unity初心者におすすめの練習課題は、シンプルなミニゲームを作ることです。
たとえば、次のような課題があります。
プレイヤーをキーボードで動かす、ステージ上のアイテムを集める、アイテムを取ったらスコアを増やす、敵に当たったらHPを減らす、HPが0になったらゲームオーバーにする、制限時間を作る、ゴールに到達したらクリアにする、などです。
これらの要素を組み合わせると、簡単なゲームが作れます。
最初は見た目にこだわりすぎず、C#スクリプトで動く仕組みを作ることを優先しましょう。CubeやSphereだけでも、移動、当たり判定、スコア、ゲームクリアなどの基本は学べます。
12. Unity C#スクリプトに関するよくある質問
ここでは、Unity初心者がC#スクリプトを学ぶときによく疑問に感じる点を解説します。
12-1. UnityでC#以外の言語は使える?
現在のUnity開発では、基本的にC#を使ってスクリプトを書きます。
過去にはUnityScriptと呼ばれるJavaScript風の言語が使われていた時期もありましたが、現在Unityでscriptを書く場合はC#を学ぶのが一般的です。
そのため、Unity初心者はC#を学べば問題ありません。UnityのチュートリアルやサンプルコードもC#で書かれているものが多いため、学習しやすいです。
12-2. C#初心者でもUnityスクリプトは書ける?
C#初心者でもUnityスクリプトは書けます。
最初からC#の高度な文法をすべて覚える必要はありません。変数、if文、メソッド、Start、Update、Transform、Inputなど、よく使う部分から少しずつ覚えれば大丈夫です。
Unityでは、GameObjectにスクリプトをアタッチして動きを確認できるため、プログラムの結果が目に見えやすいというメリットがあります。
まずは、Debug.Logで文字を表示する、Cubeを動かす、キー入力で移動するなど、簡単なscriptから始めましょう。
12-3. StartとUpdateの違いは?
Startは、スクリプトが有効になった最初のタイミングで1回だけ実行されます。初期設定に使うことが多いです。
Updateは、ゲーム実行中に毎フレーム実行されます。入力の確認や移動処理など、常に更新したい処理に使います。
たとえば、HPを最初に100にする処理はStart、キー入力でプレイヤーを動かす処理はUpdateに書くのが一般的です。
C#void Start()
{
hp = 100;
}
void Update()
{
Move();
}
この違いを理解すると、UnityのC#スクリプトが書きやすくなります。
12-4. スクリプトを複数のGameObjectに使い回せる?
C#スクリプトは複数のGameObjectに使い回せます。
たとえば、MoveSampleというスクリプトを複数のCubeにアタッチすれば、それぞれのCubeが同じ処理で動きます。
ただし、public変数や[SerializeField]の値は、GameObjectごとにInspectorで別々に設定できます。
C#public float speed = 5f;
同じscriptを使っていても、Cube Aはspeedを3、Cube Bはspeedを8にする、といった設定が可能です。
この仕組みにより、同じC#スクリプトを使いながら、GameObjectごとに違う動きを作れます。
12-5. UnityのC#スクリプトはどこまで勉強すればいい?
UnityのC#スクリプトは、作りたいものに必要な範囲から学べば問題ありません。
最初は、変数、if文、for文、メソッド、Start、Update、Transform、Input、Rigidbody、Colliderを理解することを目標にしましょう。
その後、UI、シーン管理、アニメーション、サウンド、データ保存、Prefab、ScriptableObject、イベント処理などを必要に応じて学ぶとよいです。
大切なのは、C#の文法だけを暗記するのではなく、Unityで実際に動かしながら覚えることです。
12-6. エラーが出たときは何から確認すればいい?
エラーが出たときは、まずConsoleウィンドウを確認します。
赤いエラーをクリックし、どのC#スクリプトの何行目で問題が起きているかを見ましょう。
次に、セミコロン忘れ、波括弧の数、変数名の間違い、ファイル名とクラス名の不一致、Inspectorで参照が設定されているかを確認します。
NullReferenceExceptionの場合は、使おうとしている変数に何も入っていない可能性があります。
エラーは慣れるまで難しく感じますが、原因を1つずつ確認すれば解決できます。Unity初心者は、Consoleを見る習慣を付けることが大切です。
まとめ
UnityのC#スクリプトは、GameObjectに動きや処理を追加するために欠かせない要素です。
Unityでは、C# scriptを作成し、GameObjectにアタッチすることで、プレイヤーの移動、キー入力、マウスクリック、当たり判定、オブジェクト生成、削除、スコア管理などを実装できます。
初心者がまず覚えるべきポイントは、C#スクリプトの作成方法、ファイル名とクラス名の関係、MonoBehaviour、Start、Update、変数、if文、for文、メソッド、publicとprivate、Inspectorの使い方です。
最初から難しいゲームを作ろうとせず、Debug.Logで確認する、Cubeを動かす、キー入力を受け取る、当たり判定を試すといった小さなサンプルから始めるのがおすすめです。
UnityのC#スクリプトは、書いて、動かして、エラーを直すことで少しずつ身に付きます。基本を理解しながら練習を重ねれば、Unity初心者でも自分のゲームやアプリに必要なscriptを書けるようになります。

