57 |
58 |
59 |
60 |
--------------------------------------------------------------------------------
/src/lab1/GameModel.java:
--------------------------------------------------------------------------------
1 | package lab1;
2 |
3 | import java.awt.Dimension;
4 |
5 | /**
6 | * Common superclass for all game model classes.
7 | *
8 | * Constructors of subclasses should initiate matrix elements and additional,
9 | * game-dependent fields.
10 | */
11 | public abstract class GameModel {
12 |
13 | /** A Matrix containing the state of the gameboard. */
14 | private final GameTile[][] gameboardState;
15 |
16 | /** The size of the state matrix. */
17 | private final Dimension gameboardSize = Constants.getGameSize();
18 |
19 | /**
20 | * Create a new game model. As GameModel is an abstract class, this is only
21 | * intended for subclasses.
22 | */
23 | protected GameModel() {
24 | this.gameboardState =
25 | new GameTile[this.gameboardSize.width][this.gameboardSize.height];
26 | }
27 |
28 | /**
29 | * Set the tile on a specified position in the gameboard.
30 | *
31 | * @param pos
32 | * The position in the gameboard matrix.
33 | * @param tile
34 | * The type of tile to paint in specified position
35 | */
36 | protected void setGameboardState(final Position pos, final GameTile tile) {
37 | setGameboardState(pos.getX(), pos.getY(), tile);
38 | }
39 |
40 | /**
41 | * Set the tile on a specified position in the gameboard.
42 | *
43 | * @param x
44 | * Coordinate in the gameboard matrix.
45 | * @param y
46 | * Coordinate in the gameboard matrix.
47 | * @param tile
48 | * The type of tile to paint in specified position
49 | */
50 | protected void setGameboardState(final int x, final int y,
51 | final GameTile tile) {
52 | this.gameboardState[x][y] = tile;
53 | }
54 |
55 | /**
56 | * Returns the GameTile in logical position (x,y) of the gameboard.
57 | *
58 | * @param pos
59 | * The position in the gameboard matrix.
60 | */
61 | public GameTile getGameboardState(final Position pos) {
62 | return getGameboardState(pos.getX(), pos.getY());
63 | }
64 |
65 | /**
66 | * Returns the GameTile in logical position (x,y) of the gameboard.
67 | *
68 | * @param x
69 | * Coordinate in the gameboard matrix.
70 | * @param y
71 | * Coordinate in the gameboard matrix.
72 | */
73 | public GameTile getGameboardState(final int x, final int y) {
74 | return this.gameboardState[x][y];
75 | }
76 |
77 | /**
78 | * Returns the size of the gameboard.
79 | */
80 | public Dimension getGameboardSize() {
81 | return this.gameboardSize;
82 | }
83 |
84 | /**
85 | * This method is called repeatedly so that the game can update it's state.
86 | *
87 | * @param lastKey
88 | * The most recent keystroke.
89 | */
90 | public abstract void gameUpdate(int lastKey) throws GameOverException;
91 |
92 |
93 | /**
94 | * Returns the current score.
95 | */
96 | public abstract int getScore();
97 | }
98 |
--------------------------------------------------------------------------------
/doc/lab1/package-frame.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | lab1
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 | lab1
20 |
84 |
85 |
86 |
87 |
88 |
--------------------------------------------------------------------------------
/src/lab1/RoundTile.java:
--------------------------------------------------------------------------------
1 | package lab1;
2 |
3 | import java.awt.BasicStroke;
4 | import java.awt.Color;
5 | import java.awt.Dimension;
6 | import java.awt.Graphics;
7 | import java.awt.Graphics2D;
8 | import java.awt.Stroke;
9 |
10 | /**
11 | * A round tile manages painting of a circle
12 | * in a specified area of the screen.
13 | *
14 | * Whenever the object should paint itself,
15 | * it is told what size and position that
16 | * should be used to paint it.
17 | */
18 | public class RoundTile extends GameTile {
19 |
20 | /** The color of the circle */
21 | private final Color strokeColor;
22 | private final Color fillColor;
23 | private final Stroke stroke;
24 | private final double scale;
25 |
26 | /**
27 | * Creates a circular game tile.
28 | *
29 | * @param fillColor
30 | * the color of the interior of the circle.
31 | */
32 | public RoundTile(final Color fillColor) {
33 | this(fillColor, fillColor);
34 | }
35 |
36 | /**
37 | * Creates a circular game tile with a stroke around it.
38 | *
39 | * @param strokeColor
40 | * the color of the stroke around the circle.
41 | * @param fillColor
42 | * the color of the interior of the circle.
43 | */
44 | public RoundTile(final Color strokeColor, final Color fillColor) {
45 | this(strokeColor, fillColor, 1.0);
46 | }
47 |
48 | /**
49 | * Creates a circular game tile with a stroke around it.
50 | *
51 | * @param strokeColor
52 | * the color of the stroke around the circle.
53 | * @param fillColor
54 | * the color of the interior of the circle.
55 | * @param thickness
56 | * the thickness of the stroke.
57 | */
58 | public RoundTile(final Color strokeColor, final Color fillColor,
59 | final double thickness) {
60 | this(strokeColor, fillColor, thickness, 1.0);
61 | }
62 |
63 | /**
64 | * Creates a circular game tile with a stroke around it.
65 | *
66 | * @param strokeColor
67 | * the color of the stroke around the circle.
68 | * @param fillColor
69 | * the color of the interior of the circle.
70 | * @param thickness
71 | * the thickness of the stroke.
72 | * @param scale
73 | * size of the circle relative to the tile size.
74 | */
75 | public RoundTile(final Color strokeColor, final Color fillColor,
76 | final double thickness, final double scale) {
77 | this.strokeColor = strokeColor;
78 | this.fillColor = fillColor;
79 | this.stroke = new BasicStroke((float) thickness);
80 | this.scale = scale;
81 | }
82 |
83 | /**
84 | * Draws itself in a given graphics context, position and size.
85 | *
86 | * @param g
87 | * graphics context to draw on.
88 | * @param x
89 | * pixel x coordinate of the tile to be drawn.
90 | * @param y
91 | * pixel y coordinate of the tile to be drawn.
92 | * @param d
93 | * size of this object in pixels.
94 | */
95 | @Override
96 | public void draw(final Graphics g, final int x, final int y,
97 | final Dimension d) {
98 | Graphics2D g2 = (Graphics2D) g;
99 | g2.setColor(this.fillColor);
100 | double xOffset = (d.width * (1.0 - this.scale)) / 2.0;
101 | double yOffset = (d.height * (1.0 - this.scale)) / 2.0;
102 | g2.fillOval((int) (x + xOffset), (int) (y + yOffset),
103 | (int) (d.width - xOffset * 2),
104 | (int) (d.height - yOffset * 2));
105 | g2.setStroke(this.stroke);
106 | g2.setColor(this.strokeColor);
107 | g2.drawOval((int) (x + xOffset), (int) (y + yOffset),
108 | (int) (d.width - xOffset * 2),
109 | (int) (d.height - yOffset * 2));
110 | }
111 | }
112 |
--------------------------------------------------------------------------------
/src/lab1/GameView.java:
--------------------------------------------------------------------------------
1 | package lab1;
2 |
3 | import java.awt.Color;
4 | import java.awt.Dimension;
5 | import java.awt.Font;
6 | import java.awt.Graphics;
7 | import java.awt.Image;
8 |
9 | import javax.swing.JComponent;
10 |
11 | /**
12 | * A view Component suitable for inclusion in an AWT Frame. Paints itself by
13 | * consulting its model.
14 | */
15 | public class GameView extends JComponent {
16 |
17 | /**
18 | *
19 | */
20 | private static final long serialVersionUID = 1534474796794225462L;
21 |
22 | /** Size of game model */
23 | private final Dimension modelSize;
24 |
25 | /** Size of every tile in the model */
26 | private final Dimension tileSize;
27 |
28 | /** The game model which is drawn */
29 | private GameModel model;
30 |
31 | /** The offscreen buffer */
32 | private Graphics offscreenGraphics;
33 |
34 | /** Image representing the offscreen graphics */
35 | private Image offscreenImage;
36 |
37 | /**
38 | * Creates a view where each GameObject has side length 40 pixels..
39 | */
40 | public GameView() {
41 | this(40);
42 | }
43 |
44 | /**
45 | * Creates a view where each GameObject has a given size.
46 | *
47 | * @param tileSide
48 | * side length in pixels of each GameObject.
49 | */
50 | public GameView(final int tileSide) {
51 | this.tileSize = new Dimension(tileSide, tileSide);
52 | this.modelSize = Constants.getGameSize();
53 | Dimension preferredSize =
54 | new Dimension(this.modelSize.width * tileSide,
55 | this.modelSize.height * tileSide);
56 | setPreferredSize(preferredSize);
57 | }
58 |
59 | /**
60 | * Updates the view with a new model.
61 | */
62 | public void setModel(final GameModel model) {
63 | this.model = model;
64 | repaint();
65 | }
66 |
67 | /**
68 | * This method ensures that the painting is performed double-buffered. This
69 | * means there won't be any flicker when repainting all the time.
70 | */
71 | @Override
72 | public void update(final Graphics g) {
73 | // Create an offscreen buffer (if we don't have one)
74 | if (this.offscreenImage == null) {
75 | Dimension size = getSize();
76 |
77 | this.offscreenImage = createImage(size.width, size.height);
78 | this.offscreenGraphics = this.offscreenImage.getGraphics();
79 | }
80 |
81 | // This will invoke painting correctly on the offscreen buffer
82 | super.update(this.offscreenGraphics);
83 |
84 | // Draw the contents of the offscreen buffer to screen.
85 | g.drawImage(this.offscreenImage, 0, 0, this);
86 | }
87 |
88 | /**
89 | * Consults the model to paint the game matrix. If model is null, draws a
90 | * default text.
91 | */
92 | @Override
93 | public void paintComponent(final Graphics g) {
94 | // Check if we have a running game
95 | super.paintComponent(g);
96 | g.setColor(this.getBackground());
97 | g.fillRect(0, 0, getWidth(), getHeight());
98 |
99 | if (this.model != null) {
100 |
101 | /*
102 | * Show the current score in the graphics context. Requires a
103 | * getter method in the model (forced by having an abstract
104 | * 'getScore' method in GameModel).
105 | */
106 | g.setColor(Color.BLACK);
107 | g.setFont(new Font("Sans", Font.BOLD, 14));
108 |
109 | String scoreString = (this.model.getScore() == 1) ? "point" : "points";
110 | g.drawString(this.model.getScore() + " " + scoreString, 10, 20);
111 |
112 | // Draw all tiles by going over them x-wise and y-wise.
113 | for (int i = 0; i < this.modelSize.width; i++) {
114 | for (int j = 0; j < this.modelSize.height; j++) {
115 | GameTile tile = this.model.getGameboardState(i, j);
116 | tile.draw(g, i * this.tileSize.width, j
117 | * this.tileSize.height,
118 | this.tileSize);
119 | }
120 | }
121 | } else {
122 | g.setFont(new Font("Sans", Font.BOLD, 24));
123 | g.setColor(Color.BLACK);
124 | final char[] message = "No model chosen.".toCharArray();
125 | g.drawChars(message, 0, message.length, 50, 50);
126 | }
127 | }
128 | }
129 |
--------------------------------------------------------------------------------
/src/lab1/GUIView.java:
--------------------------------------------------------------------------------
1 | package lab1;
2 |
3 | import java.awt.BorderLayout;
4 | import java.awt.Color;
5 | import java.awt.event.ActionEvent;
6 | import java.awt.event.ActionListener;
7 |
8 | import javax.swing.JButton;
9 | import javax.swing.JComboBox;
10 | import javax.swing.JPanel;
11 |
12 | /**
13 | * This panel is meant to be the base of a window or applet. It will add a new
14 | * GameView with a corresponding GameController to itself. It will also provide
15 | * a gui for choosing a new game. The list of games will be aquired from
16 | * a GameFactory.
17 | */
18 | public class GUIView extends JPanel {
19 | /**
20 | *
21 | */
22 | private static final long serialVersionUID = -3394100357075618465L;
23 |
24 | /** The "Start Game" button */
25 | private final JButton startGameButton;
26 |
27 | /** The chooser (also called drop-down menu) with names of different games */
28 | private final JComboBox