Set fields and variables to final when possible
This commit is contained in:
parent
431924adb6
commit
c70ec31da6
@ -1,117 +1,117 @@
|
||||
package jtictactoe;
|
||||
|
||||
import java.awt.Dimension;
|
||||
import java.awt.Graphics;
|
||||
import java.awt.Point;
|
||||
import java.awt.event.MouseAdapter;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.awt.image.BufferedImage;
|
||||
import javax.swing.JPanel;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author aNNiMON
|
||||
*/
|
||||
public class GameBoard extends JPanel {
|
||||
private static final int CELL_SIZE = 150;
|
||||
private static final int OFFSET = 15;
|
||||
|
||||
private BufferedImage strikedHor, strikedVer, strikedDiag, strikedDiagRev;
|
||||
private BufferedImage background, figureX, figureO;
|
||||
private Table table;
|
||||
private TitlePanel title;
|
||||
private int imgWidth, imgHeight;
|
||||
|
||||
public GameBoard(TitlePanel title) {
|
||||
this.title = title;
|
||||
initImages();
|
||||
imgWidth = background.getWidth();
|
||||
imgHeight = background.getHeight();
|
||||
setPreferredSize( new Dimension(imgWidth, imgHeight) );
|
||||
addMouseListener(new MouseAdapter() {
|
||||
@Override
|
||||
public void mousePressed(MouseEvent evt) {
|
||||
gameBoardMousePressed(evt);
|
||||
}
|
||||
});
|
||||
table = new Table();
|
||||
table.resetTable();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void paintComponent(Graphics g) {
|
||||
super.paintComponent(g);
|
||||
g.drawImage(background, 0, 0, null);
|
||||
drawTable(g);
|
||||
drawStrike(g);
|
||||
}
|
||||
|
||||
private void drawTable(Graphics g) {
|
||||
Figure[][] figures = table.getFiguresArray();
|
||||
for (int i = 0; i < figures.length; i++) {
|
||||
for (int j = 0; j < figures[0].length; j++) {
|
||||
char figure = figures[i][j].getFigure();
|
||||
if (figure != Figure.EMPTY) {
|
||||
BufferedImage image = ( (figure == Figure.X) ? figureX : figureO );
|
||||
int x = j * CELL_SIZE + OFFSET + (CELL_SIZE - image.getWidth()) / 2;
|
||||
int y = i * CELL_SIZE + OFFSET + (CELL_SIZE - image.getHeight()) / 2;
|
||||
g.drawImage(image, x, y, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void drawStrike(Graphics g) {
|
||||
int strikeMode = table.getStrikedMode();
|
||||
if (strikeMode != Table.MODE_NOT_STRIKED) {
|
||||
final int strikedSize = strikedHor.getHeight();
|
||||
int coord = OFFSET + (CELL_SIZE - strikedSize) / 2;
|
||||
int strikePos = strikeMode & 0x03;
|
||||
|
||||
if ( (strikeMode & Table.MODE_STRIKE_DIAGONAL) != 0 ) {
|
||||
g.drawImage(strikedDiag, coord, coord, null);
|
||||
} else if ( (strikeMode & Table.MODE_STRIKE_DIAGONAL_REVERSE) != 0 ) {
|
||||
g.drawImage(strikedDiagRev, coord - OFFSET / 2, coord - OFFSET / 2, null);
|
||||
} else if ( (strikeMode & Table.MODE_STRIKE_HORIZONTAL) != 0 ) {
|
||||
g.drawImage(strikedHor, coord, coord + strikePos * CELL_SIZE, null);
|
||||
} else if ( (strikeMode & Table.MODE_STRIKE_VERTICAL) != 0 ) {
|
||||
g.drawImage(strikedVer, coord + strikePos * CELL_SIZE, coord, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void gameBoardMousePressed(MouseEvent evt) {
|
||||
Point id = convertToID( evt.getPoint() );
|
||||
//table.computerMove();
|
||||
table.setFigure(id.x, id.y);
|
||||
|
||||
if (table.getStrikedMode() == Table.MODE_NOT_STRIKED) title.setMessage("");
|
||||
|
||||
if (!table.hasMoreMoves()) {
|
||||
char winner = table.checkWinner();
|
||||
if (winner != Figure.EMPTY) {
|
||||
int winX = (winner == Figure.X) ? 1 : 0;
|
||||
title.updateWin(winX, 1 - winX);
|
||||
title.setMessage(winner + " is win");
|
||||
} else title.setMessage("Drow");
|
||||
}
|
||||
repaint();
|
||||
}
|
||||
|
||||
private void initImages() {
|
||||
background = Util.getImage("/res/table_bg.jpg");
|
||||
figureX = Util.getImage("/res/x.png");
|
||||
figureO = Util.getImage("/res/o.png");
|
||||
strikedHor = Util.getImage("/res/striked.png");
|
||||
strikedVer = Util.getImage("/res/striked_ver.png");
|
||||
strikedDiag = Util.getImage("/res/striked_diagonal.png");
|
||||
strikedDiagRev = Util.getImage("/res/striked_diagonal_rev.png");
|
||||
}
|
||||
|
||||
private Point convertToID(Point point) {
|
||||
point.x /= imgWidth / 3;
|
||||
point.y /= imgHeight / 3;
|
||||
|
||||
return point;
|
||||
}
|
||||
}
|
||||
package jtictactoe;
|
||||
|
||||
import java.awt.Dimension;
|
||||
import java.awt.Graphics;
|
||||
import java.awt.Point;
|
||||
import java.awt.event.MouseAdapter;
|
||||
import java.awt.event.MouseEvent;
|
||||
import java.awt.image.BufferedImage;
|
||||
import javax.swing.JPanel;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author aNNiMON
|
||||
*/
|
||||
public class GameBoard extends JPanel {
|
||||
private static final int CELL_SIZE = 150;
|
||||
private static final int OFFSET = 15;
|
||||
|
||||
private BufferedImage strikedHor, strikedVer, strikedDiag, strikedDiagRev;
|
||||
private BufferedImage background, figureX, figureO;
|
||||
private final Table table;
|
||||
private final TitlePanel title;
|
||||
private final int imgWidth, imgHeight;
|
||||
|
||||
public GameBoard(TitlePanel title) {
|
||||
this.title = title;
|
||||
initImages();
|
||||
imgWidth = background.getWidth();
|
||||
imgHeight = background.getHeight();
|
||||
setPreferredSize( new Dimension(imgWidth, imgHeight) );
|
||||
addMouseListener(new MouseAdapter() {
|
||||
@Override
|
||||
public void mousePressed(MouseEvent evt) {
|
||||
gameBoardMousePressed(evt);
|
||||
}
|
||||
});
|
||||
table = new Table();
|
||||
table.resetTable();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void paintComponent(Graphics g) {
|
||||
super.paintComponent(g);
|
||||
g.drawImage(background, 0, 0, null);
|
||||
drawTable(g);
|
||||
drawStrike(g);
|
||||
}
|
||||
|
||||
private void drawTable(Graphics g) {
|
||||
final Figure[][] figures = table.getFiguresArray();
|
||||
for (int i = 0; i < figures.length; i++) {
|
||||
for (int j = 0; j < figures[0].length; j++) {
|
||||
final char figure = figures[i][j].getFigure();
|
||||
if (figure != Figure.EMPTY) {
|
||||
BufferedImage image = ( (figure == Figure.X) ? figureX : figureO );
|
||||
int x = j * CELL_SIZE + OFFSET + (CELL_SIZE - image.getWidth()) / 2;
|
||||
int y = i * CELL_SIZE + OFFSET + (CELL_SIZE - image.getHeight()) / 2;
|
||||
g.drawImage(image, x, y, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void drawStrike(Graphics g) {
|
||||
final int strikeMode = table.getStrikedMode();
|
||||
if (strikeMode != Table.MODE_NOT_STRIKED) {
|
||||
final int strikedSize = strikedHor.getHeight();
|
||||
final int coord = OFFSET + (CELL_SIZE - strikedSize) / 2;
|
||||
final int strikePos = strikeMode & 0x03;
|
||||
|
||||
if ( (strikeMode & Table.MODE_STRIKE_DIAGONAL) != 0 ) {
|
||||
g.drawImage(strikedDiag, coord, coord, null);
|
||||
} else if ( (strikeMode & Table.MODE_STRIKE_DIAGONAL_REVERSE) != 0 ) {
|
||||
g.drawImage(strikedDiagRev, coord - OFFSET / 2, coord - OFFSET / 2, null);
|
||||
} else if ( (strikeMode & Table.MODE_STRIKE_HORIZONTAL) != 0 ) {
|
||||
g.drawImage(strikedHor, coord, coord + strikePos * CELL_SIZE, null);
|
||||
} else if ( (strikeMode & Table.MODE_STRIKE_VERTICAL) != 0 ) {
|
||||
g.drawImage(strikedVer, coord + strikePos * CELL_SIZE, coord, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void gameBoardMousePressed(MouseEvent evt) {
|
||||
final Point id = convertToID( evt.getPoint() );
|
||||
//table.computerMove();
|
||||
table.setFigure(id.x, id.y);
|
||||
|
||||
if (table.getStrikedMode() == Table.MODE_NOT_STRIKED) title.setMessage("");
|
||||
|
||||
if (!table.hasMoreMoves()) {
|
||||
final char winner = table.checkWinner();
|
||||
if (winner != Figure.EMPTY) {
|
||||
final int winX = (winner == Figure.X) ? 1 : 0;
|
||||
title.updateWin(winX, 1 - winX);
|
||||
title.setMessage(winner + " is win");
|
||||
} else title.setMessage("Drow");
|
||||
}
|
||||
repaint();
|
||||
}
|
||||
|
||||
private void initImages() {
|
||||
background = Util.getImage("/res/table_bg.jpg");
|
||||
figureX = Util.getImage("/res/x.png");
|
||||
figureO = Util.getImage("/res/o.png");
|
||||
strikedHor = Util.getImage("/res/striked.png");
|
||||
strikedVer = Util.getImage("/res/striked_ver.png");
|
||||
strikedDiag = Util.getImage("/res/striked_diagonal.png");
|
||||
strikedDiagRev = Util.getImage("/res/striked_diagonal_rev.png");
|
||||
}
|
||||
|
||||
private Point convertToID(Point point) {
|
||||
point.x /= imgWidth / 3;
|
||||
point.y /= imgHeight / 3;
|
||||
|
||||
return point;
|
||||
}
|
||||
}
|
||||
|
@ -1,32 +1,32 @@
|
||||
package jtictactoe;
|
||||
|
||||
import java.awt.BorderLayout;
|
||||
import javax.swing.JFrame;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author aNNiMON
|
||||
*/
|
||||
public class Main extends JFrame {
|
||||
|
||||
public static void main(String[] args) {
|
||||
new Main().setVisible(true);
|
||||
|
||||
}
|
||||
|
||||
public Main() {
|
||||
super("JTicTacToe");
|
||||
setResizable(false);
|
||||
setUndecorated(true);
|
||||
setAlwaysOnTop(true);
|
||||
setBounds(300, 120, 0, 0);
|
||||
setDefaultCloseOperation(EXIT_ON_CLOSE);
|
||||
setLayout(new BorderLayout(0, 0));
|
||||
|
||||
TitlePanel title = new TitlePanel(this);
|
||||
add(title, BorderLayout.NORTH);
|
||||
add(new GameBoard(title));
|
||||
|
||||
pack();
|
||||
}
|
||||
}
|
||||
package jtictactoe;
|
||||
|
||||
import java.awt.BorderLayout;
|
||||
import javax.swing.JFrame;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author aNNiMON
|
||||
*/
|
||||
public class Main extends JFrame {
|
||||
|
||||
public static void main(String[] args) {
|
||||
new Main().setVisible(true);
|
||||
|
||||
}
|
||||
|
||||
public Main() {
|
||||
super("JTicTacToe");
|
||||
setResizable(false);
|
||||
setUndecorated(true);
|
||||
setAlwaysOnTop(true);
|
||||
setBounds(300, 120, 0, 0);
|
||||
setDefaultCloseOperation(EXIT_ON_CLOSE);
|
||||
setLayout(new BorderLayout(0, 0));
|
||||
|
||||
final TitlePanel title = new TitlePanel(this);
|
||||
add(title, BorderLayout.NORTH);
|
||||
add(new GameBoard(title));
|
||||
|
||||
pack();
|
||||
}
|
||||
}
|
||||
|
@ -1,201 +1,201 @@
|
||||
package jtictactoe;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author aNNiMON
|
||||
*/
|
||||
public class Table {
|
||||
|
||||
public static final int
|
||||
MODE_NOT_STRIKED = 0,
|
||||
MODE_STRIKE_HORIZONTAL = 0x04,
|
||||
MODE_STRIKE_VERTICAL = 0x08,
|
||||
MODE_STRIKE_DIAGONAL = 0x10,
|
||||
MODE_STRIKE_DIAGONAL_REVERSE = 0x20;
|
||||
|
||||
private boolean nextMoveIsX;
|
||||
private Figure[][] table;
|
||||
private Random random;
|
||||
private int strikedMode;
|
||||
|
||||
public Table() {
|
||||
table = new Figure[3][3];
|
||||
random = new Random();
|
||||
}
|
||||
|
||||
public void resetTable() {
|
||||
for (int i = 0; i < table.length; i++) {
|
||||
for (int j = 0; j < table[0].length; j++) {
|
||||
table[i][j] = new Figure();
|
||||
}
|
||||
}
|
||||
strikedMode = MODE_NOT_STRIKED;
|
||||
nextMoveIsX = true;
|
||||
}
|
||||
|
||||
public int getStrikedMode() {
|
||||
return strikedMode;
|
||||
}
|
||||
|
||||
public Figure[][] getFiguresArray() {
|
||||
return table;
|
||||
}
|
||||
|
||||
public void setFigure(int x, int y) {
|
||||
if( (checkWinner() != Figure.EMPTY) || (!hasMoreMoves()) ) {
|
||||
resetTable();
|
||||
return;
|
||||
}
|
||||
|
||||
boolean xIsNorm = ( (0 <= x) && (x < 3) );
|
||||
boolean yIsNorm = ( (0 <= y) && (y < 3) );
|
||||
if (xIsNorm && yIsNorm && table[y][x].isEmpty()) {
|
||||
table[y][x].setFigure(nextMoveIsX ? Figure.X : Figure.O);
|
||||
nextMoveIsX = !nextMoveIsX;
|
||||
computerMove();
|
||||
}
|
||||
}
|
||||
|
||||
public void computerMove() {
|
||||
if( (checkWinner() != Figure.EMPTY) || (!hasMoreMoves()) ) {
|
||||
//resetTable();
|
||||
return;
|
||||
}
|
||||
|
||||
computerAI();
|
||||
nextMoveIsX = !nextMoveIsX;
|
||||
}
|
||||
|
||||
private void computerAI() {
|
||||
final Figure[][] array = new Figure[][] {
|
||||
// Horizontal check
|
||||
table[0],
|
||||
table[1],
|
||||
table[2],
|
||||
|
||||
// Vertical check
|
||||
{ table[0][0], table[1][0], table[2][0] },
|
||||
{ table[0][1], table[1][1], table[2][1] },
|
||||
{ table[0][2], table[1][2], table[2][2] },
|
||||
|
||||
// Diagonal check
|
||||
{ table[0][0], table[1][1], table[2][2] },
|
||||
{ table[0][2], table[1][1], table[2][0] }
|
||||
};
|
||||
char[] maybeWinnerArray = new char[array.length];
|
||||
// Calculate winning situations for computer (zeroes).
|
||||
for (int i = 0; i < array.length; i++) {
|
||||
Figure[] figures = array[i];
|
||||
char maybeWinner = maybeWinnerComboIs(figures);
|
||||
maybeWinnerArray[i] = maybeWinner;
|
||||
if (maybeWinner == Figure.O) {
|
||||
if (setCompFigure(figures)) return;
|
||||
}
|
||||
}
|
||||
// Calculate winning situations for the player (crosses).
|
||||
for (int i = 0; i < array.length; i++) {
|
||||
Figure[] figures = array[i];
|
||||
char maybeWinner = maybeWinnerArray[i];
|
||||
if (maybeWinner == Figure.X) {
|
||||
if (setCompFigure(figures)) return;
|
||||
}
|
||||
}
|
||||
|
||||
// Trying to put figure to the center.
|
||||
int x = 1, y = 1;
|
||||
if(!table[y][x].isEmpty() || (random.nextInt(5) <= 3) ) {
|
||||
// If it's busy, put to the corners.
|
||||
int count = 0;
|
||||
do {
|
||||
x = random.nextBoolean() ? 0 : 2;
|
||||
y = random.nextBoolean() ? 0 : 2;
|
||||
count++;
|
||||
} while ( (!table[y][x].isEmpty()) && (count < 10));
|
||||
|
||||
if (count > 9) {
|
||||
// Put to the remaining cells.
|
||||
int[][] pair = {{0, 1}, {1, 0}, {1, 2}, {2, 1}};
|
||||
count = 0;
|
||||
do {
|
||||
x = pair[random.nextInt(pair.length)][0];
|
||||
y = pair[random.nextInt(pair.length)][1];
|
||||
count++;
|
||||
} while ( (!table[y][x].isEmpty()) && (count < 10));
|
||||
}
|
||||
}
|
||||
table[y][x].setFigure(nextMoveIsX ? Figure.X : Figure.O);
|
||||
}
|
||||
|
||||
public char checkWinner() {
|
||||
// Horizontal check
|
||||
for (int y = 0; y < 3; y++) {
|
||||
if (isWinnerCombo(table[y][0], table[y][1], table[y][2])) {
|
||||
strikedMode = MODE_STRIKE_HORIZONTAL | y;
|
||||
return table[y][0].getFigure();
|
||||
}
|
||||
}
|
||||
// Vertical check
|
||||
for (int x = 0; x < 3; x++) {
|
||||
if (isWinnerCombo(table[0][x], table[1][x], table[2][x])) {
|
||||
strikedMode = MODE_STRIKE_VERTICAL | x;
|
||||
return table[0][x].getFigure();
|
||||
}
|
||||
}
|
||||
// Diagonal check
|
||||
if (isWinnerCombo(table[0][0], table[1][1], table[2][2])) {
|
||||
strikedMode = MODE_STRIKE_DIAGONAL;
|
||||
return table[0][0].getFigure();
|
||||
}
|
||||
if (isWinnerCombo(table[0][2], table[1][1], table[2][0])) {
|
||||
strikedMode = MODE_STRIKE_DIAGONAL_REVERSE;
|
||||
return table[0][2].getFigure();
|
||||
}
|
||||
// No winner
|
||||
return Figure.EMPTY;
|
||||
}
|
||||
|
||||
public boolean hasMoreMoves() {
|
||||
if (checkWinner() != Figure.EMPTY) return false;
|
||||
|
||||
int emptyFiguresCount = 0;
|
||||
for (int i = 0; i < table.length; i++) {
|
||||
for (int j = 0; j < table[0].length; j++) {
|
||||
if (table[i][j].isEmpty()) emptyFiguresCount++;
|
||||
}
|
||||
}
|
||||
|
||||
return (emptyFiguresCount != 0);
|
||||
}
|
||||
|
||||
private boolean isWinnerCombo(Figure f1, Figure f2, Figure f3) {
|
||||
if (f1.isEmpty()) return false;
|
||||
char figure = f1.getFigure();
|
||||
return ( (figure == f2.getFigure()) &&
|
||||
(figure == f3.getFigure()) );
|
||||
}
|
||||
|
||||
private char maybeWinnerComboIs(Figure[] array) {
|
||||
int numX = 0, numO = 0;
|
||||
for (int i = 0; i < array.length; i++) {
|
||||
if (!array[i].isEmpty()) {
|
||||
if (array[i].getFigure() == Figure.X) numX++;
|
||||
else numO++;
|
||||
}
|
||||
}
|
||||
if (numX == 2) return Figure.X;
|
||||
if (numO == 2) return Figure.O;
|
||||
return Figure.EMPTY;
|
||||
}
|
||||
|
||||
private boolean setCompFigure(Figure[] array) {
|
||||
for (int i = 0; i < array.length; i++) {
|
||||
if (array[i].isEmpty()) {
|
||||
array[i].setFigure(Figure.O);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
package jtictactoe;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author aNNiMON
|
||||
*/
|
||||
public class Table {
|
||||
|
||||
public static final int
|
||||
MODE_NOT_STRIKED = 0,
|
||||
MODE_STRIKE_HORIZONTAL = 0x04,
|
||||
MODE_STRIKE_VERTICAL = 0x08,
|
||||
MODE_STRIKE_DIAGONAL = 0x10,
|
||||
MODE_STRIKE_DIAGONAL_REVERSE = 0x20;
|
||||
|
||||
private final Figure[][] table;
|
||||
private final Random random;
|
||||
private int strikedMode;
|
||||
private boolean nextMoveIsX;
|
||||
|
||||
public Table() {
|
||||
table = new Figure[3][3];
|
||||
random = new Random();
|
||||
}
|
||||
|
||||
public void resetTable() {
|
||||
for (int i = 0; i < table.length; i++) {
|
||||
for (int j = 0; j < table[0].length; j++) {
|
||||
table[i][j] = new Figure();
|
||||
}
|
||||
}
|
||||
strikedMode = MODE_NOT_STRIKED;
|
||||
nextMoveIsX = true;
|
||||
}
|
||||
|
||||
public int getStrikedMode() {
|
||||
return strikedMode;
|
||||
}
|
||||
|
||||
public Figure[][] getFiguresArray() {
|
||||
return table;
|
||||
}
|
||||
|
||||
public void setFigure(int x, int y) {
|
||||
if( (checkWinner() != Figure.EMPTY) || (!hasMoreMoves()) ) {
|
||||
resetTable();
|
||||
return;
|
||||
}
|
||||
|
||||
boolean xIsNorm = ( (0 <= x) && (x < 3) );
|
||||
boolean yIsNorm = ( (0 <= y) && (y < 3) );
|
||||
if (xIsNorm && yIsNorm && table[y][x].isEmpty()) {
|
||||
table[y][x].setFigure(nextMoveIsX ? Figure.X : Figure.O);
|
||||
nextMoveIsX = !nextMoveIsX;
|
||||
computerMove();
|
||||
}
|
||||
}
|
||||
|
||||
public void computerMove() {
|
||||
if( (checkWinner() != Figure.EMPTY) || (!hasMoreMoves()) ) {
|
||||
//resetTable();
|
||||
return;
|
||||
}
|
||||
|
||||
computerAI();
|
||||
nextMoveIsX = !nextMoveIsX;
|
||||
}
|
||||
|
||||
private void computerAI() {
|
||||
final Figure[][] array = new Figure[][] {
|
||||
// Horizontal check
|
||||
table[0],
|
||||
table[1],
|
||||
table[2],
|
||||
|
||||
// Vertical check
|
||||
{ table[0][0], table[1][0], table[2][0] },
|
||||
{ table[0][1], table[1][1], table[2][1] },
|
||||
{ table[0][2], table[1][2], table[2][2] },
|
||||
|
||||
// Diagonal check
|
||||
{ table[0][0], table[1][1], table[2][2] },
|
||||
{ table[0][2], table[1][1], table[2][0] }
|
||||
};
|
||||
final char[] maybeWinnerArray = new char[array.length];
|
||||
// Calculate winning situations for computer (zeroes).
|
||||
for (int i = 0; i < array.length; i++) {
|
||||
Figure[] figures = array[i];
|
||||
char maybeWinner = maybeWinnerComboIs(figures);
|
||||
maybeWinnerArray[i] = maybeWinner;
|
||||
if (maybeWinner == Figure.O) {
|
||||
if (setCompFigure(figures)) return;
|
||||
}
|
||||
}
|
||||
// Calculate winning situations for the player (crosses).
|
||||
for (int i = 0; i < array.length; i++) {
|
||||
Figure[] figures = array[i];
|
||||
char maybeWinner = maybeWinnerArray[i];
|
||||
if (maybeWinner == Figure.X) {
|
||||
if (setCompFigure(figures)) return;
|
||||
}
|
||||
}
|
||||
|
||||
// Trying to put figure to the center.
|
||||
int x = 1, y = 1;
|
||||
if(!table[y][x].isEmpty() || (random.nextInt(5) <= 3) ) {
|
||||
// If it's busy, put to the corners.
|
||||
int count = 0;
|
||||
do {
|
||||
x = random.nextBoolean() ? 0 : 2;
|
||||
y = random.nextBoolean() ? 0 : 2;
|
||||
count++;
|
||||
} while ( (!table[y][x].isEmpty()) && (count < 10));
|
||||
|
||||
if (count > 9) {
|
||||
// Put to the remaining cells.
|
||||
int[][] pair = {{0, 1}, {1, 0}, {1, 2}, {2, 1}};
|
||||
count = 0;
|
||||
do {
|
||||
x = pair[random.nextInt(pair.length)][0];
|
||||
y = pair[random.nextInt(pair.length)][1];
|
||||
count++;
|
||||
} while ( (!table[y][x].isEmpty()) && (count < 10));
|
||||
}
|
||||
}
|
||||
table[y][x].setFigure(nextMoveIsX ? Figure.X : Figure.O);
|
||||
}
|
||||
|
||||
public char checkWinner() {
|
||||
// Horizontal check
|
||||
for (int y = 0; y < 3; y++) {
|
||||
if (isWinnerCombo(table[y][0], table[y][1], table[y][2])) {
|
||||
strikedMode = MODE_STRIKE_HORIZONTAL | y;
|
||||
return table[y][0].getFigure();
|
||||
}
|
||||
}
|
||||
// Vertical check
|
||||
for (int x = 0; x < 3; x++) {
|
||||
if (isWinnerCombo(table[0][x], table[1][x], table[2][x])) {
|
||||
strikedMode = MODE_STRIKE_VERTICAL | x;
|
||||
return table[0][x].getFigure();
|
||||
}
|
||||
}
|
||||
// Diagonal check
|
||||
if (isWinnerCombo(table[0][0], table[1][1], table[2][2])) {
|
||||
strikedMode = MODE_STRIKE_DIAGONAL;
|
||||
return table[0][0].getFigure();
|
||||
}
|
||||
if (isWinnerCombo(table[0][2], table[1][1], table[2][0])) {
|
||||
strikedMode = MODE_STRIKE_DIAGONAL_REVERSE;
|
||||
return table[0][2].getFigure();
|
||||
}
|
||||
// No winner
|
||||
return Figure.EMPTY;
|
||||
}
|
||||
|
||||
public boolean hasMoreMoves() {
|
||||
if (checkWinner() != Figure.EMPTY) return false;
|
||||
|
||||
int emptyFiguresCount = 0;
|
||||
for (int i = 0; i < table.length; i++) {
|
||||
for (int j = 0; j < table[0].length; j++) {
|
||||
if (table[i][j].isEmpty()) emptyFiguresCount++;
|
||||
}
|
||||
}
|
||||
|
||||
return (emptyFiguresCount != 0);
|
||||
}
|
||||
|
||||
private boolean isWinnerCombo(Figure f1, Figure f2, Figure f3) {
|
||||
if (f1.isEmpty()) return false;
|
||||
final char figure = f1.getFigure();
|
||||
return ( (figure == f2.getFigure()) &&
|
||||
(figure == f3.getFigure()) );
|
||||
}
|
||||
|
||||
private char maybeWinnerComboIs(Figure[] array) {
|
||||
int numX = 0, numO = 0;
|
||||
for (int i = 0; i < array.length; i++) {
|
||||
if (!array[i].isEmpty()) {
|
||||
if (array[i].getFigure() == Figure.X) numX++;
|
||||
else numO++;
|
||||
}
|
||||
}
|
||||
if (numX == 2) return Figure.X;
|
||||
if (numO == 2) return Figure.O;
|
||||
return Figure.EMPTY;
|
||||
}
|
||||
|
||||
private boolean setCompFigure(Figure[] array) {
|
||||
for (int i = 0; i < array.length; i++) {
|
||||
if (array[i].isEmpty()) {
|
||||
array[i].setFigure(Figure.O);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user