Double Buffering

Let's look at the code, which can be found in DB.java:

Line 4 specifies the DB class as extending the Applet class. This time, besides declaring the image, we also declare a boolean that indicates if the whole image has been loaded:

	public class DB extends Applet {
		Image background;
		boolean done_loading = false;

Initializing

Int the initialization function, we get the image and storing it in background. Then we create an image offscreen, and get the grapics context for the offscreen image. Then we draw the image offscreen with the drawImage function. We pass this as the last parameter to drawImage, which is the ImageObserver class. The ImageObserver class is an Interface defined in the java.awt.image package. The applet uses the this keyword as the ImageObserver parameter for the offscreen image, which means the applet must contain the ImageObserver interface function, which is the imageUpdate function.
	public void init() {
		background = getImage(getCodeBase(), "./images/ANIM0.GIF");
		Image offscreen = createImage(442, 341);
		Graphics myGC = offscreen.getGraphics();
		myGC.drawImage(background, 0, 0, this);
	}

Updating the Image

To use the ImageObserver class, the applet must implement the imageUpdate function. As it turns out, each time the runs, it creates a thread that in turn calls imageUpdate. The last parameter in the drawImage function determines whether or not it calls the imageUpdate function. If the parameter is null, then drawImage does not call imageUpdate. If the parameter passed is this then drawImage will call the imageUpdate function defined by the current class:
	public boolean imageUpdate(Image img, int flag, int x, int y, int w, int h) {
		if (flag == ALLBITS) {
			done_loading = true;
			repaint();
			return false;
		}
		else
			return true;
	}
The function returns a boolean value that specifies whether or not the function should be called again for the next block of the image. The function uses the flag parameter to determine how much of the image has been drawn. When this parameter equals ALLBITS, the image is done and the done_loading variable is set to true, and calls repaint() so that the paint function can draw the image.

Painting

The paint method just draws the image on the screen without waiting for the image to be completely loaded:
	public void paint(Graphics g) {
		if (done_loading)
		g.drawImage(background, 0, 0, null);
	}
When the image has been drawn, the applet will not use the drawImage to call the imageUpdate function again. Therefore, the applet passes the drawImage function a null value for the ImageObserver parameter.


Back to Lecture2