10 Replies - 5858 Views - Last Post: 05 March 2014 - 08:09 PM Rate Topic: -----

#1 redVaryant  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 5
  • Joined: 28-February 14

N x N GUI TicTacToe game, winning algorithm?

Posted 28 February 2014 - 04:52 PM

Hello,

I'm relatively new to Java, and I've been programming for about 6 months.
I want to get better at Java programming, so I decided to build my own side project.

I'm building a N x N TicTacToe game with a GUI, in which the user can specify the board size, instead of having a standard 3 x 3 board. I am able to get everything to work, except for a winning algorithm.
I've limited the upper limit of N to 25, and the lower limit to 3.

Here's my idea on the winning algorithm:

1)Subdivide a N x N square into 3 x 3 squares. For example, a 4 x 4 square would have 4, 3 x 3 squares, and so on.

2)Check the 8 possible win configurations in that 3 x 3 square, and if there aren't any, move to the next sub-square.

I have a 2D array of JButtons, to display the GUI. Whenever the user clicks on a specific button, it's i,j value is mapped to the 2D array of Strings. After a game is finished, the String[][] has the Xs and Os in the respective positions that the user had clicked. I then check the String[][] for the wins.

Here's my code:


import java.awt.Color;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JTextField;

public class Board implements ActionListener
{
        private	boolean player1turn;
	private boolean player2turn;
	private int boardSize;
	private int count = 0;
	
	private String[][] gameData;
	private JButton[][] gameGrid;
	
	public Board()
	{
	    initialize();
	}
	
	/**
	 * Returns a boolean value of true or false of player 1's turn state.
	 */
	public boolean getPlayer1Turn()
	{
	    return player1turn;
	}
	
	/**  
	 * Sets player 1's turn to the specified turn boolean. 
	 */
	public void setPlayer1turn(boolean turn)
	{
	    player1turn = turn;
	}
	   
	/**
	 * Returns a boolean value of true or false of player 2's turn state.
	 */
	public boolean getPlayer2turn()
	{
	    return player2turn;
	}
	
	/**
	 * Returns the current size of the board.
	 */
	public int getBoardSize()
	{
	    return boardSize;
	}
	
	/**
	 * @param size The size of the board to be set when the user starts the game.
	 */
	public void setBoardSize(int size)
	{
	    boardSize = size;
	}
	   
	/**
	 * Sets player 2's turn to the specified turn boolean
	 */
	public void setPLayer2turn(boolean turn)
	{
	    player2turn = turn;
	}
	 
