views:

149

answers:

1

Hi, so I have a function that handles key presses in a game I'm working on in OpenGL. But, the thing is that even though I have made two squares and they both move when the correct key is pressed only one square is moved. Is there a way I can make the two squares move. This is the glutKeyboardFunc function I implimented:

    void handleKeypress(unsigned char key, int x, int y) 
{
        if (key == 'w')
        {
            for (int i = 0; i < 12; i++)
            {
                if (i == 1 || i == 7 || i == 10 || i == 4)
                {
                    square[i] = square[i] + 0.1;
                }
            }
        }
        if (key == 'd')
        {
            for (int i = 0; i < 12; i++)
            {
                if (i == 0 || i % 3 == 0)
                {
                    square[i] = square[i] + 0.1;
                }
            }
        }
    if (key == 's')
    {
        for (int i = 0; i < 12; i++)
        {
            if (i == 1 || i == 7 || i == 10 || i == 4)
            {
                square[i] = square[i] - 0.1;
            }
        }
    }
        if (key == 'a')
        {
            for (int i = 0; i < 12; i++)
            {
                if (i == 0 || i % 3 == 0)
                {
                    square[i] = square[i] - 0.1;
                }
            }
        }
    glutPostRedisplay();
}

If you need any more code just ask.

+2  A: 

Edited for comments below.

// I'm making some assumptions about your functions here. Make adjustments.
// You can handle both players' key inputs here.
void handleKeypress(unsigned char key, int x, int y) 
{
    if (key == 27)
        exit(0);

    // Player 1
    if (key == 'w')
    {
        A.moveSquareUp();
    }
    if (key == 'd')
    {
        A.moveSquareRight();
    }
    if (key == 's')
    {
        A.moveSquareDown();
    }
    if (key == 'a')
    {
        A.moveSquareLeft();
    }
}

void handleSpecialKeypress(int key, int x, int y) 
{
    // Player 2
    if (key == GLUT_KEY_UP)
    {
        B.moveSquareUp();
    }
    if (key == GLUT_KEY_RIGHT)
    {
        B.moveSquareRight();
    }
    if (key == GLUT_KEY_DOWN)
    {
        B.moveSquareDown();
    }
    if (key == GLUT_KEY_LEFT)
    {
        B.moveSquareLeft();
    }
}

You need to handle your keyboard events somewhere in your game logic (the main loop, or a callback from glutKeyboardFunc()), and call the desired behaviours. This has some advantages:

  1. Your keyboard input handling is unified in one place.
  2. Using if instead of switch allows multiple keys being used.
  3. You can organise this event handling inside your main loop, instead of depending on the timer.
Xavier Ho
Thanks for you help but, the problem is that I want it so two players could move at once so for example one person presses the up arrow key moving one square up and another person presses 'a' which would be equivalent to moving left.
thyrgle
Right then. Let me edit my sample code to reflect what you would do. || Edited now. Please have a look again, thyrgle. `:]`
Xavier Ho
@Xavier Ho: I have reposted a segment of my code (for player one only) but am still getting two problems: let's say player one presses 'as' he should move left and down almost simultaneously but he doesn't plus GLUT_KEY_* (the star indicates any of those 4 keys) does not work on my computer for some odd reason.
thyrgle
Ah yes, apologies. You need to use `glutSpecialFunc()` for the arrow keys - it's one of the GLUT's annoyances. I'll edit my post to reflect that. || I suspect the reason you aren't getting two keys to work together is because you're calling `glutPostRedisplay()` right afterwards. Try putting that at the very end of the `handleKeypress()` function.
Xavier Ho
@Xavier Ho: Sorry but, it still doesn't work... when I press two keys (for player one) the square only moves in a direction as if only one key was press even when I put the glutPostRedisplay at the end.
thyrgle
Strange. Can you provide a paste?
Xavier Ho
@Xavier Ho: I have pasted an update version of the code maybe I am doing something wrong... So far I am only working with one player at the moment though...
thyrgle
@thyrgle: Can you give me a link on http://pastebin.com/ with both that function you have on here, and the function for array keys handling, as well as your main game loop? (That is, the part where you're binding `glutSpecFunc()`.) Also, I don't understand your usage of the for loop there. It's not doing anything special to your game.
Xavier Ho
@Xavier Ho: So paste all the code?
thyrgle
@thyrgle: Anything you feel relavent. I'm mainly interested to see your game loop, at the moment, and where you're updating drawings, as well as binding functions to the glut events.
Xavier Ho
@Xavier Ho: http://pastebin.com/b5h7iFEa Note: I'm not implementing two player just yet right now... I just want player one (the only square I made) to move correctly when two of its keys are pressed at the same time.
thyrgle
@thrygle: Sorry to say, but frankly that code is really ugly. That aside, I do see what your for loop is for now. But I think this will solve your problem: http://pastebin.com/4w4WdQ4y. Remove `glutPostRedisplay()` completely from keyPress, and use the timer to update the screen at a regular time. This will allow the screen from updating after processing multiple keys. || Also, try rewriting your code to get rid of the ugly for loops!
Xavier Ho
@Xavier Ho: Thanks for the criticism and help...
thyrgle
@Xavier Ho: Also, what do you recommend I replace the for loops with?
thyrgle
@thyrgle: I recommend you aggregate the methods and the array of 12 floats into a class, and just update your `x/y/z` position via `[0] [4] [8] (for x)`. It's cleaner, and it doesn't take 12 iterations, which is unnecessary overhead. Besides, explicit is better than implicit.
Xavier Ho
@Xavier Ho: Thanks for the advice!
thyrgle