HangmanCanvas

Chapter: Object Oriented Design
...Section: Hangman
... ...Subsection: HangmanCanvas

From the lecture we see we need:

class HangmanCanvas extends Canvas {

To keep track of the wrong guesses we need:

  private int wrongGuesses = 0;

and we'll need ways to correctly maintain this state element:

  public void resetWrongGuesses() {
    wrongGuesses = 0;
    repaint();
  }
  public void addWrongGuess() {
    wrongGuesses++;
    repaint();
  }

Q. 1
Why the repaint()?


The paint() method needs access to int wrongGuesses:

    if (wrongGuesses >= 1) {
      g.drawOval(20,20,50,50);  // head
      g.fillOval(30,40,7,7);    // left eye
      g.fillOval(50,40,7,7);    // right eye
      if (wrongGuesses < 7) g.fillArc(35,40,20,20,-10,-170);  // smile
      else g.fillArc(35,50,20,20,10,170);             // no smile
    }
    if (wrongGuesses >= 2) g.drawLine(45,70,45,140); // body
    if (wrongGuesses >= 3) g.drawLine(45,85,10,65);  // left arm
    if (wrongGuesses >= 4) g.drawLine(45,85,80,65);  // right arm
    if (wrongGuesses >= 5) g.drawLine(45,140,20,200);// left leg
    if (wrongGuesses >= 6) g.drawLine(45,140,70,200);// right leg
    if (wrongGuesses >= 7) g.fillRect(45,5,5,15);   // rope

We always draw the scaffold. The head will be drawn with a smiling mouth unless wrongGuesses is 7 (the smile goes away at that point), and portions of the body are drawn according to the value of the variable wrongGuesses. This code is embedded in the canvas' paint method.

A slick trick to achieve the same result can be done using the switch construct:

    switch (wrongGuesses) {
    case 7: g.fillRect(45,5,5,15);   // rope
      g.fillArc(35,50,20,20,10,170);             // exMouth
    case 6: g.drawLine(45,140,70,200);// right leg
    case 5: g.drawLine(45,140,20,200);// left leg
    case 4: g.drawLine(45,85,80,65);  // right arm
    case 3: g.drawLine(45,85,10,65);  // left arm
    case 2: g.drawLine(45,70,45,140); // body
    case 1: if (wrongGuesses < 7) g.fillArc(35,40,20,20,-10,-170);  // mouth
      g.drawOval(20,20,50,50);  // head
      g.fillOval(30,40,7,7);    // left eye
      g.fillOval(50,40,7,7);    // right eye
    }
Normally, one terminates each case of a switch construct with a break. This causes control to transfer to the code immediately following the entire switch structure once the identified case has been processed. It is a very common programming error to omit this break. In this example, however, we really do want control to trickle down through the lower numbered cases. Click here to see the entire code for the HangmanCanvas class.

Now of course, you should write a test program to make sure the HangmanCanvas works. Here's mine.


Exercise 8

Coloring the Victim

This is more an artistic than a programming exercise. Quite simple really. Modify the code of HangmanCanvas.java so that the artistic rendition is improved somewhat. You may resize, reposition, replace, or recolor any pieces you like. You may create and/or import gifs or sound files -- anything you like. Have fun! Keep working on this outside of class. The best canvas I see will be shown off to the class. Your grade will not be greatly improved by an elaborate solution to this exercise; but I will certainly be pleased to see amusing solutions.