第一次使用unity, 做點事情就比較笨。簡單的事情也做了許久,主要是對unity這個引擎邏輯不熟悉,對C#這個語言的邏輯也不是很熟,走了許多彎路。
開始想的是真的有九個格子那樣的對象,然後有一箇中控對象去負責統計結果,然後發現對象之間的通訊好像還有點麻煩,現在沒有太多時間去深入學習,所以使用了簡單一些的使用方式,全部都是GUI來做,只用一個腳本。
首先就是創建9個格子:
GUI.Button(new Rect(x, y, width, length), ""))
值得注意的是,這個函數,如果這個位置的按鈕不存在那麼就創建這個按鈕,如果這個按鈕已經存在了,那麼就會返回這個按鈕是否被點擊。
所以創建按鈕和檢測按鈕是否被點擊都寫在一起,寫在onGUI中。
// draw the chess table on each frame
for (int i = 0; i < 3; ++i)
for (int j = 0; j < 3; ++j) {
switch (state [i, j]) {
case 0:
if (GUI.Button (new Rect (i * 50 + xMove, j * 50 + yMove, 50, 50), ""))
click (i, j);
break;
case 1:
if (GUI.Button (new Rect (i * 50 + xMove, j * 50 + yMove, 50, 50), "O"))
click (i, j);
break;
case 2:
if (GUI.Button (new Rect (i * 50 + xMove, j * 50 + yMove, 50, 50), "X"))
click (i, j);
break;
default:
break;
}
}
這裏的state是一個3x3二維數組,用於儲存當前遊戲的狀態,同時根據當前遊戲狀態畫出不同的方格。
若被點擊則調用click進行處理。
reset按鈕就是通過恢復state數組使得下一楨的UI回覆到最初的樣子。
勝利信息通過GUI.label顯示出來。
public static void Label(Rect position, string text);
public static void Label(Rect position, Texture image);
public static void Label(Rect position, GUIContent content);
public static void Label(Rect position, string text, GUIStyle style);
public static void Label(Rect position, Texture image, GUIStyle style);
public static void Label(Rect position, GUIContent content, GUIStyle style);
遊戲中的代碼如下:
if (whetherEqual) {
GUI.Label (new Rect (xMove, 170 + yMove, 200, 100), "No winner here, press Restart!");
}
else if (whetherEnd) {
char winner = (turn == 2) ? 'O' : 'X';
GUI.Label (new Rect (xMove, 170 + yMove, 200, 100), winner + " win! press restart to start over");
}
至於判斷邏輯就不多說了,畢竟不是這裏的重點。
附完整代碼:
chess.cs 掛在主攝影機上即可運行
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Chess : MonoBehaviour
{
/* 0 for no chess
* 1 for player1
* 2 for player2
*/
private int[,] state = new int[3, 3];
/* switch turn
* 1 for player1
* 2 for player2
*/
private int turn = 1;
private bool whetherEnd = false;
private bool whetherEqual = false;
private int xMove = 350;
private int yMove = 150;
// Use this for initialization
void Start ()
{
init ();
Camera view = GetComponent<Camera> ();
view.backgroundColor = Color.white;
}
void OnGUI ()
{
GUI.backgroundColor = Color.white;
// reset button
if (GUI.Button (new Rect (25 + xMove, 250 + yMove, 100, 50), "Restart")) {
init ();
return;
}
// draw the chess table on each frame
for (int i = 0; i < 3; ++i)
for (int j = 0; j < 3; ++j) {
switch (state [i, j]) {
case 0:
if (GUI.Button (new Rect (i * 50 + xMove, j * 50 + yMove, 50, 50), ""))
click (i, j);
break;
case 1:
if (GUI.Button (new Rect (i * 50 + xMove, j * 50 + yMove, 50, 50), "O"))
click (i, j);
break;
case 2:
if (GUI.Button (new Rect (i * 50 + xMove, j * 50 + yMove, 50, 50), "X"))
click (i, j);
break;
default:
break;
}
}
GUI.color = Color.black;
if (whetherEqual) {
GUI.Label (new Rect (xMove, 170 + yMove, 200, 100), "No winner here, press Restart!");
}
else if (whetherEnd) {
char winner = (turn == 2) ? 'O' : 'X';
GUI.Label (new Rect (xMove, 170 + yMove, 200, 100), winner + " win! press restart to start over");
}
}
void click (int x, int y)
{
if (state [x, y] == 0 && !whetherEnd) {
state [x, y] = turn;
checkWhetherWin (x, y);
turn = (turn == 2) ? 1 : 2;
}
}
void checkWhetherWin (int x, int y)
{
// horizontal
if (state [x, 0] == state [x, 1] && state [x, 1] == state [x, 2]) {
whetherEnd = true;
Debug.Log ("win at horizontal");
}
// vertical
if (state [0, y] == state [1, y] && state [1, y] == state [2, y]) {
whetherEnd = true;
Debug.Log ("win at vertical");
}
// diagonal
bool flag = true;
for (int i = 0; i < 3; ++i) {
if (state [i, i] != state [x, y])
flag = false;
}
if (flag == true) {
whetherEnd = true;
Debug.Log ("win at diagonal 1");
}
flag = true;
for (int i = 2; i > -1; --i) {
if (state [2 - i, i] != state [x, y])
flag = false;
}
if (flag == true) {
whetherEnd = true;
Debug.Log ("win at diagonal 2");
}
flag = true;
for (int i = 0; i < 3; ++i)
for (int j = 0; j < 3; ++j) {
if (state [i, j] == 0)
flag = false;
}
if (flag) {
whetherEnd = true;
whetherEqual = true;
}
}
// init all things when restart button pressed
void init ()
{
Debug.Log ("chess start");
for (int i = 0; i < 3; ++i)
for (int j = 0; j < 3; ++j)
state [i, j] = 0;
whetherEnd = false;
whetherEqual = false;
turn = 1;
}
}