Chapter 11

The exercises here are taken from my forthcoming book The Java Developer's Resource.

Quiz

  1. What happens if you try to draw objects at negative coordinates? e.g. g.drawLine(-5, -4, 64, 50)?

    Negative coordinates are valid. However you won't see anything drawn there, at least not until you learn how to make the screen scrollable. This line will appear to enter the applet from above and to the left.

  2. What's the difference between g.drawLine(0, 1, 5, 6) and g.drawLine(5, 6, 0, 1)?

    These are two different ways of specifying the same line. One draws from top to bottom and left to right, the other from bottom right to top left. However, both produce the same line.

  3. What's the difference between g.drawLine(0, 1, 5, 6) and g.drawLine(1, 0, 6, 5)?

    These are two different lines. The first is between the two points (x=0, y=1) and (x=5, y=6); the second between (x=1, y=0) and (x=6, y=5). This isn't a large difference, but it is a difference.

Exercises

  1. Modify the WrapText applet so that it optionally accepts FONT, SIZE and STYLE PARAMs which set the font face, point size and style in which the String is drawn. Be sure to gracefully handle the case when the APPLET tag does not include any or all of these PARAMs or includes invalid values (e.g. STYLE="UNDERLINE").

    
    import java.applet.Applet;    
    import java.awt.Graphics; 
    import java.awt.FontMetrics;
    import java.util.StringTokenizer;
    import java.awt.Font;
                 
    public class WrapTextApplet extends Applet {
    
      String input_from_page;
      int margin = 5;
      Font theFont;
      
    
      public void init() {
      
        String s;
        int fontsize = 12;
        String fontname = "Courier";
        int fontstyle = Font.PLAIN;
    
        input_from_page = getParameter("Text");
        if ((s = getParameter("Size")) != null) {
          fontsize = Integer.parseInt(s);    
        }
        if ((s = getParameter("Style")) != null) {
          if (s.equalsIgnoreCase("Italic")) fontstyle = Font.ITALIC;
          if (s.equalsIgnoreCase("Bold")) fontstyle = Font.BOLD;
        }
        if ((s = getParameter("Font")) != null) {
          fontname = s;    
        }
        theFont = new Font(fontname, fontstyle, fontsize); 
      }
      
      public void paint(Graphics g) {
        int i = 0;
        int linewidth = 0;
        StringBuffer sb = new StringBuffer();
        g.setFont(theFont);
      	FontMetrics fm = g.getFontMetrics();
      	StringTokenizer st = new StringTokenizer(input_from_page);
      	while (st.hasMoreTokens()) {
      	  String nextword = st.nextToken();
      	  if (fm.stringWidth(sb.toString() + nextword) < size().width) {
        	sb.append(nextword);
      	    sb.append(' ');
      	  }
      	  else if (sb.length() == 0) {
      	    g.drawString(nextword, margin, ++i*fm.getHeight());
      	  }
      	  else {
            g.drawString(sb.toString(), margin, ++i*fm.getHeight());
            sb = new StringBuffer(nextword + " ");
          }      
          
        }
        if (sb.length() > 0) {
      	  g.drawString(sb.toString(), margin, ++i*fm.getHeight());
      	 }   
        
      }
      
    } 
    
  2. The default StringTokenizer used by the WrapText applet breaks words on white space, i.e. spaces, tabs, newlines and carriage returns. Make it more intelligent about choosing line breaks. In particular, let it break a line on a hyphen and have it jump to the next line (i.e. end a paragraph) on a newline or a carriage return. To do this you'll need to use a different StringTokenizer constructor, specifically StringTokenizer(String s, String delimiters) where s is the String to tokenize and delimiters is a String that contains all the characters you want to break on.

  3. If the String won't fit in the applet, even after breaking into pieces, shrink the font size so that it does fit. What's the smallest font size you can use?

  4. Add labeled coordinate axes to the SineApplet graph. Make sure they adjust if the applet is resized.

  5. Modify the SineApplet so that it looks for xmin, xmax, ymin, and ymax to be specified via parameters. However for robustness if the author of the HTML forgets to specify them, supply some reasonable default values. You will probably need to make these member variables rather than local variables.


[ Exercises | Cafe Au Lait | Books | Trade Shows | Links | FAQ | Tutorial | User Groups ]

Copyright 1996 Elliotte Rusty Harold
elharo@sunsite.unc.edu
Last Modified August 23, 1996