src/events/SDL_keyboard.c
author Bob Pendleton <bob@pendleton.com>
Tue, 15 Jan 2008 22:37:17 +0000
changeset 2300 c97ad1abe05b
parent 2295 dbc6d1893869
child 2303 d87417504c75
permissions -rw-r--r--
Minimal implementation of textinput events for x11. It only works for latin-1.
slouken@0
     1
/*
slouken@0
     2
    SDL - Simple DirectMedia Layer
slouken@1312
     3
    Copyright (C) 1997-2006 Sam Lantinga
slouken@0
     4
slouken@0
     5
    This library is free software; you can redistribute it and/or
slouken@1312
     6
    modify it under the terms of the GNU Lesser General Public
slouken@0
     7
    License as published by the Free Software Foundation; either
slouken@1312
     8
    version 2.1 of the License, or (at your option) any later version.
slouken@0
     9
slouken@0
    10
    This library is distributed in the hope that it will be useful,
slouken@0
    11
    but WITHOUT ANY WARRANTY; without even the implied warranty of
slouken@0
    12
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
slouken@1312
    13
    Lesser General Public License for more details.
slouken@0
    14
slouken@1312
    15
    You should have received a copy of the GNU Lesser General Public
slouken@1312
    16
    License along with this library; if not, write to the Free Software
slouken@1312
    17
    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
slouken@0
    18
slouken@0
    19
    Sam Lantinga
slouken@252
    20
    slouken@libsdl.org
slouken@0
    21
*/
slouken@1402
    22
#include "SDL_config.h"
slouken@0
    23
slouken@0
    24
/* General keyboard handling code for SDL */
slouken@0
    25
slouken@1358
    26
#include "SDL_timer.h"
slouken@0
    27
#include "SDL_events.h"
slouken@0
    28
#include "SDL_events_c.h"
slouken@0
    29
#include "SDL_sysevents.h"
slouken@2268
    30
#include "SDL_keynames.h"
slouken@0
    31
slouken@0
    32
slouken@1895
    33
/* Global keyboard information */
slouken@0
    34
int SDL_TranslateUNICODE = 0;
slouken@1895
    35
static int SDL_num_keyboards;
slouken@1895
    36
static int SDL_current_keyboard;
slouken@1895
    37
static SDL_Keyboard **SDL_keyboards;
slouken@0
    38
bob@2295
    39
/* Taken from SDL_iconv() */
bob@2300
    40
char *
bob@2300
    41
SDL_Ucs4ToUtf8(Uint32 ch, char *dst)
bob@2295
    42
{
bob@2295
    43
    Uint8 *p = (Uint8 *) dst;
bob@2295
    44
    if (ch <= 0x7F) {
bob@2295
    45
        *p = (Uint8) ch;
bob@2295
    46
        ++dst;
bob@2295
    47
    } else if (ch <= 0x7FF) {
bob@2295
    48
        p[0] = 0xC0 | (Uint8) ((ch >> 6) & 0x1F);
bob@2295
    49
        p[1] = 0x80 | (Uint8) (ch & 0x3F);
bob@2295
    50
        dst += 2;
bob@2295
    51
    } else if (ch <= 0xFFFF) {
bob@2295
    52
        p[0] = 0xE0 | (Uint8) ((ch >> 12) & 0x0F);
bob@2295
    53
        p[1] = 0x80 | (Uint8) ((ch >> 6) & 0x3F);
bob@2295
    54
        p[2] = 0x80 | (Uint8) (ch & 0x3F);
bob@2295
    55
        dst += 3;
bob@2295
    56
    } else if (ch <= 0x1FFFFF) {
bob@2295
    57
        p[0] = 0xF0 | (Uint8) ((ch >> 18) & 0x07);
bob@2295
    58
        p[1] = 0x80 | (Uint8) ((ch >> 12) & 0x3F);
bob@2295
    59
        p[2] = 0x80 | (Uint8) ((ch >> 6) & 0x3F);
bob@2295
    60
        p[3] = 0x80 | (Uint8) (ch & 0x3F);
bob@2295
    61
        dst += 4;
bob@2295
    62
    } else if (ch <= 0x3FFFFFF) {
bob@2295
    63
        p[0] = 0xF8 | (Uint8) ((ch >> 24) & 0x03);
bob@2295
    64
        p[1] = 0x80 | (Uint8) ((ch >> 18) & 0x3F);
bob@2295
    65
        p[2] = 0x80 | (Uint8) ((ch >> 12) & 0x3F);
bob@2295
    66
        p[3] = 0x80 | (Uint8) ((ch >> 6) & 0x3F);
bob@2295
    67
        p[4] = 0x80 | (Uint8) (ch & 0x3F);
bob@2295
    68
        dst += 5;
bob@2295
    69
    } else {
bob@2295
    70
        p[0] = 0xFC | (Uint8) ((ch >> 30) & 0x01);
bob@2295
    71
        p[1] = 0x80 | (Uint8) ((ch >> 24) & 0x3F);
bob@2295
    72
        p[2] = 0x80 | (Uint8) ((ch >> 18) & 0x3F);
bob@2295
    73
        p[3] = 0x80 | (Uint8) ((ch >> 12) & 0x3F);
bob@2295
    74
        p[4] = 0x80 | (Uint8) ((ch >> 6) & 0x3F);
bob@2295
    75
        p[5] = 0x80 | (Uint8) (ch & 0x3F);
bob@2295
    76
        dst += 6;
bob@2295
    77
    }
bob@2295
    78
    return dst;
bob@2295
    79
}
bob@2295
    80
