[comp.sys.mac.programmer] Raw keyCode ==> ASCII?

2fmlcalls@kuhub.cc.ukans.edu (04/13/91)

I would like to be able allow the user to reconfigure the keys used to control
a game I'm working on.  The game uses GetKeys() when the user is playing to see
if a key is down.
My question is, how can you convert a keyCode into ASCII or a keyDown event
into its keyCode?  I could special-case every known keyborad type, but this
gets real kludgy real fast.  (If the user hits the left cursor arrow, I want to
allow this as a control - the problem is, I want to display "left arrow" so
that they know what key has been assigned.)
I tried to use KeyTrans, but there is little explanation of it.  To get the
pointer to a KCHR I dereferended a call from RGetResource('KCHR',0).  I don't
know - it seemed to work on my keyboard (didn't work on the extended though).

Anyone have experience doing this?

Thanks in advance...

john calhoun

TOGE@SLACVM.SLAC.STANFORD.EDU (Nobukazu Toge) (04/14/91)

I had an experience converting KeyCodes into Ascii codes, or something
that is readily display-able.  A problem here is that there is no single
characters characters "left-arrow", "home", "enter", "F1" etc.
So as you are afraid, it gets pretty messy.
It looks as if you need to hard-code (or at the best, make it
driven by your custom-made resource) to handle F-keys etc extensions.
I, too, would like to know if there's a more elegant solution.
Part of the code I'm using follows -

void Key2Char(short myKey, Str255 *chars)
/* myKey is the KeyCode (input), chars is the output char string */
{
    SysEnvRec   theWorld;
    short       theErr;
    Handle      myHandle;
    Ptr         myPointer;
    short       qChar;
    short       kchrID;

    theErr = SysEnvirons(1, &theWorld);
    kchrID = GetScript(GetEnvirons(smKeyScript), smScriptKeys);
    myHandle = GetResource('KCHR',kchrID);

    /* Strictly speaking you'd better check myhandle != NIL but I'm lazy */

    qChar = 0xFF;
        myPointer = *myHandle+260+myKey;
        qChar = (short)(*myPointer) & 0xFF;

    if ((qChar >= 0x21) && (qChar <= 0x7E) &&
         (qChar != 0x7F))
    {
        if (myKey < 0x40)
        {
            (*chars)[0] = 1;
            (*chars)[1] = qChar;
        }
        /*  You need to handle keypad key-characters by hand */
        /*  In my case, I did '1' --> '[1]' if it's from the keypad */
    }
    /* You need to handle other "weird" character cases by hand */
    /* In my case, I did a grand switch/case coding here */
}