Improved clocks (OPTIONAL)

The goal of this lab is to clean up all your clock drawing code. Make one or more of the following improvements as you see fit.

Clean up the teaching program

Convert your clock teaching program which uses procedures.

I recommend you actually combine the teaching program and the time-zone clock drawing program, adding any additional procedures as needed. Simple changes to main() will determine whether you want to display time zones, or if you want to teach a kid to tell time.

I'll start you off with a few suggestions:

  1. Write a procedure, normalizeAngle which takes an angle and adds or subtracts 2*PI; as needed until the angle is between -PI and PI.

  2. Use normalizeAngle to write a procedure anglesAboutEqual which checks if the difference in two angles is within a reasonable tolerance.

  3. There are two significant problems with using atan() to determine the angle of the mouse-click. First, atan() comes out the same for a point, p = (x,y), and it's reflection about the origin, p' = (x',y'). Second, if x is 0 (or nearly zero) then y/x is infinite (or huge).

    Write a procedure atan(x, y) which behaves like atan(y/x), with some improvements. Basically, it only calls atan() if the point lies in the first quadrant, and beneath the line y = x. Otherwise, use the following facts to bring the point to within this region:

Animating your clock

You can animate your clock if you wish. Add a second hand so you can see the animation. You'll need a few new ideas:

  1. You'll need to clear the graphics window and redraw. See page 657 for a summary of the graphics commands.

  2. If you refresh too often, the window will blink anoyingly. Use sleep(1) to sleep for 1 second between refreshes.

  3. Lastly, the graphics window buffers graphics. It only get around to displaying your graphics when (a) the buffer gets full, (b) you perform a get_mouse or (c) you exit. The following code will fill the buffer and force a redraw:
      for (int i=0; i<50; i++)
         cwin << Point (10,10);