Purpose: To create a program with a 2D animation with multiple controls. You will be writing the code to display the present state of the world, show the animation of the world as the simulation runs, plot the number of sharks and fish over time, and create some of the controls for the GUI. The code that handles the simulation is being provided to you.
In this assignment you will use the same animation framework we have used in class and on assignments. I am providing a shell of the program with some code already completed.
Implement a program that displays the Wa-Tor World Simulation. The world is based on an article by A.K. Dewdney in Scientific American entitled Sharks and Fish Wage an Ecological War on the Toroidal Planet Wa-Tor. This is a biological simulation. It takes place on a world covered with an ocean. The world is a torus (like a doughnut) not a sphere. The world is divided into cells or locations. Every location has four adjacent locations: above, below, left, and right.
The only two animals in the world are fish and sharks.
Fish eat microscopic kelp. The supply of kelp is never exhausted. Every turn of the simulation a fish will move to a random adjacent cell unless all four are occupied. If the fish has survived the number of turns necessary to breed it produces a new fish if there is an empty adjacent cell.
Sharks eat fish. Each turn if there is a fish adjacent to a shark the shark eats it. If there are multiple adjacent fish the shark eats one at random. If there are no adjacent fish the shark moves in the same manner as fish. After eating or moving if the shark has survived the number of turns necessary to breed it produces a new shark if there is an empty adjacent cell.
You will write a program that display a graph of the fish and shark population over time, the current status of the world, and controls for the simulation. The program is animated to show the simulation in action.
The shell program I am giving you contains some of the code already. The shell consists of 4 files / classes: WatorMain.java, WatorFrame.java, GraphPanel.java, WatorPanel.java
The code that handles the simulation itself is in a jar file. (Java Archive) named A4.jar(link to the file). Download WatorWorldSimulation.jar to your computer and add to your IDE / environment as necessary.
Here is the
documentation for the classes that handle the simulation. Your code should
only have to interact with the
WatorWorld class and
depending on what modifications you make.
There is a lot to do in this assignment. You will add instance variables and /or methods to the
GraphPanel classes. The
WatorFrame holds the
GraphPanel at the top, the
WatorPanel in the middle, and a control panel at the bottom. The control panel
is part of the
WatorFrame, not a separate class.
Here is an overview of what you need to complete. This is a summary. Be sure to use good coding style, constants and helper methods to help solve the problem. Good style and constants also make it easier to understand the program and easier to make changes the program if desired.
1. First you will want to add the Step, Start, Stop, and Reset
buttons. Do this in the
addControlPanel method or create a helper method which
is called from
addControlPanel. The purpose of the buttons are:
When the GUI is first shown the initial world is displayed, but not animated. When the step button is pressed the simulation and animation should perform a single step and stop.
The start button should start the animation by starting the
frame's timer. (Instead of using the threaded timer for animation as we did in
the LilacChaser assignment this program uses a time, a built in Java class, in
WatorFrame class. When the timer goes off the
WatorPanel update and render
methods are called.)
When the stop button is pressed the animation should pause. (Call the stop method on the frame's timer.)
When the reset button is pressed the current world and graph
should be discarded. The
WatorWorld variable in the
WatorPanel should be
reset. (There is a reset method in the
WatorWorld class.) I chose to put the
WatorWorld variable in the
WatorPanel and the
GraphPanel so you will have to
add a method the frame can call on the
WatorPanel to reset the world. The timer
should also be stopped.
2. Finish the
addTimer method in the frame class. When the timer
goes off the
GraphPanel should be
updated, rendered, and repainted.
3. Next finish the
WatorPanel class. You will have to finish the
constructor. It is important to call the call the
method on the panel based on the world size and the number of pixels you want to
each cell to take up. In the screenshots I have each cell set to 3 by 3, but you
can use different values or vary it based on the size of the world. You can also
change the parameters for the world. Alternatively you can set the size of the
panel and adjust the pixels per cell based on the size of the world.
5. Finish the
WatorPanel update and render methods.
step method on
theWorld to have the simulation perform one "turn" and
then fill all the rectangles in the panel for every cell in
theWorld. You will
have to use a nested loop to generate the coordinates of all the rows and
theWorld and call the
getColor method from
theWorld for each of
these. (There are other options for drawing the world and you are free to take a
GraphPanel displays the fish and shark populations over
time. There are methods in the
WatorWorld class to get the current number of
fish and sharks.
Time is the horizontal axis and number of fish and sharks is the vertical axis. In the screenshots the number of fish is plotted in green. The number of sharks is plotted in orange. For each step in the simulation plot the new point. The values should be scaled based on the total number of cells in the world. So if the world is all fish the green line would be at the very top and the orange line would be at the very bottom. The picture below shows what happens if all the sharks die out and the fish breed to fill the whole world.
There are many ways of plotting the population over time,. One
would be to store the populations in two
ArrayLists and call
between each point. When the size of the
ArrayList is greater than the width of
GraphPanel clear the
ArrayList and start adding numbers again. Another option
would be to create a
GeneralPath object for each of the population lines and
then just draw those in each call to render.
7. The last thing is to add at least one more control that changes some aspect of the simulation. Add a button or slider to the control panel to change some aspect of the simulation. This could include changing the breed time for fish, the breed time for sharks, or the starve time for sharks. Other options would be to make controls for the number of fish and / or sharks to start with when the simulation is reset. You may also add controls of your own design as long as they alter the parameters of the simulation in some way.
The following shows a version of the program with multiple extra controls: