
Unity再開03・スクリプトによるダンジョン生成の復習
以前やっていたけれど中断してしまい、さっぱりわからなくなっていた、Unity。Unityに限らず、便利すぎるプログラミング言語というのは、感覚を忘れてしまうと思い出すのに苦労しますね。
Unityの場合は特に、「3Dモデルの作成」、「3Dのシーンの作成」、「オブジェクト指向によるコーディング」、という3つを、別々の操作で行う必要があるため、その3つのうちの、どれかを忘れると手も足も出なくなります。
そこで私が以前考えたのが、「スクリプト指向によるUnityプログラミング」です。例えば下記のように、スクリプトで迷宮を生成するようにしておけば、ダンジョンをモデリングソフトで作成するという、非常にハードルの高い作業が、不要になるわけです。やったね。
で、今日はその記事を引用しながら、本当にダンジョンが生成できるのかを確認し、さらに今後どう進めていくかを検討したいと思います。
まず今回も、Unity Hubから「新しいプロジェクト」を作成します。使うテンプレートは、「3D コア」ですね。
Unity Hubを立ち上げます。わかりやすくするために、リスト上のすべてのプロジェクトを削除しておきました。リストから削除してもフォルダは残っており、右上の「追加」からそれを指定してやると、表示を復活できます。

右上の「新しいプロジェクト」ボタンを押して、「3Dコア」を選びます。上部の「エディターのバージョン」を押すと、私の場合3つのバージョンが表示されますが、そのうちの「2021.3.21f1」を選びます。これは、以前使っていたバージョンがそれだというだけで、絶対にこれでないとダメというわけではありません。最初の画面の「インストール」で最新のバージョンをインストールし、それで試してみて、動けばそれを使った方がいいかも知れません。しかし、アセットで対応しているバージョンなども関係するため、最新のバージョンが必ずしもいいというわけでないのが、難しい所ですね。

バージョンを選んだら、右下の「プロジェクトを作成」を押します。
プロジェクトが作成されました。選択して開いてみましょう。

プロジェクト新規作成後の状態です。メインカメラとライトだけが設置された状態ですね。

