CompSci 6, Summer 2007
Classwork: Circles Animation Mini-Project
Due: Thursday, July 26

This small project builds off of the Circle class implemented in the previous classwork. After completing both exercises, the interface of the Circle class should be as follows (note: the parameter names you chose do not have to match the names given here exactly):

Constructor:
public Circle(double radius, double x, double y, double xVel, double yVel)

Methods:
double getArea()
double getCircumference()
double getRadius()
void setRadius(double newRadius)
double getXPos()
double getYPos()
void setXPos(double newX)
void setYPos(double newY)
double getXVel()
double getYVel()
void setXVel()
void setYVel()
void move()
If your class does not conform to the interface given above, continue working on it. Be sure to write Javadoc comments for your class. When you are done, submit the current version of the class as Circles1, and then begin working on the following exercises.
  1. Drawing the circle: As a first step towards animating the circle, we are going to draw it in the center of the screen. Start by snarfing the starter code Circles_Animation. There are two classes, CirclesMain, which contains the main method you run to start the program, and CirclesCanvas, which is a class for a graphical user interface (GUI) component onto which you will draw your circle. You will not need to modify the CirclesMain class for this project. The CirclesCanvas class has two methods of interest, namely the constructor and the paintComponent method.

    paintComponent is a special method that is automatically called whenever the portion of screen that contains the canvas needs to be redrawn (e.g. if the window is uncovered, or you resize it, etc.). We'll modify this method to draw the circle. Find the paintComponent method and look at the code. Notice that it takes a parameter, pen, which is an object of the class Graphics. The pen object has methods for drawing on the canvas.

    Complete the following steps:

    1. Add a Circle instance variable to the CirclesCanvas class, and modify the constructor to initialize it. The initial position should be at the center of the canvas; to find the center, you must use the size parameter, which is a Dimension object that contains the width and height of the canvas. Take a look at the Javadoc pages in the Java API Specification to learn how to use the Dimension class.
    2. Add a method
      void draw(Graphics pen)
      to your circle class. You will need to add the line
      import java.awt.Graphics;
      
      to the top of the file. Use the pen object's methods to draw a solid (i.e. filled-in) red circle with the current radius at the current position (which indicates the center). Look at the Javadoc page for the Graphics class and find the setColor and drawOval methods. See if you can figure out how to use these methods to draw the circle at the position stored in the circle's instance variables.
    3. Modify the paintComponent method in the CirclesCanvas so that it calls the circle's draw method that you just added. By passing in the pen object as a parameter, you are allowing the Circle object to draw itself directly on the canvas.
  2. Simple Animation: Once you've drawn the circle, animate it by modifying the paintComponent method in the CircleCanvas class so that it calls the circle's move method before the draw method is called. Once this is done, pushing the "step" button should perform one step of the animation at a time, and pushing the "run" button should run the animation continuously. Experiment with different velocity values until you find an acceptable speed.

    When you have gotten the animation working, submit your project as Circles2 before going on.

  3. Bouncing Circle (conditional statements): Modify the move method of the Circle class so that the circle does not drift outside the canvas. When the circle hits the edge of the canvas, you should change its velocity so that the circle appears to bounce off of the edge. For example, if the circle hits the left or right edges, you should flip the sign of the x-component of the velocity.

    Make sure that the circle bounces when the edge of the circle touches the edge of the canvas (not the center of the circle). The bouncing should always function correctly, even if the user resizes the window (what parameters do you need to add to the move method so that it knows how big the window currently is?). When you are done, submit the project as Circle3.

  4. Random Circle: Look at the Javadoc page for the Random class in the java.util package. The Random class generates pseudorandom numbers, which allow your programs to behave in an unpredictable manner.

    Using Random, modify the CirclesCanvas class so that the circle it constructs has a randomly-generated size, starting position, velocity, and color. That is, each time you run the program, the circle's appearance and motion should be different. When you are done, submit the project as Circles4.

  5. Multiple Circles (loops and ArrayLists): Add an additional parameter numCircles to the CircleCanvas constructor. Modify the CircleCanvas class so that it creates numCircle circles with random properties and then animates them all simultaneously. Each circle should move according to its own velocity. In other words, you should modify the paintComponent method to update and draw all of the circles, instead of just one.

    When you are done, submit the project as Circles5.

  6. Final Program: The above exercises are the minimum amount of work required for this project. If you complete all of them, and do nothing else, the maximum grade you can earn on this project will be in the B range. If you would like to try for an A, you must add to the Circle class some additional functionality of your own choosing. Some examples would be:
    • Gravity: Simulate gravity by modifying the velocity of the circles in addition to their position at each update.
    • User interaction: Read and understand the code that creates and responds to the buttons at the top of the frame. Augment the GUI by adding new buttons that manipulate the motion of the circles when clicked. For instance, you could have a button that randomly "warps" a circle to a new location, or a button that simulates a force by changing the velocity of circle when clicked.
    • Collision detection: Modify your code so that only two circles are on the canvas. Augment the Circle class with a method that takes in another Circle object as a parameter and decides whether or not the two circles are currently overlapping. Give some visual feedback (e.g. change colors) to indicate when the circles are overlapping and when they are not. For an even more ambitious extension, try to have the circles bounce off of each other in a realistic manner.
    You are not limited to the ideas above. Choose something that interests you, but do not be too ambitious. The quality of your code and documentation is the most significant factor in your grade. A perfect grade is reserved for truly outstanding work.

    The final version of the project should be submitted as CirclesFinal. Follow the submission guidelines -- a README file is required for the final submission. The due date will be announced at least a week in advance.