Welcome to the Java Programming Forums


The professional, friendly Java community. 21,500 members and growing!


The Java Programming Forums are a community of Java programmers from all around the World. Our members have a wide range of skills and they all have one thing in common: A passion to learn and code Java. We invite beginner Java programmers right through to Java professionals to post here and share your knowledge. Become a part of the community, help others, expand your knowledge of Java and enjoy talking with like minded people. Registration is quick and best of all free. We look forward to meeting you.


>> REGISTER NOW TO START POSTING


Members have full access to the forums. Advertisements are removed for registered users.

Results 1 to 4 of 4

Thread: Difficulty with understanding interaction between Classes

  1. #1
    Junior Member
    Join Date
    Aug 2012
    Posts
    3
    Thanks
    0
    Thanked 0 Times in 0 Posts

    Default Difficulty with understanding interaction between Classes

    When I was making a multi-class version to tic-tac-toe, I have ran into several errors, which most of them have to do with how I made them interact between the two classes.

    The following classes I have made with the intention:

    GameBoard

    /** This class will handle all the aspects of updating the gamebaord
        after every turm
     
     
      @author John Peter McGrath
     
    */
    import Java.util.Arrays;
    public class GameBoard{
     
     
    //instance variables for game board
     
      private final int BOARD_LENGTH = 3;
      private final int LAST_TURN = BOARD_LENGTH * BOARD_LENGTH;
     
      private boolean gameOver = false;
      private int turns = 0;
      private int totalPlayers = players.length;
      private int playerNumber = turns % totalPlayers;
     
     
      // shortened versions of instance variables
      private final int bl = BOARD_LENGTH;
     
      // arrays
     
      private Player[] players = new Player[2];
      private char[][] game_board = new char[bl][bl];
     
      // this will be modified after each player's turn
      // the 2nd array is arranged by rows
      public char[][] claimedSpaces = new char [bl][bl];
     
    // instance vaiables for player will be labeled as
    // Player.instanceVariable
     
      public GameBoard(){
     
        // customize the players tokens, but leave the last two
        // parameters false to keep the game fair
        players[0] = Player('X', false, false);
        players[1] = Player('O', false, false);
        private boolean stalemate = (turns >= LAST_TURN);
        while (gameOver != true && !stalemate){
          gameOver = checkWin(players, gameOver);
          playerNumber = turns % totalPlayers;
          playerTurn(Player[playerNumber]);
          printGameBoard(game_board);
          // debug
          System.out.println(Arrays.deepToString(claimedSpaces));
     
          turns ++;
        }
        showOutcome(gameOver, stalemate, players);
     
      }
     
    // the instance methods for gameboard
     
      /** The player will take its turn
          @param player - the current player taking a turn  
     
      */
      public void playerTurn(Player player){
        player.playersTurn = true;
        player.placeMove();
      }
     
      /** Check to see if any player won the game yet
     
     
     
      @return true if any player won the game
        false if no player won and continue game
      */
     
       public boolean checkWin(Player[] totalPlayers, boolean endGame){
         for (int i = 0; i < totalPlayers; i++){
           if (totalPlayers[i].playerWins == true)
             endGame = true;
           return endGame;
        }
     
      }
     
     
      /** The game will reveal either the winner of the game or
         declare stalemate when no player wins by last turn
      @param gameEnded - has the game ended?
      @param noWinner - if there are no winners, declare stalemate
      @param winner - which player has won the game
         (if and only if game ended without stalemate)
      */
      public void showOutcome(boolean gameEnded,boolean noWinner,
                  Player[] winner){
      // precondition
        if (noWinner == true)
           System.out.println("Stalemate");
        else{
          for (int w = 0; w < winner.length; w++){
            if (winner[w].playerWins == true){
              System.out.println("Player " + winner[w]
                  + " is the winner!");
            }
          }
        }
      }
     
      // now the printing methods
     
     
      public void printGameBoard(char[][] game){
        for (int r = 0; r < game.length; r++){
          for (int c = 0; c < game[i].length; c++){
            System.out.print(game[r][c] + " ");
          }
          // debug
          System.out.println(Arrays.deepToString(game));
        }
     
      }
     
      // retrieving data
     
      public int getBoardLength()
        {return BOARD_LENGTH;}
     
    }

    Player

    /** This class will handle all the aspects of the player's turn
     
      which includes placing the token and checking to see if that
      space on the gameboard is unclaimed
     
      @author John Peter McGrath
    */
     
    import java.util.Scanner;
    import java.util.Arrays;
    public class Player{
     
     
    // INSTANCE VARIABLES
     
      private char playerToken;
      private boolean playerWins;
     
      // this must be modified by the game board
      public boolean playersTurn;
     
      // sevaral varibales used from game board
      private int bl = GameBoard.getBoardLength();
      private final int winningLines = 2 * bl + 2;
     
      private char[][] claimedSpaces = new char[bl][bl];
      private char[][] possibleWins = new char[winningLines][bl]
     
      public Player(char token, boolean playersTurn, boolean playerWins){
        this.token = token;
        this.playersTurn = playersTurn;
        this.playerWins = playerWins;
     
      }
     
      // instance methods
     
      /** Player takes turn by placing a token on an unclaimed space
     
      */
      public void placeMove(){
        int endValue = bl - 1;
        private Scanner move = new Scanner(System.in);
     
        while (playersTurn == true){
          System.out.print("Please choose row number from 0 to "
          + endValue + ":" ); row = in.nextInt();
          System.out.print("Please choose column number from 0 to "
          + endValue + ":" ); col = in.nextInt();
          checkMove(GameBoard.claimedSpaces, row, col);
        }
     
      }
     
      /** Check if the player made a valid move on the board
        @param spaceClaimed - player can only occupy
               unclaimed spaces
        @param row - the row position of the space
        @param col - the column position of the space
     
      */
     
      public void checkMove(boolean[][] spaceClaimed,
                  char[][] playersClaim,
                  int row, int col){
     
        if (spaceClaimed[row][col] == true)
            {System.out.println("Sorry, this space has been claimed"
            + " please choose an empty space.");
        }else{
            playersClaim[row][col] = token;
            spaceClaimed[row][col] = true;
            unpdatePossibleWins(possibleWins, playersClaim);
            System.out.println(Arrays.deepToString(possibleWins));
            playerWins = didWinGame(possibleWins)
            playersTurn = false;
          }
      }
     
      /** Check if the player won the game by claiming the whole line
     
        @param winningLine - check each line to ensure that
          the player really has claimed the whole line
     
        @return true if the player did claim at least one line
                false otherwise
     
      */
     
      public boolean didPlayerWin(char[][] winningLine){
        boolean didWinGame = false;
        int spacesPerLine = bl;
        for (int i = 0; i < winningLine.length; i++){
          int countTokens = 0;
          for (int j = 0; i < winningLine[i].length; j++){
            if (winningLine[i][j] == token)
              countTokens ++;
          }
          if (countTokens == spacesPerLine)
            didWinGame = true;
        }
        return didWinGame
      }
     
      /** Create an array based on the winning lines (n is board length)
        there are 2n + 2 ways to win the game since there are
        n rows,
        n columns,
        and 2 diagonal lines based on board length  
     
        @param winningLines - scan all the winning lines to
                    find any of the player's tokens
        @param occSpaces - use the n*n board to detect player's tokens
     
      */
     
      public char[][] updatePoosibleWins(char[][] winningLines,
              char[][] occSpaces){
        // the following vairbales only concern index position
        int rowRange = bl;
        int colRange = rowRange*2;
        int diagonalRange = colRange + 2;
        // scan the entire combination of winning lines
        // by scanning it in one dimension
     
        // first scan n columns
        for (int i = 0; i < rowRange; i++){
          for (int r = 0; r < occSpaces.length; r++){
            for (int c = 0; c < occSpaces[r]; c++){
              if (c == i )
                winningLines[r][c] = occSpaces[r][c];
              }
            }
          winningLines[i] = scanLine(winningLines[i], occSpaces; i);
     
          }
     
        // next scan n rows
        for (int i = rowRange; i < colRange; i++){
          for(int r = 0; r < occSpaces.length; r++){
            for (int c = 0; c < occSpaces[r]; c++){
                winningLinesi[i][c] = occSpaces[r][c];
              }
             winningLines[i] = scanLine(winningLines[i], occSpaces; i);
            }
     
          } 
     
        // last scan the diagonal lines
        for (int i = colRange; i < diagonalRange; i++){
          for (int r = 0; r < occSpaces.length; r++){
            for (int c = 0; c < occSpaces[r]; c++){
              // scan the first daigonal from up-left to down-right
              // by making a boolean condition
              boolean firstDiagonal = i == colRange;
              if (firstDiagonal){
                if (c == r)
                 {winningLines[i][c] = occSpaces[r][c];}
              }
     
              // scan the second diagonal from up-right to down-ieft
              else if (c == bl - (r + 1)){
               winningLines[i][c] = occSpaces[r][c];
              }
     
     
            }
           winningLines[i] = scanLine(winningLines[i], occSpaces; i);
          }
     
        }
     
        return winningLines;
      }
     
      /** This method will scan for player's claimed tokens
          for each possible winning line
     
      */
      public char[] scanLines(char[] currentLine, char[][] tokenSpace,
                     int iterator){
        for (int i = 0; i < currentLine.length; i++)
          currentLine[i] = tokenSpace[i][iterator]
        return currentLine;
      }
     
      /** Scan the diagonal lines:
        the first goes from top-left to bottom-right
        the second goes from top-right to bottom-left
     
      */
     
     /*
      public char[] scanDiagonals(int iter, int row, int, col,
                    char[][] occSpace, char[] currentLine,
                    ){
        currentLine[iter] = scanLine(winningLines[iter], occSpace; iter);
     
     
      }
     */
     
    }

    Main Game (I did not want to put anything else besides creating the game object since the player objects are already created in GameBoard)

    /**This Program will run the Tic-Tac-Toe Game
     
    This game will consist of only players, no computers
    the gameboard can be customized based on board length
       and the number og players by modifying source code
    the game will be over if there are no more empty spaces
    or that one of the players win the game
     
    @author John Peter McGrath
    */
     
    public class TicTacToeV1_Main{
     
     
    // Main Game
      public static void main(String[] args){
      GameBoard game = new GameBoard();
     
     
      }
     
     
    }

    BTW, I do believe that some compilation errors may be the link to that problem

    ./GameBoard.java:44: illegal start of expression
        private boolean stalemate = (turns >= LAST_TURN);
        ^
    ./GameBoard.java:8: package Java.util does not exist
    import Java.util.Arrays;
                    ^
    ./GameBoard.java:28: cannot find symbol
    symbol  : class Player
    location: class GameBoard
      private Player[] players = new Player[2];
              ^
    ./GameBoard.java:65: cannot find symbol
    symbol  : class Player
    location: class GameBoard
      public void playerTurn(Player player){
                             ^
    ./GameBoard.java:78: cannot find symbol
    symbol  : class Player
    location: class GameBoard
       public boolean checkWin(Player[] totalPlayers, boolean endGame){
                               ^
    ./GameBoard.java:96: cannot find symbol
    symbol  : class Player
    location: class GameBoard
                  Player[] winner){
                  ^
    ./GameBoard.java:19: illegal forward reference
      private int totalPlayers = players.length;
                                 ^
    ./GameBoard.java:28: cannot find symbol
    symbol  : class Player
    location: class GameBoard
      private Player[] players = new Player[2];
                                     ^
    ./GameBoard.java:42: cannot find symbol
    symbol  : method Player(char,boolean,boolean)
    location: class GameBoard
        players[0] = Player('X', false, false);
                     ^
    ./GameBoard.java:43: cannot find symbol
    symbol  : method Player(char,boolean,boolean)
    location: class GameBoard
        players[1] = Player('O', false, false);
                     ^
    ./GameBoard.java:48: cannot find symbol
    symbol  : variable Player
    location: class GameBoard
          playerTurn(Player[playerNumber]);
                     ^
    ./GameBoard.java:51: cannot find symbol
    symbol  : variable Arrays
    location: class GameBoard
          System.out.println(Arrays.deepToString(claimedSpaces));
                             ^
    ./GameBoard.java:115: cannot find symbol
    symbol  : variable i
    location: class GameBoard
          for (int c = 0; c < game[i].length; c++){
                                   ^
    ./GameBoard.java:119: cannot find symbol
    symbol  : variable Arrays
    location: class GameBoard
          System.out.println(Arrays.deepToString(game));
    Last edited by JBRPG; August 13th, 2012 at 10:23 AM.


  2. #2
    Super Moderator Norm's Avatar
    Join Date
    May 2010
    Location
    SW Missouri
    Posts
    20,420
    Thanks
    49
    Thanked 2,215 Times in 2,188 Posts

    Default Re: Difficulty with understanding interaction between Classes

    private boolean stalemate
    Variables defined inside of methods are local to that method and can't be declared private etc

    Java is case sensitive. Check your spelling.

    You need an import statement to access classes in a package.


    BTW You should compile the code more often as you type it in to keep from getting so many error messages at one time.
    If you don't understand my answer, don't ignore it, ask a question.

  3. #3
    Junior Member
    Join Date
    Aug 2012
    Posts
    3
    Thanks
    0
    Thanked 0 Times in 0 Posts

    Default Re: Difficulty with understanding interaction between Classes

    Quote Originally Posted by Norm View Post
    Variables defined inside of methods are local to that method and can't be declared private etc

    Java is case sensitive. Check your spelling.

    You need an import statement to access classes in a package.


    BTW You should compile the code more often as you type it in to keep from getting so many error messages at one time.
    Thanks, and I also have a few additional problems relevant to the topic.

    After making some successful compilation, I get a run-time error, and I will share the details below:


    Main Game

     
    public class TicTacToeV1_Main01{
     
    // Main Game
      public static void main(String[] args){
      GameBoard game = new GameBoard();
     
     
      }
     
     
    }

    Game Board

    /** This class will handle all the aspects of updating the gamebaord
        after every turm
     
     
      @author John Peter McGrath
     
    */
    import java.util.Arrays;
    public class GameBoard{
     
     
    //instance variables for game board
     
      private final int BOARD_LENGTH = 3;
      private final int LAST_TURN = BOARD_LENGTH * BOARD_LENGTH;
     
      // player-related variables 
      private Player[] players = new Player[2];
      private boolean gameOver = false;
     
     
      // shortened versions of instance variables
      private int bl = BOARD_LENGTH;
     
      // arrays
     
      private char[][] game_board = new char[bl][bl];
     
      // this will be modified after each player's turn
      // the 2nd array is arranged by rows
      public boolean[][] claimedSpaces = new boolean [bl][bl];
     
    // instance vaiables for player will be labeled as
    // Player.instanceVariable
     
      public GameBoard(){
     
        // customize the players tokens, but leave the last two
        // parameters false to keep the game fair 
        int turns = 0;
        int totalPlayers = players.length;
        int playerNumber = turns % totalPlayers;
        players[0] = new Player('X', false, false);
        players[1] = new Player('O', false, false);
        boolean stalemate = false; // if the board is filled up
        while (gameOver != true && !stalemate){
          gameOver = checkWin(players, gameOver);
          playerNumber = turns % totalPlayers;
          playerTurn(players[playerNumber]);
          printGameBoard(game_board);
          // debug
          System.out.println(Arrays.deepToString(claimedSpaces));
          turns ++;
          stalemate = turns >= LAST_TURN;
        }
        showOutcome(gameOver, stalemate, players);
     
      }
     
    // the instance methods for gameboard
     
      /** The player will take its turn
          @param player - the current player taking a turn  
     
      */
      public void playerTurn(Player player){
        player.playersTurn = true;
        player.placeMove();
      }
     
      /** Check to see if any player won the game yet
     
     
     
      @return true if any player won the game
        false if no player won and continue game
      */
     
       public boolean checkWin(Player[] totalPlayers, boolean endGame){
         for (int i = 0; i < totalPlayers.length; i++){
           if (totalPlayers[i].getPlayerWins() == true)
             endGame = true;
        }
        return endGame;
     
      }
     
     
      /** The game will reveal either the winner of the game or
         declare stalemate when no player wins by last turn
      @param gameEnded - has the game ended?
      @param noWinner - if there are no winners, declare stalemate
      @param winner - which player has won the game
         (if and only if game ended without stalemate)
      */
      public void showOutcome(boolean gameEnded,boolean noWinner,
                  Player[] winner){
      // precondition
        if (noWinner == true)
           System.out.println("Stalemate");
        else{
          for (int w = 0; w < winner.length; w++){
            if (winner[w].getPlayerWins() == true){
              System.out.println("Player " + w
                  + " is the winner!");
            }
          }
        }
      }
     
      // now the printing methods
     
     
      public void printGameBoard(char[][] game){
        for (int r = 0; r < game.length; r++){
          for (int c = 0; c < game[r].length; c++){
            System.out.print(game[r][c] + " ");
          }
          // debug
          System.out.println(Arrays.deepToString(game));
        }
     
      }
     
      // retrieving data
     
      public int getBoardLength(){
        return bl;
      }
     
    //  public boolean[][] getspaceClaims(){
    //    return claimedSpaces; 
    //  }
     
    }

    Player

    /** This class will handle all the aspects of the player's turn
     
      which includes placing the token and checkiung to see if that
      space on the gameboard is unclaimed
     
      @author John Peter McGrath
    */
     
    import java.util.Scanner;
    import java.util.Arrays;
    public class Player{
     
     
    // INSTANCE VARIABLES
     
      private char playerToken;
      private boolean playerWins;
     
      // this must be modified by the game board
      public boolean playersTurn;
     
      // sevaral varibales used from game board
     
      // placing the keyword static in bl causes run-time error
      private static int bl = GameBoard.getBoardLength();
     
      private final int winningLines = 2 * bl + 2;
     
      private char[][] playersClaim = new char[bl][bl];
      private char[][] possibleWins = new char[winningLines][bl];
      public Player(char piece, boolean takeTurn,
                       boolean didWin){
        piece = playerToken;
        takeTurn = playersTurn;
        didWin = playerWins;
     
      }
      // instance methods
     
      /** Player takes turn by placing a token on an unclaimed space
      */
      public void placeMove(){
        int row, col;
        int endValue = bl - 1;
        Scanner move = new Scanner(System.in);
        while (playersTurn == true){
          System.out.print("Please choose row number from 0 to "
          + endValue + ":" ); row = move.nextInt();
          System.out.print("Please choose column number from 0 to "
          + endValue + ":" ); col = move.nextInt();
          checkMove(GameBoard.claimedSpaces, row, col, playerToken);
        }
     
      }
     
      /** Check if the player made a valid move on the board
        @param spaceClaimed - player can only occupy
               unclaimed spaces
        @param row - the row position of the space
        @param col - the column position of the space
      */
      public void checkMove(boolean[][] spaceClaimed,
                  char[][] playersClaim,
                  int row, int col, char token){
     
        if (spaceClaimed[row][col] == true)
            {System.out.println("Sorry, this space has been claimed"
            + " please choose an empty space.");
        }else{
            playersClaim[row][col] = token;
            spaceClaimed[row][col] = true;
            unpdatePossibleWins(possibleWins, playersClaim);
            System.out.println(Arrays.deepToString(possibleWins));
            playerWins = didPlayerWin(possibleWins);
            playersTurn = false;
          }
      }
      /** Check if the player won the game by claiming the whole line
     
        @param winningLine - check each line to ensure that
          the player really has claimed the whole line
     
        @return true if the player did claim at least one line
                false otherwise 
      */
     
      public boolean didPlayerWin(char[][] winningLine){
        boolean didWinGame = false;
        int spacesPerLine = bl;
        for (int i = 0; i < winningLine.length; i++){
          int countTokens = 0;
          for (int j = 0; i < winningLine[i].length; j++){
            if (winningLine[i][j] == playerToken)
              countTokens ++;
          }
          if (countTokens == spacesPerLine)
            didWinGame = true;
        }
        return didWinGame;
      }
     
      /** Create an array based on the winning lines (n is board length)
        there are 2n + 2 ways to win the game since there are
        n rows,
        n columns,
        and 2 diagonal lines based on board length  
     
        @param winningLines - scan all the winning lines to
                    find any of the player's tokens
        @param occSpaces - use the n*n board to detect player's tokens
      */
     
      public char[][] updatePoosibleWins(char[][] winningLines,
              char[][] occSpaces){
        // the following vairbales only concern index position
        int rowRange = bl;
        int colRange = rowRange*2;
        int diagonalRange = colRange + 2;
        // scan the entire combination of winning lines
        // by scanning it in one dimension
     
        // first scan n columns
        for (int i = 0; i < rowRange; i++){
          for (int r = 0; r < occSpaces.length; r++){
            for (int c = 0; c < occSpaces[r].length; c++){
              if (c == i )
                winningLines[r][c] = occSpaces[r][c];
              }
            }
          winningLines[i] = scanLines(winningLines[i], occSpaces, i);
     
          }
     
        // next scan n rows
        for (int i = rowRange; i < colRange; i++){
          for(int r = 0; r < occSpaces.length; r++){
            for (int c = 0; c < occSpaces[r].length; c++){
                winningLines[i][c] = occSpaces[r][c];
              }
             winningLines[i] = scanLines(winningLines[i], occSpaces, i);
            }
     
          } 
     
        // last scan the diagonal lines
        for (int i = colRange; i < diagonalRange; i++){
          for (int r = 0; r < occSpaces.length; r++){
            for (int c = 0; c < occSpaces[r].length; c++){
              // scan the first daigonal from up-left to down-right
              // by making a boolean condition
              boolean firstDiagonal = i == colRange;
              if (firstDiagonal){
                if (c == r)
                 {winningLines[i][c] = occSpaces[r][c];}
              }
              // scan the second diagonal from up-right to down-ieft
              else if (c == bl - (r + 1)){
               winningLines[i][c] = occSpaces[r][c];
              }
            }
           winningLines[i] = scanLines(winningLines[i], occSpaces, i);
          }
        }
        return winningLines;
      }
     
      /** This method will scan for player's claimed tokens
          for each possible winning line
     
      */
      public char[] scanLines(char[] currentLine, char[][] tokenSpace,
                     int iterator){
        for (int i = 0; i < currentLine.length; i++)
          currentLine[i] = tokenSpace[i][iterator];
        return currentLine;
      }
     
      // the data-gathering methods
     
      public boolean getPlayerWins()
        {return playerWins;}
     
     
    }

    Run-time error when applying static to specified variable

    Exception in thread "main" java.lang.NoClassDefFoundError: Player
    	at GameBoard.<init>(GameBoard.java:18)
    	at TicTacToeV1_Main01.main(TicTacToeV1_Main01.java:17)

    Compiler error when not applying the "static"

    ./Player.java:23: non-static method getBoardLength() cannot be referenced from a static context
      private int bl = GameBoard.getBoardLength();
                                ^
    ./Player.java:48: non-static variable claimedSpaces cannot be referenced from a static context
          checkMove(GameBoard.claimedSpaces, row, col, playerToken);
                             ^
    ./Player.java:48: checkMove(boolean[][],char[][],int,int,char) in Player cannot be applied to (boolean[][],int,int,char)
          checkMove(GameBoard.claimedSpaces, row, col, playerToken);
          ^
    ./Player.java:69: cannot find symbol
    symbol  : method unpdatePossibleWins(char[][],char[][])
    location: class Player
            unpdatePossibleWins(possibleWins, playersClaim);
            ^

  4. #4
    Super Moderator Norm's Avatar
    Join Date
    May 2010
    Location
    SW Missouri
    Posts
    20,420
    Thanks
    49
    Thanked 2,215 Times in 2,188 Posts

    Default Re: Difficulty with understanding interaction between Classes

    java.lang.NoClassDefFoundError: Player
    There is no class file for the Player class because of the compiler errors.
    cannot be referenced from a static context
    private int bl = GameBoard.getBoardLength();
    getBoardLength() is a non-static method in the GameBoard class. You need to have a reference variable that points to an instance of the class to call it. You are trying to all that method like it was a static method.

    Where is unpdatePossibleWins defined? Check your spelling.
    If you don't understand my answer, don't ignore it, ask a question.

Similar Threads

  1. Replies: 3
    Last Post: July 8th, 2012, 03:44 PM
  2. JScrollPane Difficulty. Help Please
    By AceApple in forum AWT / Java Swing
    Replies: 2
    Last Post: June 24th, 2012, 05:30 PM
  3. NEEDING HELP UNDERSTANDING A CODE FROM THREE CLASSES!!!
    By BlackShadow in forum Java Theory & Questions
    Replies: 1
    Last Post: April 6th, 2012, 10:11 PM
  4. NEEDING HELP UNDERSTANDING A CODE FROM THREE CLASSES!!!
    By BlackShadow in forum What's Wrong With My Code?
    Replies: 1
    Last Post: April 5th, 2012, 09:29 AM
  5. State Variables interaction with outside classes?
    By Ace Coder in forum What's Wrong With My Code?
    Replies: 2
    Last Post: October 24th, 2010, 03:52 PM

Tags for this Thread