	/**
	 * Checks the board size that the user has submitted, and verifies that it is between 3 and 25, inclusive.
	 * @param size The size of the board.
	 */
	public boolean checkBoardSize(int size)
	{
		//checks that the size is between 3 and 25
		if(size < 3 || size > 25)
		{
			return false;
		}
		
		return true;
	}
	
	
	/**
	 * Declares the winner.
	 */
	public void checkWin()
	{
		for(int i = 0; i < getBoardSize(); i++)
		{
			for(int j = 0; j < getBoardSize(); j++)
			{
				//case 1: top row win
				if(gameData[i][j].equals("X") && gameData[i][j+1].equals("X") && gameData[i][j+2].equals("X") && j+2 < getBoardSize() && i+2 < getBoardSize())
				{
					JOptionPane.showMessageDialog(null, "Player 1 wins");
					break;
				}
		/*		
				//case 2: second row win
				if(gameData[i+1][j].equals("X") && gameData[i+1][j+1].equals("X") && gameData[i+1][j+2].equals("X") && j+2 < getBoardSize() && i+2 < getBoardSize())
				{
					JOptionPane.showMessageDialog(null, "Player 1 wins");
					break;
				}
				
				//case 3: last row win
				if(gameData[i+2][j].equals("X") && gameData[i+2][j+1].equals("X") && gameData[i+2][j+2].equals("X") && j+2 < getBoardSize() && i+2 < getBoardSize())
				{
					JOptionPane.showMessageDialog(null, "Player 1 wins");
					break;
				}
				
				//case 4: first column wins
				if(gameData[i][j].equals("X") && gameData[i+1][j].equals("X") && gameData[i+2][j].equals("X") && j+2 < getBoardSize() && i+2 < getBoardSize())
				{
					JOptionPane.showMessageDialog(null, "Player 1 wins");
					break;
				}
				
				//case 5: second column wins
				if(gameData[i][j+1].equals("X") && gameData[i+1][j+1].equals("X") && gameData[i+2][j+2].equals("X") && j+2 < getBoardSize() && i+2 < getBoardSize())
				{
					JOptionPane.showMessageDialog(null, "Player 1 wins");
					break;
				}
				
				//case 6: third column wins
				if(gameData[i][j+2].equals("X") && gameData[i+1][j+2].equals("X") && gameData[i+2][j+2].equals("X") && j+2 < getBoardSize() && i+2 < getBoardSize())
				{
					JOptionPane.showMessageDialog(null, "Player 1 wins");
					break;
				}
				
				//case 7: left diagonal wins
				if(gameData[i][j].equals("X") && gameData[i+1][j+1].equals("X") && gameData[i+2][j+2].equals("X") && j+2 < getBoardSize() && i+2 < getBoardSize())
				{
					JOptionPane.showMessageDialog(null, "Player 1 wins");
					break;
				}
				
				//case 8: right diagonal wins
				if(gameData[i][j+2].equals("X") && gameData[i+1][j+1].equals("X") && gameData[i+2][j].equals("X") && j+2 < getBoardSize() && i+2 < getBoardSize())
				{
					JOptionPane.showMessageDialog(null, "Player 1 wins");
					break;
				} */
			}
		}
	}

	/**
	 * Displays game introduction to the user.
	 */
	public void initialize()
	{
		final JFrame introFrame = new JFrame();
		JPanel introPanel = new JPanel();
		
		JLabel blank = new JLabel();
		JLabel blank2 = new JLabel();
		JLabel blank3 = new JLabel();
		JLabel blank4 = new JLabel();
		final JLabel blank5 = new JLabel();
		
		JButton playGame = new JButton("Play!");
		JLabel welcomeLabel = new JLabel("Tic Tac Toe");
		
		JLabel boardSize = new JLabel("Board Size");
		final JTextField boardInput = new JTextField();
		
		introPanel.add(blank);
		introPanel.add(welcomeLabel);
		introPanel.add(blank2);
		introPanel.add(boardSize);
		introPanel.add(boardInput);
		introPanel.add(blank3);
		introPanel.add(blank4);
		introPanel.add(playGame);
		introPanel.add(blank5);
		
		introPanel.setLayout(new GridLayout(3,3));
		
		introFrame.setTitle("Welcome to Tic Tac Toe!");
		introFrame.add(introPanel);
		introFrame.setVisible(true);
		introFrame.setSize(725,300);
		
		playGame.addActionListener(new ActionListener()
		{
			@Override
			public void actionPerformed(ActionEvent arg0)
			{
				String input = boardInput.getText();
				
				if(input.length() == 0)
				{
					blank5.setText("Input cannot be empty");
					return;
				}
				
				else
				{
					try
					{
						if((Integer) Integer.parseInt(input) instanceof Integer)
						{
							if(checkBoardSize(Integer.parseInt(boardInput.getText())))
							{
								setBoardSize(Integer.parseInt(boardInput.getText()));
								introFrame.setVisible(false);
								playGame();
							}
							
							else
							{
								blank5.setText("Size must be between 3 and 25");
								return;
							}
						}
					}
					
					catch(NumberFormatException e)
					{
						blank5.setText("Input must be a number");
						return;
					}
				}
			}
		});

		introFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
	}
	
