java swing实战——baba is you(游戏规则判定)
5. 游戏规则判定
本游戏的创意性之一就在于规则的改变,玩家的行动会影响之后的胜利条件、推动规则等,在之前的编写中,我们默认规则baba is you、flag is win、wall is stop, rock is push.现在,我们编写改变规则的逻辑,这一部分的处理代码位于GameText.
5.1 who is you
最重要的判定是谁可以移动,当然移动的对象可以有多个,在GameText采用如下的方法:
/**
* 判定 who is you
* 即从上到下,从左到右的组合
* 如果存在组合放置于list中,反之,返回null
* @return
*/
public List<String> whoIsYou() {
return null;
}
在GameFrame中调用:
private void peopleMove(KeyEvent e) {
String stop = PeopleLocation.WALL; // 默认wall is stop
String push = PeopleLocation.ROCK; // 默认rock is push
String win = PeopleLocation.FLAG; // 默认flag is win
List<String> youList = gameText.whoIsYou();
if (youList == null) {
System.out.println("游戏失败");
return;
}
/**
* 遍历循环(添加GamePeople的getPeopleList()方法)
* 寻找可以移动的角色
*/
List<People> peopleList = gamePeople.getPeopleList();
for (int i = 0; i < peopleList.size(); i++) {
People people = peopleList.get(i);
for (int j = 0; j < youList.size(); j++) { // 遍历可控制的角色
String you = youList.get(j);
if(you.equalsIgnoreCase(people.getName())) {
switch (e.getKeyCode()) {
case KeyEvent.VK_UP:
gamePeople.move(1,people,stop,push, win,gameText);
break;
case KeyEvent.VK_DOWN:
gamePeople.move(-1,people,stop,push, win,gameText);
break;
case KeyEvent.VK_RIGHT:
gamePeople.move(2,people,stop,push, win,gameText);
break;
case KeyEvent.VK_LEFT:
gamePeople.move(-2,people,stop,push, win,gameText);
break;
}
}
}
}
}
GameText的判定逻辑如下:
-
找到textList中的you块
-
横向判定
- you的左边第一块是is
- you的左边第二块是可移动的角色
-
纵向判定
- you的上面第一块是is
- you的上面第二块是可移动角色
代码如下:
/**
* 判定 who is you
* 即从上到下,从左到右的组合
* 如果存在组合放置于list中,反之,返回null
* @return
*/
public List<String> whoIsYou() {
// 返回结果
List<String> res = new ArrayList<>();
//找到textList中的you块
Text you = null;
for (int i = 0; i < textList.size(); i++) {
if (textList.get(i).getRule().equalsIgnoreCase(TextLocation.YOU)) {
you = textList.get(i);
break;
}
}
// 横向判定
//- you的左边第一块是is
boolean flagL = false;
for (int i = 0; i < textList.size(); i++) {
Text text = textList.get(i);
if (you.getX() - you.getWidth() == text.getX() && you.getY() == text.getY()) {
if (text.getRule().equalsIgnoreCase(TextLocation.IS)) {
flagL = true; // 左边第一块是is
break;
} else {
break; // 左边第一块不是is
}
}
}
//- you的左边第二块是可移动的角色
if (flagL) {
for (int i = 0; i < textList.size(); i++) {
Text text = textList.get(i);
if (you.getX() - 2 * you.getWidth() == text.getX() && you.getY() == text.getY()) {
switch (text.getRule()) {
case TextLocation.BABA:
res.add(PeopleLocation.BABA);
break;
case TextLocation.FLAG:
res.add(PeopleLocation.FLAG);
break;
case TextLocation.ROCK:
res.add(PeopleLocation.ROCK);
break;
case TextLocation.WALL:
res.add(PeopleLocation.WALL);
break;
default:
break;
}
}
}
}
// 纵向判定
//- you的上边第一块是is
boolean flagU = false;
for (int i = 0; i < textList.size(); i++) {
Text text = textList.get(i);
if (you.getX() == text.getX() && you.getY() - you.getHeight() == text.getY()) {
if (text.getRule().equalsIgnoreCase(TextLocation.IS)) {
flagU = true; // 上边第一块是is
break;
} else {
break; // 上边第一块不是is
}
}
}
//- you的上边第二块是可移动的角色
if (flagU) {
for (int i = 0; i < textList.size(); i++) {
Text text = textList.get(i);
if (you.getX() == text.getX() && you.getY() - 2 * you.getHeight() == text.getY()) {
switch (text.getRule()) {
case TextLocation.BABA:
res.add(PeopleLocation.BABA);
break;
case TextLocation.FLAG:
res.add(PeopleLocation.FLAG);
break;
case TextLocation.ROCK:
res.add(PeopleLocation.ROCK);
break;
case TextLocation.WALL:
res.add(PeopleLocation.WALL);
break;
default:
break;
}
}
}
}
if (res.size() > 0) return res;
return null;
}
至此,我们改变角色规则,当然,此时wall is you由于stop的默认规则,暂时不能移动
5.2 who is stopwho is winwho is push
完成了上述逻辑,我们很容易的复制修改出对应的代码,首先,我们提取条件判定的公共代码
/**
* 公共代码
* @param rule
* @return
*/
private List<String> whoIs(String rule) {
// 返回结果
List<String> res = new ArrayList<>();
//找到textList中的you块
Text you = null;
for (int i = 0; i < textList.size(); i++) {
if (textList.get(i).getRule().equalsIgnoreCase(rule)) {
you = textList.get(i);
break;
}
}
// 横向判定
//- you的左边第一块是is
boolean flagL = false;
for (int i = 0; i < textList.size(); i++) {
Text text = textList.get(i);
if (you.getX() - you.getWidth() == text.getX() && you.getY() == text.getY()) {
if (text.getRule().equalsIgnoreCase(TextLocation.IS)) {
flagL = true; // 左边第一块是is
break;
} else {
break; // 左边第一块不是is
}
}
}
//- you的左边第二块是可移动的角色
if (flagL) {
for (int i = 0; i < textList.size(); i++) {
Text text = textList.get(i);
if (you.getX() - 2 * you.getWidth() == text.getX() && you.getY() == text.getY()) {
switch (text.getRule()) {
case TextLocation.BABA:
res.add(PeopleLocation.BABA);
break;
case TextLocation.FLAG:
res.add(PeopleLocation.FLAG);
break;
case TextLocation.ROCK:
res.add(PeopleLocation.ROCK);
break;
case TextLocation.WALL:
res.add(PeopleLocation.WALL);
break;
default:
break;
}
}
}
}
// 纵向判定
//- you的上边第一块是is
boolean flagU = false;
for (int i = 0; i < textList.size(); i++) {
Text text = textList.get(i);
if (you.getX() == text.getX() && you.getY() - you.getHeight() == text.getY()) {
if (text.getRule().equalsIgnoreCase(TextLocation.IS)) {
flagU = true; // 上边第一块是is
break;
} else {
break; // 上边第一块不是is
}
}
}
//- you的上边第二块是可移动的角色
if (flagU) {
for (int i = 0; i < textList.size(); i++) {
Text text = textList.get(i);
if (you.getX() == text.getX() && you.getY() - 2 * you.getHeight() == text.getY()) {
switch (text.getRule()) {
case TextLocation.BABA:
res.add(PeopleLocation.BABA);
break;
case TextLocation.FLAG:
res.add(PeopleLocation.FLAG);
break;
case TextLocation.ROCK:
res.add(PeopleLocation.ROCK);
break;
case TextLocation.WALL:
res.add(PeopleLocation.WALL);
break;
default:
break;
}
}
}
}
if (res.size() > 0) return res;
return null;
}
下面便是规则判定的4个函数
/**
* 判定 who is you
* 即从上到下,从左到右的组合
* 如果存在组合放置于list中,反之,返回null
* @return
*/
public List<String> whoIsYou() {
return whoIs(TextLocation.YOU);
}
public List<String> whoIsStop() {
return whoIs(TextLocation.STOP);
}
public List<String> whoIsPush() {
return whoIs(TextLocation.PUSH);
}
public List<String> whoIsWin() {
return whoIs(TextLocation.WIN);
}
5.3 优化move逻辑
由于我们的判定都可以有横向两种形式,而之前我们只是假定了一个变量,因此,这里我们重构代码为集合类型。
GameFrame中的变化:
private void peopleMove(KeyEvent e) {
// String stop = PeopleLocation.WALL; // 默认wall is stop
// String push = PeopleLocation.ROCK; // 默认rock is push
// String win = PeopleLocation.FLAG; // 默认flag is win
List<String> stop = gameText.whoIsStop();
List<String> push = gameText.whoIsPush();
List<String> win = gameText.whoIsWin();
List<String> youList = gameText.whoIsYou();
if (youList == null) {
System.out.println("游戏失败");
return;
}
/**
* 遍历循环(添加GamePeople的getPeopleList()方法)
* 寻找可以移动的角色
*/
List<People> peopleList = gamePeople.getPeopleList();
for (int i = 0; i < peopleList.size(); i++) {
People people = peopleList.get(i);
for (int j = 0; j < youList.size(); j++) { // 遍历可控制的角色
String you = youList.get(j);
if(you.equalsIgnoreCase(people.getName())) {
switch (e.getKeyCode()) {
case KeyEvent.VK_UP:
gamePeople.move(1,people,stop,push, win,gameText);
break;
case KeyEvent.VK_DOWN:
gamePeople.move(-1,people,stop,push, win,gameText);
break;
case KeyEvent.VK_RIGHT:
gamePeople.move(2,people,stop,push, win,gameText);
break;
case KeyEvent.VK_LEFT:
gamePeople.move(-2,people,stop,push, win,gameText);
break;
}
}
}
}
}
GamePeople的变化:
public void move(int direction, Block you, List<String> stop, List<String> push, List<String> win , GameText gameText) {
/**
* 先移动
*/
switch (direction) {
case 1:
you.up = true;
you.down = you.right = you.left = false;
you.setY(you.getY() - 24);//y -= 24;
break;
case -1:
you.down = true;
you.up = you.right = you.left = false;
you.setY(you.getY() + 24);//y += 24;
break;
case 2:
you.right = true;
you.up = you.down = you.left = false;
you.setX(you.getX() + 24);//x += 24;
break;
case -2:
you.left = true;
you.up = you.right = you.down = false;
you.setX(you.getX() - 24);//x -= 24;
break;
}
/**
* stop逻辑
*/
if (stop != null && stop.size() > 0) {
for (int i = 0; i < stop.size(); i++) {
String s = stop.get(i);
List<People> stopList = this.peopleMap.get(s);
for (int j = 0; j < stopList.size(); j++) { // 遍历所有不可动的对象判断
People stopPeople = stopList.get(j);
if(stopPeople.getX() == you.getX() && stopPeople.getY() == you.getY()) { // 发生碰撞
// 反弹
if (you.up) {
you.setY(you.getY() + 24);//y += 24;
} else if (you.down) {
you.setY(you.getY() - 24);//y -= 24;
} else if (you.right) {
you.setX(you.getX() - 24);//x -= 24;
} else if (you.left) {
you.setX(you.getX() + 24);//x += 24;
}
return;// 优化
}
}
}
}
/**
* push逻辑
*/
if (push != null && push.size() > 0) {
for (int i = 0; i < push.size(); i++) {
String s = push.get(i);
List<People> pushList = this.peopleMap.get(s);
for (int j = 0; j < pushList.size(); j++) { // 遍历所有Push的对象判断
People pushPeople = pushList.get(j);
if (pushPeople == you) continue;
if (pushPeople.getX() == you.getX() && pushPeople.getY() == you.getY()) { // 发生碰撞
move(direction, pushPeople, stop, push,win, gameText);
}
}
}
}
/**
* text推动逻辑
*/
List<Text> textList = gameText.getTextList();
for (int i = 0; i < textList.size(); i++) {
Text text = textList.get(i);
if(text == you) continue;
if(text.getX() == you.getX() && text.getY() == you.getY()) {
move(direction, text, stop, push,win, gameText);
return;
}
}
/**
* win逻辑
*/
if(win != null && win.size() > 0) {
for (int i = 0; i < win.size(); i++) {
String s = win.get(i);
List<People> winList = this.peopleMap.get(s);
for (int j = 0; j < winList.size(); j++) {
People winPeople = winList.get(j);
if(winPeople.getX() == you.getX() && winPeople.getY() == you.getY()) {
System.out.println("胜利了");
return;
}
}
}
}
}
至此,我们完成了游戏规则判定的逻辑,我们游戏的所有逻辑基本完成(此外,游戏还有flag is baba等的角色切换逻辑,这个我们之后编写),下面我们首先进行地图位置坐标的优化。
本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
THE END
二维码