4.Writing the Board Manager
C#スクリプトを使ってゲームロジックとステージを作っていきます。
ここからがっつりスクリプトの内容になるので、気になる部分をチェックしていきたいと思います。
//Clears our list gridPositions and prepares it to generate a new board. void InitialiseList () { //Clear our list gridPositions. gridPositions.Clear (); //Loop through x axis (columns). for(int x = 1; x < columns-1; x++) { //Within each column, loop through y axis (rows). for(int y = 1; y < rows-1; y++) { //At each index add a new Vector3 to our list with the x and y coordinates of that position. gridPositions.Add (new Vector3(x, y, 0f)); } } }
gridPositionsはVector3を格納できる配列で、まずステージ内部の座標を生成して、gridPositionsに追加していきます。床のScaleは1なので、x座標とy座標はそのままx,yを1づつ増やすループで生成することができます。
//Sets up the outer walls and floor (background) of the game board. void BoardSetup () { //Instantiate Board and set boardHolder to its transform. boardHolder = new GameObject ("Board").transform; //Loop along x axis, starting from -1 (to fill corner) with floor or outerwall edge tiles. for(int x = -1; x < columns + 1; x++) { //Loop along y axis, starting from -1 to place floor or outerwall tiles. for(int y = -1; y < rows + 1; y++) { //Choose a random tile from our array of floor tile prefabs and prepare to instantiate it. GameObject toInstantiate = floorTiles[Random.Range (0,floorTiles.Length)]; //Check if we current position is at board edge, if so choose a random outer wall prefab from our array of outer wall tiles. if(x == -1 || x == columns || y == -1 || y == rows) toInstantiate = outerWallTiles [Random.Range (0, outerWallTiles.Length)]; //Instantiate the GameObject instance using the prefab chosen for toInstantiate at the Vector3 corresponding to current grid position in loop, cast it to GameObject. GameObject instance = Instantiate (toInstantiate, new Vector3 (x, y, 0f), Quaternion.identity) as GameObject; //Set the parent of our newly instantiated object instance to boardHolder, this is just organizational to avoid cluttering hierarchy. instance.transform.SetParent (boardHolder); } } }
外壁と、床を配置していきます。
Instantiateの戻り値をGameObjectにcastして変数に格納し、boardHolderの子要素にする、という操作を行っています。
Instantinate時の引数Quaternion.identityは、全く回転していない状態を表します。
//RandomPosition returns a random position from our list gridPositions. Vector3 RandomPosition () { //Declare an integer randomIndex, set it's value to a random number between 0 and the count of items in our List gridPositions. int randomIndex = Random.Range (0, gridPositions.Count); //Declare a variable of type Vector3 called randomPosition, set it's value to the entry at randomIndex from our List gridPositions. Vector3 randomPosition = gridPositions[randomIndex]; //Remove the entry at randomIndex from the list so that it can't be re-used. gridPositions.RemoveAt (randomIndex); //Return the randomly selected Vector3 position. return randomPosition; }
RandomPositionというメソッドですが、ゲーム内可動範囲の全マス(gridPositions)から1つをランダムに選択して、選択されたマスをgridPositionsから削除する、という内容になっています。これを使って、各level毎の規定数のアイテムやエネミー、障害物を順番にマスに割り当てていきます。(一度割り当てられたマスはgridPositionsから削除されるので、もう一度使われることはありません)
グリッド型のステージを生成するときには使えそうなテクニックですね。
5.Writing the Game Manager
ここでは、GameManagerの扱いについて重要な事を言っています。まず、GameManagerはシングルトンにするということ。
そのために、GameManagerをprefab化してしまい、Loaderスクリプトを使ってインスタンス化します。LoaderスクリプトはMain Cameraにアタッチします。
これはいままで僕が見たサンプルには無かった考え方で勉強になります。こういった、クラスの構造の大枠を理解することは大切ですね。