How do you handle mapping keys to names

Started by
8 comments, last by Max Piano 17 years, 4 months ago
When you are writing stuff for users to customise controls in a game, how do you lot handle mapping a key to a string description. I've found GetKeyCodeName() (or something) in the Win32 API, but that seems to get its names from the keyboard driver so you don't have a lot of control of the format of the names of some of the weirder keys. Do games provide their own mappings for all different nationality keyboards or something, or is there a simpler way I'm missing? Ta.
Advertisement
I remember having the problem a while ago and a solution i saw was infact to have a #define for each key, mapping it to some internal engine specific ID for the key.

Dave
Quote:Original post by Dave
I remember having the problem a while ago and a solution i saw was infact to have a #define for each key, mapping it to some internal engine specific ID for the key.

Dave


That's what I started doing last night. I got as far as writing about 50 lines in a massive switch statement that was mapping virtual key codes to strings when I discovered that, without knowing the actually nationality of the keyboard layout I was targetting, it doesn't work for every key.

A lot of the punctuation keys send the same scan code but represent different characters on say UK and US keyboard layouts. According to the Win32 docs on the subject, there are a whole bunch of virtual key codes that can represent different keys depending on the keyboard nationality.

Its a real puzzler. Every commercial game I've ever played seems to be able to handle this correctly so there must be a solution.
Key mapping:

struct UIInputMap{    int         keyAction;  // move up side down fire    int         dikKey;     // key code SCAN code or DInput code      TCHAR       name[16];   };


Maped keys
UIInputMap mykeys[] ={  {1,VK_UP,    "Move Up"},  {2,VK_DOWN,  "Move Down"},  {3,VK_SPACE, "Fire"},  {0,0,0}}


You can remap as user wants just by replacing
'dikKey' to another keydown for a name.

And handling something like:

UIInputMap* p = mykeys;while(p->keyAction){     if(GetAsyncKeyState(p->dikKey)&0x800)   {      GameAction(p->keyAction);   }   ++p;}void GameAction(int action){    switch(action)    {       case 1:           player.position+=camera.forward*speed;           break;       case 3:          player.Shoot();}
MCO
Marius - thanks for the effort, but I'm actually interested in generating a text name for a keyboard key that takes keyboard nationality into account, not just literally mapping a keystroke to an action. Perhaps my post title was misleading.
SDL just uses a table, to be honest.
I suppose when defining keys for a game, you don't really care too much if the punctuation mark printed differs from the one on your keyboard. I guess a table solution is acceptable and simple.

I'm still curious to know how pro games handle this though.
Quote:Original post by EasilyConfused
I suppose when defining keys for a game, you don't really care too much if the punctuation mark printed differs from the one on your keyboard. I guess a table solution is acceptable and simple.

I'm still curious to know how pro games handle this though.


You "localize" the UI. So the actual layout of your UI looks something like this (I am totally making up random syntactic garbage here just to convey the idea):

<FireKeyName> = assignedKey;
<JumpKeyName> = assignedKey;

You have a localization system that reads a UI layout that looks something like that and plugs in the appropriate region-specific key. You can also lookup the keyboard language layout through windows somehow (look on MSDN) so you can decide whether to display the $ or the £, for instance.

Basically, have a good UI system where the layout of the UI is not defined in code, but rather is defined in a markup language. The code looks up values in a localization database and prints the correct text to the screen.

-me
I'm using SDL, which has a function that returns a character array for each key code (SDL_GetKeyName). However given I'm only using an alphanumeric font I found I couldn't use this, as the strings will contain symbols. So I just hacked together my own string array mapping every SDL key code to my own string description that seems to work fine.
If you are not concerned about cross-platform solutions (like SDL) you could use MapVirtualKeyEx function.

This topic is closed to new replies.

Advertisement