Index: src/video/dga/SDL_dgaevents.c =================================================================== RCS file: /home/sdlweb/libsdl.org/cvs/SDL12/src/video/dga/SDL_dgaevents.c,v retrieving revision 1.11 diff -c -r1.11 SDL_dgaevents.c *** src/video/dga/SDL_dgaevents.c 1 Feb 2006 06:32:20 -0000 1.11 --- src/video/dga/SDL_dgaevents.c 3 Feb 2006 13:26:10 -0000 *************** *** 37,44 **** /* Heheh we're using X11 event code */ extern int X11_Pending(Display *display); extern void X11_InitKeymap(void); ! extern SDL_keysym *X11_TranslateKey(Display *display, XIC ic, XKeyEvent *xkey, ! KeyCode kc, SDL_keysym *keysym); static int DGA_DispatchEvent(_THIS) { --- 37,43 ---- /* Heheh we're using X11 event code */ extern int X11_Pending(Display *display); extern void X11_InitKeymap(void); ! extern SDL_keysym *X11_TranslateKey(Display *display, KeyCode kc, SDL_keysym *keysym); static int DGA_DispatchEvent(_THIS) { *************** *** 82,89 **** SDL_NAME(XDGAKeyEventToXKeyEvent)(&xevent.xkey, &xkey); posted = SDL_PrivateKeyboard((xevent.type == KeyPress), ! X11_TranslateKey(DGA_Display, NULL/*no XIC*/, ! &xkey, xkey.keycode, &keysym)); } break; --- 81,88 ---- SDL_NAME(XDGAKeyEventToXKeyEvent)(&xevent.xkey, &xkey); posted = SDL_PrivateKeyboard((xevent.type == KeyPress), ! X11_TranslateKey(DGA_Display, ! xkey.keycode, &keysym)); } break; Index: src/video/x11/SDL_x11events.c =================================================================== RCS file: /home/sdlweb/libsdl.org/cvs/SDL12/src/video/x11/SDL_x11events.c,v retrieving revision 1.23 diff -c -r1.23 SDL_x11events.c *** src/video/x11/SDL_x11events.c 1 Feb 2006 06:32:24 -0000 1.23 --- src/video/x11/SDL_x11events.c 3 Feb 2006 13:26:10 -0000 *************** *** 57,64 **** /* The translation tables from an X11 keysym to a SDL keysym */ static SDLKey ODD_keymap[256]; static SDLKey MISC_keymap[256]; ! SDL_keysym *X11_TranslateKey(Display *display, XIC ic, XKeyEvent *xkey, KeyCode kc, ! SDL_keysym *keysym); /* Check to see if this is a repeated key. (idea shamelessly lifted from GII -- thanks guys! :) --- 57,65 ---- /* The translation tables from an X11 keysym to a SDL keysym */ static SDLKey ODD_keymap[256]; static SDLKey MISC_keymap[256]; ! SDL_keysym *X11_TranslateKey(Display *display, KeyCode kc, SDL_keysym *keysym); ! static int X11_HandleKeyEvent(Display *display, XIC ic, XEvent *event); ! static SDL_keysym *X11_HandleUnicode(XIC ic, XKeyEvent *xkey, SDL_keysym *keysym); /* Check to see if this is a repeated key. (idea shamelessly lifted from GII -- thanks guys! :) *************** *** 282,312 **** /* Key press? */ case KeyPress: { - SDL_keysym keysym; - #ifdef DEBUG_XEVENTS printf("KeyPress (X11 keycode = 0x%X)\n", xevent.xkey.keycode); #endif ! posted = SDL_PrivateKeyboard(SDL_PRESSED, ! X11_TranslateKey(SDL_Display, SDL_IC, &xevent.xkey, ! xevent.xkey.keycode, ! &keysym)); } break; /* Key release? */ case KeyRelease: { - SDL_keysym keysym; - #ifdef DEBUG_XEVENTS printf("KeyRelease (X11 keycode = 0x%X)\n", xevent.xkey.keycode); #endif /* Check to see if this is a repeated key */ if ( ! X11_KeyRepeat(SDL_Display, &xevent) ) { ! posted = SDL_PrivateKeyboard(SDL_RELEASED, ! X11_TranslateKey(SDL_Display, SDL_IC, &xevent.xkey, ! xevent.xkey.keycode, ! &keysym)); } } break; --- 283,303 ---- /* Key press? */ case KeyPress: { #ifdef DEBUG_XEVENTS printf("KeyPress (X11 keycode = 0x%X)\n", xevent.xkey.keycode); #endif ! posted = X11_HandleKeyEvent(SDL_Display, SDL_IC, &xevent); } break; /* Key release? */ case KeyRelease: { #ifdef DEBUG_XEVENTS printf("KeyRelease (X11 keycode = 0x%X)\n", xevent.xkey.keycode); #endif /* Check to see if this is a repeated key */ if ( ! X11_KeyRepeat(SDL_Display, &xevent) ) { ! posted = X11_HandleKeyEvent(SDL_Display, SDL_IC, &xevent); } } break; *************** *** 507,512 **** --- 498,523 ---- for ( i=0; iunicode = 0; keysym->sym = SDLK_UNKNOWN; if ( xsym ) { switch (xsym>>8) { *************** *** 807,817 **** } keysym->mod = KMOD_NONE; ! /* If UNICODE is on, get the UNICODE value for the key */ ! keysym->unicode = 0; ! if ( SDL_TranslateUNICODE && xkey ) { ! static XComposeStatus state; #define BROKEN_XFREE86_INTERNATIONAL_KBD /* This appears to be a magical flag that is used with AltGr on --- 818,832 ---- } keysym->mod = KMOD_NONE; ! return(keysym); ! } ! ! static SDL_keysym *X11_HandleUnicode(XIC ic, XKeyEvent *xkey, SDL_keysym *keysym) ! { ! static Status state; ! static XComposeStatus cstatus; + keysym->unicode = 0; #define BROKEN_XFREE86_INTERNATIONAL_KBD /* This appears to be a magical flag that is used with AltGr on *************** *** 820,861 **** FIXME: Check to see if this code is safe for other servers. */ #ifdef BROKEN_XFREE86_INTERNATIONAL_KBD ! /* Work around what appears to be a bug in XFree86 */ ! if ( SDL_GetModState() & KMOD_MODE ) { ! xkey->state |= (1<<13); ! } #endif ! /* Look up the translated value for the key event */ ! /* if there is no connection with the IM server, use the regular method */ ! if (ic == NULL || xkey->type != KeyPress) { ! unsigned char keybuf[32]; ! if ( pXLookupString(xkey, (char *)keybuf, sizeof(keybuf), ! NULL, &state) ) { ! /* ! * FIXME,: XLookupString() may yield more than one ! * character, so we need a mechanism to allow for ! * this (perhaps generate null keypress events with ! * a unicode value) ! */ ! keysym->unicode = keybuf[0]; ! } ! } else { /* else, use the IM protocol */ ! #ifdef X_HAVE_UTF8_STRING ! /* A UTF-8 character can be at most 6 bytes */ ! unsigned char keybuf[6]; ! pXSetICFocus(ic); ! if ( pXutf8LookupString(ic, (XKeyPressedEvent *)xkey, (char *)keybuf, sizeof(keybuf), ! NULL, (Status *)&state) ) ! keysym->unicode = Utf8ToUcs4(keybuf); ! pXUnsetICFocus(ic); ! #endif } } return(keysym); } /* X11 modifier masks for various keys */ static unsigned meta_l_mask, meta_r_mask, alt_l_mask, alt_r_mask; static unsigned num_mask, mode_switch_mask; --- 835,922 ---- FIXME: Check to see if this code is safe for other servers. */ #ifdef BROKEN_XFREE86_INTERNATIONAL_KBD ! /* Work around what appears to be a bug in XFree86 */ ! if ( SDL_GetModState() & KMOD_MODE ) { ! xkey->state |= (1<<13); ! } #endif ! /* Look up the translated value for the key event */ ! /* if there is no connection with the IM server, use the regular method */ ! if (ic == NULL || xkey->type != KeyPress) { ! unsigned char keybuf[32]; ! ! if ( pXLookupString(xkey, (char *)keybuf, sizeof(keybuf), ! NULL, &cstatus) ) { ! /* ! * FIXME,: XLookupString() may yield more than one ! * character, so we need a mechanism to allow for ! * this (perhaps generate null keypress events with ! * a unicode value) ! */ ! keysym->unicode = keybuf[0]; ! } ! } else { /* else, use the IM protocol */ ! #ifdef X_HAVE_UTF8_STRING ! unsigned char keybuf[6]; ! pXSetICFocus(ic); ! if (pXutf8LookupString(ic, xkey, keybuf, sizeof(keybuf), NULL, &state)) { ! keysym->unicode = Utf8ToUcs4(keybuf); } + #endif } return(keysym); } + + + static int X11_HandleKeyEvent(Display *display, XIC ic, XEvent *event) + { + static KeyCode last_scancode; + static KeySym last_xsym; + XKeyEvent *xkey = &event->xkey; + int posted = 0; + SDL_keysym keysym; + + X11_TranslateKey(display, xkey->keycode, &keysym); + + switch(xkey->type) { + case KeyRelease: + { + if (SDL_TranslateUNICODE) { + X11_HandleUnicode(ic, xkey, &keysym); + } + posted = SDL_PrivateKeyboard(SDL_RELEASED, &keysym); + pXFilterEvent(event, None); + break; + } + case KeyPress: + { + if (xkey->keycode) { + last_scancode = xkey->keycode; + last_xsym = keysym.sym; + } + if (pXFilterEvent(event, None)) { + if (xkey->keycode) { + posted = SDL_PrivateKeyboard(SDL_PRESSED, &keysym); + } + break; + } + if (SDL_TranslateUNICODE) { + X11_HandleUnicode(ic, xkey, &keysym); + if (!keysym.scancode) { + keysym.scancode = last_scancode; + keysym.sym = last_xsym; + } + } + posted = SDL_PrivateKeyboard(SDL_PRESSED, &keysym); + } + } + + return posted; + } + /* X11 modifier masks for various keys */ static unsigned meta_l_mask, meta_r_mask, alt_l_mask, alt_r_mask; static unsigned num_mask, mode_switch_mask; *************** *** 1018,1024 **** if(key_vec[i] & (1 << j)) { SDL_keysym sk; KeyCode kc = i << 3 | j; ! X11_TranslateKey(display, ic, NULL, kc, &sk); new_kstate[sk.sym] = SDL_PRESSED; xcode[sk.sym] = kc; } --- 1079,1085 ---- if(key_vec[i] & (1 << j)) { SDL_keysym sk; KeyCode kc = i << 3 | j; ! X11_TranslateKey(display, kc, &sk); new_kstate[sk.sym] = SDL_PRESSED; xcode[sk.sym] = kc; } Index: src/video/x11/SDL_x11sym.h =================================================================== RCS file: /home/sdlweb/libsdl.org/cvs/SDL12/src/video/x11/SDL_x11sym.h,v retrieving revision 1.9 diff -c -r1.9 SDL_x11sym.h *** src/video/x11/SDL_x11sym.h 1 Feb 2006 08:03:04 -0000 1.9 --- src/video/x11/SDL_x11sym.h 3 Feb 2006 13:26:10 -0000 *************** *** 123,128 **** --- 123,129 ---- SDL_X11_SYM(1,void,XDestroyIC,(XIC)) SDL_X11_SYM(1,void,XSetICFocus,(XIC)) SDL_X11_SYM(1,void,XUnsetICFocus,(XIC)) + SDL_X11_SYM(1,Bool,XFilterEvent,(XEvent*,Window)) SDL_X11_SYM(1,XIM,XOpenIM,(Display*,struct _XrmHashBucketRec*,char*,char*)) SDL_X11_SYM(1,Status,XCloseIM,(XIM)) #endif