	public void playGame()
	{
		JFrame gameframe = new JFrame();
		JPanel gamePanel = new JPanel();
		int size = getBoardSize();
		gameGrid = new JButton[size][size];
		gameData = new String[size][size];
		
		//game panel variables
		final int rows = size;
		final int columns = size;
		
		setPlayer1turn(true);
		
		for(int i = 0; i < rows; i++)
		{
			for(int j = 0; j < columns; j++)
			{
				gameGrid[i][j] = new JButton();
				gamePanel.add(gameGrid[i][j]);
				gameGrid[i][j].setBackground(Color.black);
				
				gameGrid[i][j].addActionListener(this);
				gameData[i][j] = " ";
			}
		}
		
		gamePanel.setLayout(new GridLayout(size, size));
		gameframe.add(gamePanel);
		gameframe.setVisible(true);
		gameframe.setSize(500, 500);
		  
		gameframe.setLayout(new GridLayout());
		gameframe.setTitle("Tic Tac Toe");
		gameframe.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
	}
	
   @Override
   public void actionPerformed(ActionEvent e) 
   {
	   final int rows = getBoardSize();
	   final int columns = getBoardSize();
	   JButton b = (JButton) e.getSource();
	   
	   for(int i = 0; i < rows; i++)
	   {
		   for(int j = 0; j < columns; j++)
		   {
			   if(b == gameGrid[i][j])
			   {
				   if(getPlayer1Turn())
				   {
					   if(count == (rows * columns) - 1)
					   {
						   ((JButton) e.getSource()).setText("X");
						   ((JButton) e.getSource()).setBackground(Color.red);
						   setPlayer1turn(false);
								
						   setPLayer2turn(false);
						   ((JButton) e.getSource()).setEnabled(false);
						   gameData[i][j] = "X";
						   
						   count++;
						   printGameData();
						   return;
					   }
					   
					   ((JButton) e.getSource()).setText("X");
					   ((JButton) e.getSource()).setBackground(Color.red);
					   setPlayer1turn(false);
					
					   setPLayer2turn(true);
					   ((JButton) e.getSource()).setEnabled(false);
					   gameData[i][j] = "X";
					   count++;
					   checkWin();
				   }
			   
			      //otherwise put o
			      else
			      {
			    	  ((JButton) e.getSource()).setText("O");
			    	  ((JButton) e.getSource()).setBackground(Color.blue);
			    	  setPlayer1turn(true);
					
			    	  setPLayer2turn(false);
			    	  ((JButton) e.getSource()).setEnabled(false);
			    	  gameData[i][j] =  "O";
			    	  count++;
			      }
			   }
		   }
	   }
   }
	
	public void printGameData()
	{
		for(int i = 0; i < this.getBoardSize(); i++)
		{
			for(int j = 0; j < this.getBoardSize(); j++)
			{
				System.out.print(gameData[i][j]);
			}	
			System.out.println();
		}
	}

   public static void main(String[] args)
   {
	   Board myBoard = new Board();
	   myBoard.printGameData();
   }
}


Any help would be greatly appreciated. Also, sorry about the length of this post, it's my first post to DIC.

Is This A Good Question/Topic? 0
  • +

Replies To: N x N GUI TicTacToe game, winning algorithm?

#2 x68zeppelin80x  Icon User is offline

  • D.I.C Addict

Reputation: 130
  • View blog
  • Posts: 576
  • Joined: 07-March 09

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 28 February 2014 - 06:11 PM

The way that I have done this is the following:

int n = 4;
char playerO = 'O'; // --> 79
char playerX = 'X'; // --> 88
char[][] grid = new char[n][n];



X | O | X
--+---+---
O | O | O <-- Check horizontal
--+---+---
O | X | X




You can treat each player as ASCII integer value for their respective character.

for each row:
    int total := 0
    for each col:
        total := total + grid[row][col]
    if total % playerO == 0:
        return "Player 'O' wins horizontally!"

This post has been edited by x68zeppelin80x: 28 February 2014 - 06:44 PM

Was This Post Helpful? 0
  • +
  • -

#3 CasiOo  Icon User is offline

  • D.I.C Lover
  • member icon