上の画像はトリミングしているので若干違うように見えますが、たぶん同じ状態ですね。一番下のステータスバーに、赤文字でエラーが表示されていますが、よく覚えてないため今は放置します(笑。

今日もその状態で、Main Cameraにスクリプトをアタッチします。名前は前回と同じ、「TestScript」にしておきます。
ふうむ。ダンジョン生成スクリプトは、Main Cameraにアタッチするのですね。なぜかというと、生成したダンジョンのサイズなどに合わせて、カメラの位置や角度を調整しないといけないからです。別のオブジェクトにアタッチした場合、カメラオブジェクトをスクリプトにアタッチして、参照可能とする必要があるためです。
(ただ、今考えると「ダンジョン生成用オブジェクト」をアセット化し、そのアセットにカメラオブジェクトの操作をさせる方が自然かも知れません)
Main Cameraへのスクリプトのアタッチ方法は、下記の画像だけで説明しちゃってますね。今日はその詳細を、説明してみましょう。

まず左上のヒエラルキーパネルで、「SampleScene」を選び、

下の「Assets」という所の、あいてる部分で右クリックし、「Create」「C#Script」という順に選びます。

「#」というアイコンが出来ます。これがスクリプトですね。NewBehaviourScriptという名前から、つけたい名前、今回はTestScriptに変更します。

変更できました。次にこのスクリプトを、Main Cameraにアタッチします。

左上、ヒエラルキーパネルから「Main Camera」を選びます。

右のインスペクターパネルをずっと下にスクロールさせ、「Add Component」を押します。

そこで表示されたメニューから「Scripts」を選ぶと、現在選択可能なスクリプトが一覧表示されます。そこに、さっき作成した「TestScript」があると思います。それを選びます。

以上で、さっきの「Main Cameraへのスクリプトのアタッチ」の部分の画像と同じになりましたね。1枚の画像でこれだけの作業を省略しちゃってました。ちょっと無理がありましたね、てへぺろっ!

いや、言っちゃうとこういう、「あるゲームオブジェクトに、新規スクリプトを割り当てる」というだけのことに、上記のようにわずらわしい操作が必要になるというのが、Unityというゲーム開発プラットフォームの最大の欠点、なのですけどそこはあきらめましょう。ここまでできればあとは簡単、だったはず…...。
TestScriptを開いて、次のコードを貼り付けましょう。コードの説明は後で簡単に行います。
Unityの完全初心者の方にとっては、「TestScriptを開いて」がまずわからないと思います。さっきアタッチできた「Test Script」の右の点々を押し、表示されたメニューのEdit Scriptを選択です。(さっき作った「#」というアイコンをダブルクリックでも、開くことが出来ます)

エディターとしてMicrosfot Visual Studioをインストールしている場合、それを使ってTest Scriptが開かれます。インストールされてない場合は、メモ帳か何かで開かれるんでしょうね。

新規作成直後の、スクリプトの状態です。

上記を、次のスクリプトですべて置き換えます。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class TestScript : MonoBehaviour
{
float num = 10f;
string[] maze = new string[] {
"■■■■■■■■■■",
"■□■□□□■□□■",
"■□■■■□■■□■",
"■□□□□□□□□■",
"■■■■□□■■■■",
"■□□□□□□□□■",
"■□■□■■■□■■",
"■■■□■□□□□■",
"■□□□□□■■□■",
"■■■■■■■■■■",
};
private void make_ground(float num)
{
//Planeオブジェクトを追加して地面にする
GameObject Plane = GameObject.CreatePrimitive(PrimitiveType.Plane);
Plane.transform.localScale = new Vector3(2f, 2f, 2f);
}
private void move_camera()
{
//カメラの移動と回転
transform.position = new Vector3(0, 10, -10);
Quaternion newRotation = Quaternion.Euler(50f, 0f, 0f);
transform.rotation = newRotation;
}
void SetBlock(float num, float x, float z, Color col)
{
GameObject obj = GameObject.CreatePrimitive(PrimitiveType.Cube);
obj.transform.position = new Vector3((float)x * 2f - num + 1f, 0.5f, (float)z * 2f - num + 1f);
obj.GetComponent<Renderer>().material.color = col;
obj.transform.localScale = new Vector3(2f, 4f, 2f);
// Rigidbody rb = obj.AddComponent<Rigidbody>();
}
void Start()
{
make_ground(num);
move_camera();
Color col = new Color(0.3f, 0.3f, 0.3f);
for (int i = 0; i < num; i++)
{
for (int j = 0; j < num; j++)
{
if (maze[i].Substring(j, 1) == "■")
{
SetBlock(num, i, j, col);
}
}
}
}
}
置き換えました。保存してエディターを終了します。

上部の実行ボタンを押します。

迷路が作られました!

再びエディターでTestScriptを開き、迷路のデータを変更してみましょう。ちゃんと反映されるでしょうか?

反映されました。が、カメラの方向が少し違っているようですね。こういうのはデータで何とかするよりも、早めにプログラムを修正しておいた方がいいですね。

と、思って修正しようとしたんですけど、どう修正すればいいのか簡単にはわかりません! そこは次回までの宿題とさせていただきますね。
で、今後どう進めていくかですが、「ただ単に立方体を置いてダンジョンにするのではなく、もっとダンジョンっぽい造形にしてみる」、というのを考えていたのですけど、今日ふと思った、「ダンジョン生成アセットを作ってみる」、というのもいいかも知れませんね。でもまあ、「便利になるほど理解が難しくなる」と私は思っているため、アセット化という超便利な機能は後回しにして、「もっとダンジョンっぽいダンジョン」を、先にやってみることにしますね。
続きはこちら。