Suppose we would like to move a set of 10 rabbits together, such that when one rabbit reaches a border, all rabbits change direction. Because we are using object-oriented design style, every action is about a specific object. Thus, a sentence "When a rabbit reaches the left border, all rabbits move right" is not addressing a specific object and would not accomplish the task. However, recall that we can say "When [some object] is ..., the rabbit moves right." This gives us an opportunity to explore and think about how we might carry out this task.
Essentially, we use another single-instance object to serve as an arbiter. We then assign a Boolean attribute to this arbiter to indicate the direction that the rabbits will be moving. For example, consider using the brick as the arbiter. We will assign a Boolean attribute 'facing_east' to the brick. The following illustrates the game plan step by step.
There are 10 rabbits. There is one brick. The brick is invisible. When the brick is facing_east, the rabbits move right. Otherwise, the rabbits move left. |
First assign a Boolean attribute to another object. The rabbits will move according to the attribute of the object. In this example, we'll use a brick and the attribute 'facing_east'. When the brick is facing_east, the rabbits move right. When the brick is not facing_east, the rabbits move left. |
When a rabbit reaches the left border, it is at_the_left_border. Otherwise, the rabbit is not at_the_left_border. When a rabbit is at_the_left_border, the brick becomes facing_east. |
Note that border events cannot involve two different characters, so first give the rabbit the attribute 'at_the_left_border' and then relate it to the brick to separate the two characters. Effectively, whenever a rabbit reaches the left border, the brick will become facing_east. |
When a rabbit reaches the right border, it is at_the_right_border. Otherwise, the rabbit is not at_the_right_border. When a rabbit is at_the_right_border, the brick becomes not facing_east. |
Finally, add similar sentences for the other border. |
If we align the rabbits in the map textbox, we can use the subset indices to determine the facing_east attribute of the brick in the following game plan.
There is a brick.
The brick is invisible.
When the brick is facing_east, the rabbits move right.
Otherwise, the rabbits move left.
When rabbit[0] reaches the left border, it is at_the_left_border.
Otherwise, it is not at_the_left_border.
When rabbit[9] reaches the right border, it is at_the_right_border.
Otherwise, it is not at_the_right_border.
When rabbit[0] is at_the_left_border, the brick becomes facing_east.
When rabbit[9] is at_the_right_border, the brick becomes not facing_east.
Map:
r-r-r-r-r
-r-r-r-r-r
Finally, instead of using the at_the_left_border Boolean attribute, we can also use variable attributes, which will be discussed at a later point. This could help us reduce the number of sentences a bit.
Can you make 3 rabbits and 3 foxes move together? Hint: both rabbits and foxes depend on the same brick arbiter!
// Game #1. Get the cheeses.
// Game #2. Crazy Pong.
// Game #3. Legend of the foxes - push the carrots to touch, etc.