This site requires JavaScript, please enable it in your browser!
Greenfoot back
JaneSmith
JaneSmith wrote ...

2016/1/7

Exercise 7.19/7.20 Questions

1
2
JaneSmith JaneSmith

2016/1/7

#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
import greenfoot.*;
 
/**
 * Write a description of class Pear here.
 *
 * @author (your name)
 * @version (a version number or a date)
 */
public class Pear extends Actor
{
 private int speed;
    /**
     * Create the pear.
     */
    public Pear()
    {
        speed = Greenfoot.getRandomNumber(3) + 1;     
        setRotation(Greenfoot.getRandomNumber(360));
    }
     
    /**
     * Move around.
     */
    public void act()
    {
        if (isAtEdge())
        {
             
            turn(180);
             
             
        }
         
        move(speed);
         
        if (Greenfoot.getRandomNumber(100) < 50)
        {
            turn(Greenfoot.getRandomNumber(5) - 2);  
        }
    }
}
Jane Smith wrote...
"In Exercise 7.19 in the course textbook we are asked to modify the pear-moving code so that pears are only moved right if they are not already at the right edge. If they are at the right edge, they are moved the left edge instead." As you can see from my code I have everything completed up to an including 7.18 but now I am stuck. I just don't know how to code the scenario so that it recognizes "not already at the right edge." In addition, 7.20 wants the program to recognize if we are on the left half or the right half of the World. Sorry I just don't know this one.
Super_Hippo Super_Hippo

2016/1/8

#
You could create a boolean to save it.
1
private boolean alreadyAtRightEdge = false; //of course you can give it an other name
And when it reaches the right edge, use this:
1
alreadyAtRightEdge = true;
Then you can determine what to do with an if-else-statement:
1
2
3
4
5
6
7
8
if (alreadyAtRightEdge)
{
    //what it should do when it already reached the right edge
}
else
{
    //what it should do when it didn't reach the right edge yet
}
JaneSmith JaneSmith

2016/1/8

#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
import greenfoot.*;
 
/**
 * Write a description of class Pear here.
 *
 * @author (your name)
 * @version (a version number or a date)
 */
public class Pear extends Actor
{
    private int speed;
    private boolean alreadyAtRightEdge = false;
 
   public boolean alreadyAtRightEdge()
    {
        if (alreadyAtRightEdge())
        {
            turn(4);
        }
        else
        {
            turn(-4);
        }
    }
 
    /**
     * Create the pear.
     */
    public Pear()
    {
        speed = Greenfoot.getRandomNumber(3) + 1;     
        setRotation(Greenfoot.getRandomNumber(360));
    }
 
    /**
     * Move around.
     */
    public void act()
    {
        if (isAtEdge())
        {
 
            turn(180);
 
        }
        move(speed);
        if (Greenfoot.getRandomNumber(100) < 50)
        {
            turn(Greenfoot.getRandomNumber(5) - 2);  
        }
         
    }
}
Jane Smith wrote...
Dear Super, Thank you - I think I am getting closer but not there yet. Can you tell me what I've done incorrectly here?
danpost danpost

2016/1/8

#
If the actor is only to move right and left, then the random turning code and the initial random rotation setting line should be removed -- and you should not need the code given by Super_Hippo (especially with the turning included within it). If you still want to set a random rotation, use the following:
1
setRotation(Greenfoot.getRandomNumber(2)*180);
so that only zero and '180' are valid initial random rotations.
JaneSmith JaneSmith

2016/1/8

#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
import greenfoot.*;
  
/**
 * Write a description of class Pear here.
 *
 * @author (your name)
 * @version (a version number or a date)
 */
public class Pear extends Actor
{
 private int speed;
    /**
     * Create the pear.
     */
    public Pear()
    {
        setRotation(Greenfoot.getRandomNumber(2)*180);
        speed = Greenfoot.getRandomNumber(3) + 1;     
         
    }
      
    /**
     * Move around.
     */
    public void act()
    {
        if (isAtEdge())
        {
              
            turn(180);
              
              
        }
          
        move(speed);
          
        if (Greenfoot.getRandomNumber(100) < 50)
        {
            turn(Greenfoot.getRandomNumber(5) - 2);  
        }
    }
}
Jane Smith wrote...
Dan - thank you. Did I use your code correctly? The new code you provided says that the rotation is 180 degrees. OK I get that one. But the multiplication of the degrees to a random number between 0 and 1 seems to force the pear to only go from right to left. But I don't understand why it seems to do that.
danpost danpost

2016/1/8

#
instructions wrote...
pears are only moved right if they are not already at the right edge. If they are at the right edge, they are moved the left edge instead
The instructions appear to be saying that is what is wanted. The lines 37 through 40 should also be removed to eliminate any small changes in the rotation of the actor.
JaneSmith JaneSmith

2016/1/10

#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
import greenfoot.*;  // (World, Actor, GreenfootImage, Greenfoot and MouseInfo)
import java.util.List;
 
/**
 * A block that bounces back and forth across the screen.
 *
 * @author Michael Kölling // and edited by Suzanna McGee
 * @version 1.0
 */
