这次的作业要用Unity写一个井字棋游戏,显然,并不需要用到3D,因此只要建一个2D的项目就可以了。要做成一个井字棋游戏,必然用到Unity内置的GUI系统。
1.Unity中GUI的使用
UnityGUI控制是利用一个OnGUI()的函数,这个函数可以在每帧调用,就像是Update函数一样。(因此我们的代码中无需用到Update函数)
再了解下常用的控件:
(1)GUI.Label:
在OnGui中,GUI.Label(new Rect(300,40,40,40),"你好");
Rect设置Label显示的位置,4个参数分别记录X,Y,width,height,第2个参数显示文本内容()
——在井字棋游戏中,这个方法用来显示提示信息
(2)GUI.Button:
在OnGui中,if (GUI.Button(new Rect(300,40,40,40),"你好")) {...}
通过在OnGui里面判断GUI.Button是否返回true,显示是否按下(当然也可以直接使用)
——在井字棋游戏中,这个方法用于实现游戏的主要部分
在开始写之前,要先把上面两个函数用熟。
2.主要构思
在了解GUI的使用后,就要开始思考实现这个井字棋游戏需要用到什么变量和方法。
变量:
(1)确定每一个格子的状态:一个3*3的数组
(2)确定处于哪一方的回合:一个int变量
方法:
(1)初始化函数:把上面的两个变量都初始化(在Start()函数和)
(2)判断游戏是否结束(我一开始忘了有平局的情况):这个方法我采取的是很笨的办法,其实可能还有更好的算法实现
3.完整代码
把下面的代码挂载在main camera上就能运行。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class NewBehaviourScript : MonoBehaviour
{
public int[,] Status = new int[3, 3]; //0表示还没有选择,1表示√,-1表示×
public int turn; //1表示√的回合,-1表示×的回合
public GUIStyle setStyle = new GUIStyle(); //自己上网查的,用于改GUI.Label()中文字的样式
void init()
{
for (int i = 0; i < 3; i++)
{
for (int j = 0; j < 3; j++)
{
Status[i, j] = 0;
}
}
turn = 1; //√先走
}
void Start()
{
setStyle.fontSize = 20;
init();
}
void OnGUI()
{
if (Result() != 0)
{
if (Result() == 1)
{
GUI.Label(new Rect(300, 195, 40, 40), "√赢了", setStyle);
}
else if (Result() == -1)
{
GUI.Label(new Rect(300, 195, 40, 40), "×赢了", setStyle);
}
else
{
GUI.Label(new Rect(300, 195, 40, 40), "平局了", setStyle);
}
turn = 0;
if (GUI.Button(new Rect(275, 225, 100, 50), "重新开始?"))
{
init();
}
}
for (int i = 0; i < 3; i++)
{
for (int j = 0; j < 3; j++)
{
if (Status[i, j] == 1)
{
GUI.Button(new Rect(250 + i * 50, 30 + j * 50, 50, 50), "√");
continue;
}
if (Status[i, j] == -1)
{
GUI.Button(new Rect(250 + i * 50, 30 + j * 50, 50, 50), "×");
continue;
}
if (Status[i, j] == 0 && GUI.Button(new Rect(250 + i * 50, 30 + j * 50, 50, 50), ""))
{
if (turn == 1)
{
Status[i, j] = 1;
turn = -1;
}
else if (turn == -1)
{
Status[i, j] = -1;
turn = 1;
}
}
}
}
}
//返回1表示√赢,-1表示×赢,0表示还没结束,2表示平局
int Result()
{
if ((Status[0, 0] == Status[0, 1] && Status[0, 0] == Status[0, 2] && Status[0, 2] == Status[0, 1])
|| (Status[0, 0] == Status[1, 0] && Status[0, 0] == Status[2, 0] && Status[1, 0] == Status[2, 0]))
{
if (Status[0, 0] == 1)
{
return 1;
}
else if (Status[0, 0] == -1)
{
return -1;
}
}
if ((Status[0, 2] == Status[1, 2] && Status[0, 2] == Status[2, 2] && Status[1, 2] == Status[2, 2])
|| (Status[2, 0] == Status[2, 1] && Status[2, 1] == Status[2, 2] && Status[2, 2] == Status[2, 0]))
{
if (Status[2, 2] == 1)
{
return 1;
}
else if (Status[2, 2] == -1)
{
return -1;
}
}
if ((Status[1, 1] == Status[0, 1] && Status[1, 1] == Status[2, 1] && Status[2, 1] == Status[0, 1])
|| (Status[1, 1] == Status[1, 0] && Status[1, 1] == Status[1, 2] && Status[1, 2] == Status[1, 0])
|| (Status[0, 0] == Status[1, 1] && Status[1, 1] == Status[2, 2] && Status[2, 2] == Status[0, 0])
|| (Status[0, 2] == Status[1, 1] && Status[1, 1] == Status[2, 0] && Status[2, 0] == Status[0, 2]))
{
if (Status[1, 1] == 1)
{
return 1;
}
else if (Status[1, 1] == -1)
{
return -1;
}
}
if (isTie())
{
return 2;
}
return 0;
}
bool isTie()
{
int sum = 0;
for (int i = 0; i < 3; i++)
{
for (int j = 0; j < 3; j++)
{
if (Status[i, j] != 0)
{
sum++;
}
}
}
if (sum == 9)
{
return true;
}
else
{
return false;
}
}
}
4.理解
虽然是很简单的项目,但是可以帮我们熟悉Unity3D的操作,以及OnGUI的使用。
但是,OnGUI在真正开发中用得比较少——“实际项目中,这种方式不够灵活并且执行效率低,一般是采用第三方的NGUI插件来制作游戏界面”。