src/video/bwindow/SDL_sysevents.cc

/* [<][>]
[^][v][top][bottom][index][help] */

FUNCTIONS

This source file includes following functions.
  1. CTRL

   1 /*
   2     SDL - Simple DirectMedia Layer
   3     Copyright (C) 1997, 1998, 1999, 2000, 2001  Sam Lantinga
   4 
   5     This library is free software; you can redistribute it and/or
   6     modify it under the terms of the GNU Library General Public
   7     License as published by the Free Software Foundation; either
   8     version 2 of the License, or (at your option) any later version.
   9 
  10     This library is distributed in the hope that it will be useful,
  11     but WITHOUT ANY WARRANTY; without even the implied warranty of
  12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  13     Library General Public License for more details.
  14 
  15     You should have received a copy of the GNU Library General Public
  16     License along with this library; if not, write to the Free
  17     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  18 
  19     Sam Lantinga
  20     slouken@devolution.com
  21 */
  22 
  23 #ifdef SAVE_RCSID
  24 static char rcsid =
  25  "@(#) $Id: SDL_sysevents.cc,v 1.3.2.4 2001/02/10 07:20:05 hercules Exp $";
  26 #endif
  27 
  28 #include <support/UTF8.h>
  29 #include <stdio.h>
  30 #include <string.h>
  31 #include "SDL_error.h"
  32 #include "SDL_events.h"
  33 #include "SDL_BWin.h"
  34 #include "SDL_lowvideo.h"
  35 
  36 extern "C" {
  37 
  38 #include "SDL_events_c.h"
  39 #include "SDL_sysevents.h"
  40 #include "SDL_sysevents_c.h"
  41 
  42 /* A note on why the polling loops are necessary.
  43    The BeOS Preview 2 implementation of BView->MouseMoved() only notifies
  44    the view when the mouse enters or leaves the view.  The documentation 
  45    says that you should loop and use GetMouse() to detect mouse motion.
  46    The BeOS Preview 2 implementation of BView->KeyDown() and BView->KeyUp()
  47    are only called for keys that generate ASCII characters.  Since we want
  48    to act like a low level raw keyboard, we need to poll the state of the
  49    keys instead of catching the keys in callbacks.
  50    These are documented portions of the BeBook for Preview Release 2
  51 */
  52  
  53 /* Table to convert scancodes to SDL virtual keys */
  54 static SDLKey keymap[128];
  55 
  56 /* Function to convert from a key scancode to a UNICODE character */
  57 static key_map *be_keymap;
  58 static int32 *option_caps_map[2], *option_map[2], *caps_map[2], *normal_map[2];
  59 static char *unicode_map;
  60 static Uint16 TranslateScancode(int scancode)
  61 {
  62         SDLMod modstate;
  63         int shifted;
  64         int32 index;            /* Index into system unicode map */
  65         Uint16 unicode;
  66 
  67         /* Set the default character -- no character */
  68         unicode = 0;
  69 
  70         /* See whether or not the shift state is set */
  71         modstate = SDL_GetModState();
  72         if ( modstate & KMOD_SHIFT ) {
  73                 shifted = 1;
  74         } else {
  75                 shifted = 0;
  76         }
  77 
  78         if ( modstate & KMOD_NUM ) {
  79         /* If numlock is on, numeric keypad keys have shift state inverted */
  80                 switch (keymap[scancode]) {
  81                     case SDLK_KP0:
  82                     case SDLK_KP1:
  83                     case SDLK_KP2:
  84                     case SDLK_KP3:
  85                     case SDLK_KP4:
  86                     case SDLK_KP5:
  87                     case SDLK_KP6:
  88                     case SDLK_KP7:
  89                     case SDLK_KP8:
  90                     case SDLK_KP9:
  91                     case SDLK_KP_PERIOD:
  92                     case SDLK_KP_DIVIDE:
  93                     case SDLK_KP_MULTIPLY:
  94                     case SDLK_KP_MINUS:
  95                     case SDLK_KP_PLUS:
  96                     case SDLK_KP_ENTER:
  97                     case SDLK_KP_EQUALS:
  98                         shifted = !shifted;
  99                         break;
 100                     default:
 101                         break;
 102                 }
 103         }
 104 
 105         /* Get the index based on modifier state */
 106         if ( modstate & KMOD_CTRL )
 107                 index = be_keymap->control_map[scancode];
 108         else
 109         if ( (modstate & KMOD_META) && (modstate & KMOD_CAPS) )
 110                 index = option_caps_map[shifted][scancode];
 111         else
 112         if ( modstate & KMOD_META )
 113                 index = option_map[shifted][scancode];
 114         else
 115         if ( modstate & KMOD_CAPS )
 116                 index = caps_map[shifted][scancode];
 117         else
 118                 index = normal_map[shifted][scancode];
 119 
 120         /* If there is a mapping, convert character from UTF-8 to UNICODE */
 121         if ( unicode_map[index] ) {
 122                 int32 state, srclen, dstlen;
 123                 unsigned char destbuf[2];
 124 
 125                 state = 0;
 126                 srclen = unicode_map[index++];
 127                 dstlen = sizeof(destbuf);
 128                 convert_from_utf8(B_UNICODE_CONVERSION,
 129                         &unicode_map[index], &srclen, (char *)destbuf, &dstlen,
 130                                                                         &state);
 131                 unicode = destbuf[0];
 132                 unicode <<= 8;
 133                 unicode |= destbuf[1];
 134 
 135                 /* Keyboard input maps newline to carriage return */
 136                 if ( unicode == '\n' ) {
 137                         unicode = '\r';
 138                 }
 139 
 140                 /* For some reason function keys map to control characters */
 141 # define CTRL(X)        ((X)-'@')
     /* [<][>][^][v][top][bottom][index][help] */
 142                 switch (unicode) {
 143                     case CTRL('A'):
 144                     case CTRL('B'):
 145                     case CTRL('C'):
 146                     case CTRL('D'):
 147                     case CTRL('E'):
 148                     case CTRL('K'):
 149                     case CTRL('L'):
 150                     case CTRL('P'):
 151                         if ( ! (modstate & KMOD_CTRL) )
 152                                 unicode = 0;
 153                         break;
 154                     default:
 155                         break;
 156                 }
 157         }
 158         return(unicode);
 159 }
 160 
 161 /* Function to translate a keyboard transition and queue the key event */
 162 static void QueueKey(int scancode, int pressed)
 163 {
 164         SDL_keysym keysym;
 165 
 166         /* Set the keysym information */
 167         keysym.scancode = scancode;
 168         keysym.sym = keymap[scancode];
 169         keysym.mod = KMOD_NONE;
 170         if ( SDL_TranslateUNICODE ) {
 171                 keysym.unicode = TranslateScancode(scancode);
 172         } else {
 173                 keysym.unicode = 0;
 174         }
 175 
 176         /* NUMLOCK and CAPSLOCK are implemented as double-presses in reality */
 177         if ( (keysym.sym == SDLK_NUMLOCK) || (keysym.sym == SDLK_CAPSLOCK) ) {
 178                 pressed = 1;
 179         }
 180 
 181         /* Queue the key event */
 182         if ( pressed ) {
 183                 SDL_PrivateKeyboard(SDL_PRESSED, &keysym);
 184         } else {
 185                 SDL_PrivateKeyboard(SDL_RELEASED, &keysym);
 186         }
 187 }
 188 
 189 /* This is special because we know it will be run in a loop in a separate
 190    thread.  Normally this function should loop as long as there are input
 191    states changing, i.e. new events arriving.
 192 */
 193 void BE_PumpEvents(_THIS)
 194 {
 195         BView *view;
 196         BRect bounds;
 197         BPoint point;
 198         uint32 buttons;
 199         const uint32 button_masks[3] = {
 200                 B_PRIMARY_MOUSE_BUTTON,
 201                 B_TERTIARY_MOUSE_BUTTON, 
 202                 B_SECONDARY_MOUSE_BUTTON,
 203         };
 204         unsigned int    i, j;
 205 
 206         /* Check out the mouse buttons and position (slight race condition) */
 207         if ( SDL_Win->Lock() ) {
 208                 /* Don't do anything if we have no view */
 209                 view = SDL_Win->View();
 210                 if ( ! view ) {
 211                         SDL_Win->Unlock();
 212                         return;
 213                 }
 214                 bounds = view->Bounds();
 215                 /* Get new input state, if still active */
 216                 if ( SDL_Win->IsActive() ) {
 217                         key_flip = !key_flip;
 218                         get_key_info(&keyinfo[key_flip]);
 219                         view->GetMouse(&point, &buttons, true);
 220                 } else {
 221                         key_flip = key_flip;
 222                         point = last_point;
 223                         buttons = last_buttons;
 224                 }
 225                 SDL_Win->Unlock();
 226         } else {
 227                 return;
 228         }
 229 
 230         /* If our view is active, we'll find key changes here */
 231         if ( memcmp(keyinfo[0].key_states, keyinfo[1].key_states, 16) != 0 ) {
 232                 for ( i=0; i<16; ++i ) {
 233                         Uint8 new_state, transition;
 234 
 235                         new_state = keyinfo[key_flip].key_states[i];
 236                         transition = keyinfo[!key_flip].key_states[i] ^
 237                                         keyinfo[ key_flip].key_states[i];
 238                         for ( j=0; j<8; ++j ) {
 239                                 if ( transition&0x80 )
 240                                         QueueKey(i*8+j, new_state&0x80);
 241                                 transition <<= 1;
 242                                 new_state <<= 1;
 243                         }
 244                 }
 245         }
 246 
 247         /* We check keyboard, but not mouse if mouse isn't in window */
 248         if ( ! bounds.Contains(point) ) {
 249                 /* Mouse moved outside our view? */
 250                 if ( SDL_GetAppState() & SDL_APPMOUSEFOCUS ) {
 251                         SDL_PrivateAppActive(0, SDL_APPMOUSEFOCUS);
 252                         be_app->SetCursor(B_HAND_CURSOR);
 253                 }
 254                 return;
 255         }
 256         /* Has the mouse moved back into our view? */
 257         if ( ! (SDL_GetAppState() & SDL_APPMOUSEFOCUS) ) {
 258                 /* Reset the B_HAND_CURSOR to our own */
 259                 SDL_PrivateAppActive(1, SDL_APPMOUSEFOCUS);
 260                 SDL_SetCursor(NULL);
 261         }
 262 
 263         /* Check for mouse motion */
 264         if ( point != last_point ) {
 265                 SDL_PrivateMouseMotion(0, 0, (int)point.x, (int)point.y);
 266         }
 267         last_point = point;
 268 
 269         /* Add any mouse button events */
 270         for ( i=0; i<SDL_TABLESIZE(button_masks); ++i ) {
 271                 if ( (buttons ^ last_buttons) & button_masks[i] ) {
 272                         if ( buttons & button_masks[i] ) {
 273                                 SDL_PrivateMouseButton(SDL_PRESSED, 1+i, 0, 0);
 274                         } else {
 275                                 SDL_PrivateMouseButton(SDL_RELEASED, 1+i, 0, 0);
 276                         }
 277                 }
 278         }
 279         last_buttons = buttons;
 280 }
 281 
 282 void BE_InitOSKeymap(_THIS)
 283 {
 284         unsigned int i;
 285 
 286         /* Initialize all the key states as "up" */
 287         key_flip = 0;
 288         memset(keyinfo[key_flip].key_states, 0, 16);
 289 
 290         /* Initialize the BeOS key translation table */
 291         /* Source: <be/interface/InterfaceDefs.h> and BeOS keyboard info */
 292         for ( i=0; i<SDL_TABLESIZE(keymap); ++i )
 293                 keymap[i] = SDLK_UNKNOWN;
 294 
 295         keymap[0x01]            = SDLK_ESCAPE;
 296         keymap[B_F1_KEY]        = SDLK_F1;
 297         keymap[B_F2_KEY]        = SDLK_F2;
 298         keymap[B_F3_KEY]        = SDLK_F3;
 299         keymap[B_F4_KEY]        = SDLK_F4;
 300         keymap[B_F5_KEY]        = SDLK_F5;
 301         keymap[B_F6_KEY]        = SDLK_F6;
 302         keymap[B_F7_KEY]        = SDLK_F7;
 303         keymap[B_F8_KEY]        = SDLK_F8;
 304         keymap[B_F9_KEY]        = SDLK_F9;
 305         keymap[B_F10_KEY]       = SDLK_F10;
 306         keymap[B_F11_KEY]       = SDLK_F11;
 307         keymap[B_F12_KEY]       = SDLK_F12;
 308         keymap[B_PRINT_KEY]     = SDLK_PRINT;
 309         //keymap[B_SCROLL_KEY]  = SDLK_SCROLLOCK;
 310         keymap[B_PAUSE_KEY]     = SDLK_PAUSE;
 311         keymap[0x11]            = SDLK_BACKQUOTE;
 312         keymap[0x12]            = SDLK_1;
 313         keymap[0x13]            = SDLK_2;
 314         keymap[0x14]            = SDLK_3;
 315         keymap[0x15]            = SDLK_4;
 316         keymap[0x16]            = SDLK_5;
 317         keymap[0x17]            = SDLK_6;
 318         keymap[0x18]            = SDLK_7;
 319         keymap[0x19]            = SDLK_8;
 320         keymap[0x1a]            = SDLK_9;
 321         keymap[0x1b]            = SDLK_0;
 322         keymap[0x1c]            = SDLK_MINUS;
 323         keymap[0x1d]            = SDLK_EQUALS;
 324         keymap[0x1e]            = SDLK_BACKSPACE;
 325         keymap[0x1f]            = SDLK_INSERT;
 326         keymap[0x20]            = SDLK_HOME;
 327         keymap[0x21]            = SDLK_PAGEUP;
 328         //keymap[0x22]          = SDLK_NUMLOCK;
 329         keymap[0x23]            = SDLK_KP_DIVIDE;
 330         keymap[0x24]            = SDLK_KP_MULTIPLY;
 331         keymap[0x25]            = SDLK_KP_MINUS;
 332         keymap[0x26]            = SDLK_TAB;
 333         keymap[0x27]            = SDLK_q;
 334         keymap[0x28]            = SDLK_w;
 335         keymap[0x29]            = SDLK_e;
 336         keymap[0x2a]            = SDLK_r;
 337         keymap[0x2b]            = SDLK_t;
 338         keymap[0x2c]            = SDLK_y;
 339         keymap[0x2d]            = SDLK_u;
 340         keymap[0x2e]            = SDLK_i;
 341         keymap[0x2f]            = SDLK_o;
 342         keymap[0x30]            = SDLK_p;
 343         keymap[0x31]            = SDLK_LEFTBRACKET;
 344         keymap[0x32]            = SDLK_RIGHTBRACKET;
 345         keymap[0x33]            = SDLK_BACKSLASH;
 346         keymap[0x34]            = SDLK_DELETE;
 347         keymap[0x35]            = SDLK_END;
 348         keymap[0x36]            = SDLK_PAGEDOWN;
 349         keymap[0x37]            = SDLK_KP7;
 350         keymap[0x38]            = SDLK_KP8;
 351         keymap[0x39]            = SDLK_KP9;
 352         keymap[0x3a]            = SDLK_KP_PLUS;
 353         //keymap[0x3b]          = SDLK_CAPSLOCK;
 354         keymap[0x3c]            = SDLK_a;
 355         keymap[0x3d]            = SDLK_s;
 356         keymap[0x3e]            = SDLK_d;
 357         keymap[0x3f]            = SDLK_f;
 358         keymap[0x40]            = SDLK_g;
 359         keymap[0x41]            = SDLK_h;
 360         keymap[0x42]            = SDLK_j;
 361         keymap[0x43]            = SDLK_k;
 362         keymap[0x44]            = SDLK_l;
 363         keymap[0x45]            = SDLK_SEMICOLON;
 364         keymap[0x46]            = SDLK_QUOTE;
 365         keymap[0x47]            = SDLK_RETURN;
 366         keymap[0x48]            = SDLK_KP4;
 367         keymap[0x49]            = SDLK_KP5;
 368         keymap[0x4a]            = SDLK_KP6;
 369         keymap[0x4b]            = SDLK_LSHIFT;
 370         keymap[0x4c]            = SDLK_z;
 371         keymap[0x4d]            = SDLK_x;
 372         keymap[0x4e]            = SDLK_c;
 373         keymap[0x4f]            = SDLK_v;
 374         keymap[0x50]            = SDLK_b;
 375         keymap[0x51]            = SDLK_n;
 376         keymap[0x52]            = SDLK_m;
 377         keymap[0x53]            = SDLK_COMMA;
 378         keymap[0x54]            = SDLK_PERIOD;
 379         keymap[0x55]            = SDLK_SLASH;
 380         keymap[0x56]            = SDLK_RSHIFT;
 381         keymap[0x57]            = SDLK_UP;
 382         keymap[0x58]            = SDLK_KP1;
 383         keymap[0x59]            = SDLK_KP2;
 384         keymap[0x5a]            = SDLK_KP3;
 385         keymap[0x5b]            = SDLK_KP_ENTER;
 386         //keymap[0x5c]          = SDLK_LCTRL;
 387         //keymap[0x5d]          = SDLK_LALT;
 388         keymap[0x5e]            = SDLK_SPACE;
 389         //keymap[0x5f]          = SDLK_RALT;
 390         //keymap[0x60]          = SDLK_RCTRL;
 391         keymap[0x61]            = SDLK_LEFT;
 392         keymap[0x62]            = SDLK_DOWN;
 393         keymap[0x63]            = SDLK_RIGHT;
 394         keymap[0x64]            = SDLK_KP0;
 395         keymap[0x65]            = SDLK_KP_PERIOD;
 396         //keymap[0x66]          = SDLK_LMETA;
 397         //keymap[0x67]          = SDLK_RMETA;
 398         //keymap[0x68]          = SDLK_MENU;
 399         keymap[0x69]            = SDLK_EURO;
 400         keymap[0x6a]            = SDLK_KP_EQUALS;
 401         keymap[0x6b]            = SDLK_POWER;
 402 
 403         /* Get the system keymap and UNICODE table.
 404            Note that this leaks memory since the maps are never freed.
 405          */
 406         get_key_map(&be_keymap, &unicode_map);
 407 
 408         /* Set the modifier keys from the system keymap */
 409         keymap[be_keymap->caps_key] = SDLK_CAPSLOCK;
 410         keymap[be_keymap->scroll_key] = SDLK_SCROLLOCK;
 411         keymap[be_keymap->num_key] = SDLK_NUMLOCK;
 412         keymap[be_keymap->left_shift_key] = SDLK_LSHIFT;
 413         keymap[be_keymap->right_shift_key] = SDLK_RSHIFT;
 414         keymap[be_keymap->left_command_key] = SDLK_LALT;
 415         keymap[be_keymap->right_command_key] = SDLK_RALT;
 416         keymap[be_keymap->left_control_key] = SDLK_LCTRL;
 417         keymap[be_keymap->right_control_key] = SDLK_RCTRL;
 418         keymap[be_keymap->left_option_key] = SDLK_LMETA;
 419         keymap[be_keymap->right_option_key] = SDLK_RMETA;
 420         keymap[be_keymap->menu_key] = SDLK_MENU;
 421 
 422         /* Set the modifier map pointers */
 423         option_caps_map[0] = be_keymap->option_caps_map;
 424         option_caps_map[1] = be_keymap->option_caps_shift_map;
 425         option_map[0] = be_keymap->option_map;
 426         option_map[1] = be_keymap->option_shift_map;
 427         caps_map[0] = be_keymap->caps_map;
 428         caps_map[1] = be_keymap->caps_shift_map;
 429         normal_map[0] = be_keymap->normal_map;
 430         normal_map[1] = be_keymap->shift_map;
 431 }
 432 
 433 }; /* Extern C */

/* [<][>][^][v][top][bottom][index][help] */