象棋
中国象棋是一项策略型棋类游戏,具有深厚历史和文化背景。游戏双方通过布局、运筹帷幄展开对抗,遵循完整的规则体系以保证比赛公平和规范。中国象棋的规则包括盘和棋子的设置、走棋方式、胜负条件、记录、计时和违规与处罚等规定。中国象棋的历史可以追溯到春秋战国时期,象棋不仅仅是一种游戏,更是一种文化符号和智慧的象征。理解和遵守规则能帮助棋手发挥战略和技巧,享受比赛乐趣,同时确保比赛的公正性和顺利进行。
开发准备
1.首先你需要有一个Unity游戏引擎
Unity [1]是实时3D互动内容创作和运营平台 [2]。包括游戏开发、美术、建筑、汽车设计、影视在内的所有创作者,借助Unity将创意变成现实。 [3]Unity平台提供一整套完善的软件解决方案 [3],可用于创作、运营和变现任何实时互动的2D和3D内容,支持平台包括手机、平板电脑、PC、游戏主机、增强现实和虚拟现实设备。 [3]
网上类似的教程有很多我这里就不过多赘述了。
https://blog.csdn.net/Dugege007/article/details/128472571
这里有一个网上的教程可以放心使用。
2.创建项目
打开Unity 你会出现如下界面 这里先别急编辑器的版本无所谓
接着点击右上角的“新项目” 然后接着你会出现如下界面
选择2D 核心模板 ,取一名字选择你的项目要存放在哪里,我一般习惯放在D盘,你只需放在自己喜欢的位置就行了
你们可以移动那些格子拖动来找到你们最舒服的位置,好接下来我们正式开始开发
正式开发
接下来我们要了解一些基本组件,这次开发我使用的的是纯UI开发虽然利用非UI也能开发,但是我们需要学习一些组件其次才能进行开发
接着我们创建一个画布,并在画布上创建一个空物体挂上组件:Image (以此来添加棋盘图片),你可以为你的新物体创建一个新的名字,并创建一个脚本命名为ChessManager 挂在空物体上,并添加一个管理子物体的组件如下图
接着我们常见一个小物体挂照着我的组件挂上,并创建一个 Square 脚本挂上自己的Slots
接着我们预先在棋盘上摆出想起的样子:
开始写代码
ChessManager 这个最后再看 先看下面两个
using System;
using UnityEngine.UI;
using UnityEngine;
public class ChessManager : MonoBehaviour
{
// 得到空照片
[SerializeField] private Sprite Nonephoto;
// 实例化格子
[SerializeField] private Square[] slots;
// 当前阵营
public Camp currentCamp;
private Vector2Int curPos;
private bool isSelectChess;
/* 单例模式 */
private static ChessManager instance;
private ChessManager() {}
public static ChessManager Instance()
{
if(instance == null) instance = new ChessManager();
return instance;
}
/* 单例模式 */
private void Awake()
{
isSelectChess = false;
curPos = new Vector2Int(-1, -1);
currentCamp = Camp.Red;
InitIndex();
}
// 坐标 位置转换
public Vector2Int GetIndex(int index)
{
return new Vector2Int(index % 9, index / 9);
}
public int GetNum(Vector2Int pos)
{
return pos.y * 9 + pos.x;
}
// 初始化
public void InitIndex()
{
for(int i = 0; i < slots.Length; i ++)
{
slots[i].index = GetIndex(i);
}
}
// 事件呼叫
private void OnEnable()
{
EventHandler.SlotClicked += OnSlotClicked;
}
private void OnDisable()
{
EventHandler.SlotClicked -= OnSlotClicked;
}
private void OnSlotClicked(Vector2Int pos) // 选择后触发事件
{
if (isSelectChess)
{
if (pos == curPos)
{
Debug.Log(slots[GetNum(curPos)].chessType +"该棋子已经选中!");
return;
}
if (slots[GetNum(pos)].camp == currentCamp)
{
Debug.Log("无法移动到己方棋子上!");
}
Debug.Log(curPos);
MoveChess(pos);
}
else
{
if (slots[GetNum(pos)].camp == currentCamp)
{
curPos = pos;
isSelectChess = true;
}
else
{
return;
}
}
}
private void MoveChess(Vector2Int pos) // 判断当前位置棋子类型并执行移动
{
switch (slots[GetNum(curPos)].chessType)
{
case ChessType.Check: // 将军
CheckMove(pos);
break;
case ChessType.Soldier: // 兵
SoldierMove(pos);
break;
case ChessType.Satute: // 炮
SatuteMove(pos);
break;
case ChessType.Elephant: // 象
ElephantMove(pos);
break;
case ChessType.Horse: // 马
HorseMove(pos);
break;
case ChessType.Car: // 车
CarMove(pos);
break;
case ChessType.Bachelor: // 士
BachelorMove(pos);
break;
}
}
private void MoveTheChess(Vector2Int movePos) // 将格子移动
{
slots[GetNum(movePos)].camp = slots[GetNum(curPos)].camp;
slots[GetNum(movePos)].chessType = slots[GetNum(curPos)].chessType;
slots[GetNum(curPos)].camp = Camp.None;
slots[GetNum(curPos)].chessType = ChessType.None;
slots[GetNum(movePos)].icon.GetComponent<Image>().sprite = slots[GetNum(curPos)].icon.GetComponent<Image>().sprite;
slots[GetNum(curPos)].icon.GetComponent<Image>().sprite = Nonephoto;
}
// 各类棋子移动
private void CheckMove(Vector2Int pos) // 将军移动
{
if (currentCamp == Camp.Red)
{
Debug.Log("当前为红方");
if (pos.x < 3 || pos.x > 5)
{
Debug.Log("帅并不能走出方格!");
return;
}
else if (pos.y > 9 || pos.y < 7)
{
Debug.Log("帅并不能走出方格!");
return;
}
else if (pos.x != curPos.x && pos.y != curPos.y)
{
Debug.Log("帅不能斜侧移动!");
return;
}
else
{
if (pos.x == curPos.x)
{
if (pos.y == curPos.y + 1 || pos.y == curPos.y - 1)
{
MoveTheChess(pos);
currentCamp = Camp.Black;
isSelectChess = false;
return;
}
Debug.Log("一次只能移动一个");
return;
}
else if (curPos.y == pos.y)
{
if (pos.x == curPos.x + 1 || pos.x == curPos.x - 1)
{
MoveTheChess(pos);
currentCamp = Camp.Black;
isSelectChess = false;
return;
}
Debug.Log("一次只能移动一个");
return;
}
}
}
else if (currentCamp == Camp.Black)
{
Debug.Log("当前为黑色!");
if (pos.x < 3 || pos.x > 5)
{
Debug.Log("将并不能走出方格!");
return;
}
else if (pos.y > 2 || pos.y < 0)
{
Debug.Log("将并不能走出方格!");
return;
}
else if (pos.x != curPos.x && pos.y != curPos.y)
{
Debug.Log("将不能斜侧移动!");
return;
}
else
{
if (pos.x == curPos.x)
{
if (pos.y == curPos.y + 1 || pos.y == curPos.y - 1)
{
MoveTheChess(pos);
currentCamp = Camp.Red;
isSelectChess = false;
return;
}
Debug.Log("一次只能移动一个");
return;
}
else if (curPos.y == pos.y)
{
if (pos.x == curPos.x + 1 || pos.x == curPos.x - 1)
{
MoveTheChess(pos);
currentCamp = Camp.Red;
isSelectChess = false;
return;
}
Debug.Log("一次只能移动一个");
return;
}
}
}
}
private void SoldierMove(Vector2Int pos) // 小兵移动
{
if (currentCamp == Camp.Red)
{
if (curPos.y > 4)
{
if (pos.x == curPos.x && pos.y == curPos.y - 1)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Black;
}
Debug.Log("兵在过河前只能前进");
return;
}
else
{
if (pos.y < curPos.y)
{
Debug.Log("兵无法向后移动");
return;
}
else if (pos.x != curPos.x && pos.y != curPos.y)
{
Debug.Log("兵无法斜侧移动");
return;
}
else
{
if (pos.x == curPos.x)
{
if (pos.y == curPos.y + 1)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Black;
return;
}
}
else if (pos.y == curPos.y)
{
if (pos.x == curPos.x + 1 || pos.x == curPos.x - 1)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Black;
return;
}
}
}
}
}
else if (currentCamp == Camp.Black)
{
if (curPos.y > 6)
{
if (pos.x == curPos.x && pos.y == curPos.y + 1)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Red;
}
Debug.Log("卒在过河前只能前进");
return;
}
else
{
if (pos.y < curPos.y)
{
Debug.Log("卒无法向后移动");
return;
}
else if (pos.x != curPos.x && pos.y != curPos.y)
{
Debug.Log("卒无法斜侧移动");
return;
}
else
{
if (pos.x == curPos.x)
{
if (pos.y == curPos.y + 1)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Red;
return;
}
}
else if (pos.y == curPos.y)
{
if (pos.x == curPos.x + 1 || pos.x == curPos.x - 1)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Red;
return;
}
}
}
}
}
}
private void SatuteMove(Vector2Int pos) // 炮移动
{
if (pos.x != curPos.x && pos.y != curPos.y)
{
Debug.Log("炮不能斜侧移动");
return;
}
else if (pos.x == curPos.x)
{
int ma = Math.Max(pos.y, curPos.y);
int mi = Math.Min(pos.y, curPos.y);
Debug.Log(ma + " " + mi);
int num = 0;
for (int i = mi + 1; i < ma; i ++)
{
Vector2Int temp = new Vector2Int(curPos.x, i);
if (slots[GetNum(temp)].camp != Camp.None)
{
num ++;
}
}
if (num > 1)
{
Debug.Log("炮不能跳过两个以上棋子");
return;
}
if (num == 1)
{
if (currentCamp == Camp.Red)
{
if (slots[GetNum(pos)].camp == Camp.Black)
{
MoveTheChess(pos);
currentCamp = Camp.Black;
isSelectChess = false;
return;
}
Debug.Log("无法移动到当前位置");
}
if (currentCamp == Camp.Black)
{
if (slots[GetNum(pos)].camp == Camp.Red)
{
MoveTheChess(pos);
currentCamp = Camp.Red;
isSelectChess = false;
return;
}
Debug.Log("无法移动到当前位置");
}
}
if (num == 0 && slots[GetNum(pos)].camp == Camp.None)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
}
else if (curPos.y == pos.y)
{
int ma = Math.Max(pos.x, curPos.x);
int mi = Math.Min(pos.x, curPos.x);
Debug.Log(ma + " " + mi);
int num = 0;
for (int i = mi + 1; i < ma; i ++)
{
Vector2Int temp = new Vector2Int(i, curPos.y);
if (slots[GetNum(temp)].camp != Camp.None)
{
num ++;
}
}
Debug.Log("炮跳过" + num);
if (num > 1)
{
Debug.Log("炮不能跳过两个以上棋子");
return;
}
if (num == 1)
{
if (currentCamp == Camp.Red)
{
if (slots[GetNum(pos)].camp == Camp.Black)
{
MoveTheChess(pos);
currentCamp = Camp.Black;
isSelectChess = false;
return;
}
Debug.Log("无法移动到当前位置");
}
if (currentCamp == Camp.Black)
{
if (slots[GetNum(pos)].camp == Camp.Red)
{
MoveTheChess(pos);
currentCamp = Camp.Red;
isSelectChess = false;
return;
}
Debug.Log("无法移动到当前位置");
}
}
if (num == 0 && slots[GetNum(pos)].camp == Camp.None)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
}
}
private void CarMove(Vector2Int pos) // 车移动
{
if (pos.x != curPos.x && pos.y != curPos.y)
{
Debug.Log("车不能斜向移动");
return;
}
else if (pos.x == curPos.x)
{
int ma = Math.Max(pos.y, curPos.y);
int mi = Math.Min(pos.y, curPos.y);
int num = 0;
for (int i = mi + 1; i < ma; i ++)
{
Vector2Int temp = new Vector2Int(curPos.x, i);
if (slots[GetNum(temp)].camp != Camp.None)
{
num ++;
}
}
if (num == 0)
{
if (currentCamp == Camp.Red && slots[GetNum(pos)].camp != currentCamp)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Black;
return;
}
if (currentCamp == Camp.Black && slots[GetNum(pos)].camp != currentCamp)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Red;
return;
}
return;
}
return;
}
else if (pos.y == curPos.y)
{
int ma = Math.Max(pos.x, curPos.x);
int mi = Math.Min(pos.x, curPos.x);
int num = 0;
for (int i = mi + 1; i < ma; i ++)
{
Vector2Int temp = new Vector2Int(i, curPos.y);
if (slots[GetNum(temp)].camp != Camp.None)
{
num ++;
}
}
if (num == 0)
{
if (currentCamp == Camp.Red && slots[GetNum(pos)].camp != currentCamp)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Black;
return;
}
if (currentCamp == Camp.Black && slots[GetNum(pos)].camp != currentCamp)
{
MoveTheChess(pos);
isSelectChess = false;
currentCamp = Camp.Red;
return;
}
return;
}
return;
}
}
private void ElephantMove(Vector2Int pos) // 象移动
{
if (pos.x == curPos.x + 2 && pos.y == curPos.y + 2)
{
if (pos.x == curPos.x + 1 && pos.y == curPos.y + 1)
{
Debug.Log("堵象眼");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x - 2 && pos.y == curPos.y - 2)
{
if (pos.x == curPos.x - 1 && pos.y == curPos.y - 1)
{
Debug.Log("堵象眼");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x - 2 && pos.y == curPos.y + 2)
{
if (pos.x == curPos.x - 1 && pos.y == curPos.y + 1)
{
Debug.Log("堵象眼");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x + 2 && pos.y == curPos.y - 2)
{
if (pos.x == curPos.x + 1 && pos.y == curPos.y - 1)
{
Debug.Log("堵象眼");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
}
private void HorseMove(Vector2Int pos) // 马移动
{
Debug.Log(pos + " " + curPos);
if (pos.x == curPos.x + 1 && pos.y == curPos.y + 2)
{
Vector2Int front = new Vector2Int(curPos.x, curPos.y + 1);
Debug.Log(front);
if (slots[GetNum(front)].camp != Camp.None)
{
Debug.Log("堵马脚");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x - 1 && pos.y == curPos.y - 2)
{
Vector2Int front = new Vector2Int(curPos.x, curPos.y - 1);
Debug.Log(front);
if (slots[GetNum(front)].camp != Camp.None)
{
Debug.Log("堵马脚");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x - 1 && pos.y == curPos.y + 2)
{
Vector2Int front = new Vector2Int(curPos.x, curPos.y + 1);
Debug.Log(front);
if (slots[GetNum(front)].camp != Camp.None)
{
Debug.Log("堵马脚");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x + 1 && pos.y == curPos.y - 2)
{
Vector2Int front = new Vector2Int(curPos.x, curPos.y - 1);
Debug.Log(front);
if (slots[GetNum(front)].camp != Camp.None)
{
Debug.Log("堵马脚");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x + 2 && pos.y == curPos.y + 1)
{
Vector2Int front = new Vector2Int(curPos.x + 1, curPos.y);
Debug.Log(front);
if (slots[GetNum(front)].camp != Camp.None)
{
Debug.Log("堵马脚");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x - 2 && pos.y == curPos.y - 1)
{
Vector2Int front = new Vector2Int(curPos.x - 1, curPos.y);
Debug.Log(front);
if (slots[GetNum(front)].camp != Camp.None)
{
Debug.Log("堵马脚");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x - 2 && pos.y == curPos.y + 1)
{
Vector2Int front = new Vector2Int(curPos.x - 1, curPos.y);
Debug.Log(front);
if (slots[GetNum(front)].camp != Camp.None)
{
Debug.Log("堵马脚");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
if (pos.x == curPos.x + 2 && pos.y == curPos.y - 1)
{
Vector2Int front = new Vector2Int(curPos.x + 1, curPos.y);
Debug.Log(front);
if (slots[GetNum(front)].camp != Camp.None)
{
Debug.Log("堵马脚");
return;
}
MoveTheChess(pos);
isSelectChess = false;
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
return;
}
}
private void BachelorMove(Vector2Int pos) // 士移动
{
if (currentCamp == Camp.Red)
{
if (pos.x < 3 || pos.x > 5)
{
Debug.Log("士只能在方格内走!");
return;
}
if (pos.y <= 6)
{
Debug.Log("士只能在方格内走!");
return;
}
if (pos.x == curPos.x + 1 && pos.y == curPos.y + 1)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
if (pos.x == curPos.x - 1 && pos.y == curPos.y - 1)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
if (pos.x == curPos.x - 1 && pos.y == curPos.y + 1)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
if (pos.x == curPos.x + 1 && pos.y == curPos.y - 1)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
return;
}
if (currentCamp == Camp.Black)
{
if (pos.x < 3 || pos.x > 5)
{
Debug.Log("士只能在方格内走!");
return;
}
if (pos.y > 2)
{
Debug.Log("士只能在方格内走!");
return;
}
if (pos.x == curPos.x + 1 && pos.y == curPos.y + 1)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
if (pos.x == curPos.x - 1 && pos.y == curPos.y - 1)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
if (pos.x == curPos.x - 1 && pos.y == curPos.y + 1)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
if (pos.x == curPos.x + 1 && pos.y == curPos.y - 1)
{
MoveTheChess(pos);
if (currentCamp == Camp.Red) currentCamp = Camp.Black;
else if (currentCamp == Camp.Black) currentCamp = Camp.Red;
isSelectChess = false;
return;
}
return;
}
}
}
Square
using UnityEngine;
public class Square : MonoBehaviour
{
public Camp camp;
public ChessType chessType;
public GameObject Select;
public GameObject icon;
public Vector2Int index;
public void SlotOnClicked()
{
EventHandler.CallSlotClicked(index);
}
}
using System;
using UnityEngine;
public static class EventHandler
{
public static event Action<Vector2Int> SlotClicked;
public static void CallSlotClicked(Vector2Int pos)
{
SlotClicked?.Invoke(pos);
}
}
public enum Camp
{
None,
Red,
Black
}
public enum ChessType
{
None,
Check,
Soldier,
Satute,
Elephant,
Horse,
Car,
Bachelor
}
这个代码在我的仓库里开源有但是我图方便直接开源给你们, 我也水水博客这闲的无聊搞得,最近大项目创作瓶颈都不知道做啥了感觉做的不好玩,想重新搞但是做了这么久又不想弃坑,我技术还是不好得再加强!!!