Reputation: 1575
  • View blog
  • Posts: 3,541
  • Joined: 05-April 11

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 28 February 2014 - 08:11 PM

Yes giving each player some int value and add each cell up could work in this case

I really really want to focus more on splitting the problem into smaller tasks for you
Hopefully the problem gets easier for you to solve in smaller parts
It would probably be a good idea to have a model for the match result
The match result could contain the winning player, tell if it was a tie, or if the match hasn't ended yet
public class MatchResult {
	private Player winner;
	private boolean tie;
	
	public MatchResult setWinner(Player winner) {
		this.winner = winner;
		return this;
	}
	
	public MatchResult setTie(boolean tie) {
		this.tie = tie;
		return this;
	}
	
	public boolean hasWinner() {
		return winner != null;
	}
	
	public boolean isTie() {
		return tie;
	}
	
	public boolean isMatchOver() {
		return !hasWinner() && !isTie();
	}
}


It then become very easy to split the "find winner" algorithm into smaller parts
(the methods are made up by me of course)
public MatchResult findWinner(Board board) {
	MatchResult result = checkWinnerHorizontal(board);
	if (!result.isMatchOver()) result = checkWinnerVertical(board);
	if (!result.isMatchOver()) result = checkWinnerDiagonal(board);
	return result;
}


This post has been edited by CasiOo: 28 February 2014 - 08:11 PM

Was This Post Helpful? 0
  • +
  • -

#4 redVaryant  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 5
  • Joined: 28-February 14

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 02 March 2014 - 12:58 PM

View Postx68zeppelin80x, on 28 February 2014 - 06:11 PM, said:

The way that I have done this is the following:
...


Could you explain a bit further on how treating each player as ASCII integer value would help in determining who won?
I decided to implement your suggestion, but it didn't quite work. What happens is that when I click the button in the
top left corner, it automatically tell me that player O has won, in just one move.

Am I doing something wrong here?

Here's my updated checkWin(). I also removed some previous code in the action performed method, as it wasn't doing much except for causing ArrayIndexOutOfBoundsException.

public void checkWin()
	{
		final int row = getBoardSize();
		final int column = getBoardSize();
		
		grid = new char[row][column];
		
		for(int i = 0; i < getBoardSize(); i++)
		{
			int total = 0;
			
			for(int j = 0; j < getBoardSize(); j++)
			{
			   total = total + grid[i][j];	
			}
			
			if(total % playerO == 0)
			{
				System.out.println("Player O wins horizontally");
			}
		}
	}



View PostCasiOo, on 28 February 2014 - 08:11 PM, said:

Yes giving each player some int value and add each cell up could work in this case
...


Thanks for your suggestion, I'll definitely add a model for Match results, after I'm done with the win algorithm!

This post has been edited by andrewsw: 02 March 2014 - 02:49 PM
Reason for edit:: Reduced quotes

Was This Post Helpful? 0
  • +
  • -

#5 CasiOo  Icon User is offline

  • D.I.C Lover
  • member icon

Reputation: 1575
  • View blog
  • Posts: 3,541
  • Joined: 05-April 11

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 02 March 2014 - 02:29 PM

Why are you initializing grid again at line 6?
I think you should remove that part completly
grid = new char[row][column];



Also, what is the result when you mod with 0 :) ?
The total might be 0 if the columns are all empty with the default char value \u0000
//What do you believe the results will be?
0 mod 'O';
0 mod 'X';


Was This Post Helpful? 0
  • +
  • -

#6 x68zeppelin80x  Icon User is offline

  • D.I.C Addict

Reputation: 130
  • View blog
  • Posts: 576
  • Joined: 07-March 09

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 02 March 2014 - 03:07 PM

View PostredVaryant, on 02 March 2014 - 03:58 PM, said:

Could you explain a bit further on how treating each player as ASCII integer value would help in determining who won?
I decided to implement your suggestion, but it didn't quite work. What happens is that when I click the button in the
top left corner, it automatically tell me that player O has won, in just one move.