slouken@0
    81
/* Public functions */
slouken@1895
    82
int
slouken@1895
    83
SDL_KeyboardInit(void)
slouken@0
    84
{
slouken@1895
    85
    /* Set default mode of UNICODE translation */
slouken@1895
    86
    SDL_EnableUNICODE(DEFAULT_UNICODE_TRANSLATION);
slouken@0
    87
slouken@1895
    88
    return (0);
slouken@1123
    89
}
slouken@0
    90
slouken@1895
    91
SDL_Keyboard *
slouken@1895
    92
SDL_GetKeyboard(int index)
slouken@0
    93
{
slouken@1895
    94
    if (index < 0 || index >= SDL_num_keyboards) {
slouken@1895
    95
        return NULL;
slouken@1895
    96
    }
slouken@1895
    97
    return SDL_keyboards[index];
slouken@0
    98
}
slouken@0
    99
slouken@1895
   100
int
slouken@1895
   101
SDL_AddKeyboard(const SDL_Keyboard * keyboard, int index)
slouken@0
   102
{
slouken@1895
   103
    SDL_Keyboard **keyboards;
slouken@0
   104
slouken@1895
   105
    /* Add the keyboard to the list of keyboards */
slouken@1895
   106
    if (index < 0 || index >= SDL_num_keyboards || SDL_keyboards[index]) {
slouken@1895
   107
        keyboards =
slouken@1895
   108
            (SDL_Keyboard **) SDL_realloc(SDL_keyboards,
slouken@1895
   109
                                          (SDL_num_keyboards +
slouken@1895
   110
                                           1) * sizeof(*keyboards));
slouken@1895
   111
        if (!keyboards) {
slouken@1895
   112
            SDL_OutOfMemory();
slouken@1895
   113
            return -1;
slouken@1895
   114
        }
slouken@1895
   115
slouken@1895
   116
        SDL_keyboards = keyboards;
slouken@1895
   117
        index = SDL_num_keyboards++;
slouken@1895
   118
    }
slouken@1895
   119
    SDL_keyboards[index] =
slouken@1895
   120
        (SDL_Keyboard *) SDL_malloc(sizeof(*SDL_keyboards[index]));
slouken@1895
   121
    if (!SDL_keyboards[index]) {
slouken@1895
   122
        SDL_OutOfMemory();
slouken@1895
   123
        return -1;
slouken@1895
   124
    }
slouken@1895
   125
    *SDL_keyboards[index] = *keyboard;
slouken@1895
   126
slouken@1895
   127
    return index;
slouken@0
   128
}
slouken@0
   129
slouken@1895
   130
void
slouken@1895
   131
SDL_DelKeyboard(int index)
slouken@0
   132
{
slouken@1895
   133
    SDL_Keyboard *keyboard = SDL_GetKeyboard(index);
slouken@1895
   134
slouken@1895
   135
    if (!keyboard) {
slouken@1895
   136
        return;
slouken@1895
   137
    }
slouken@1895
   138
slouken@1895
   139
    if (keyboard->FreeKeyboard) {
slouken@1895
   140
        keyboard->FreeKeyboard(keyboard);
slouken@1895
   141
    }
slouken@1895
   142
    SDL_free(keyboard);
slouken@1895
   143
slouken@1895
   144
    SDL_keyboards[index] = NULL;
slouken@0
   145
}
slouken@0
   146
