Take the 2-minute tour ×
Game Development Stack Exchange is a question and answer site for professional and independent game developers. It's 100% free, no registration required.

I'm making a pong game, and my paddles no longer continue to move after holding down the left thumbstick or dpad down. It simply moves once with each press. I think it is because I'm not checking for a LastKeyPressed anymore now that I've begun to use a new input class, which uses arrays to check for which controller is being uses, and that's not what I was using before.

I've got to store the previous state, but I'm not sure of how to o that with these arrays.

// From my input class:

  public Input()
    {
        // Get input state
        CurrentKeyboardState = new KeyboardState[MaxInputs];
        CurrentGamePadState = new GamePadState[MaxInputs];

        // Preserving last states to check for isKeyUp events
        LastKeyboardState = new KeyboardState[MaxInputs];
        LastGamePadState = new GamePadState[MaxInputs];
}

    /// <summary>
    /// Helper for checking if a button was newly pressed during this update.
    /// The controllingPlayer parameter specifies which player to read input for.
    /// If this is null, it will accept input from any player. When a button press
    /// is detected, the output playerIndex reports which player pressed it.
    /// </summary>
    public bool IsNewButtonPress(Buttons button, PlayerIndex? controllingPlayer, out PlayerIndex playerIndex)
    {
        if (controllingPlayer.HasValue)
        {
            // Read input from the specified player.
            playerIndex = controllingPlayer.Value;

            var i = (int)playerIndex;

            return CurrentGamePadState[i].IsButtonDown(button) && LastGamePadState[i].IsButtonUp(button);
        }
        else
        {
            // Accept input from any player.
            return IsNewButtonPress(button, PlayerIndex.One, out playerIndex)
                    || IsNewButtonPress(button, PlayerIndex.Two, out playerIndex)
                    || IsNewButtonPress(button, PlayerIndex.Three, out playerIndex)
                    || IsNewButtonPress(button, PlayerIndex.Four, out playerIndex);
        }
    }



    // Tells the left paddle to move down
    public bool LeftDown(PlayerIndex? controllingPlayer)
    {
        PlayerIndex playerIndex;

        return IsNewKeyPress(Keys.Down, controllingPlayer, out playerIndex)
               || IsNewButtonPress(Buttons.DPadDown, controllingPlayer, out playerIndex)
               || IsNewButtonPress(Buttons.LeftThumbstickDown, controllingPlayer, out playerIndex);
    }

    // Tells the left paddle to move up
    public bool LeftUp(PlayerIndex? controllingPlayer)
    {
        PlayerIndex playerIndex;

        return IsNewKeyPress(Keys.Up, controllingPlayer, out playerIndex)
               || IsNewButtonPress(Buttons.DPadUp, controllingPlayer, out playerIndex)
               || IsNewButtonPress(Buttons.LeftThumbstickUp, controllingPlayer, out playerIndex);
    }



// And now from my Gameplay class:

public override void Update(GameTime gameTime, bool otherScreenHasFocus, bool coveredByOtherScreen)
........
input.Update();
            // Controls movement of the bats              
            if (rightBat.GetType() != typeof(AIBat))
            {
                if (input.LeftDown(ControllingPlayer))
                {
                    leftBat.MoveDown();
                }
                else if (input.LeftUp(ControllingPlayer))
                {
                    leftBat.MoveUp();
                }

                if (input.RightDown(ControllingPlayer))
                {
                    rightBat.MoveDown();
                }
                else if (input.RightUp(ControllingPlayer))
                {
                    rightBat.MoveUp();
                }


// From my bat class, so that you see what the MoveUp and MoveDown functions do:

    public Vector2 GetPosition()
    {
        return position;
    }

    public void MoveUp()
    {
        SetPosition(position + new Vector2(0, -moveSpeed));
    }

    public void MoveDown()
    {
        SetPosition(position + new Vector2(0, moveSpeed));
    }
share|improve this question
add comment

1 Answer 1

up vote 2 down vote accepted

First I see a naming issue: You're using a method named LeftDown to check if the down arrow key is currently pressed. You might want to rename it to IsLeftPlayerGoingDown or something less ambiguous like that. At first glance, I thought "LeftDown" meant it checked whether the left arrow key was down.

Now, your LeftDown / IsLeftPlayerGoingDown method checks if there was a new key or button press (during the last frame). You should just check whether it's currently down, not if it has just been pressed. So your code would be something like:

public bool LeftDown(PlayerIndex? controllingPlayer)
{
    PlayerIndex playerIndex;

    return IsKeyPressed(Keys.Down, controllingPlayer, out playerIndex)
           || IsButtonPressed(Buttons.DPadDown, controllingPlayer, out playerIndex)
           || IsButtonPressed(Buttons.LeftThumbstickDown, controllingPlayer, out playerIndex);
}

And you'll have to define IsKeyPressed and IsButtonPressed to check against your Current{something}State (something being Keyboard or GamePad), ignoring the Last{something}State.

share|improve this answer
    
Thanks! Worked like a charm! For those who were curious, I followed his instructions, and created another helper, one for KeyPressed and another for ButtonPressed. It was nearly identical to the helper I previously had, and now checks against the current state. –  Dave Voyles May 25 '12 at 13:48
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.