Here is a very simple method of checking if there exists a winner:

Be advised that this does nothing in regards to telling the user where the win has occurred. That is up to you.

public class TicTacToe {

	public static final char PLAYER_O = 'O';
	public static final char PLAYER_X = 'X';

	public static void main(String[] args) {
		char[][] board = {
				{ 'O' , 'O' , 'X' , 'X' },
				{ 'O' , 'X' , 'O' , 'X' },
				{ 'O' , 'O' , 'X' , 'O' },
				{ 'O' , 'X' , 'X' , 'X' }
		};

		TicTacToe t = new TicTacToe(board);

		System.out.println(printWinStatus(t, PLAYER_O));
		System.out.println(printWinStatus(t, PLAYER_X));
	}

	public static String printWinStatus(TicTacToe t, char p) {
		return String.format("Did player %c win?: %b", p, t.checkWin(p));
	}

	// Begin TicTacToe.class

	private int size;
	private char[][] grid;

	public TicTacToe(int size) {
		this.size = size;
		this.grid = new char[size][size];
	}

	public TicTacToe(char[][] grid) {
		this.size = grid.length;
		this.grid = grid;
	}

	public boolean checkWin(char player) {
		if (checkHorizontalWin(player)) {
			return true;
		}

		if (checkVerticalWin(player)) {
			return true;
		}

		if (checkDiagonalWin(player)) {
			return true;
		}

		return false;
	}

	public boolean checkHorizontalWin(char player) {
		for (int row = 0; row < size; row++) {
			int total = 0;
			for (int col = 0; col < size; col++) {
				total += grid[row][col];
			}
			if (total % player == 0) {
				return true;
			}
		}
		return false;
	}

	public boolean checkVerticalWin(char player) {
		for (int col = 0; col < size; col++) {
			int total = 0;
			for (int row = 0; row < size; row++) {
				total += grid[row][col];
			}
			if (total % player == 0) {
				return true;
			}
		}
		return false;
	}

	public boolean checkDiagonalWin(char player) {
		int total = 0;
		for (int lr = 0; lr < size; lr++) {
			total += grid[lr][lr];
		}
		if (total % player == 0) {
			return true;
		}
		total = 0;
		for (int rl = 0; rl < size; rl++) {
			total += grid[rl][size - rl - 1];
		}
		if (total % player == 0) {
			return true;
		}
		return false;
	}
}

Was This Post Helpful? 0
  • +
  • -

#7 redVaryant  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 5
  • Joined: 28-February 14

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 04 March 2014 - 09:47 AM

View PostCasiOo, on 02 March 2014 - 02:29 PM, said:

Why are you initializing grid again at line 6?
I think you should remove that part completly
grid = new char[row][column];



Also, what is the result when you mod with 0 :)/>/>/> ?
The total might be 0 if the columns are all empty with the default char value \u0000
//What do you believe the results will be?
0 mod 'O';
0 mod 'X';



I am initializing it on line 6, because that was just a trial. In-fact I already have a String[][] called gameData, which I realize I should have converted to a Char[][], and used that instead. Here's my updated code, which now has the String[][] converted to a Char[][].

The result when 0 mod any number except 0 will be 0. Right?
0 mod 0 is not defined.

@x68zeppelin80x
I have included your code into mine, and I think I can get it work after I give it some more effort.

Here's my update full code.

package Games;

import java.awt.Color;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;


public class Board implements ActionListener
{
	public static final char playerO = 'O'; // --> 79
	public static final char playerX = 'X'; // --> 88
	
        private	boolean player1turn;
	private boolean player2turn;
	private int size;
	
	private char[][] grid;
	private JButton[][] gameGrid;
	
	public Board()
	{
		initialize();
	}
	
	/**
	 * Returns a boolean value of true or false of player 1's turn state.
	 */
	public boolean getPlayer1Turn()
	{
		return player1turn;
	}
	
