1

When pressing two keys and then pressing a third key, all without releasing, Input.GetKeyDown does not know that the third key has been pressed.

Here is my code:

public class Keys
    {
        internal bool leftPressed = false;
        internal bool rightPressed = false;
        internal bool upPressed = false;
        internal bool downPressed = false;
    }

    public Keys keys = new Keys();

    void Start () {
    }

    void Update ()
    {
        updateButton(KeyCode.LeftArrow);
        updateButton(KeyCode.RightArrow);
        updateButton(KeyCode.UpArrow);
        updateButton(KeyCode.DownArrow);
    }

    void updateButton(KeyCode key)
    {
        if (Input.GetKeyDown(key))
        {
            if (key == KeyCode.LeftArrow)
                keys.leftPressed = true;
            if (key == KeyCode.RightArrow)
                keys.rightPressed = true;
            if (key == KeyCode.UpArrow)
                keys.upPressed = true;
            if (key == KeyCode.DownArrow)
                keys.downPressed = true;
        }
        else if (Input.GetKeyUp(key))
        {
            if (key == KeyCode.LeftArrow)
                keys.leftPressed = false;
            if (key == KeyCode.RightArrow)
                keys.rightPressed = false;
            if (key == KeyCode.UpArrow)
                keys.upPressed = false;
            if (key == KeyCode.DownArrow)
                keys.downPressed = false;
        }
    }

All I wanted to do was have a player class move a gameobject when a key was pressed down. If both directions were pressed they would cancel each other out and set the player's velocity to 0.

Hitting left and right at the same time does so, but trying to press up or down doesn't change the up or downs value at that point. It's as though Input.GetKeyDown only contained 2 values and not the whole keyboard keys states?

Note: even pressing two random keys on the keyboard would stop left, down, up or right from changing values.

Does anyone have a suggestion or a fix to my code? Thanks,

Programmer
  • 121,791
  • 22
  • 236
  • 328
Alox
  • 651
  • 12
  • 24
  • I'm aware that the code is not optimized, I'm doing this as a small side project for fun and optimize as I go. – Alox Aug 11 '16 at 19:49

2 Answers2

4

Unless I'm missing something it seems like you would be better off using the built in axes system. Also your keyboard might not support more than two keys down at once. Also GetKeyDown does not return if the key is down it returns if it was pushed down last frame: https://docs.unity3d.com/ScriptReference/Input.GetKeyDown.html

You want Input.GetKey to get the keys current state if you don't want to use the axes system.

  • Actually, it would seem I can press left, right and then pressing down works, but not up. It's very confusing to me. – Alox Aug 11 '16 at 20:23
  • 1
    Maybe this will help: https://www.microsoft.com/appliedsciences/antighostingexplained.mspx – Drew Barrett Aug 11 '16 at 20:28
  • That is precisely what I wanted to know. Thank you. Now if you'd know a way to counter ghosting keys, that'd be super helpful, but from that brief read over, it's unfortunately on the hardware side and has software side fix right? – Alox Aug 11 '16 at 20:37
  • At Least, your link is what I believe reasons with what is going on. (keyboard ghosting) – Alox Aug 11 '16 at 20:41
  • I'm not sure if it is made to counter the key ghosting but the axes system is designed for controlling movement in unity so I would try that. Here's some example code for controlling a Rigidbody2D if it helps at all `void FixedUpdate() { Vector2 newvel; newvel = new Vector2(Input.GetAxis("Horizontal"), Input.GetAxis("Vertical")); if (newvel.magnitude > 1.0f) { newvel = newvel.normalized; } newvel *= moveSpeed; GetComponent().velocity = newvel; }` – Drew Barrett Aug 11 '16 at 20:45
0
void Start() 
{
    StartCoroutine(crMoveIt());
}

private IEnumerator crMoveIt() 
{
    while(true) // have a bool var for this
    {
        if(Input.GetKeyDown(KeyCode.A)) 
        {
            // Move object here
        }
        yield return null;
    }
}

Where you want to move the object, see this

https://docs.unity3d.com/ScriptReference/Vector3.MoveTowards.html

Or if you're using a rigidbody please read

https://docs.unity3d.com/ScriptReference/Rigidbody.html

Instead of passing in a keycode to check each frame, just have a coroutine handle the input and then call something after that each frame. A coroutine will do that same as an Update, but you can have several of these running versus just one Update() method.

I would of wrote more code for the movement of an object, but you provided no references to any GameObject in your example. I answered a question not to long ago that shows how to move an object a different way that does not use Vector3.MoveTowards() here

Unity; Random Object Movement

Hope this helps. Edited, forgot something. =)

Community
  • 1
  • 1
TheNoob
  • 861
  • 2
  • 11
  • 25
  • 1.This will freeze Unity/Game unless `yield return null;` is added to `while` loop. 2.This does not answer the question. I think you should read it again. It says something about discarding result on multiple key press..... – Programmer Aug 11 '16 at 20:17
  • Lol, and if you read my answer I mentioned I didnt put that code there because there is no reference to an object. Furthermore, I think I do answer the question. Honestly, the way he approached this is over the top. He doesn't need half the stuff there. Moreover, its a test project. Let it freeze and have him find out why. Learning by mistakes sticks the best. Lastly, your main point here is I left out a yield statement becuase i did this off the top of my head without Unity here, big deal. And he wouldnt need to discard a result if this was handled differently. Just my opinion. =) – TheNoob Aug 11 '16 at 20:24
  • Big deal? Yes, that answer will freeze Unity. Anyways, I suggest you read the question again. He doesn't want to move stuff if more than one key is pressed. Just read it then fix your answer. – Programmer Aug 11 '16 at 20:27
  • I want to move a gameobject when pressing left, right, up or down. The problem I'm having is that when I press left, right and up at the same time, unity only understands as though I pressed left and right. Unity does not understand that I pressed up as well. Which I assumed it should. – Alox Aug 11 '16 at 20:32
  • Just a thought, instead of going after others answers why don't you supply your own? I suggest you read both again, including my answer. If he doesn't want multiple inputs all he needs is a single keyword. https://msdn.microsoft.com/en-us/library/923ahwt1.aspx I guess I could throw that keyword all over his code, but instead I think a different approach would be better. Anyways, have a good day =) If you really think my answer is that bad, then just delete it or down vote it. – TheNoob Aug 11 '16 at 20:33
  • **"Just a thought, instead of going after others answers why don't you supply your own?"** There is nothing wrong with pointing a mistake in an answer. That's what I did and you fixed that part. I could downvote but only do so when no effort is put in the answer. He already had good answer from@DrewBarrett so there is no need to provide another one. **"All I wanted to do was have a player class move a gameobject when a key was pressed down. If both directions were pressed they would cancel each other out and set the player's velocity to 0"** That's the part of hisquestion I was taklking about – Programmer Aug 11 '16 at 20:48
  • "All I wanted to do was have a player class move a gameobject when a key was pressed down. If both directions were pressed they would cancel each other out and set the player's velocity to 0" Different approach would be better. =) Anyways, Im not going at this anymore. You didnt see which answer came first and furthermore, you are still going at me even after fixing a little mistake. Really? – TheNoob Aug 11 '16 at 20:51