slouken@1895
   147
void
slouken@1895
   148
SDL_ResetKeyboard(int index)
slouken@0
   149
{
slouken@1895
   150
    SDL_Keyboard *keyboard = SDL_GetKeyboard(index);
slouken@2268
   151
    int key;
slouken@0
   152
slouken@1895
   153
    if (!keyboard) {
slouken@1895
   154
        return;
slouken@1895
   155
    }
slouken@1895
   156
slouken@1895
   157
    for (key = SDLK_FIRST; key < SDLK_LAST; ++key) {
slouken@1895
   158
        if (keyboard->keystate[key] == SDL_PRESSED) {
slouken@2268
   159
            SDL_SendKeyboardKey(index, SDL_RELEASED, 0,
slouken@2268
   160
                                key | SDL_KEY_CAN_BE_PHYSICAL_BIT);
slouken@1895
   161
        }
slouken@1895
   162
    }
slouken@0
   163
}
slouken@0
   164
slouken@1895
   165
void
slouken@1895
   166
SDL_KeyboardQuit(void)
slouken@0
   167
{
slouken@1895
   168
    int i;
slouken@0
   169
slouken@1895
   170
    for (i = 0; i < SDL_num_keyboards; ++i) {
slouken@1895
   171
        SDL_DelKeyboard(i);
slouken@1895
   172
    }
slouken@1895
   173
    SDL_num_keyboards = 0;
slouken@1895
   174
    SDL_current_keyboard = 0;
slouken@0
   175
slouken@1895
   176
    if (SDL_keyboards) {
slouken@1895
   177
        SDL_free(SDL_keyboards);
slouken@1895
   178
        SDL_keyboards = NULL;
slouken@1895
   179
    }
slouken@1895
   180
}
slouken@1895
   181
slouken@1895
   182
int
slouken@1895
   183
SDL_GetNumKeyboards(void)
slouken@1895
   184
{
slouken@1895
   185
    return SDL_num_keyboards;
slouken@1895
   186
}
slouken@1895
   187
slouken@1895
   188
int
slouken@1895
   189
SDL_SelectKeyboard(int index)
slouken@1895
   190
{
slouken@1895
   191
    if (index >= 0 && index < SDL_num_keyboards) {
slouken@1895
   192
        SDL_current_keyboard = index;
slouken@1895
   193
    }
slouken@1895
   194
    return SDL_current_keyboard;
slouken@1895
   195
}
slouken@1895
   196
slouken@1895
   197
int
slouken@1895
   198
SDL_EnableUNICODE(int enable)
slouken@1895
   199
{
slouken@1895
   200
    int old_mode;
slouken@1895
   201
slouken@1895
   202
    old_mode = SDL_TranslateUNICODE;
slouken@1895
   203
    if (enable >= 0) {
slouken@1895
   204
        SDL_TranslateUNICODE = enable;
slouken@1895
   205
    }
slouken@1895
   206
    return (old_mode);
slouken@1895
   207
}
slouken@1895
   208
slouken@1895
   209
Uint8 *
slouken@1895
   210
SDL_GetKeyState(int *numkeys)
slouken@1895
   211
{
slouken@1895
   212
    SDL_Keyboard *keyboard = SDL_GetKeyboard(SDL_current_keyboard);
slouken@1895
   213
slouken@1895
   214
    if (numkeys != (int *) 0) {
slouken@1895
   215
        *numkeys = SDLK_LAST;
slouken@1895
   216
    }
slouken@1895
   217
slouken@1895
   218
    if (!keyboard) {
slouken@1895
   219
        return NULL;
slouken@1895
   220
    }
slouken@1895
   221
    return keyboard->keystate;
slouken@1895
   222
}
slouken@1895
   223
slouken@1895
   224
SDLMod
slouken@1895
   225