	/**  
	 * Sets player 1's turn to the specified turn boolean. 
	 */
	public void setPlayer1turn(boolean turn)
	{
		player1turn = turn;
	}
	   
	/**
	 * Returns a boolean value of true or false of player 2's turn state.
	 */
	public boolean getPlayer2turn()
	{
		return player2turn;
	}
	
	/**
	 * Returns the current size of the board.
	 */
	public int getBoardSize()
	{
		return size;
	}
	
	/**
	 * @param size The size of the board to be set when the user starts the game.
	 */
	public void setBoardSize(int size)
	{
		this.size = size;
	}
	   
	/**
	 * Sets player 2's turn to the specified turn boolean
	 */
	public void setPLayer2turn(boolean turn)
	{
		player2turn = turn;
	}
	 
	/**
	 * Checks the board size that the user has submitted, and verifies that it is between 3 and 25, inclusive.
	 * @param size The size of the board.
	 */
	public boolean checkBoardSize(int size)
	{
		//checks that the size is between 3 and 25
		if(size < 3 || size > 25)
		{
			return false;
		}
		
		return true;
	}
	
	
	/**
	 * Declares the winner.
	 */
	public boolean checkWin(char player)
	{
        if (checkHorizontalWin(player))
        {
            return true;
        }

        if (checkVerticalWin(player))
        {
            return true;
        }

        if (checkDiagonalWin(player))
        {
            return true;
        }
        
        return false;
    }

	
	 public boolean checkHorizontalWin(char player)
	 {
		 for (int row = 0; row < size; row++)
		 {
			 int total = 0;
			 
			 for (int col = 0; col < size; col++)
			 {
				 total += grid[row][col];
			 }
		             
			 if (total % player == 0) 
			 {
				 return true;
			 }
		 }

		 return false;
	 }
	 
	 public boolean checkVerticalWin(char player)
	 {
		 for (int col = 0; col < size; col++)
		 {
			 int total = 0;
			 
			 for (int row = 0; row < size; row++)
			 {
				 total += grid[row][col];
			 }
			 
			 if (total % player == 0)
			 {
				 return true;
			 }
		 }
		 
		 return false;
	 }
	 
	 public boolean checkDiagonalWin(char player)
	 {
		 int total = 0;
		 
		 for (int lr = 0; lr < size; lr++) 
		 {
			 total += grid[lr][lr];
		 }

		 if (total % player == 0)
		 {
			 return true;
		 }
		 
		 total = 0;
		 
		 for (int rl = 0; rl < size; rl++)
		 {
			 total += grid[rl][size - rl - 1];

		 }
		 
		 if (total % player == 0)
		 {
		             return true;
         }
		         return false;
	 }

	/**
	 * Displays game introduction to the user.
	 */
	public void initialize()
	{
		final JFrame introFrame = new JFrame();
		JPanel introPanel = new JPanel();
		
		JLabel blank = new JLabel();
		JLabel blank2 = new JLabel();
		JLabel blank3 = new JLabel();
		JLabel blank4 = new JLabel();
		final JLabel blank5 = new JLabel();
		
		JButton playGame = new JButton("Play!");
		JLabel welcomeLabel = new JLabel("Tic Tac Toe");
		
		JLabel boardSize = new JLabel("Board Size");
		final JTextField boardInput = new JTextField();
		
		introPanel.add(blank);
		introPanel.add(welcomeLabel);
		introPanel.add(blank2);
		introPanel.add(boardSize);
		introPanel.add(boardInput);
		introPanel.add(blank3);
		introPanel.add(blank4);
		introPanel.add(playGame);
		introPanel.add(blank5);
		
		introPanel.setLayout(new GridLayout(3,3));
		
		introFrame.setTitle("Welcome to Tic Tac Toe!");
		introFrame.add(introPanel);
		introFrame.setVisible(true);
		introFrame.setSize(725,300);
		
		playGame.addActionListener(new ActionListener()
		{
			@Override
			public void actionPerformed(ActionEvent arg0)
			{
				String input = boardInput.getText();
				
				if(input.length() == 0)
				{
					blank5.setText("Input cannot be empty");
					return;
				}
				
				else
				{
					try
					{
						if((Integer) Integer.parseInt(input) instanceof Integer)
						{
							if(checkBoardSize(Integer.parseInt(boardInput.getText())))
							{
								setBoardSize(Integer.parseInt(boardInput.getText()));
								introFrame.setVisible(false);
								playGame();
							}
							
							else
							{
								blank5.setText("Size must be between 3 and 25");
								return;
							}
						}
					}
					
					catch(NumberFormatException e)
					{
						blank5.setText("Input must be a number");
						return;
					}
				}
			}
		});

		introFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
	}
	
