Reputation: 7
I want to try to evaluate the winning state in the tic-tac-toe below game.
So what I end up doing normally is trying to use the getText()
method on the buttons in a for loop and evaluate for example if cells[0][i].getText()
is equal to cells[0][1]
and cells[0][2]
.
Then I see if cells[0][2]
aren't blank (so not equal to " "
) then that would finish the first row.
The problem is that this doesn't work and I would appreciate if someone provides me with a better alternative to this approach, if there is any.
package tictactoe;
import java.awt.Dimension;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JFrame;
public class TicTacToe implements ActionListener
{
JFrame window;
static JButton[][]cells=new JButton[3][3];
boolean playing;
char turn='X';
public TicTacToe()
{
//SETS UP THE WINDOW
window=new JFrame("TicTacToe");
window.setSize(new Dimension(400,400));
window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
window.setResizable(false);
//**********************//
createCells();
window.setVisible(true);
}
public static void main(String[] args)
{
new TicTacToe();
}
private void createCells()
{
window.setLayout(new GridLayout(3,3));
for(int i=0;i<cells.length;i++)
{
for(int j=0;j<cells.length;j++)
{
cells[i][j]=new JButton();
cells[i][j].addActionListener(this);
window.add(cells[i][j]);
}
}
}
@Override
public void actionPerformed(ActionEvent e)
{
playing=true;
JButton _buttonPressed=(JButton)e.getSource();
while(playing)
{
if(turn=='X')
{
_buttonPressed.setText("X");
_buttonPressed.setEnabled(false);
turn='O';
}
else
{
_buttonPressed.setText("O");
_buttonPressed.setEnabled(false);
}
}
}
}
Upvotes: 0
Views: 652
Reputation: 71
Good approach to finding the winner of Tic-Tac-Toe:
You only ever need to check if the last move by a user caused the board to go into a winning state. You also know that the user placed either an X or an O at position board[x][y].
it will look something like this:
public bool gameOver(cells, x, y)
if cells[0,y] == cells[1,y] == cells[2,y]
//win on vertical line
if cells[x,0] == cells[x,1] == cells[x,2]
//win on horizontal line
if x == y and cells[0,0] == cells[1,1] == cells[2,2]
//win on diagonal
if x == y and cells[0,2] == cells[1,1] == cells[2,0]
//win on other diagonal
return false
Upvotes: 0
Reputation: 191743
I'm not seeing where you are evaluating the winning state, but try removing the infinite loop from the click listener.
@Override
public void actionPerformed(ActionEvent e) {
JButton _buttonPressed = (JButton) e.getSource();
_buttonPressed.setText("" + turn);
_buttonPressed.setEnabled(false);
if (turn == 'X') {
turn = 'O';
} else {
turn = 'X';
}
}
And these are mostly suggestions, so feel free to ignore this, if you wish.
Make the TicTacToe class be a JFrame
itself - no need to instantiate one.
public class TicTacToe extends JFrame implements ActionListener {
private JButton[][] cells = new JButton[3][3];
private char turn = 'X';
private boolean playing;
public TicTacToe() {
setTitle("TicTacToe");
setSize(new Dimension(400, 400));
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setResizable(false);
createCells();
pack();
}
Secondly, the recommended way to start a Swing app, is on its own thread like so
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
TicTacToe ttt = new TicTacToe();
ttt.setVisible(true);
}
});
}
Upvotes: 2