| CSC 8310: Example Applet
with GUI David Matuszek, Villanova University |
This applet uses a simple GUI, and exemplifies the Model-View-Controller design pattern. That is, it divides the problem in three parts and assigns behaviors to each, as follows:
view.model = model;
view.controller = this;
This clean separation should make it a lot easier for you to adapt my code to your needs.
import java.applet.*;
import java.awt.*;
import java.awt.event.*;
/**
* The Controller defines the layout, initializes the Model, and
* put up the controls (in this case, a single "Step" button).
* It controls the Model by calling makeOneStep(), and it controls
* the View by calling view.repaint() as needed.
*/
public class Controller extends Applet {
// Declare components here, where they are visible to inner classes
Panel buttonPanel = new Panel ();
Button stepButton = new Button ("Step");
Model model = new Model ();
View view = new View ();
/**
* Creates and lays out components. Also tells the View about
* the Controller so that it can access the status line.
*/
public void init () {
// Lay out components
setLayout (new BorderLayout ());
buttonPanel.add (stepButton);
this.add (BorderLayout.SOUTH, buttonPanel);
this.add (BorderLayout.CENTER, view);
// Attach actions to components
stepButton.addActionListener (new ActionListener () {
public void actionPerformed (ActionEvent event) {
model.makeOneStep ();
view.repaint ();
}});
// Tell the View about myself (Controller) and about the Model
view.model = model;
view.controller = this;
}
/**
* Records the Applet size. We can't do this in init() because
* the Applet doesn't actually have a size until it has been
* initialized.
*/
public void start () {
model.xLimit = view.getSize ().width - model.BALL_SIZE;
model.yLimit = view.getSize ().height - model.BALL_SIZE;
repaint ();
}
}
/** The Model is the actual simulation (in this case, of a
* bouncing ball). The Controller class causes it to do something
* by calling makeOneStep(). The model class doesn't know or care
* about either the Controller class or the View class.
*/
class Model {
final int BALL_SIZE = 20;
int xPosition = 0;
int yPosition = 0;
int xLimit, yLimit;
int xDelta = 6;
int yDelta = 4;
/**
* Advances the simulation one step.
*/
void makeOneStep () {
xPosition += xDelta;
if (xPosition < 0) {
xPosition = 0;
xDelta = -xDelta;
}
if (xPosition >= xLimit) {
xPosition = xLimit;
xDelta = -xDelta;
}
yPosition += yDelta;
if (yPosition < 0 || yPosition >= yLimit) {
yDelta = -yDelta;
yPosition += yDelta;
}
}
}
/**
* The View class is responsible for displaying the current
* condition of the Model. It is entirely concerned with display,
* not with running or controlling the simulation. (It does,
* however, use the showStatus(String) method to put a message
* in the part of the display owned by the Controller.)
*/
class View extends Canvas {
Controller controller;
Model model;
int stepNumber = 0;
/**
* Display the current state of the simulation.
*/
public void paint (Graphics g) {
g.setColor (Color.red);
g.fillOval (model.xPosition, model.yPosition,
model.BALL_SIZE, model.BALL_SIZE);
controller.showStatus ("Step " + (stepNumber++) +
", x = " + model.xPosition +
", y = " + model.yPosition);
}
}