	public void playGame()
	{
		JFrame gameframe = new JFrame();
		JPanel gamePanel = new JPanel();
		int size = getBoardSize();
		gameGrid = new JButton[size][size];
		grid = new char[size][size];
		
		//game panel variables
		final int rows = size;
		final int columns = size;
		
		setPlayer1turn(true);
		
		for(int i = 0; i < rows; i++)
		{
			for(int j = 0; j < columns; j++)
			{
				gameGrid[i][j] = new JButton();
				gamePanel.add(gameGrid[i][j]);
				gameGrid[i][j].setBackground(Color.black);
				
				gameGrid[i][j].addActionListener(this);
				grid[i][j] = ' ';
			}
		}
		
		gamePanel.setLayout(new GridLayout(size, size));
		gameframe.add(gamePanel);
		gameframe.setVisible(true);
		gameframe.setSize(500, 500);
		  
		gameframe.setLayout(new GridLayout());
		gameframe.setTitle("Tic Tac Toe");
		gameframe.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
	}
	
   @Override
   public void actionPerformed(ActionEvent e) 
   {
	   final int rows = getBoardSize();
	   final int columns = getBoardSize();
	   JButton b = (JButton) e.getSource();
	   
	   for(int i = 0; i < rows; i++)
	   {
		   for(int j = 0; j < columns; j++)
		   {
			   if(b == gameGrid[i][j])
			   {
				   //put x
				   if(getPlayer1Turn())
				   {
					   ((JButton) e.getSource()).setText("X");
					   ((JButton) e.getSource()).setBackground(Color.red);
					   setPlayer1turn(false);
					
					   setPLayer2turn(true);
					   ((JButton) e.getSource()).setEnabled(false);
					   grid[i][j] = 'X';
					   checkWin(playerX);
				   }
			   
			      //otherwise put o
			      else
			      {
			    	  ((JButton) e.getSource()).setText("O");
			    	  ((JButton) e.getSource()).setBackground(Color.blue);
			    	  setPlayer1turn(true);
					
			    	  setPLayer2turn(false);
			    	  ((JButton) e.getSource()).setEnabled(false);
			    	  grid[i][j] =  'O';
			      }
			   }
		   }
	   }
   }
	
	public void printGameData()
	{
		for(int i = 0; i < this.getBoardSize(); i++)
		{
			for(int j = 0; j < this.getBoardSize(); j++)
			{
				System.out.print(grid[i][j]);
			}	
			System.out.println();
		}
	}
	
	public static String printWinStatus(Board b, char p)
	{
		return String.format("Did player %c win?: %b", p, b.checkWin(p));
	}

   public static void main(String[] args)
   {
	   Board b = new Board();
	   b.printGameData();
	   System.out.println(printWinStatus(b, playerO));
	   System.out.println(printWinStatus(b, playerX));
   }
}



Thanks for all of your help, I appreciate it.
Was This Post Helpful? 0
  • +
  • -

#8 x68zeppelin80x  Icon User is offline

  • D.I.C Addict

Reputation: 130
  • View blog
  • Posts: 576
  • Joined: 07-March 09

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 04 March 2014 - 02:55 PM

redVaryant said:

The result when 0 mod any number except 0 will be 0. Right?
0 mod 0 is not defined.