SDL_GetModState(void)
slouken@1895
   226
{
slouken@1895
   227
    SDL_Keyboard *keyboard = SDL_GetKeyboard(SDL_current_keyboard);
slouken@1895
   228
slouken@1895
   229
    if (!keyboard) {
slouken@1895
   230
        return KMOD_NONE;
slouken@1895
   231
    }
slouken@1895
   232
    return keyboard->modstate;
slouken@1895
   233
}
slouken@1895
   234
slouken@1895
   235
void
slouken@1895
   236
SDL_SetModState(SDLMod modstate)
slouken@1895
   237
{
slouken@1895
   238
    SDL_Keyboard *keyboard = SDL_GetKeyboard(SDL_current_keyboard);
slouken@1895
   239
slouken@1895
   240
    if (!keyboard) {
slouken@1895
   241
        return;
slouken@1895
   242
    }
slouken@1895
   243
    keyboard->modstate = modstate;
slouken@1895
   244
}
slouken@1895
   245
slouken@2268
   246
SDLKey
slouken@2268
   247
SDL_GetLayoutKey(SDLKey physicalKey)
slouken@2268
   248
{
slouken@2268
   249
    SDL_VideoDevice *_this = SDL_GetVideoDevice();
slouken@2268
   250
    if (_this && _this->GetLayoutKey) {
slouken@2268
   251
        return _this->GetLayoutKey(_this, physicalKey)
slouken@2268
   252
            | (physicalKey & SDL_KEY_KEYPAD_BIT);
slouken@2268
   253
    } else {
slouken@2268
   254
        return physicalKey;
slouken@2268
   255
    }
slouken@2268
   256
}
slouken@2268
   257
slouken@1895
   258
const char *
slouken@2268
   259
SDL_GetKeyName(SDLKey layoutKey)
slouken@1895
   260
{
slouken@2268
   261
    const char *keyname = NULL;
slouken@1895
   262
slouken@2268
   263
    if ((layoutKey & SDL_KEY_LAYOUT_SPECIAL_BIT) != 0) {
slouken@2268
   264
        SDL_VideoDevice *_this = SDL_GetVideoDevice();
slouken@2268
   265
        if (_this && _this->GetSpecialKeyName) {
slouken@2268
   266
            keyname = _this->GetSpecialKeyName(_this, layoutKey);
slouken@2268
   267
        }
slouken@2268
   268
    } else if ((layoutKey & SDL_KEY_CAN_BE_PHYSICAL_BIT) == 0) {
bob@2300
   269
        /* SDLK_INDEX(layoutKey) is the unicode code point of the
bob@2300
   270
           character generated by the key */
slouken@2268
   271
        static char buffer[9];  /* 6 (maximal UTF-8 char length) + 2 ([] for keypad) + 1 (null teminator) */
slouken@2268
   272
        char *bufferPtr = &buffer[1];
slouken@2268
   273
        Uint32 codepoint = SDLK_INDEX(layoutKey);
slouken@2268
   274
bob@2300
   275
        /* Unaccented letter keys on latin keyboards are normally
bob@2300
   276
           labeled in upper case (and probably on others like Greek or
bob@2300
   277
           Cyrillic too, so if you happen to know for sure, please
bob@2300
   278
           adapt this). */
slouken@2268
   279
        if (codepoint >= 'a' && codepoint <= 'z') {
slouken@2268
   280
            codepoint -= 32;
slouken@2268
   281
        }
slouken@2268
   282
bob@2300
   283
        bufferPtr = SDL_Ucs4ToUtf8(codepoint, bufferPtr);
slouken@2268
   284
        *bufferPtr = '\0';
slouken@2268
   285
slouken@2268
   286
        if ((layoutKey & SDL_KEY_KEYPAD_BIT) != 0) {
slouken@2268
   287
            buffer[0] = '[';
slouken@2268
   288
            *bufferPtr++ = ']';
slouken@2268
   289
            *bufferPtr = '\0';
slouken@2268
   290
            keyname = buffer;
slouken@2268
   291
        } else {
slouken@2268
   292
            keyname = &buffer[1];
slouken@2268
   293
        }
slouken@1895
   294
    } else {
slouken@2268
   295
        /* SDLK_INDEX(layoutKey) is a physical key number */
slouken@2268
   296
        if (SDLK_INDEX(layoutKey) < SDL_arraysize(SDL_keynames)) {
slouken@2268
   297
            keyname = SDL_keynames[SDLK_INDEX(layoutKey)];
slouken@1895
   298
        }
slouken@1895
   299
    }
slouken@2268
   300
slouken@2268
   301
    if (keyname == NULL) {
slouken@2268
   302
        keyname = SDL_keynames[SDLK_INDEX(SDLK_UNKNOWN)];
slouken@2268
   303
    }
slouken@2268
   304
slouken@1895
   305
    return keyname;
slouken@1895
   306
}
slouken@1895
   307
