Next: HTML-Seite für das Applet:
Up: Von C++ zu Java
Previous: C++ Implementation 11/11
import java.awt.*; import java.awt.event.*; // For MouseListener import java.applet.Applet; public class FourInaRow extends Applet implements MouseListener, FourInaRowBase { Board c_4 = new Board(); // The playing board Player contestant[] = new Player [NO_OF_PLAYERS]; // No of players int state = PLAY; int no = 0; int moveNumber = 0; public void init() { setSize(200, 200); addMouseListener(this); for (int i=0; i<NO_OF_PLAYERS; i++) { contestant[i] = new Player(); } setBackground(BACKGROUND); c_4.printMessage(aboutString); } // paint is called by repaint() public void paint(Graphics g) { Dimension d = getSize(); c_4.set_graphic_size(d); g.translate(0,d.height-40); c_4.displayBoard(g, d); // next lines: Display status message; also triggered with repaint() g.translate(0,-(d.height-40)); g.setColor(BACKGROUND); g.drawString(c_4.last_message(),5,20); g.setColor(BLACK); g.drawString(c_4.message(),5,20); System.out.println(c_4.message()); c_4.last_message(c_4.message()); g.translate(0,d.height-40); } public void mouseReleased(MouseEvent e) { int x = e.getX(); int y = e.getY(); moveNumber++; Dimension d = getSize(); int c = (x * DEF_COLUMNS) / d.width; int r = ((d.height - y) * DEF_ROWS) / d.height; c_4.printMessage("Move number " + moveNumber); if (!c_4.move_ok_for_column(c)) c_4.printMessage("Illegal move"); else c_4.drop_in_column(c, contestant[no].get_counter()); repaint(); // Refresh the whole board state = c_4.situation(); if (state == PLAY) no = (no+1)%NO_OF_PLAYERS; else c_4.printMessage(contestant[no].announce(state)); // The result } public void mousePressed(MouseEvent e) { } public void mouseClicked(MouseEvent e) { } public void mouseEntered(MouseEvent e) { } public void mouseExited(MouseEvent e) { } public String getAppletInfo() { return aboutString; } } interface FourInaRowBase { final int MAXROW = 9; // Maximun Rows final int MAXCOLUMN = 9; // Maximum Columns final int DRAW = 0; final int WIN = 1; final int PLAY = 2; final int STONES_IN_A_WIN_LINE = 4; final int NO_OF_PLAYERS = 2; final int DEF_ROWS = 6; // Default number of rows final int DEF_COLUMNS = 7; // Default number of columns final Color INVISIBLE = Color.black; final Color BACKGROUND = new Color(225,225,255); final Color BLACK = Color.black; final int SELECT_REPRESENTATION = 1; final String aboutString = "Four in a Row by Gottfried Rudorfer"; } class Counter implements FourInaRowBase { public static void prelude() { the_counter_no = 0; } public Counter() { the_colour = INVISIBLE; } public Counter(Color representation) { the_colour = representation; } public Counter(int dummy) { Color[] colors = {Color.white, Color.red, Color.green, Color.blue}; String[] names = {"White", "Red", "Green", "Blue"}; the_colour = colors[the_counter_no]; the_colour_name = names[the_counter_no]; the_counter_no++; } public Color colour() // Returns the colour of a counter { return the_colour; } public String colour_name() // Returns the colour of a counter { return the_colour_name; } private static int the_counter_no = 0; // Which colour to allocate next private Color the_colour; // The colour of the counter private String the_colour_name; // The name of the colour } class Cell implements FourInaRowBase { public Cell() { the_counter = new Counter(INVISIBLE); } public void clear() { the_counter = new Counter(INVISIBLE); } public void drop(Counter c) { the_counter = new Counter(c.colour()); } public Color holds() { return the_counter.colour(); } public Graphics g() { return gr; } public void displayCounter(Graphics g, int xoff, int yoff, int xdiff, int ydiff) { g.setColor(the_counter.colour()); g.fillOval(xoff, yoff, xdiff, ydiff); gr = g; } public void fill(Graphics g) { g.setColor(the_counter.colour()); } private Counter the_counter; private Graphics gr; } class Player implements FourInaRowBase { public Player() { the_players_counter = new Counter(SELECT_REPRESENTATION); } Counter get_counter() // Get a counter { return the_players_counter; } String announce(final int what) // Announce win/draw { String playerName = the_players_counter.colour_name(); String resultStr=playerName; switch(what) { case WIN: resultStr+=" wins."; break; case DRAW: resultStr+=" has filled the board."; break; } return resultStr; } private Counter the_players_counter; } class Board extends Applet implements FourInaRowBase { public Board() { reset(); } public Board(final int rows, final int columns) { reset(rows, columns); } public void reset() { reset(DEF_ROWS, DEF_COLUMNS); } public void reset(final int rows, final int columns) { the_row_size = rows; the_column_size = columns; for (int i=0; i<the_column_size; i++) { for (int j=0; j<the_row_size; j++) { the_grid[j][i] = new Cell(); } the_height[i] = 0; } the_last_row = the_last_col = 0; the_no_empty_cells = rows * columns; the_last_message = ""; } public void drop_in_column(final int column, final Counter c) { the_last_col = column; the_last_row = the_height[column]; add_counter_to_board(column, c); } public boolean move_ok_for_column(final int column) { if (column >= 0 && column < the_column_size) { if (the_height[column] < the_row_size) { return true; } } return false; } public void displayBoard(Graphics g, Dimension d) { for (int i=the_row_size - 1; i >= 0; i--) { for (int j=0; j < the_column_size; j++) { int xunit = d.width / (1 + the_column_size); int yunit = d.height / (1 + the_row_size); the_grid[i][j].displayCounter(g, j * yunit, -i * xunit, yunit, xunit); } } } public void set_graphic_size(Dimension d) { the_graphic_size = d; } public int situation() { if (is_there_a_win() == true) { return WIN; } if (the_no_empty_cells == 0) { return DRAW; } return PLAY; } public String message() { return the_message; } public String last_message() { return the_last_message; } public void last_message(String msg) { the_last_message = msg; } public void printMessage(String messageText) { the_message = messageText; repaint(); } protected int check_for_a_win(final int dir, final int x_coord, final int y_coord, final Color counter) { int x = x_coord; int y = y_coord; if ( (x >= 0) && (x < the_row_size) && (y >= 0) && (y < the_column_size) && (the_grid[x][y].holds() == counter) ) { switch(dir) { case 1: y++; break; case 2: x++; y++; break; case 3: x++; break; case 4: x++; y--; break; case 5: y--; break; case 6: x--; y--; break; case 7: x--; break; case 8: x--; y++; break; default: printMessage("internal error 1\n"); } return 1 + check_for_a_win(dir, x, y, counter); } else { return 0; } } protected void add_counter_to_board(final int column, final Counter players_counter) { int row = the_height[column]; the_grid[row][column].drop(players_counter); the_grid[row][column].fill(the_grid[row][column].g()); the_height[column]++; the_no_empty_cells--; } protected boolean is_there_a_win() { Color stone = the_grid[the_last_row][the_last_col].holds(); for (int dir=1; dir <= 4; dir++) { int stones_in_a_line = check_for_a_win(dir, the_last_row, the_last_col, stone) + check_for_a_win(dir+4, the_last_row, the_last_col, stone) - 1; if ( stones_in_a_line >= STONES_IN_A_WIN_LINE ) { return true; } } return false; } private Cell the_grid[][] = new Cell [MAXROW][MAXCOLUMN]; private int the_height[] = new int [MAXCOLUMN]; // Current height of counters col private int the_row_size; private int the_column_size; // Size of playing area private int the_last_col; private int the_last_row; // Last counter placed private int the_no_empty_cells; // No. of cells still empty private String the_last_message; // Last printed message private String the_message; // the message private Dimension the_graphic_size; // Dimension of graphic }
© 1997 Gottfried Rudorfer, C++-AG, Lehrveranstaltungen, Abteilung für Angewandte Informatik, Wirtschaftsuniversität Wien, 3/19/1998 |