Tino Intro To Java

Last modified: March 09, 2023

Lab A4.7 Creature AI - Scouting Line of Movement

If you have not done Lab A4.6 Creature AI - Direct Path, you should go do that first as this lab will build upon that foundation.

Mission

You are writing the AI for a creature that will wander the world finding and collecting food while avoiding walls. The creature must follow these rules while collecting treats:

  1. The creature can never end a frame even partially inside a wall. No going through walls.
  2. The creature can never end a frame more than 2 pixels from where they started (i.e. no moving faster than 2).
  3. You cannot remove or change any properties of any walls.
  4. You cannot move any treats or change the properties of any treats.
  5. You cannot remove any treats the creature is not touching.
  6. You cannot change the size or image of the creature.

Smarter Treat Detection

In this version we will begin to address the situation where there is no direct path between treats because walls are in the way. In particular, you will be writing a method that finds the nearest treat that can be reached directly without encountering a wall.

Notice in the picture above, the creature might be able to go directly to some of the treats, but others are blocked by walls. In this lab, you will make your creature target the closest treat that can be reached by moving directly toward it, rather than just choosing the first treat or a random treat from the list.

If you need to review the set up, you should read about it in Lab A4.6 Creature AI - Direct Path

Class Name and Header

Update the date in the header of your creature class to today's date.

Review Lists

To review useful methods that return a List in Greenfoot, you should review Lab A4.6 Creature AI - Direct Path.

Helper Method 1: Number of Moves to Reach a Treat

In order to find the closest treat the creature can reach, first we need a way to determine the distance to each treat. Since we will also need to know if the treat can even be reached, we can find out the answer to both questions with a single helper method. Here is a description of what this method should do:

  1. Declare an instance method takes a Treat as a parameter and returns an int representing how many moves it takes to get to that treat (or -1 if a wall is reached first).
  2. You should save the original location and rotation of the creature, so these can be restored at the appropriate times.
  3. Make your creature keep moving by 2 toward the treat until the creature either reaches the treat or reaches a wall.
  4. The creature should set rotation back to the original rotation after each move and before checking for a Treat or Wall so the orientation will always be the same when it checks for collisions.
  5. Keep track of how many times the creature has moved.
  6. If the creature reaches the target treat, put the creature back at the location it started in and return the number of moves it took to get to the treat. Warning: make sure the treat detected is the target treat and not some other treat.
  7. If the creature reaches a wall, put the creature back at the location it started in and return -1.
  8. It is important that no matter what the result, the creature ends up back in the same location it started with the same orientation it started in. The purpose of this method is to gather information, not to actually move the creature.

Helper Method 2: Closest Reachable Treat

  1. Declare an instance method in your creature class that takes no parameters and returns a Treat. This method will return the closest reachable treat or null if no such treat exists. In this case the closest treat is defined as the one that takes the least number of moves to reach as measured by the previous helper method.
  2. In this method, make a loop that iterates through all the the treats in the world.
  3. For each treat, use the previous helper method to find the number of moves it takes to reach the treat.
  4. Keep track of the closest reachable treat and update it as needed. In order to do this, you will probably also want to keep track of the number of moves it took to get to the closest treat, so you will know when you find a closer treat.
  5. Return the closest reachable treat or return null if none of the treats are reachable.

Go To The Closest Reachable Treat

In the first assignment, you implemented a simple strategy that made the creature pick a treat and go straight to it. That version works fine when all the treats are in an open world like in level 1, but the creature gets stuck as soon as there is a wall between the creature and the target treat. In this version, we will change the strategy so that each time it chooses a new target treat, it will choose the closest reachable treat. This could still fail if the creature is ever in a position where there are no reachable treats, but it will do much better than the last version. For this version it is ok if your creature just stops when there are no reachable treats.

Demo

If you implemented all the creature behaviors correctly, your program should behave like this demo.

Optional: Handle The Case Where There Are No Reachable Treats

Once you have the basic lab working, see if you can come up with a strategy for handling the case where there are no reachable treats so the creature will still have a chance of eventually finding all the treats. It doesn't have to be perfect. What would be a better reaction than stopping?

Submission

Submit only your PX_LastName_FirstName_Creature.java file. For example if you were in 3rd period and named Michael Wang, then you would submit P3_Wang_Michael_Creature.java.

You must Sign In to submit to this assignment

Dark Mode

Outline