import java.awt.*; import java.awt.event.*; import java.applet.*; /** BigPixelApplet is the superclass for applets that draw big fat pixels on screen. It doesn't do anything interesting by itself */ public class BigPixelApplet extends Applet implements Runnable { BigPixelCanvas canvas; //drawing area Button step; //The button that user clicks on to get algorithm to do next step Checkbox stepMode; //So user can turn off single step execution TextArea state; //For displaying internal state of a particular algorithm /* Next four methods are for convenience - we just use method forwarding to the BigPixelCanvas object */ /* map from virtual pixels to real ones */ int toScreenX(int x) { return canvas.toScreenX(x); } /* map from virtual pixels to real ones */ int toScreenY(int y) { return canvas.toScreenY(y); } /* map from real pixels to virtual ones */ int fromScreenX(int x) { return canvas.fromScreenX(x); } /* map from real pixels to virtual ones */ int fromScreenY(int y) { return canvas.fromScreenY(y); } void fillSpan(int startx, int endx, int y) { canvas.fillSpan(startx,endx,y); } void drawPixel(int x, int y) { canvas.drawPixel(x,y); } /** Thread that executes given algorithm */ Thread runner; /** Start thread that executes given algorithm */ public void begin() { runner = new Thread(this); runner.start(); //Do drawing is separate thread so it can step } /** Subclasses should overide this method to call the particular algorithm being animated. */ public void run() { /* Do nothing - subclasses should override */ } /** Make algorithm continue execution after step() has been called */ synchronized void wakeUp() { notify(); } /** Stop execution until "Step" button is pressed */ /* if this returns true, running thread should stop itself since another one has started */ synchronized boolean step() { state.append("\n---------\n"); state.append(showState()); state.setCaretPosition(999999); if (stepMode.getState()) { try { wait(); } catch (InterruptedException e) { /*nothing */ } } //System.out.println(Thread.currentThread() != runner); return Thread.currentThread() != runner; } /** show state of important data structures used by this algorithm */ String showState() { return ""; //default is nothing } /** init() is called by browser to initialize the applet */ public void init() { setBackground(Color.white); setFont(new Font("Default",Font.PLAIN,16)); setLayout(new BorderLayout()); canvas = new BigPixelCanvas(); add(canvas,"Center"); Panel p = new Panel(); /* When this button is clicked on the wakeUp method is called */ step = new Button("Step"); p.add(step); step.addActionListener( new ActionListener() { public void actionPerformed(ActionEvent e){ wakeUp(); } }); /* No need to do anything when user changes state of the checkbox */ stepMode = new Checkbox("Step Mode",true); p.add(stepMode); Button clear = new Button("Clear"); p.add(clear); clear.addActionListener( new ActionListener() { public void actionPerformed(ActionEvent e){ canvas.clear(); state.setText(""); } }); add(p,"South"); state = new TextArea(20,30); add(state,"East"); } }