public class Block extends Actor
{
    private int delta = 2;
    World world = getWorld();
 
    /**
     * Move across the screen, bounce off edges. Turn leaves, if we touch any.
     */
    public void act()
    {
        move();
        checkEdge();
        checkLeaf();
        checkApple();
        checkMouseClick();
 
    }
 
    /**
     * Move sideways, either left or right.
     */
    private void move()
    {
        setLocation(getX()+delta, getY());
    }
 
    /**
     * Check whether we are at the edge of the screen. If we are, turn around.
     */
    private void checkEdge()
    {
        if (isAtEdge())
        {
            delta = -delta;
 
        }
    }
 
    /**
     * Check whether the mouse button was clicked. If it was, change all leaves.
     */
 
    public void checkMouseClick()
    {
        if (Greenfoot.mouseClicked(null))
        {
            World world = getWorld();
            List<Leaf> leaves = world.getObjects(Leaf.class);
 
            for (Leaf leaf : leaves)
            {
                if(getX() < 20 || getX() > getWorld().getWidth() - 20)
 
                {
                    leaf.changeImage();
                }
            }
        }
    }
 
    /**
     * Check whether we're touching a leaf. If we are, turn it a bit.
     */
    private void checkLeaf()
    {
        Leaf leaf = (Leaf) getOneIntersectingObject(Leaf.class);
 
        if (leaf != null) {
            leaf.turn(9);
        }
    }
 
    private void checkApple()
    {
        Apple apple = (Apple) getOneIntersectingObject(Apple.class);
 
        if (apple != null) {
            apple.turn(9);
        }
    }
}
jane wrote...
When I click my mouse nothing changes. I thought I'd written the code so that the leaves would change images on the left side of the world when the mouse is clicked. What have I don't incorrectly here?
danpost danpost

2016/1/10

#
What are the dimensions and cell size of your world? Line 61 does not appear to be selecting leafs on the left side of the world and if that is to select half of them, then your world should only be of width 80.
JaneSmith JaneSmith

2016/1/10

#
public MyWorld() { // Create a new world with 600x400 cells with a cell size of 1x1 pixels. super(600, 400, 1); setUp(); }
danpost danpost

2016/1/10

#
Another thing -- why did you place that code in the Block class? It will be executed once for every Block object in your world. It would seem more appropriate to place that code in your World subclass act method.
JaneSmith JaneSmith

2016/1/10

#
I had the mouse click method already in the Block class.
danpost danpost

2016/1/10

#
JaneSmith wrote...
I had the mouse click method already in the Block class.
I am suggesting that you move that method, with appropriate changes, to the World subclass -- called from the act method of the World subclass.
JaneSmith JaneSmith

2016/1/10

#
jane wrote...
I am trying to do this but the textbook instructs us to write the checkMouse method in the block class. At the same time we are asked to set up a List but nothing is working now that I moved it. And of course I don't need to call the world class because I am now in the world. Any thoughts?
/** * Autumn. A world with some leaves. * * @author Michael Kölling * @version 1.0 */ public class MyWorld extends World { /** * Create the world and objects in it. */ public MyWorld() { // Create a new world with 600x400 cells with a cell size of 1x1 pixels. super(600, 400, 1); setUp(); checkMouseClick(); } public void checkMouseClick() { if (Greenfoot.mouseClicked(null)) { World world = getWorld(); List<Leaf> leaves = world.getObjects(Leaf.class); for (Leaf leaf : leaves) { if(getX() < 20 || getX() > getWorld().getWidth() - 20) { leaf.changeImage(); } } } } /** * Create the initial objects in the world. */ private void setUp() { int i = 0; while (i<8) { int x = Greenfoot.getRandomNumber(getWidth()); int y = Greenfoot.getRandomNumber(getHeight()); addObject( new Pear(), x, y ); i++; } while (i<12) { int x = Greenfoot.getRandomNumber(getWidth()); int y = Greenfoot.getRandomNumber(getHeight()); addObject( new Apple(), x, y ); i++; } while (i<100) { int x = Greenfoot.getRandomNumber(getWidth()); int y = Greenfoot.getRandomNumber(getHeight()); addObject( new Leaf(), x, y ); i++; } addObject(new Block(), 300, 200); } }
danpost danpost

2016/1/10

#
The call to 'checkMouseClick' needs to be in an act method. Remove it from the constructor ( 'public MyWorld' ) and add an act method with the call:
1
2
3
4
public void act()
{
    checkMouseClick();
}
The changes to the 'checkMouseClick' method should produce this:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
public void checkMouseClick()
{
    if (Greenfoot.mouseClicked(null))
    {
        List<Leaf> leaves = getObjects(Leaf.class);
        for (Leaf leaf : leaves)
        {
            if (leaf.getX() < 20 || leaf.getX() > getWidth()-20)
            {
                leaf.changeImage();
            }
        }
    }
}
The condition on line 8 will determine which leafs are changed. Currently, only those close to the left and edges of the world will change.
JaneSmith JaneSmith

2016/1/10

#
Ignore that last pot. I will struggle with this and post again one way or the other.
There are more replies on the next page.
1
2