各个棋子的走子规则
自己基本上写完了整个程序,可能会有小问题,没有时间也不准备看了。上传到了github的18845143731的用户里,需要的可以自己看看
卒
下面是“兵”这个类里的重写的setLocation
方法:
@Override
public void setLocation(int setsimX, int setsimY) {
// TODO Auto-generated method stub
if((CurrentsimY<5 && (setsimY-CurrentsimY)==1) ||
(CurrentsimY>=5 && ((setsimY-CurrentsimY)==1||(setsimX-CurrentsimX)==-1||(setsimX-CurrentsimX)==1))) {
Data.panelArray[CurrentsimX][CurrentsimY] = 0;
Data.panelArray[setsimX][setsimY] = 1;
this.CurrentsimX = setsimX;
this.CurrentsimY = setsimY;
Data.selectPiece = null;
Data.BorRRun = !Data.BorRRun;
this.move(Data.simnum2xy(setsimX),Data.simnum2xy(setsimY));
}
else {
this.move(Data.simnum2xy(CurrentsimX),Data.simnum2xy(CurrentsimY));
}
}
判断语句中的条件,就是用来约束它的。“兵”在过河之前是不能左右走的,也不能后退,只能向前。以棋盘的左上角为原点,棋子当前的横坐标为CurrentX纵坐标为CurrentY。所以当Y<5时,也就是没过河时,只有setsimY-CurrentY==1
时,也就是向前走一步时,才会执行下面的move操作。而当Y>=5时,也就是过河后,有(setsimY-CurrentsimY)==1||(setsimX-CurrentsimX)==-1||(setsimX-CurrentsimX)==1)
,也就是可以向前和向左向右。“兵”的判断操作也是类似额。
将
下面是“将”这个类里的重写的setLocation
方法:
@Override
public void setLocation(int setsimX, int setsimY) {
// TODO Auto-generated method stub
if(setsimX>2&&setsimX<6&&setsimY<3) {
if(setsimX+setsimY-CurrentsimX-CurrentsimY == 1 || setsimX+setsimY-CurrentsimX-CurrentsimY == -1) {
Data.panelArray[CurrentsimX][CurrentsimY] = 0;
Data.panelArray[setsimX][setsimY] = 1;
this.CurrentsimX = setsimX;
this.CurrentsimY = setsimY;
Data.selectPiece = null;
Data.BorRRun = !Data.BorRRun;
this.move(Data.simnum2xy(setsimX),Data.simnum2xy(setsimY));
}
else {
this.move(Data.simnum2xy(CurrentsimX),Data.simnum2xy(CurrentsimY));
}
}
}
因为“将”不能出那个田字格,所以可以先加一个if(setsimX>2&&setsimX<6&&setsimY<3)
来限制它。下面的那个if里面setsimX+setsimY-CurrentsimX-CurrentsimY == 1||...
很容易理解嘛,就是只能走到邻近的一个格子的限制嘛。
士
下面是“士”这个类里的重写的setLocation
方法:
if(setsimX>2&&setsimX<6&&setsimY<3) {
if(setsimX==CurrentsimX-1&&setsimY==CurrentsimY+1 || setsimX==CurrentsimX+1&&setsimY==CurrentsimY+1
|| setsimX==CurrentsimX+1&&setsimY==CurrentsimY-1 || setsimX==CurrentsimX-1&&setsimY==CurrentsimY-1) {
Data.panelArray[CurrentsimX][CurrentsimY] = 0;
Data.panelArray[setsimX][setsimY] = 1;
this.CurrentsimX = setsimX;
this.CurrentsimY = setsimY;
Data.selectPiece = null;
Data.BorRRun = !Data.BorRRun;
this.move(Data.simnum2xy(setsimX),Data.simnum2xy(setsimY));
}
else {
this.move(Data.simnum2xy(CurrentsimX),Data.simnum2xy(CurrentsimY));
}
}
}
“士”和将有点类似,先设置一下不能出那个田字格。然后把它向左上左下右上右下的四种情况用“或”连起来就好。
象
下面是“象”这个类里的重写的setLocation
方法:
@Override
public void setLocation(int setsimX, int setsimY) {
// TODO Auto-generated method stub
if(setsimY<5 && Data.panelArray[(CurrentsimX+setsimX)/2][(CurrentsimY+setsimY)/2]==0) {//别象脚和不能过河
if(setsimX==CurrentsimX-2&&setsimY==CurrentsimY+2 || setsimX==CurrentsimX+2&&setsimY==CurrentsimY+2//象的走子规则
|| setsimX==CurrentsimX+2&&setsimY==CurrentsimY-2 || setsimX==CurrentsimX-2&&setsimY==CurrentsimY-2) {
Data.panelArray[CurrentsimX][CurrentsimY] = 0;
Data.panelArray[setsimX][setsimY] = 1;
this.CurrentsimX = setsimX;
this.CurrentsimY = setsimY;
Data.selectPiece = null;
Data.BorRRun = !Data.BorRRun;
this.move(Data.simnum2xy(setsimX),Data.simnum2xy(setsimY));
}
}
else {
this.move(Data.simnum2xy(CurrentsimX),Data.simnum2xy(CurrentsimY));
}
}
“象”不可以过河,先用setsimY<5
限制一下。再就是如果有别的棋子在“象”走的那个“田”子的中间的话,也是不可以的额,(我们叫塞象眼)。用Data.panelArray[(CurrentsimX+setsimX)/2][(CurrentsimY+setsimY)/2]==0
就可以限制了。这里的Data.panelArray二维数组上次说过是记录整个棋盘各个地方有没有子的,有的话,那个地方的值被设为1,无则为0。(CurrentsimX+setsimX)/2
就是“象”走的“田”求中间的那个地方的坐标额。再就是“象”走左上左下右上右下这几种情况,都列出来就好。
马
下面是“马”这个类里的重写的setLocation
方法:
@Override
public void setLocation(int setsimX, int setsimY) {
// TODO Auto-generated method stub
if(((setsimX-CurrentsimX==2 || setsimX-CurrentsimX==-2) && Data.panelArray[(CurrentsimX+setsimX)/2][CurrentsimY]==0)
||((setsimY-CurrentsimY==2 || setsimY-CurrentsimY==-2) && Data.panelArray[CurrentsimX][(CurrentsimY+setsimY)/2]==0)) {
if(setsimX==CurrentsimX+1&&setsimY==CurrentsimY+2 || setsimX==CurrentsimX+2&&setsimY==CurrentsimY+1
|| setsimX==CurrentsimX-1&&setsimY==CurrentsimY-2 || setsimX==CurrentsimX-2&&setsimY==CurrentsimY-1
|| setsimX==CurrentsimX-1&&setsimY==CurrentsimY+2 || setsimX==CurrentsimX-2&&setsimY==CurrentsimY+1
|| setsimX==CurrentsimX+1&&setsimY==CurrentsimY-2 || setsimX==CurrentsimX+2&&setsimY==CurrentsimY-1) {
Data.panelArray[CurrentsimX][CurrentsimY] = 0;
Data.panelArray[setsimX][setsimY] = 1;
this.CurrentsimX = setsimX;
this.CurrentsimY = setsimY;
Data.selectPiece = null;
Data.BorRRun = !Data.BorRRun;
this.move(Data.simnum2xy(setsimX),Data.simnum2xy(setsimY));
}
}
else {
this.move(Data.simnum2xy(CurrentsimX),Data.simnum2xy(CurrentsimY));
}
}
本来因为觉得“马”可以过河,if里的限制应该可以简单点,但是好像不是这样的。外面的那一个if语句是别马腿(我就是这么叫的。。)的操作。分为横向走“日”和纵向走“日”的两种情况(setsimX-CurrentsimX==2 || setsimX-CurrentsimX==-2)
就是判断它是横向走“日” 。Data.panelArray[(CurrentsimX+setsimX)/2][CurrentsimY]==0
是判断“马腿”位置没有其他的棋子。
下面那个if语句是“马”的八种走子情况啦,可以自己数。感觉应该可以简化条件,太长了 。
车
下面是“车”这个类里的重写的setLocation
方法:
public void setLocation(int setsimX, int setsimY) {
// TODO Auto-generated method stub
int BRflagX = 0;
int BRflagY = 0;
if(setsimX < CurrentsimX)
for(int i=setsimX+1;i<CurrentsimX;i++)
BRflagX = Data.panelArray[i][CurrentsimY] + BRflagX;
else if(setsimX > CurrentsimX)
for(int i=CurrentsimX+1;i<setsimX;i++)
BRflagX = Data.panelArray[i][CurrentsimY] + BRflagX;
if(setsimY < CurrentsimY)
for(int i=setsimY+1;i<CurrentsimY;i++)
BRflagY = Data.panelArray[CurrentsimX][i] + BRflagY;
else if(setsimY > CurrentsimY)
for(int i=CurrentsimY+1;i<setsimY;i++)
BRflagY = Data.panelArray[CurrentsimX][i] + BRflagY;
if(setsimX==CurrentsimX&&BRflagY==0 || setsimY==CurrentsimY&&BRflagX==0 ) {
Data.panelArray[CurrentsimX][CurrentsimY] = 0;
Data.panelArray[setsimX][setsimY] = 1;
this.CurrentsimX = setsimX;
this.CurrentsimY = setsimY;
Data.selectPiece = null;
Data.BorRRun = !Data.BorRRun;
this.move(Data.simnum2xy(setsimX),Data.simnum2xy(setsimY));
}
else {
this.move(Data.simnum2xy(CurrentsimX),Data.simnum2xy(CurrentsimY));
}
}
这里“车”因为要判断走子起始位置和终点位置是否有其余的棋子,所以引入了BRflagX ``BRflagY
两个量,分别对应“车”横着走和竖着走两种情况。先判断下起始位置和终点位置哪个坐标大,然后for循环把对应的Data.panelArray
里面的数值加起来,如果中间没有其他棋子,BRflagX ``BRflagY
就会等于0的。有其他子它们则不等于0。接下来用if(setsimX==CurrentsimX&&BRflagY==0 || setsimY==CurrentsimY&&BRflagX==0 )
就既可以让“车”沿着直线走,又限制它在起点和终点有其他子的时候不可以走。下面的“炮”也有类似的限制。
炮
下面是“炮”这个类里的重写的setLocation
方法:
@Override
public void setLocation(int setsimX, int setsimY) {
// TODO Auto-generated method stub
int BRflagX = 0;
int BRflagY = 0;
if(setsimX < CurrentsimX)//跟车的走子规则判断差不多,但是吃子的时候有点区别中间要隔一个子嘛
for(int i=setsimX+1;i<CurrentsimX;i++)
BRflagX = Data.panelArray[i][CurrentsimY] + BRflagX;
else if(setsimX > CurrentsimX)
for(int i=CurrentsimX+1;i<setsimX;i++)
BRflagX = Data.panelArray[i][CurrentsimY] + BRflagX;
if(setsimY < CurrentsimY)
for(int i=setsimY+1;i<CurrentsimY;i++)
BRflagY = Data.panelArray[CurrentsimX][i] + BRflagY;
else if(setsimY > CurrentsimY)
for(int i=CurrentsimY+1;i<setsimY;i++)
BRflagY = Data.panelArray[CurrentsimX][i] + BRflagY;
if((setsimX==CurrentsimX&&BRflagY==1 || setsimY==CurrentsimY&&BRflagX==1)&& Data.panelArray[setsimX][setsimY]==1 ) {//中间隔一个子时进行吃子操作
Data.panelArray[CurrentsimX][CurrentsimY] = 0;
Data.panelArray[setsimX][setsimY] = 1;
this.CurrentsimX = setsimX;
this.CurrentsimY = setsimY;
Data.selectPiece = null;
Data.BorRRun = !Data.BorRRun;
this.move(Data.simnum2xy(setsimX),Data.simnum2xy(setsimY));
}
else if((setsimX==CurrentsimX&&BRflagY==0 || setsimY==CurrentsimY&&BRflagX==0) && Data.panelArray[setsimX][setsimY]==0) {//中间没有子时代表正常的走子,panelArray=0时代表setXY没有子
Data.panelArray[CurrentsimX][CurrentsimY] = 0;
Data.panelArray[setsimX][setsimY] = 1;
this.CurrentsimX = setsimX;
this.CurrentsimY = setsimY;
Data.selectPiece = null;
Data.BorRRun = !Data.BorRRun;
this.move(Data.simnum2xy(setsimX),Data.simnum2xy(setsimY));
}
else {
this.move(Data.simnum2xy(CurrentsimX),Data.simnum2xy(CurrentsimY));
}
}
这个“炮”应该算是最复杂的了。最前面BRflagX
和BRflagY
的操作与车一样。后面的分成了吃子和正常走子的两部分。因为吃敌方的子时,也只是把自己的子挪到了敌方子的位置上,然后把敌方的子设置成 不可见。所以吃子的时候也是会用到setLocation
的方法的。f((setsimX==CurrentsimX&&BRflagY==1 || setsimY==CurrentsimY&&BRflagX==1)&& Data.panelArray[setsimX][setsimY]==1 )
中BRflagX==1
就是判断“炮”走的起始位置和终点位置相隔一个子,而Data.panelArray[setsimX][setsimY]==1
是判断终点位置是有棋子的,不加这一句的话,炮可以直接隔着一个子跳到对面的地方。后面的正常的走子情况就是和“车”基本上一样了。