Implemented UCI handshake with engine

+ UCI game start in MenuBar
+ UCI game creation method in Game
- Fixed double game instance bug after starting a new game
+ Name and author parsing in UCIReceiver
This commit is contained in:
Kai S. K. Engelbart 2019-07-21 14:35:14 +02:00
parent bce35fc950
commit 77cf661f6f
7 changed files with 31 additions and 12 deletions

View File

@ -62,6 +62,14 @@ public class Game {
return new Game(players, boardPane);
}
public static Game createUCI(BoardPane boardPane, String enginePath) {
Map<Color, Player> players = new HashMap<>();
players.put(Color.WHITE, new NaturalPlayer(Color.WHITE, boardPane.getOverlayComponent()));
players.put(Color.BLACK, new UCIPlayer(Color.BLACK, enginePath));
return new Game(players, boardPane);
}
public void onMove(Player player, Move move) {
if (board.getPos(move).getColor() == player.color && board.attemptMove(move)) {
System.out.printf("%s: %s%n", player.color, move);

View File

@ -22,6 +22,7 @@ public class UCIPlayer extends Player {
handle = new UCIHandle(enginePath);
listener = new UCIPlayerListener();
handle.setListener(listener);
handle.start();
} catch (IOException ex) {
ex.printStackTrace();
}

View File

@ -28,25 +28,21 @@ class UCIPlayerListener implements UCIListener {
@Override
public void onUCIOk() {
// TODO Auto-generated method stub
}
@Override
public void onReadyOk() {
// TODO Auto-generated method stub
}
@Override
public void onBestMove(String move) {
// TODO Auto-generated method stub
}
@Override
public void onBestMove(String move, String ponderMove) {
// TODO Auto-generated method stub
}
@Override
@ -72,7 +68,6 @@ class UCIPlayerListener implements UCIListener {
@Override
public void onRegistrationOk() {
System.out.println("Registration ok");
}
@Override

View File

@ -17,13 +17,13 @@ public class UCIHandle {
public UCIHandle(String enginePath) throws IOException {
process = new ProcessBuilder(enginePath).start();
out = new PrintWriter(process.getOutputStream());
out = new PrintWriter(process.getOutputStream(), true);
receiver = new UCIReceiver(process.getInputStream());
}
public void start() {
uci();
new Thread(receiver).start();
uci();
}
/**

View File

@ -31,8 +31,9 @@ public class UCIReceiver implements Runnable {
@Override
public void run() {
try {
while (in.ready())
parse(in.readLine());
String line;
while (!Thread.currentThread().isInterrupted())
if ((line = in.readLine()) != null) parse(line);
} catch (IndexOutOfBoundsException ex) {
System.err.println("Too few arguments were provided!");
ex.printStackTrace();
@ -72,9 +73,9 @@ public class UCIReceiver implements Runnable {
}
private void parseId(String line) {
String param = line.substring(line.indexOf(' '));
String param = line.substring(0, line.indexOf(' '));
String arg = line.substring(param.length() + 1);
switch (line) {
switch (param) {
case "name":
listener.onIdName(arg);
break;

View File

@ -76,5 +76,8 @@ public class MainWindow {
public Game getGame() { return game; }
public void setGame(Game game) { this.game = game; }
public void setGame(Game game) {
if (this.game != null) this.game.disconnect();
this.game = game;
}
}

View File

@ -3,6 +3,7 @@ package dev.kske.chess.ui;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JOptionPane;
import dev.kske.chess.game.Game;
@ -32,6 +33,7 @@ public class MenuBar extends JMenuBar {
JMenuItem naturalMenuItem = new JMenuItem("Game against natural opponent");
JMenuItem aiMenuItem = new JMenuItem("Game against artificial opponent");
JMenuItem aiVsAiMenuItem = new JMenuItem("Watch AI vs. AI");
JMenuItem uciMenuItem = new JMenuItem("UCI");
naturalMenuItem.addActionListener((evt) -> startGame(Game.createNatural(boardPane)));
@ -44,9 +46,18 @@ public class MenuBar extends JMenuBar {
aiVsAiMenuItem.addActionListener((evt) -> startGame(Game.createAIVsAI(boardPane, 4, 3, -10, -10)));
uciMenuItem.addActionListener((evt) -> {
String enginePath = JOptionPane.showInputDialog(getParent(),
"Enter the path to a UCI-compatible chess engine:",
"Engine selection",
JOptionPane.QUESTION_MESSAGE);
if (enginePath != null) startGame(Game.createUCI(boardPane, enginePath));
});
gameMenu.add(naturalMenuItem);
gameMenu.add(aiMenuItem);
gameMenu.add(aiVsAiMenuItem);
gameMenu.add(uciMenuItem);
add(gameMenu);