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

2017/1/17

Platforms

colinj colinj

2017/1/17

#
Hey all! Im making a platformer and i have my gravity in it but i want to be able for the character to stop when it hits a block heres the code hopefully you can help!
  public void act() 
    {
        
        checkKeys(); 
        kill();
        Actor grounddd = getOneIntersectingObject(grounddd.class);
        Actor block = getOneIntersectingObject(block.class);
         int groundLevel = 520 - getImage().getHeight()/2;
        boolean onGround = (getY() == groundLevel);
        if (!onGround) // in middle of jump
        {
            ySpeed++; // adds gravity effect
            setLocation(getX(), getY()+ySpeed); // fall (rising slower or falling faster)
            if (getY()>=groundLevel) // has landed (reached ground level)
            {
                setLocation(getX(), groundLevel); // set on ground
                Greenfoot.getKey(); // clears any key pressed during jump
                
           }
        }
        
        else // on ground
        { if(isTouching(block.class)){
        
                setLocation( getX(), getY()); 
        
        }
            if ("space".equals(Greenfoot.getKey())) // jump key detected
            {   Greenfoot.playSound("jump.mp3");
                ySpeed = -20; // add jump speed
                setLocation(getX(), getY()+ySpeed); // leave ground
            }
        

    }
    
if(canSee(wall.class)){
 setLocation( getX() - speed, getY() );

}
danpost danpost

2017/1/17

#
It presume that your character could hit a block from above or from below. To determine which, you can get the sign of the speed:
int dir = (int)Math.signum(ySpeed);
Now if touching a block, you can move off it no matter which side your character hits it with:
while (isTouching(block.class)){
    setLocation(getX(), getY()-dir); // edging off block
    ySpeed = 0; // kills speed
}
You should probably use the 'isKeyDown' method rather than the 'getKey' method for game play (the 'getKey' method is more suited for text input). You can add a boolean to track the state of the 'space' key. To detect a change in the state of the key, use:
// with the following field
private boolean spaceDown;

// detect change with
if (spaceDown != Greenfoot.isKeyDown("space"))
When the condition is true, change the value of 'spaceDown':
spaceDown = ! spaceDown;
and check to see if the key is changed to the down state:
if (spaceDown)
This is one of the conditions for jumping; you are missing the other one:
if (onGround)
If you set 'onGround' to false on line 9 and set it to true when is touching grounddd or block, then you can simply use:
if (onGround && spaceDown)
for initiating a new jump. Also, you can remove line 31 as the next act cycle will start the jump. I presume that lines 37 through 40 were part of the horizontal movement code and were inadvertently added to the post. I usually do the horizontal movement first because gravity does not play a role with it. If you do the vertical movement first, there is no guarantee that the actor will still be over a block after the horizontal movement is done.
danpost danpost

2017/1/17

#
The code given above does not give the behavior you were wanting. However, using the same added field, you can replace lines 28 through 32 with this to get the desired behavior:
if (onGround && ! Greenfoot.isKeyDown("space")){
    spaceDown = false;
}
if (onGround && ! spaceDown && Greenfoot.isKeyDown("space"))
{
    spaceDown = true;
    ySpeed = -20;
}
You need to login to post a reply.