If you think about it, with X mod N, you are trying to simply find the remainder of X/N.

Since 0/0 (Division By Zero) results in an undefined response, the same should occur with modulo operations.
Was This Post Helpful? 0
  • +
  • -

#9 redVaryant  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 5
  • Joined: 28-February 14

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 05 March 2014 - 11:35 AM

View Postx68zeppelin80x, on 04 March 2014 - 02:55 PM, said:

redVaryant said:

The result when 0 mod any number except 0 will be 0. Right?
0 mod 0 is not defined.


If you think about it, with X mod N, you are trying to simply find the remainder of X/N.

Since 0/0 (Division By Zero) results in an undefined response, the same should occur with modulo operations.


Alright, I understand how the modulus works, but the win condition is still not working, with regards to my most recent code. When I run the program, it immediately prints out that playerO and playerX have both won.

How do I fix this so that it only displays the actual winner?

My idea is this: keep checking for the win in the actionPerformed(), because that is where all of the clicking takes place. I will also double check that the printGameData() is working properly, since it is not displaying the correct data.
Was This Post Helpful? 0
  • +
  • -

#10 x68zeppelin80x  Icon User is offline

  • D.I.C Addict

Reputation: 130
  • View blog
  • Posts: 576
  • Joined: 07-March 09

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 05 March 2014 - 11:51 AM

View PostredVaryant, on 05 March 2014 - 02:35 PM, said:

How do I fix this so that it only displays the actual winner?


Well, as CasiOo had stated earlier, you must check for a total that is equal to zero as well. My initial code was to really check for a filled up board. To fix this, you just have to update 4 places in your code.

Anywhere you see this:
if (total % player == 0) {
    return true;
}

Change it to this:
if (total != 0 && total % player == 0) {
    return true;
}


View PostredVaryant, on 05 March 2014 - 02:35 PM, said:

My idea is this: keep checking for the win in the actionPerformed(), because that is where all of the clicking takes place. I will also double check that the printGameData() is working properly, since it is not displaying the correct data.


At the end of your actionPerformed(), you should check if a winner exists. Or better yet, make a makeMove() function and only if it is a legal move, check for a winner.
Was This Post Helpful? 0
  • +
  • -

#11 redVaryant  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 5
  • Joined: 28-February 14

Re: N x N GUI TicTacToe game, winning algorithm?

Posted 05 March 2014 - 08:09 PM

View Postx68zeppelin80x, on 05 March 2014 - 11:51 AM, said:

View PostredVaryant, on 05 March 2014 - 02:35 PM, said:

How do I fix this so that it only displays the actual winner?


Well, as CasiOo had stated earlier, you must check for a total that is equal to zero as well. My initial code was to really check for a filled up board. To fix this, you just have to update 4 places in your code.

Anywhere you see this:
if (total % player == 0) {
    return true;
}

Change it to this:
if (total != 0 && total % player == 0) {
    return true;
}


View PostredVaryant, on 05 March 2014 - 02:35 PM, said:

My idea is this: keep checking for the win in the actionPerformed(), because that is where all of the clicking takes place. I will also double check that the printGameData() is working properly, since it is not displaying the correct data.


At the end of your actionPerformed(), you should check if a winner exists. Or better yet, make a makeMove() function and only if it is a legal move, check for a winner.



Wow, thank you very much for helping me out with my first side project, I really appreciate it!
With your help, I was able to complete my first side project, and everything works now, wins and ties.
Now I did have one more question, how did you manage to come up with such a efficient win algorithm?

Also, let me reiterate the algorithm that you developed.

0 is 79 in ascii, and X is 88. When player X has 3 X's in the first row,
the value would be 88, 88, 88, which sums to 264. However, 264 mod 88 is = 0, hence player X wins.
The same applies for the vertical and the diagonal layouts.

Likewise for player O.

This is how your algorithm works right?

Thanks again for all of your help!
Was This Post Helpful? 0
  • +
  • -

Page 1 of 1