This document describes a redesign of a two-player tennis game using factory, command, and state design patterns. The factory pattern was used to create balls and players. The command pattern was implemented to control player movement via keyboard commands. The state pattern was applied to the scoring system. Screenshots show the patterns in use. Two changes were made: adding serve switching and a challenge/undo feature, though these had implementation issues. Future work includes improving challenge/serve handling using the design patterns.
2. i
Table of Contents
1 Description of Problem............................................................................................................ 1
2 Literary Review ....................................................................................................................... 1
3 Design..................................................................................................................................... 1
3.0 Use Case Diagram ........................................................................................................... 1
3.1 High-level Design ............................................................................................................. 2
3.2 Patterns............................................................................................................................ 3
3.2.1 Factory Pattern .......................................................................................................... 3
3.2.2 Command Pattern...................................................................................................... 5
3.2.3 State Pattern.............................................................................................................. 8
3.3 Results ............................................................................................................................10
3.4 Changes..........................................................................................................................12
4 Future Work ...........................................................................................................................16
5 References ............................................................................................................................16
6 Appendix: Detailed Class Information ....................................................................................17
Table of Figures
Figure 1 Use Case Diagram....................................................................................................... 2
Figure 2 High-level Class Diagram............................................................................................. 2
Figure 3 Ball Factory Pattern...................................................................................................... 3
Figure 4 Ball Factory Pattern Sequence Diagram ...................................................................... 4
Figure 5 Player Factory Pattern ................................................................................................. 4
Figure 6 Command Pattern........................................................................................................ 5
Figure 7 Move Down Command Pattern Sequence Diagram ..................................................... 6
Figure 8 Stop Vertical Move Sequence Diagram........................................................................ 6
Figure 9 Score State Diagram.................................................................................................... 9
Figure 10 State Pattern Sequence Diagram............................................................................... 9
Figure 11 Mario Tennis Start Up ...............................................................................................10
Figure 12 Mario Tennis Player Movement.................................................................................11
Figure 13 Mario Tennis Tie Score .............................................................................................11
Figure 14 Mario Tennis A Score................................................................................................12
Figure 15 Mario Tennis Change Serve Dialog...........................................................................14
Figure 16 Mario Tennis Switch Serve........................................................................................14
Figure 17 Mario Tennis Challenge Point ...................................................................................15
Figure 18 Mario Tennis Challenge Undo...................................................................................15
3. 1
1 Description of Problem
This project aims to redesign a two player tennis game using factory, command, and state
design patterns.
2 Literary Review
The literature reviewed for this project included PowerPoint slides from Dr. Shehata’s
lectures on design patterns and Java Swing, and code for a two player tennis game created by
pochaKodu4793 (2014) on http://www.dreamincode.net. The tennis game code on the website
has five classes: ball, player, computer, tcourt, and tennis. The ball, player, and computer classes
are run inside threads which are created in the tcourt class. These three classes have a runnable
interface which is used for threads. A search was also conducted using Google search to
determine if there were any tennis game designs using design patterns. No relevant information
was found.
3 Design
The following subsections will discuss the use case diagram, high-level UML class
design, design patterns used in the project, the results, and the changes implemented into the
project.
3.0 Use Case Diagram
The figure on the next page is a use case diagram of the tennis game. The two external
entities are the players and the operating system. The user and operating system are jointly
responsible for starting the game, moving the players, moving the ball, and exiting the game. The
operating system is responsible for creating the graphical user interface and updating the score.
Player1 uses keys A,S,D,X to move backward, up, forward, and down respectively. Player2 uses
left, up, right, and down to move forward, up, backward, and down respectively. To serve the
ball, player1 uses the Q key and player2 uses the P key. The scoring system for tennis is 0, 15,
30, 40, and win unless there is a tie at 40. When there is a tie and a player scores, that player will
get an A for advantage. If they score again, that player wins.
4. 2
Figure 1 Use Case Diagram
3.1 High-level Design
The following figure shows a high level design of the tennis game project. The Main
class creates a frame called Tennis. Board extends JPanel and is the surface upon which the
players and ball are drawn. The other classes and interfaces form part of the design patterns
which will be discussed in the following sections.
Figure 2 High-level Class Diagram
5. 3
3.2 Patterns
Three design patterns were used in this project: factory, command, and state. They will
be discussed in the following subsections.
3.2.1 Factory Pattern
The factory pattern was used within the Board class to create two players and a ball. The
UML diagram below shows the factory pattern for the ball. The AbstractCreator and
ConcreteCreator classes contain a createObject method. The createObject method in the
ConcreteCreator class returns a Ball object. The method has parameters board, player1, and
player2.
The Ball class implements the Product interface which has accessors such as getX(),
mutators such as setX(), run() which starts a thread, paint which paints the ball image on the
screen, retserve() which returns a boolean indicating if the ball has been hit back by a player,
servetime() which returns if the ball needs to be served, reverseDirection() and
reverseDirectionY() which reverse the x and y coordinate directions respectively. keyPressed is
an event listener that listens for key presses.
Figure 3 Ball Factory Pattern
6. 4
The sequence diagram below shows the messages passed between classes to create a ball.
The Board class calls the createObject method of the AbstractCreator and ConcreteCreator
classes which creates and returns the ball.
Figure 4 Ball Factory Pattern Sequence Diagram
The factory pattern was also used to create both players. It differs slightly from the
factory pattern used for the ball. As can be seen from the figure below, the createPlayer method
in the AbstractPlayerCreator class takes board, two images, the x position of the player, and a
boolean called play to indicate which player is being created-player1 or player2. The sequence
diagram looks very similar to the one for the ball; hence, it will be omitted.
Figure 5 Player Factory Pattern
The following code fragments are used to implement the factory pattern.
7. 5
3.2.2 Command Pattern
The command pattern was used to control the movements of the player. Each player can
move up, down, left, and right. Player1 uses the S,X,A, and D keys to move up, down, backward,
and forward respectively. Player2 uses up, down, right, and left keys accordingly. In the UML
diagram below, the Board class acts as an invoker. It also adds a keyListener. Each of the
commands implements the KeyListener interface which has three methods keyPressed,
keyReleased, and keyTyped. The move up, move down, move left, and move right commands
use the keyPressed event, whereas the stopMoveHorizontal and stopMoveVertical commands
use the keyRelease event. Also each command’s constructor takes player1 and player2 as
parameters because the command needs to determine which player to move when it calls its
execute method. The player is the receiver of the action, and it implements all the command
methods. The pressKey method in the Player class takes a parameter command which determines
which command’s execute method will run.
Figure 6 Command Pattern
8. 6
The sequence diagram below depicts the messages for the moveDownCommand. Board
initiates a keyPressed event. The MoveDownCommand calls pressKey in Player and passes it a
command. The player, in turn, calls execute in the moveDownCommand. Finally, the
moveDownCommand calls the moveDown method in Player which moves the player down by a
factor of two. A similar sequence occurs for move up, move left, and move right.
Figure 7 Move Down Command Pattern Sequence Diagram
The figure below shows the stopMoveVertical command sequence diagram. The only
difference is that it uses the keyReleased method instead of keyPressed. When the key
corresponding to up or down motion is released the yVelocity changes to 0, and the player stops.
stopMoveHorizontal works similar except that the xVelocity changes to 0, and the player stops.
Figure 8 Stop Vertical Move Sequence Diagram
The following code was used to implement the command pattern in the Board class.
9. 7
In the constructor of the Board class the keyListener was added.
An inner class was also created in the Board class.
In the MoveLeftCommand, for instance, the execute and keyPressed methods looked like the
following.
Finally, in the Player class is the pressKey method and the moveLeft method. The moveLeft
method is what moves the player.
10. 8
3.2.3 State Pattern
The state pattern was used to implement the scoring system. The UML diagram on the
next page depicts the class diagram for the state pattern. The Ball class acts as a context
interface. The three states are normal, where the score proceeds normally (i.e. 0, 15, 30, etc);
adstate1, where player1 gets a score of A for advantage when both players are tied at 40 and
player1 scores; and adstate2, where player2 gets a score of A when both players are tied at 40
and player2 scores. Each of the states implements a ScoreState interface with a method called
scoreUpdate which takes a ball object.
11. 9
Figure 9 Score State Diagram
The following sequence diagram shows the messages passed between the classes. Ball
uses the scoreUpdate method to update the score. The various states are set in the Ball class
using the setScoreState method.
Figure 10 State Pattern Sequence Diagram
The state pattern was implemented under a new package named Score. The following
code in the Ball class sets the state to a normal state. The class also has accessors and mutators to
get and set the state accordingly.
12. 10
The state can be changed within the scoreUpdate function. The following code segment
illustrates this.
or
3.3 Results
This section will show screenshots depicting the results of the patterns implemented in
the previous section. The figure below shows the result of the factory pattern creating the ball
and two players.
Figure 11 Mario Tennis Start Up
13. 11
The following figure depicts player movement using the command pattern. Player1 has
moved forward and down (keys D and X respectively). Player2 has moved forward and up (keys
left and up respectively).
Figure 12 Mario Tennis Player Movement
The following figures show the before and after state of scoring when there is a tie at 40
using the state pattern. Notice that player1 has an A as their score.
Figure 13 Mario Tennis Tie Score
14. 12
Figure 14 Mario Tennis A Score
3.4 Changes
Two changes were required for this project. The first was a mechanism to change serves
between player1 and player2. The second was a means to undo the score after a player
challenged a score and change the serve back to the original player that served. Because of
implementation issues with the command pattern, this functionality was added by hacking the
code in the Ball class.
For the change serve feature, a few boolean variables were created. Serve was used to
indicate that a player had scored, and the ball needed to be served. Player1served was used to
indicate which player was serving. The following code was added to the keyPressed listener in
the Ball class. As indicated previously, the Q key serves the ball for player1 and P serves the ball
for player2.
15. 13
The serve method determines the player that should serve using the player1served flag.
See code below.
The figure on the next page shows a confirm dialog box indicating a change of serve
followed by the ball being drawn next to player2.
16. 14
Figure 15 Mario Tennis Change Serve Dialog
Figure 16 Mario Tennis Switch Serve
For the challenge/undo feature, first the keyPress listener determines if a player pressed
F1 or F12 after a point has been scored and before a player has served. See code at the end of the
second paragraph in this section. When a player has challenged the point, a confirm dialog box
appears. If the player chooses ok, then the scoreUndo method is called which reverts the score to
the previous score for the player that scored the point that is being challenged.
17. 15
The following figures depict a challenge and the subsequent reversal of player1’s score.
Player1 retains serve because it had the serve prior to the challenge.
Figure 17 Mario Tennis Challenge Point
Figure 18 Mario Tennis Challenge Undo
18. 16
4 Future Work
The following work still needs to be performed:
1. Implement challenge (undo) using command pattern. The F1 or F12 keys initiate a
challenge to a play when the ball is out of play.
2. Implement serve change using state pattern.
3. Implement serve action using command pattern. The Q key initiates the serve for
player1. The P key initiates the serve for player2.
4. Implement ball movement using state pattern. The ball can move six ways: horizontal-
up-forward, horizontal-straight-forward, horizontal-down-forward, horizontal-up-
backward, horizontal-straight-backward, and horizontal-down-backward.
5 References
pochaKodu4793. (2014, February 14). A Multiplayer Tennis Game. Retrieved from
http://www.dreamincode.net/forums/topic/340017-a-multiplayer-tennis-game/
Shehata, M. (2014). Unit 3: Design Patterns, Lecture 2: Command Pattern, Strategy Pattern
[PowerPoint slides]
Shehata, M. (2014). Unit 3: Design Patterns, Lecture 3: State Pattern [PowerPoint slides]
Shehata, M. (2014). Unit 3: Design Patterns, Lecture 6: Creational Pattern [PowerPoint slides]
Mohamed, A, (n.d.). Java Swing [PowerPoint slides]