DroidFish: Let the human player claim a draw that involves specifying

but not playing a move that would lead to a 50move/3rep draw.
This commit is contained in:
Peter Osterlund 2016-01-06 22:04:11 +01:00
parent ad9c97a3ef
commit 88074f5327
2 changed files with 48 additions and 23 deletions

View File

@ -305,8 +305,23 @@ public class DroidChessController {
/** Make a move for a human player. */ /** Make a move for a human player. */
public final synchronized void makeHumanMove(Move m) { public final synchronized void makeHumanMove(Move m) {
if (humansTurn()) { if (!humansTurn())
return;
Position oldPos = new Position(game.currPos()); Position oldPos = new Position(game.currPos());
if (game.pendingDrawOffer) {
ArrayList<Move> moves = new MoveGen().legalMoves(oldPos);
for (Move m2 : moves) {
if (m2.equals(m)) {
if (findValidDrawClaim(TextIO.moveToUCIString(m))) {
stopPonder();
updateGUI();
gui.setSelection(-1);
return;
}
break;
}
}
}
if (doMove(m)) { if (doMove(m)) {
if (m.equals(ponderMove) && !gameMode.analysisMode() && if (m.equals(ponderMove) && !gameMode.analysisMode() &&
(computerPlayer.getSearchType() == SearchType.PONDER)) { (computerPlayer.getSearchType() == SearchType.PONDER)) {
@ -322,7 +337,6 @@ public class DroidChessController {
gui.setSelection(-1); gui.setSelection(-1);
} }
} }
}
/** Report promotion choice for incomplete move. /** Report promotion choice for incomplete move.
* @param choice 0=queen, 1=rook, 2=bishop, 3=knight. */ * @param choice 0=queen, 1=rook, 2=bishop, 3=knight. */
@ -365,7 +379,7 @@ public class DroidChessController {
/** Help human to claim a draw by trying to find and execute a valid draw claim. */ /** Help human to claim a draw by trying to find and execute a valid draw claim. */
public final synchronized boolean claimDrawIfPossible() { public final synchronized boolean claimDrawIfPossible() {
if (!findValidDrawClaim()) if (!findValidDrawClaim(""))
return false; return false;
updateGUI(); updateGUI();
return true; return true;
@ -1158,13 +1172,15 @@ public class DroidChessController {
gui.setAnimMove(sourcePos, move, forward); gui.setAnimMove(sourcePos, move, forward);
} }
private final boolean findValidDrawClaim() { private final boolean findValidDrawClaim(String ms) {
if (!ms.isEmpty())
ms = " " + ms;
if (game.getGameState() != GameState.ALIVE) return true; if (game.getGameState() != GameState.ALIVE) return true;
game.processString("draw accept"); game.tryClaimDraw("draw accept");
if (game.getGameState() != GameState.ALIVE) return true; if (game.getGameState() != GameState.ALIVE) return true;
game.processString("draw rep"); game.tryClaimDraw("draw rep" + ms);
if (game.getGameState() != GameState.ALIVE) return true; if (game.getGameState() != GameState.ALIVE) return true;
game.processString("draw 50"); game.tryClaimDraw("draw 50" + ms);
if (game.getGameState() != GameState.ALIVE) return true; if (game.getGameState() != GameState.ALIVE) return true;
return false; return false;
} }

View File

@ -39,7 +39,7 @@ public class Game {
/** If true, add new moves as mainline moves. */ /** If true, add new moves as mainline moves. */
private AddMoveBehavior addMoveBehavior; private AddMoveBehavior addMoveBehavior;
PgnToken.PgnTokenReceiver gameTextListener; private PgnToken.PgnTokenReceiver gameTextListener;
public Game(PgnToken.PgnTokenReceiver gameTextListener, TimeControlData tcData) { public Game(PgnToken.PgnTokenReceiver gameTextListener, TimeControlData tcData) {
this.gameTextListener = gameTextListener; this.gameTextListener = gameTextListener;
@ -140,7 +140,7 @@ public class Game {
return false; return false;
if (str.startsWith("draw ")) { if (str.startsWith("draw ")) {
String drawCmd = str.substring(str.indexOf(" ") + 1); String drawCmd = str.substring(str.indexOf(" ") + 1);
handleDrawCmd(drawCmd); handleDrawCmd(drawCmd, true);
return true; return true;
} else if (str.equals("resign")) { } else if (str.equals("resign")) {
addToGameTree(new Move(0, 0, 0), "resign"); addToGameTree(new Move(0, 0, 0), "resign");
@ -160,6 +160,15 @@ public class Game {
return true; return true;
} }
/** Try claim a draw using a command string. Does not play the move involved
* in the draw claim if the draw claim is invalid. */
public final void tryClaimDraw(String str) {
if (str.startsWith("draw ")) {
String drawCmd = str.substring(str.indexOf(" ") + 1);
handleDrawCmd(drawCmd, false);
}
}
private final void addToGameTree(Move m, String playerAction) { private final void addToGameTree(Move m, String playerAction) {
if (m.equals(new Move(0, 0, 0))) { // Don't create more than one game-ending move at a node if (m.equals(new Move(0, 0, 0))) { // Don't create more than one game-ending move at a node
List<Move> varMoves = tree.variations(); List<Move> varMoves = tree.variations();
@ -446,7 +455,7 @@ public class Game {
return new Pair<Position, ArrayList<Move>>(pos, mList); return new Pair<Position, ArrayList<Move>>(pos, mList);
} }
private final void handleDrawCmd(String drawCmd) { private final void handleDrawCmd(String drawCmd, boolean playDrawMove) {
Position pos = tree.currentPos; Position pos = tree.currentPos;
if (drawCmd.startsWith("rep") || drawCmd.startsWith("50")) { if (drawCmd.startsWith("rep") || drawCmd.startsWith("50")) {
boolean rep = drawCmd.startsWith("rep"); boolean rep = drawCmd.startsWith("rep");
@ -499,7 +508,7 @@ public class Game {
addToGameTree(new Move(0, 0, 0), playerAction); addToGameTree(new Move(0, 0, 0), playerAction);
} else { } else {
pendingDrawOffer = true; pendingDrawOffer = true;
if (m != null) { if (m != null && playDrawMove) {
processString(ms); processString(ms);
} }
} }