slouken@1895
   308
void
slouken@2268
   309
SDL_SetKeyName(SDLKey physicalKey, const char *name)
slouken@2268
   310
{
slouken@2268
   311
    physicalKey = SDLK_INDEX(physicalKey);
slouken@2268
   312
    if (physicalKey < SDL_arraysize(SDL_keynames)) {
slouken@2268
   313
        SDL_keynames[physicalKey] = name;
slouken@2268
   314
    }
slouken@2268
   315
}
slouken@2268
   316
slouken@2268
   317
void
slouken@1895
   318
SDL_SetKeyboardFocus(int index, SDL_WindowID windowID)
slouken@1895
   319
{
slouken@1895
   320
    SDL_Keyboard *keyboard = SDL_GetKeyboard(index);
slouken@1895
   321
    int i;
slouken@1895
   322
    SDL_bool focus;
slouken@1895
   323
slouken@1895
   324
    if (!keyboard || (keyboard->focus == windowID)) {
slouken@1895
   325
        return;
slouken@1895
   326
    }
slouken@1895
   327
slouken@1895
   328
    /* See if the current window has lost focus */
slouken@1895
   329
    if (keyboard->focus) {
slouken@1895
   330
        focus = SDL_FALSE;
slouken@1895
   331
        for (i = 0; i < SDL_num_keyboards; ++i) {
slouken@1895
   332
            SDL_Keyboard *check;
slouken@1895
   333
            if (i != index) {
slouken@1895
   334
                check = SDL_GetKeyboard(i);
slouken@1895
   335
                if (check && check->focus == keyboard->focus) {
slouken@1895
   336
                    focus = SDL_TRUE;
slouken@1895
   337
                    break;
slouken@1895
   338
                }
slouken@1895
   339
            }
slouken@1895
   340
        }
slouken@1895
   341
        if (!focus) {
slouken@1895
   342
            SDL_SendWindowEvent(keyboard->focus, SDL_WINDOWEVENT_FOCUS_LOST,
slouken@1895
   343
                                0, 0);
slouken@1895
   344
        }
slouken@1895
   345
    }
slouken@1895
   346
slouken@1895
   347
    keyboard->focus = windowID;
slouken@1895
   348
slouken@1895
   349
    if (keyboard->focus) {
slouken@1895
   350
        focus = SDL_FALSE;
slouken@1895
   351
        for (i = 0; i < SDL_num_keyboards; ++i) {
slouken@1895
   352
            SDL_Keyboard *check;
slouken@1895
   353
            if (i != index) {
slouken@1895
   354
                check = SDL_GetKeyboard(i);
slouken@1895
   355
                if (check && check->focus == keyboard->focus) {
slouken@1895
   356
                    focus = SDL_TRUE;
slouken@1895
   357
                    break;
slouken@1895
   358
                }
slouken@1895
   359
            }
slouken@1895
   360
        }
slouken@1895
   361
        if (!focus) {
slouken@1895
   362
            SDL_SendWindowEvent(keyboard->focus, SDL_WINDOWEVENT_FOCUS_GAINED,
slouken@1895
   363
                                0, 0);
slouken@1895
   364
        }
slouken@1895
   365
    }
slouken@1895
   366
}
slouken@1895
   367
slouken@1895
   368
int
slouken@2268
   369
SDL_SendKeyboardKey(int index, Uint8 state, Uint8 scancode,
slouken@2268
   370
                    SDLKey physicalKey)
