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

2013/1/15

How to only detect a single key?

Conmore Conmore

2013/1/15

#
So I'm making a simple Tron game, but I can move diagonally, which is bad. Here's my code
private int R = 1;
    private int L = 0;
    private int U = 0;
    private int D = 0;
    public boolean inUse = false;
    /**
     * Act - do whatever the PlayerOne wants to do. This method is called whenever
     * the 'Act' or 'Run' button gets pressed in the environment.
     */
    public void act() 
    {
        determineIfInUse();
        if(inUse = false)
        {
            moveRight();
            moveLeft();
            moveUp();
            moveDown();
        }
        placeBeam();
    }  

    private void placeBeam()
    {
        getWorld().addObject(new PropOne(), getX(), getY());
    }

    private void moveRight()
    {
        if (R == 1)
        {
            setRotation(0);
            setLocation(getX() + 5, getY());
            if (Greenfoot.isKeyDown("down"))
            {
                R = 0;
                D = 1;
            }
            if (Greenfoot.isKeyDown("up"))
            {
                R = 0;
                U = 1;
            }
        }
    }

    private void moveLeft()
    {
        if (L == 1)
        {
            setRotation(0);
            setLocation(getX() - 5, getY());
            if (Greenfoot.isKeyDown("down"))
            {
                L = 0;
                D = 1;
            }
            if (Greenfoot.isKeyDown("up"))
            {
                L = 0;
                U = 1;
            }
        }
    } 

    private void moveUp()
    {
        if (U == 1)
        {
            setRotation(90);
            setLocation(getX(),getY() - 5);
            if (Greenfoot.isKeyDown("left"))
            {
                U = 0;
                L = 1;
            }
            if (Greenfoot.isKeyDown("right"))
            {
                U = 0;
                R = 1;
            }
        }
    }

    private void moveDown()
    {
        if (D == 1)
        {
            setRotation(90);
            setLocation(getX(), getY() + 5);
            if (Greenfoot.isKeyDown("left"))
            {
                D = 0;
                L = 1;
            }
            if (Greenfoot.isKeyDown("right"))
            {
                D = 0;
                R = 1;
            }
        }
    }

    private void determineIfInUse()
    {
        if (Greenfoot.isKeyDown("up") || Greenfoot.isKeyDown("down") || Greenfoot.isKeyDown("left") || Greenfoot.isKeyDown("right"))
        {
            inUse = true;
        }
        else
        {
            inUse = false;
        }
    }
danpost danpost

2013/1/15

#
You need to be looking for one user-contolled change in direction (90 degree turn, left or right), and if there is none, continue in the direction last taken. To find ONE user-controlled change in direction, you need ONE method to check the possible keystrokes and determine what direction to continue in. Also, instead of using the four fields (one for each direction), you can use the rotation of the object for the current direction of motion. Basically it would be something like:
int direction = getRotation();
int v = 0; // vertical field
if(Greenfoot.isKeyDown("up")) v++;
if(Greenfoot.isKeyDown("down")) v--;
int h = 0; // horizontal field
if(Greenfoot.isKeyDown("left")) h++;
if(Greenfoot.isKeyDown("right")) h--;
if(direction%180==0)
{ // last movement in horizontal direction
    if(h==0 && v!=0) direction=90*(v+2);
}
else
{ // last movement in vertical direction
    if(v==0 && h!=0) direction=90*(h+1);
}
setRotation(direction);
move(5);
placeBeam();
By removing all your fields and methods except for the 'placeBeam' method, you could place this code in your act method and I believe it should work properly as far as the movement of the actor (though I have not actually tested it). It should also have good feel in play, in that a key for one direction must be released or negated with its opposite before a key in another direction along the other axis will be activated.
danpost danpost

2013/1/15

#
You probably would want to place the code, down to and including line 16, in a method called 'setDirection' and call it from the act method and follow the call with some collision checking code or method call before moving and placing beam. The collision checking can also use the rotation to determine where to check for objects; and if no objects are there, perform the last two step (else "crash").
davmac davmac

2013/1/15

#
Also, line 13 is wrong: if(inUse = false) Should be: if(inUse == false) Use '==' for comparison, not '='. As you have it now, it always sets inUse to false.
You need to login to post a reply.