SDL_Keycodes are too big for storage

1.1k views Asked by At

While searching up methods of detecting multiple keys at once in SDL 2, I came across this piece of code for SDL 1.x:

//author: Rob Loach
// Global key buffer
bool keys[256];

while(SDL_PollEvent(&mainEvent))
{
   if(mainEvent.type == SDL_KEYDOWN)
   {
       keys[mainEvent.key.keysym.sym] = true;
   }
   else if(mainEvent.type == SDL_KEYUP)
   {
       keys[mainEvent.key.keysym.sym] = false;
   }
}

I tried implementing it in SDL2 and a std::array<bool, 256>, but I had Segmentation fault: 11 with the up button.

That's when I looked at this: https://wiki.libsdl.org/SDLKeycodeLookup.

Most of the 'special' keys including arrow, function, symbols, and so on have decimal representations in the billions.

Even with the simple code printf("%d\n", e.key.keysym.sym); on, say the up button gives:

1073741906
Segmentation fault: 11

I am on a Mac, if it makes any difference with the error codes.

So, what solutions are there to this in SDL 2?

1

There are 1 answers

3
olevegard On BEST ANSWER

First of all, bools don't default to anything in C++, you need to initialize them. The fact that they appear to always be true is that they're byte in size. Which means they have a size between 0 and 255 inclusive. Only 0 would mean false so its a 255 / 256 chance of true.


As for your solution, you would simply define your std::map as this :

std::map<SDLKey, bool> keyMap;

An std::map is initially empty, so you need to check that the items actually exists when you try to look it up.

bool IsKeyDown(SDLKey key)
{
    // Look for element
    auto it = keyMap.find(key);

    if (it == keyMap.end())
        // No element found, which means this key hasn't been pressed
        return false;

    // 'it' is an iterator, so we use * to return its value
    return it->second; 
}

When you try to set an item, it will automtically get created if it doesn't exists :

bool SetIsKeyDown(SDLKey key, bool isDown)
{
    keyMap[key] = isDown
}

So the fact the std::map is initially empty means you don't need to fill it. You can if you want to, but it's not required like it is with an array.