slouken@1895
   371
{
slouken@1895
   372
    SDL_Keyboard *keyboard = SDL_GetKeyboard(index);
slouken@2129
   373
    int posted;
slouken@1895
   374
    Uint16 modstate;
slouken@1895
   375
    Uint8 type;
slouken@1895
   376
slouken@2268
   377
    if (!keyboard || physicalKey == SDLK_NONE) {
slouken@1895
   378
        return 0;
slouken@1895
   379
    }
slouken@0
   380
#if 0
slouken@2268
   381
    printf("The '%s' key has been %s\n", SDL_GetKeyName(physicalKey),
slouken@1895
   382
           state == SDL_PRESSED ? "pressed" : "released");
slouken@0
   383
#endif
slouken@1895
   384
    if (state == SDL_PRESSED) {
slouken@1895
   385
        modstate = keyboard->modstate;
slouken@2268
   386
        switch (physicalKey) {
slouken@1895
   387
        case SDLK_UNKNOWN:
slouken@1895
   388
            break;
slouken@2268
   389
        case SDLK_KP_NUMLOCKCLEAR:
slouken@1895
   390
            keyboard->modstate ^= KMOD_NUM;
slouken@1895
   391
            break;
slouken@1895
   392
        case SDLK_CAPSLOCK:
slouken@1895
   393
            keyboard->modstate ^= KMOD_CAPS;
slouken@1895
   394
            break;
slouken@1895
   395
        case SDLK_LCTRL:
slouken@1895
   396
            keyboard->modstate |= KMOD_LCTRL;
slouken@1895
   397
            break;
slouken@1895
   398
        case SDLK_RCTRL:
slouken@1895
   399
            keyboard->modstate |= KMOD_RCTRL;
slouken@1895
   400
            break;
slouken@1895
   401
        case SDLK_LSHIFT:
slouken@1895
   402
            keyboard->modstate |= KMOD_LSHIFT;
slouken@1895
   403
            break;
slouken@1895
   404
        case SDLK_RSHIFT:
slouken@1895
   405
            keyboard->modstate |= KMOD_RSHIFT;
slouken@1895
   406
            break;
slouken@1895
   407
        case SDLK_LALT:
slouken@1895
   408
            keyboard->modstate |= KMOD_LALT;
slouken@1895
   409
            break;
slouken@1895
   410
        case SDLK_RALT:
slouken@1895
   411
            keyboard->modstate |= KMOD_RALT;
slouken@1895
   412
            break;
slouken@1895
   413
        case SDLK_LMETA:
slouken@1895
   414
            keyboard->modstate |= KMOD_LMETA;
slouken@1895
   415
            break;
slouken@1895
   416
        case SDLK_RMETA:
slouken@1895
   417
            keyboard->modstate |= KMOD_RMETA;
slouken@1895
   418
            break;
slouken@1895
   419
        case SDLK_MODE:
slouken@1895
   420
            keyboard->modstate |= KMOD_MODE;
slouken@1895
   421
            break;
slouken@1895
   422
        default:
slouken@1895
   423
            break;
slouken@1895
   424
        }
slouken@1895
   425
    } else {
slouken@2268
   426
        switch (physicalKey) {
slouken@1895
   427
        case SDLK_UNKNOWN:
slouken@1895
   428
            break;
slouken@2268
   429
        case SDLK_KP_NUMLOCKCLEAR:
slouken@1895
   430
        case SDLK_CAPSLOCK:
slouken@1895
   431
            break;
slouken@1895
   432
        case SDLK_LCTRL:
slouken@1895
   433
            keyboard->modstate &= ~KMOD_LCTRL;
slouken@1895
   434
            break;
slouken@1895
   435
        case SDLK_RCTRL:
slouken@1895
   436
            keyboard->modstate &= ~KMOD_RCTRL;
slouken@1895
   437
            break;
slouken@1895
   438
        case SDLK_LSHIFT:
slouken@1895
   439
            keyboard->modstate &= ~KMOD_LSHIFT;
slouken@1895
   440
            break;
slouken@1895
   441
        case SDLK_RSHIFT:
slouken@1895
   442
            keyboard->modstate &= ~KMOD_RSHIFT;
slouken@1895
   443
            break;
slouken@1895
   444
        case SDLK_LALT:
slouken@1895
   445
            keyboard->modstate &= ~KMOD_LALT;
slouken@1895
   446
            break;
slouken@1895
   447
        case SDLK_RALT:
slouken@1895
   448
            keyboard->modstate &= ~KMOD_RALT;
slouken@1895
   449
            break;
slouken@1895
   450
        case SDLK_LMETA:
slouken@1895
   451
            keyboard->modstate &= ~KMOD_LMETA;
slouken@1895
   452
            break;
slouken@1895
   453
        case SDLK_RMETA:
slouken@1895
   454
            keyboard->modstate &= ~KMOD_RMETA;
slouken@1895
   455
            break;
slouken@1895
   456
        case SDLK_MODE:
slouken@1895
   457
            keyboard->modstate &= ~KMOD_MODE;
slouken@1895
   458
            break;
slouken@1895
   459
        default:
slouken@1895
   460
            break;
slouken@1895
   461
        }
slouken@1895
   462
        modstate = keyboard->modstate;
slouken@1895
   463
    }
slouken@0
   464
slouken@1895
   465
    /* Figure out what type of event this is */
slouken@1895
   466
    switch (state) {
slouken@1895
   467
    case SDL_PRESSED:
slouken@1895
   468
        type = SDL_KEYDOWN;
slouken@1895
   469
        break;
slouken@1895
   470
    case SDL_RELEASED:
slouken@1895
   471
        type = SDL_KEYUP;
slouken@1895
   472
        break;
slouken@1895
   473
    default:
slouken@1895
   474
        /* Invalid state -- bail */
slouken@1895
   475
        return 0;
slouken@1895
   476
    }
slouken@0
   477
slouken@2268
   478
    if (physicalKey != SDLK_UNKNOWN) {
slouken@1895
   479
        /* Drop events that don't change state */
slouken@2268
   480
        if (keyboard->keystate[SDLK_INDEX(physicalKey)] == state) {
slouken@1895
   481
#if 0
slouken@1895
   482
            printf("Keyboard event didn't change state - dropped!\n");
slouken@1895
   483
#endif
slouken@1895
   484
            return 0;
slouken@1895
   485
        }
slouken@0
   486
slouken@1895
   487
        /* Update internal keyboard state */
slouken@2268
   488
        keyboard->keystate[SDLK_INDEX(physicalKey)] = state;
slouken@1895
   489
    }
slouken@0
   490
slouken@1895
   491
    /* Post the event, if desired */
slouken@1895
   492
    posted = 0;
slouken@1895
   493
    if (SDL_ProcessEvents[type] == SDL_ENABLE) {
slouken@1895
   494
        SDL_Event event;
slouken@1895
   495
        event.key.type = type;
slouken@1895
   496
        event.key.which = (Uint8) index;
slouken@1895
   497
        event.key.state = state;
slouken@1895
   498
        event.key.keysym.scancode = scancode;
slouken@2268
   499
        event.key.keysym.sym = physicalKey;
slouken@1895
   500
        event.key.keysym.mod = modstate;
slouken@1895
   501
        event.key.keysym.unicode = 0;
slouken@1895
   502
        event.key.windowID = keyboard->focus;
slouken@1895
   503
        posted = (SDL_PushEvent(&event) > 0);
slouken@1895
   504
    }
slouken@1895
   505
    return (posted);
slouken@1895
   506
}
slouken@1327
   507
slouken@1895
   508
int
slouken@1895
   509
SDL_SendKeyboardText(int index, const char *text)
slouken@1895
   510
{
slouken@1895
   511
    SDL_Keyboard *keyboard = SDL_GetKeyboard(index);
slouken@1895
   512
    int posted;
slouken@0
   513
slouken@1895
   514
    if (!keyboard) {
slouken@1895
   515
        return 0;
slouken@1895
   516
    }
slouken@1895
   517
slouken@1895
   518
    /* Post the event, if desired */
slouken@1895
   519
    posted = 0;
slouken@1895
   520
    if (SDL_ProcessEvents[SDL_TEXTINPUT] == SDL_ENABLE) {
slouken@1895
   521
        SDL_Event event;
slouken@1895
   522
        event.text.type = SDL_TEXTINPUT;
slouken@1895
   523
        event.text.which = (Uint8) index;
slouken@1895
   524
        SDL_strlcpy(event.text.text, text, SDL_arraysize(event.text.text));
slouken@1959
   525
        event.text.windowID = keyboard->focus;
slouken@1895
   526
        posted = (SDL_PushEvent(&event) > 0);
slouken@1895
   527
    }
slouken@1895
   528
    return (posted);
slouken@0
   529
}
slouken@0
   530
slouken@1895
   531
/* vi: set ts=4 sw=4 expandtab: */