bool StXDisplay::open() { hDisplay = XOpenDisplay(NULL); // get first display on server from DISPLAY in env //hDisplay = XOpenDisplay(":0.0"); //hDisplay = XOpenDisplay("somehost:0.0"); //hDisplay = XOpenDisplay("192.168.1.10:0.0"); if(isOpened()) { initAtoms(); hInputMethod = XOpenIM(hDisplay, NULL, NULL, NULL); if(hInputMethod == NULL) { return true; } XIMStyles* anIMStyles = NULL; char* anIMValues = XGetIMValues(hInputMethod, XNQueryInputStyle, &anIMStyles, NULL); if(anIMValues != NULL || anIMStyles == NULL || anIMStyles->count_styles <= 0) { // input method doesn't support any styles if(anIMStyles != NULL) { XFree(anIMStyles); } return true; } const XIMStyle anIMStyle = anIMStyles->supported_styles[0]; XFree(anIMStyles); hInputCtx = XCreateIC(hInputMethod, XNInputStyle, anIMStyle, NULL); return true; } return false; }
void CXWindowsPrimaryScreen::onPostOpen() { assert(m_window != None); // get cursor info m_screen->getCursorPos(m_x, m_y); m_screen->getCursorCenter(m_xCenter, m_yCenter); // get the input method CDisplayLock display(m_screen); m_im = XOpenIM(display, NULL, NULL, NULL); if (m_im == NULL) { return; } // find the appropriate style. synergy supports XIMPreeditNothing // only at the moment. XIMStyles* styles; if (XGetIMValues(m_im, XNQueryInputStyle, &styles, NULL) != NULL || styles == NULL) { LOG((CLOG_WARN "cannot get IM styles")); return; } XIMStyle style = 0; for (unsigned short i = 0; i < styles->count_styles; ++i) { style = styles->supported_styles[i]; if ((style & XIMPreeditNothing) != 0) { if ((style & (XIMStatusNothing | XIMStatusNone)) != 0) { break; } } } XFree(styles); if (style == 0) { LOG((CLOG_WARN "no supported IM styles")); return; } // create an input context for the style and tell it about our window m_ic = XCreateIC(m_im, XNInputStyle, style, XNClientWindow, m_window, NULL); if (m_ic == NULL) { LOG((CLOG_WARN "cannot create IC")); return; } // find out the events we must select for and do so unsigned long mask; if (XGetICValues(m_ic, XNFilterEvents, &mask, NULL) != NULL) { LOG((CLOG_WARN "cannot get IC filter events")); return; } XWindowAttributes attr; XGetWindowAttributes(display, m_window, &attr); XSelectInput(display, m_window, attr.your_event_mask | mask); // no previous keycode m_lastKeycode = 0; }
// Check whether the IM has a usable style // static GLFWbool hasUsableInputMethodStyle(void) { unsigned int i; GLFWbool found = GLFW_FALSE; XIMStyles* styles = NULL; if (XGetIMValues(_glfw.x11.im, XNQueryInputStyle, &styles, NULL) != NULL) return GLFW_FALSE; for (i = 0; i < styles->count_styles; i++) { if (styles->supported_styles[i] == (XIMPreeditNothing | XIMStatusNothing)) { found = GLFW_TRUE; break; } } XFree(styles); return found; }
void xim_init(void) { GSList *it; gchar *aname, *aclass; aname = g_strdup(g_get_prgname()); if(!aname) aname = g_strdup("obt"); aclass = g_strdup(aname); if(g_ascii_islower(aclass[0])) aclass[0] = g_ascii_toupper(aclass[0]); xim = XOpenIM(t_display, NULL, aname, aclass); if(!xim) g_message("Failed to open an Input Method"); else { XIMStyles *xim_styles = NULL; char *r; r = XGetIMValues(xim, XNQueryInputStyle, &xim_styles, NULL); if(r || !xim_styles) g_message("Input Method does not support any styles"); if(xim_styles) { int i; for(i = 0; i < xim_styles->count_styles; ++i) { if(xim_styles->supported_styles[i] == (XIMPreeditNothing | XIMStatusNothing)) { xim_style = xim_styles->supported_styles[i]; break; } } XFree(xim_styles); } if(!xim_style) { g_message("Input Method does not support a usable style"); XCloseIM(xim); xim = NULL; } } for(it = xic_all; it; it = g_slist_next(it)) t_keyboard_context_renew(it->data); g_free(aclass); g_free(aname); }
static XIMStyle get_best_supported_style(XIM im_xim) { XIMStyles* styles; int i; XIMStyle result = 0; if (XGetIMValues(im_xim, XNQueryInputStyle, &styles, NULL) != NULL) { // NULL means it's OK return 0; } for (i = 0; i < styles->count_styles; ++i) { if (styles->supported_styles[i] == (XIMPreeditCallbacks | XIMStatusNothing) || styles->supported_styles[i] == (XIMPreeditNothing | XIMStatusNothing)) { result = styles->supported_styles[i]; break; } } XFree(styles); return result; }
bool create(std::string display, int buffer, bool fullscreen, bool border, int&x, int&y, unsigned int&w, unsigned int&h, bool transparent) { int modeNum=4; #ifdef HAVE_LIBXXF86VM XF86VidModeModeInfo **modes; #endif XSetErrorHandler (ErrorHandler); if ( (dpy = XOpenDisplay(display.c_str())) == NULL) { ::error("Could not open display %s",display.c_str()); return false; } screen = DefaultScreen(dpy); if ( !glXQueryExtension(dpy, NULL, NULL) ) { throw(GemException("X server has no OpenGL GLX extension")); return false; } if (fullscreen) { if (!display.empty()) { fullscreen=false; throw(GemException("fullscreen not available on remote display")); } else { #ifdef HAVE_LIBXXF86VM XF86VidModeGetAllModeLines(dpy, screen, &modeNum, &modes); deskMode = *modes[0]; #else throw(GemException("no xxf86vm-support: cannot switch to fullscreen")); #endif } } XVisualInfo *vi=0; #ifdef HAVE_LIBXRENDER if (transparent) { static GLXFBConfig *fbconfigs, fbconfig; static int numfbconfigs; // need to get some function pointer at runtime typedef GLXFBConfig*(*glXChooseFBConfigProc)(Display* dpy, int screen, const int* attribList, int* nitems); glXChooseFBConfigProc glXChooseFBConfigFn = (glXChooseFBConfigProc) glXGetProcAddress((const GLubyte*)"glXChooseFBConfig"); typedef XVisualInfo*(*glXGetVisualFromFBConfigProc)(Display* dpy, GLXFBConfig fbconfig); glXGetVisualFromFBConfigProc glXGetVisualFromFBConfigFn = (glXGetVisualFromFBConfigProc)glXGetProcAddress((const GLubyte*) "glXGetVisualFromFBConfig"); if (glXChooseFBConfigFn && glXGetVisualFromFBConfigFn) { static int**fbbuf=0; switch(buffer) { default: ::error("only single/double buffer supported; defaulting to double"); case 2: fbbuf=dblBufFbCfg; break; case 1: fbbuf=snglBufFbCfg; break; } bool breakme=false; for(; *fbbuf; fbbuf++) { fbconfigs = glXChooseFBConfigFn(dpy, screen, *fbbuf, &numfbconfigs); fbconfig = 0; for(int i = 0; i<numfbconfigs; i++) { vi = (XVisualInfo*) glXGetVisualFromFBConfigFn(dpy, fbconfigs[i]); if(!vi) { continue; } XRenderPictFormat *pict_format = XRenderFindVisualFormat(dpy, vi->visual); if(!pict_format) { continue; } fbconfig = fbconfigs[i]; if(pict_format->direct.alphaMask > 0) { ::verbose(0,"choose fbconfig : %d", i); breakme = true; break; } } if ( breakme ) { break; } } if(!fbconfig) { ::error("Can't find valid framebuffer configuration, try again with legacy method."); } else { typedef void(*glXGetFBConfigAttribProc)(Display* dpy,GLXFBConfig fbconfig, int attr, int* val); glXGetFBConfigAttribProc glXGetFBConfigAttribFn = (glXGetFBConfigAttribProc)glXGetProcAddress((const GLubyte*) "glXGetFBConfigAttrib"); if ( glXGetFBConfigAttribFn ) { int doublebuffer; int red_bits, green_bits, blue_bits, alpha_bits, depth_bits; glXGetFBConfigAttribFn(dpy, fbconfig, GLX_DOUBLEBUFFER, &doublebuffer); glXGetFBConfigAttribFn(dpy, fbconfig, GLX_RED_SIZE, &red_bits); glXGetFBConfigAttribFn(dpy, fbconfig, GLX_GREEN_SIZE, &green_bits); glXGetFBConfigAttribFn(dpy, fbconfig, GLX_BLUE_SIZE, &blue_bits); glXGetFBConfigAttribFn(dpy, fbconfig, GLX_ALPHA_SIZE, &alpha_bits); glXGetFBConfigAttribFn(dpy, fbconfig, GLX_DEPTH_SIZE, &depth_bits); ::verbose(0, "FBConfig selected:"); ::verbose(0, " Doublebuffer: %s", doublebuffer == True ? "Yes" : "No"); ::verbose(0, " Red Bits: %d, Green Bits: %d, Blue Bits: %d, Alpha Bits: %d, Depth Bits: %d", red_bits, green_bits, blue_bits, alpha_bits, depth_bits); } else { ::error("can't get glXGetFBConfigAttrib function pointer"); } } } } #endif // HAVE_LIBXRENDER if (vi == NULL) { // if Xrender method doesn't work try legacy static int**buf=0; switch(buffer) { default: ::error("only single/double buffer supported; defaulting to double"); case 2: buf=dblBufs; break; case 1: buf=snglBufs; break; } // the user wants double buffer for(; *buf; buf++) { vi = glXChooseVisual(dpy, screen, *buf); if(vi) { break; } } } if (vi == NULL) { std::string errstr="Unable to create "; switch(buffer) { default: errstr+="???"; break; case 1: errstr+"single"; break; case 2: errstr+"double"; break; } errstr+=" buffer window"; throw(GemException(errstr)); return false; } if(vi->depth<24) { ::verbose(0, "Only using %d color bits", vi->depth); } if (vi->c_class != TrueColor && vi->c_class != DirectColor) { ::error("TrueColor visual required for this program (got %d)", vi->c_class); return false; } // create the rendering context try { // first check whether we have a shared context for 'display' GLXContext sharedContext=0; if(s_shared.count(display)>0) { sharedContext=s_shared[display].glxcontext;; } glxcontext = glXCreateContext(dpy, vi, sharedContext, GL_TRUE); } catch(void*e) { glxcontext=NULL; } if (glxcontext == NULL) { throw(GemException("Could not create rendering context")); return false; } // create the X color map cmap = XCreateColormap(dpy, RootWindow(dpy, vi->screen), vi->visual, AllocNone); if (!cmap) { throw(GemException("Could not create X colormap")); return false; } XSetWindowAttributes swa; swa.colormap = cmap; swa.border_pixel = 0; // event_mask creates signal that window has been created swa.event_mask = EVENT_MASK; int flags; #ifdef HAVE_LIBXXF86VM if (fullscreen) { int bestMode=0; /* look for mode with requested resolution */ for (int i = 0; i < modeNum; i++) { if ((modes[i]->hdisplay == w) && (modes[i]->vdisplay == w)) { bestMode = i; } } XF86VidModeSwitchToMode(dpy, screen, modes[bestMode]); XF86VidModeSetViewPort(dpy, screen, 0, 0); w = modes[bestMode]->hdisplay; h = modes[bestMode]->vdisplay; x=y=0; XFree(modes); swa.override_redirect = True; flags=CWBorderPixel|CWColormap|CWEventMask|CWOverrideRedirect; } else #endif { // !fullscren if (border) { swa.override_redirect = False; flags=CWBorderPixel|CWColormap|CWEventMask|CWOverrideRedirect; } else { swa.override_redirect = True; flags=CWBorderPixel|CWColormap|CWEventMask|CWOverrideRedirect; } } fs = fullscreen; win = XCreateWindow(dpy, RootWindow(dpy, vi->screen), x, y, w, h, 0, vi->depth, InputOutput, vi->visual, flags, &swa); XFree( vi ); if (!win) { throw(GemException("Could not create X window")); return false; } have_border=(True==swa.override_redirect); XSelectInput(dpy, win, EVENT_MASK); inputMethod = XOpenIM(dpy, NULL, NULL, NULL); if(inputMethod) { XIMStyle style=0; XIMStyles *stylePtr=NULL; const char *preedit_attname = NULL; XVaNestedList preedit_attlist = NULL; if ((XGetIMValues(inputMethod, XNQueryInputStyle, &stylePtr, NULL) != NULL)) { stylePtr=NULL; } /* * Select the best input style supported by both the IM and Tk. */ if(stylePtr) { for (int i = 0; i < stylePtr->count_styles; i++) { XIMStyle thisStyle = stylePtr->supported_styles[i]; if (thisStyle == (XIMPreeditPosition | XIMStatusNothing)) { style = thisStyle; break; } else if (thisStyle == (XIMPreeditNothing | XIMStatusNothing)) { style = thisStyle; } } XFree(stylePtr); } if (style & XIMPreeditPosition) { XPoint spot = {0, 0}; XFontSet inputXfs; memset(&inputXfs, 0, sizeof(inputXfs)); preedit_attname = XNPreeditAttributes; preedit_attlist = XVaCreateNestedList(0, XNSpotLocation, &spot, XNFontSet, inputXfs, NULL); } inputContext=XCreateIC(inputMethod, XNInputStyle, style, XNClientWindow, win, XNFocusWindow, win, preedit_attname, preedit_attlist, NULL); } /* found a bit at * http://biology.ncsa.uiuc.edu/library/SGI_bookshelves/SGI_Developer/books/OpenGL_Porting/sgi_html/apf.html * LATER think about reacting on this event... */ delete_atom = XInternAtom(dpy, "WM_DELETE_WINDOW", True); if (delete_atom != None) { XSetWMProtocols(dpy, win, &delete_atom,1); } try { xerr=0; glXMakeCurrent(dpy, win, glxcontext); if(xerr!=0) { /* seems like the error-handler was called; so something did not work the way it should * should we really prevent window-creation in this case? * LATER re-think the entire dual-context thing */ throw(GemException("problems making glX-context current: refusing to continue\ntry setting the environment variable GEM_SINGLE_CONTEXT=1")); return false; } Window winDummy; unsigned int depthDummy; unsigned int borderDummy; //int x, y; XGetGeometry(dpy, win, &winDummy, &x, &y, &w, &h, &borderDummy, &depthDummy); } catch(void*e) { throw(GemException("Could not make glX-context current")); return false; } return true; }
/*********************************************************************** * X11DRV Ime creation * * Should always be called with the x11 lock held */ static BOOL open_xim( Display *display ) { struct x11drv_thread_data *thread_data = x11drv_thread_data(); XIMStyle ximStyleCallback, ximStyleNone; XIMStyles *ximStyles = NULL; INT i; XIM xim; XIMCallback destroy; xim = XOpenIM(display, NULL, NULL, NULL); if (xim == NULL) { WARN("Could not open input method.\n"); return FALSE; } destroy.client_data = NULL; destroy.callback = X11DRV_DestroyIM; if (XSetIMValues(xim, XNDestroyCallback, &destroy, NULL)) { WARN("Could not set destroy callback.\n"); } TRACE("xim = %p\n", xim); TRACE("X display of IM = %p\n", XDisplayOfIM(xim)); TRACE("Using %s locale of Input Method\n", XLocaleOfIM(xim)); XGetIMValues(xim, XNQueryInputStyle, &ximStyles, NULL); if (ximStyles == 0) { WARN("Could not find supported input style.\n"); XCloseIM(xim); return FALSE; } else { TRACE("ximStyles->count_styles = %d\n", ximStyles->count_styles); ximStyleRoot = 0; ximStyleNone = 0; ximStyleCallback = 0; for (i = 0; i < ximStyles->count_styles; ++i) { int style = ximStyles->supported_styles[i]; TRACE("ximStyles[%d] = %s%s%s%s%s\n", i, (style&XIMPreeditArea)?"XIMPreeditArea ":"", (style&XIMPreeditCallbacks)?"XIMPreeditCallbacks ":"", (style&XIMPreeditPosition)?"XIMPreeditPosition ":"", (style&XIMPreeditNothing)?"XIMPreeditNothing ":"", (style&XIMPreeditNone)?"XIMPreeditNone ":""); if (!ximStyle && (ximStyles->supported_styles[i] == ximStyleRequest)) { ximStyle = ximStyleRequest; TRACE("Setting Style: ximStyle = ximStyleRequest\n"); } else if (!ximStyleRoot &&(ximStyles->supported_styles[i] == STYLE_ROOT)) { ximStyleRoot = STYLE_ROOT; TRACE("Setting Style: ximStyleRoot = STYLE_ROOT\n"); } else if (!ximStyleCallback &&(ximStyles->supported_styles[i] == STYLE_CALLBACK)) { ximStyleCallback = STYLE_CALLBACK; TRACE("Setting Style: ximStyleCallback = STYLE_CALLBACK\n"); } else if (!ximStyleNone && (ximStyles->supported_styles[i] == STYLE_NONE)) { TRACE("Setting Style: ximStyleNone = STYLE_NONE\n"); ximStyleNone = STYLE_NONE; } } XFree(ximStyles); if (ximStyle == 0) ximStyle = ximStyleRoot; if (ximStyle == 0) ximStyle = ximStyleNone; if (ximStyleCallback == 0) { TRACE("No callback style avalable\n"); ximStyleCallback = ximStyle; } } thread_data->xim = xim; if ((ximStyle & (XIMPreeditNothing | XIMPreeditNone)) == 0 || (ximStyle & (XIMStatusNothing | XIMStatusNone)) == 0) { char **list; int count; thread_data->font_set = XCreateFontSet(display, "fixed", &list, &count, NULL); TRACE("ximFontSet = %p\n", thread_data->font_set); TRACE("list = %p, count = %d\n", list, count); if (list != NULL) { int i; for (i = 0; i < count; ++i) TRACE("list[%d] = %s\n", i, list[i]); XFreeStringList(list); } } else thread_data->font_set = NULL; wine_tsx11_unlock(); IME_UpdateAssociation(NULL); wine_tsx11_lock(); return TRUE; }
bool TWindow::CreateInputContext() { if (!fInputContext) { XIM xim = gApplication->GetInputMethod(); if (!xim) return false; XIMStyles* supportedStyles; XGetIMValues(xim, XNQueryInputStyle, &supportedStyles, NULL, NULL); if (!supportedStyles || supportedStyles->count_styles == 0) return false; XIMStyle* bestStyle = NULL; for (unsigned short i = 0; i < supportedStyles->count_styles; i++) { XIMStyle* style = &supportedStyles->supported_styles[i]; // first check to see if it is supported if ((*style & (XIMPreeditPosition | XIMPreeditNothing | XIMPreeditNone)) && (*style & ( /*XIMStatusCallbacks |*/ XIMStatusNothing | XIMStatusNone))) { if (bestStyle) { if (((*style & XIMPreeditPosition) && !(*bestStyle & XIMPreeditPosition)) || ((*style & XIMStatusCallbacks) && !(*bestStyle & XIMStatusCallbacks))) bestStyle = style; else if (((*style & XIMPreeditNothing) && !(*bestStyle & (XIMPreeditPosition | XIMPreeditNothing))) || ((*style & XIMStatusNothing) && !(*bestStyle & (XIMStatusCallbacks | XIMStatusNothing)))) bestStyle = style; } else bestStyle = style; } } XIMStyle style = (bestStyle ? *bestStyle : 0); XFree(supportedStyles); if (!bestStyle) return false; XPoint point; point.x = point.y = 0; XRectangle rect; rect.x = rect.y = 0; rect.width = rect.height = 0x7fff; TFont* font = GetFont(); ASSERT(font && font->GetFontSet()); XVaNestedList preeditAttributes = XVaCreateNestedList(0, XNFontSet, font->GetFontSet(), XNSpotLocation, &point, XNArea, &rect, NULL); ASSERT(preeditAttributes); // XVaNestedList statusAttributes = XVaCreateNestedList(0, XNFontSet, font->GetFontSet(), NULL); // ASSERT(statusAttributes); XIC xic = XCreateIC(xim, XNInputStyle, style, XNClientWindow, fWindow, XNFocusWindow, fWindow, XNPreeditAttributes, preeditAttributes, /*XNStatusAttributes, statusAttributes, */ NULL); if (xic) fInputContext = new TInputContext(xic); /*if (fInputContext) { long mask; XGetICValues(fInputContext->GetXIC(), XNFilterEvents, &mask, NULL); printf("XIC mask = %lx\n", mask); }*/ } return (fInputContext != NULL); }
static void grab_keys(int screen) { // use default input method XIM xim = XOpenIM(dpy, NULL, NULL, NULL); if (xim == NULL) error_exit("XOpenIM failed"); XIMStyle xim_style = 0; if (xim) { XIMStyles *xim_styles; char* imvalret = XGetIMValues (xim, XNQueryInputStyle, &xim_styles, NULL); if (imvalret != NULL || xim_styles == NULL) error_exit("input method doesn't support any styles"); if (xim_styles) { int i; for (i = 0; i < xim_styles->count_styles; i++) { if (xim_styles->supported_styles[i] == (XIMPreeditNothing | XIMStatusNothing)) { xim_style = xim_styles->supported_styles[i]; break; } } if (xim_style == 0) error_exit("input method doesn't support the style we support"); XFree(xim_styles); } } XSetWindowAttributes attr; attr.event_mask = (KeyPressMask | KeyReleaseMask); Window root = RootWindow(dpy, screen); Window w = root; XWindowAttributes wattr; XGetWindowAttributes(dpy, w, &wattr); XSelectInput(dpy, w, attr.event_mask); // Grab all supported keys KeySym ks; for (ks = 0; ks <= 255; ks++) { KeyCode kc = XKeysymToKeycode(dpy, ks); if (kc != 0) { XGrabKey(dpy, kc, 0, root, False, GrabModeAsync, GrabModeAsync); XGrabKey(dpy, kc, ShiftMask, root, False, GrabModeAsync, GrabModeAsync); } } int iks; for (iks = 0; iks < nkeygrabs; iks++) { KeyCode kc = XKeysymToKeycode(dpy, keygrabs[iks]); if (kc != 0) { XGrabKey(dpy, kc, 0, root, False, GrabModeAsync, GrabModeAsync); XGrabKey(dpy, kc, ShiftMask, root, False, GrabModeAsync, GrabModeAsync); } } XIC xic = NULL; if (xim && xim_style) { xic = XCreateIC(xim, XNInputStyle, xim_style, XNClientWindow, w, XNFocusWindow, w, NULL); if (xic == NULL) error_exit("XCreateIC failed"); } }
/* x_keyboard_init * Initialise the X11 keyboard driver. */ static int x_keyboard_init(void) { #ifdef ALLEGRO_XWINDOWS_WITH_XIM char *old_locale; XIMStyles *xim_styles; XIMStyle xim_style = 0; char *imvalret; int i; #endif ALLEGRO_SYSTEM_XGLX *s = (void *)al_get_system_driver(); if (xkeyboard_installed) return 0; if (s->x11display == NULL) return 0; main_pid = getpid(); memcpy(key_names, _al_keyboard_common_names, sizeof key_names); _al_mutex_lock(&s->lock); /* HACK: XkbSetDetectableAutoRepeat is broken in some versions of X.Org */ Bool supported; XkbSetDetectableAutoRepeat(s->x11display, True, &supported); if (!supported) { ALLEGRO_WARN("XkbSetDetectableAutoRepeat failed.\n"); } #ifdef ALLEGRO_XWINDOWS_WITH_XIM ALLEGRO_INFO("Using X Input Method.\n"); old_locale = setlocale(LC_CTYPE, NULL); ALLEGRO_DEBUG("Old locale: %s\n", old_locale ? old_locale : "(null)"); if (old_locale) { /* The return value of setlocale() may be clobbered by the next call * to setlocale() so we must copy it. */ old_locale = strdup(old_locale); } /* Otherwise we are restricted to ISO-8859-1 characters. */ if (setlocale(LC_CTYPE, "") == NULL) { ALLEGRO_WARN("Could not set default locale.\n"); } /* TODO: is this needed? modifiers = XSetLocaleModifiers("@im=none"); if (modifiers == NULL) { ALLEGRO_WARN("XSetLocaleModifiers failed.\n"); } */ xim = XOpenIM(s->x11display, NULL, NULL, NULL); if (xim == NULL) { ALLEGRO_WARN("XOpenIM failed.\n"); } if (old_locale) { ALLEGRO_DEBUG("Restoring old locale: %s\n", old_locale); setlocale(LC_CTYPE, old_locale); free(old_locale); } if (xim) { imvalret = XGetIMValues(xim, XNQueryInputStyle, &xim_styles, NULL); if (imvalret != NULL || xim_styles == NULL) { ALLEGRO_WARN("Input method doesn't support any styles.\n"); } if (xim_styles) { xim_style = 0; for (i = 0; i < xim_styles->count_styles; i++) { if (xim_styles->supported_styles[i] == (XIMPreeditNothing | XIMStatusNothing)) { xim_style = xim_styles->supported_styles[i]; break; } } if (xim_style == 0) { ALLEGRO_WARN("Input method doesn't support the style we support.\n"); } else { ALLEGRO_INFO("Input method style = %ld\n", xim_style); } XFree(xim_styles); } } if (xim && xim_style) { xic = XCreateIC(xim, XNInputStyle, xim_style, NULL); if (xic == NULL) { ALLEGRO_WARN("XCreateIC failed.\n"); } else { ALLEGRO_INFO("XCreateIC succeeded.\n"); } /* In case al_install_keyboard() is called when there already is * a display, we set it as client window. */ ALLEGRO_DISPLAY *display = al_get_current_display(); ALLEGRO_DISPLAY_XGLX *display_glx = (void *)display; if (display_glx && xic) XSetICValues(xic, XNClientWindow, display_glx->window, NULL); } #endif if (!_al_xwin_get_keyboard_mapping()) { return 1; } _al_mutex_unlock(&s->lock); xkeyboard_installed = 1; return 0; }
static void setup_im (GtkOXIMInfo *info) { XIMValuesList *ic_values = NULL; XIMCallback im_destroy_callback; GdkDisplay *display; if (info->im == NULL) return; im_destroy_callback.client_data = (XPointer)info; im_destroy_callback.callback = (XIMProc)xim_destroy_callback; XSetIMValues (info->im, XNDestroyCallback, &im_destroy_callback, NULL); XGetIMValues (info->im, XNQueryInputStyle, &info->xim_styles, XNQueryICValuesList, &ic_values, NULL); info->settings = gtk_settings_get_for_screen (info->screen); if (!g_object_class_find_property (G_OBJECT_GET_CLASS (info->settings), "gtk-im-preedit-style")) gtk_settings_install_property (g_param_spec_enum ("gtk-im-preedit-style", P_("IM Preedit style"), P_("How to draw the input method preedit string"), GTK_TYPE_IM_PREEDIT_STYLE, GTK_IM_PREEDIT_CALLBACK, G_PARAM_READWRITE)); if (!g_object_class_find_property (G_OBJECT_GET_CLASS (info->settings), "gtk-im-status-style")) gtk_settings_install_property (g_param_spec_enum ("gtk-im-status-style", P_("IM Status style"), P_("How to draw the input method statusbar"), GTK_TYPE_IM_STATUS_STYLE, GTK_IM_STATUS_CALLBACK, G_PARAM_READWRITE)); info->preedit_set = g_signal_connect_swapped (info->settings, "notify::gtk-im-preedit-style", G_CALLBACK (preedit_style_change), info); info->supports_string_conversion = FALSE; if (ic_values) { int i; for (i = 0; i < ic_values->count_values; i++) if (strcmp (ic_values->supported_values[i], XNStringConversionCallback) == 0) { info->supports_string_conversion = TRUE; break; } #if 0 for (i = 0; i < ic_values->count_values; i++) g_print ("%s\n", ic_values->supported_values[i]); for (i = 0; i < xim_styles->count_styles; i++) g_print ("%#x\n", xim_styles->supported_styles[i]); #endif XFree (ic_values); } preedit_style_change (info); display = gdk_screen_get_display (info->screen); info->display_closed_cb = g_signal_connect (display, "closed", G_CALLBACK (xim_info_display_closed), info); }
/* * Try to open a XIM with the current modifiers, then see if we can * open a suitable preedit type */ bool rxvt_term::IM_get_IC (const char *modifiers) { int i, j, found; XIM xim; XPoint spot; XRectangle rect, status_rect, needed_rect; unsigned long fg, bg; const char *p; char **s; XIMStyles *xim_styles; #ifdef ENABLE_XIM_ONTHESPOT XIMCallback xcb[4]; #endif set_environ (envv); if (! ((p = XSetLocaleModifiers (modifiers)) && *p)) return false; input_method = display->get_xim (locale, modifiers); if (input_method == NULL) return false; xim = input_method->xim; spot.x = spot.y = -1; xim_styles = NULL; if (XGetIMValues (xim, XNQueryInputStyle, &xim_styles, NULL) || !xim_styles || !xim_styles->count_styles) { im_destroy (); return false; } const char *pet[] = { rs[Rs_preeditType], "OverTheSpot,OffTheSpot,Root,None" }; for (int pi = 0; pi < 2; pi++) { p = pet[pi]; if (!p) continue; s = rxvt_splitcommastring (p); for (i = found = 0; !found && s[i]; i++) { if (!strcmp (s[i], "OverTheSpot")) input_style = XIMPreeditPosition | XIMStatusNothing; else if (!strcmp (s[i], "OffTheSpot")) input_style = XIMPreeditArea | XIMStatusArea; else if (!strcmp (s[i], "Root")) input_style = XIMPreeditNothing | XIMStatusNothing; else if (!strcmp (s[i], "None")) input_style = XIMPreeditNone | XIMStatusNone; #ifdef ENABLE_XIM_ONTHESPOT else if (SHOULD_INVOKE (HOOK_XIM_PREEDIT_START) && !strcmp (s[i], "OnTheSpot")) input_style = XIMPreeditCallbacks | XIMStatusNothing; #endif else input_style = XIMPreeditNothing | XIMStatusNothing; for (j = 0; j < xim_styles->count_styles; j++) if (input_style == xim_styles->supported_styles[j]) { rxvt_freecommastring (s); found = 1; goto foundpet; } } rxvt_freecommastring (s); } foundpet: XFree (xim_styles); if (!found) { im_destroy (); return false; } XFontSet fs = 0; XVaNestedList preedit_attr = 0, status_attr = 0; if (input_style & (XIMPreeditPosition | XIMPreeditArea)) { // fake us a font-set, please char **missing_charset_list; int missing_charset_count; char *def_string; char pat[512]; sprintf (pat, "-*-*-*-R-*-*-%d-*-*-*-*-*-*," "-*-*-*-R-*-*-%d-*-*-*-*-*-*," "-*-*-*-R-*-*-%d-*-*-*-*-*-*," "-*-*-*-R-*-*-%d-*-*-*-*-*-*," "-*-*-*-R-*-*-%d-*-*-*-*-*-*," "*", fheight, fheight + 1, fheight - 1, fheight - 2, fheight + 2); fs = XCreateFontSet (dpy, rs[Rs_imFont] ? rs[Rs_imFont] : pat, &missing_charset_list, &missing_charset_count, &def_string); if (missing_charset_list) XFreeStringList (missing_charset_list); if (!fs) { input_style &= ~(XIMPreeditPosition | XIMPreeditArea); rxvt_warn ("unable to create fontset for input method, try \"-pt Root\". Continuing.\n"); } } if (input_style & XIMPreeditPosition) { im_set_size (rect); im_set_position (spot); im_set_color (fg, bg); preedit_attr = XVaCreateNestedList (0, XNForeground, fg, XNBackground, bg, XNArea, &rect, XNSpotLocation, &spot, XNFontSet, fs, NULL); } else if (input_style & XIMPreeditArea) { im_set_color (fg, bg); /* * The necessary width of preedit area is unknown * until create input context. */ needed_rect.width = 0; im_set_preedit_area (rect, status_rect, needed_rect); preedit_attr = XVaCreateNestedList (0, XNForeground, fg, XNBackground, bg, XNArea, &rect, XNFontSet, fs, NULL); status_attr = XVaCreateNestedList (0, XNForeground, fg, XNBackground, bg, XNArea, &status_rect, XNFontSet, fs, NULL); } #if ENABLE_XIM_ONTHESPOT else if (input_style & XIMPreeditCallbacks) { im_set_position (spot); xcb[0].client_data = (XPointer)this; xcb[0].callback = (XIMProc)xim_preedit_start; xcb[1].client_data = (XPointer)this; xcb[1].callback = (XIMProc)xim_preedit_done; xcb[2].client_data = (XPointer)this; xcb[2].callback = (XIMProc)xim_preedit_draw; # if 0 xcb[3].client_data = (XPointer)this; xcb[3].callback = (XIMProc)xim_preedit_caret; # endif preedit_attr = XVaCreateNestedList (0, XNSpotLocation, &spot, XNPreeditStartCallback, &xcb[0], XNPreeditDoneCallback , &xcb[1], XNPreeditDrawCallback , &xcb[2], # if 0 XNPreeditCaretCallback, &xcb[3], # endif NULL); } #endif Input_Context = XCreateIC (xim, XNInputStyle, input_style, XNClientWindow, vt, XNFocusWindow, parent[0], preedit_attr ? XNPreeditAttributes : NULL, preedit_attr, status_attr ? XNStatusAttributes : NULL, status_attr, NULL); if (preedit_attr) XFree (preedit_attr); if (status_attr) XFree (status_attr); if (fs) XFreeFontSet (dpy, fs); if (Input_Context == NULL) { rxvt_warn ("failed to create input context, continuing without XIM.\n"); im_destroy (); return false; } #if 0 // unfortunately, only the focus window is used by XIM, hard to fix if (!XGetICValues (Input_Context, XNFilterEvents, &vt_emask_xim, NULL)) vt_select_input (); #endif IMSetPosition (); return true; }
int main(int argc, char**argv) { char **missing_charset_list; int missing_charset_count; XGCValues xgcv; unsigned long mask; Display* dpy; int scr; Window w, root; XSetWindowAttributes set_attr; int i; XIMStyle *style; static char buf[128]; KeySym keysym = 0; Status status; XWMHints wm_hints; XClassHint class_hints; XIMStyle input_style = 0; char **font_name_list; char *def_string; XFontStruct **font_struct_list; char **font_encoding_list; int nb_font; int len = 0; int no_xim = 0; printf ("A -> %c \n", XUtf8Tolower('A')); if (!setlocale(LC_ALL, "")) puts("locale not supported by C library, locale unchanged"); if (!XSetLocaleModifiers("")) puts("X locale modifiers not supported, using default"); dpy = XOpenDisplay(0); if (!dpy) { puts("cannot open display.\n"); exit(-1); } scr = DefaultScreen(dpy); root = RootWindow(dpy, scr); set_attr.event_mask = KeyPressMask|FocusChangeMask; set_attr.background_pixel = WhitePixel(dpy, DefaultScreen(dpy)); set_attr.border_pixel = BlackPixel(dpy, DefaultScreen(dpy)); w = XCreateWindow(dpy, root, 10,10,200,100,0, DefaultDepth(dpy, DefaultScreen(dpy)), InputOutput, DefaultVisual(dpy, DefaultScreen(dpy)), CWEventMask | CWBackPixel | CWBorderPixel, &set_attr); if (!w) { puts("cannot creat window.\n"); exit(-1); } class_hints.res_name = "test"; class_hints.res_class = "Test"; wm_hints.input = True; wm_hints.flags = InputHint; XmbSetWMProperties(dpy, w, "test", "test", NULL, 0, NULL, &wm_hints, &class_hints); XMapWindow(dpy, w); xim_im = XOpenIM(dpy, NULL, "test", "Test"); if (!xim_im) { puts("cannot Open Input Manager: Try default.\n"); XSetLocaleModifiers("@im="); xim_im = XOpenIM(dpy, NULL, "test", "Test"); if (!xim_im) { puts("Failed exiting.\n"); exit(-1); } } XGetIMValues (xim_im, XNQueryInputStyle, &xim_styles, NULL, NULL); for (i = 0, style = xim_styles->supported_styles; i < xim_styles->count_styles; i++, style++) { if (i == 0 && *style == (XIMStatusNone|XIMPreeditNone)) { printf("this is not a XIM server !!!\n"); no_xim = 1; } printf("input style : 0x%X\n", *style); } xim_ic = XCreateIC(xim_im, XNInputStyle, (XIMPreeditNothing | XIMStatusNothing), XNClientWindow, w, XNFocusWindow, w, NULL); if (!xim_ic) { puts("cannot create Input Context.\n"); exit(-1);} XFree(xim_styles); XSetICFocus(xim_ic); /***************************************************************/ /** I don't recommand to use a font base name list similar * to the following one in a real application ;-) * You should use an iso8859-1 font, plus a single font for * your language. */ /***************************************************************/ fontset = XCreateUtf8FontStruct(dpy, "-*-*-*-*-*-*-*-*-*-*-*-*-iso8858-3," /* not valid */ "-*-*-medium-r-*-*-*-*-*-*-*-*-iso8859-1," "-*-*-*-*-*-*-*-*-*-*-*-*-iso8859-6," "-*-*-*-*-*-*-*-*-*-*-*-*-iso8859-8," "-*-*-*-*-*-*-*-*-*-*-*-*-ksc5601.1987-0," "-*-symbol-*-*-*-*-*-*-*-*-*-*-adobe-fontspecific," "-*-*-*-*-*-*-*-*-*-*-*-*-iso8859-2," "-*-*-*-*-*-*-*-*-*-*-*-*-koi8-1," "-*-*-*-*-*-*-*-*-*-*-*-*-jisx0208.1983-0," "-*-*-*-*-*-*-*-*-*-*-*-*-jisx0212.1990-0," "-*-*-*-*-*-*-*-*-*-*-*-*-big5-0," "-*-*-*-*-*-*-*-*-*-*-*-*-jisx0201.1976-0," "-*-unifont-*-*-*-*-*-*-*-*-*-*-iso10646-1[0x300 0x400_0x500]," "-*-*-*-*-*-*-*-*-*-*-*-*-*-*"); /* THIS PART IS NOT REQUIERED */ nb_font = fontset->nb_font; while (nb_font > 0) { nb_font--; if (fontset->fonts[nb_font]) { printf("encoding=\"\" fid=%d \n %s\n", // fontset->encodings[nb_font], fontset->fonts[nb_font]->fid, fontset->font_name_list[nb_font]); } } /* END OF NOT REQUIERED PART*/ mask = (GCForeground | GCBackground); xgcv.foreground = BlackPixel(dpy, DefaultScreen(dpy)); xgcv.background = WhitePixel(dpy, DefaultScreen(dpy)); gc = XCreateGC(dpy, w, mask, &xgcv); if (!gc) { puts("cannot create Graphic Context.\n"); exit(-1);} /***************************************************************/ while (1) { int filtered; static XEvent xevent; static XVaNestedList list1 = 0; int r; XNextEvent(dpy, &xevent); if (xevent.type == KeyPress) { XKeyEvent *e = (XKeyEvent*) &xevent; printf ("0x%X %d\n", e->state, e->keycode); } if (xevent.type == DestroyNotify) { /* XIM server has crashed */ no_xim = 1; XSetLocaleModifiers("@im="); xim_im = XOpenIM(dpy, NULL, "test", "Test"); if (xim_im) { xim_ic = XCreateIC(xim_im, XNInputStyle, (XIMPreeditNothing | XIMStatusNothing), XNClientWindow, w, XNFocusWindow, w, NULL); } else { xim_ic = NULL; } if (!xim_ic) { puts("Crash recovery failed. exiting.\n"); exit(-1); } } if (xevent.type != DestroyNotify) { filtered = XFilterEvent(&xevent, 0); } if (xevent.type == FocusOut && xim_ic) XUnsetICFocus(xim_ic); if (xevent.type == FocusIn && xim_ic) XSetICFocus(xim_ic); if (xevent.type == KeyPress && !filtered) { len = XUtf8LookupString(xim_ic, &xevent.xkey, buf, 127, &keysym, &status); if (len == 1 && buf[0] == '\b') { x -= XUtf8TextWidth(fontset, buf, len); XUtf8DrawImageString(dpy, w, fontset, gc, x, y, buf, len); } else if (len == 1 && buf[0] == '\r') { y += fontset->ascent + fontset->descent; x = 0; XCloseIM(xim_im); } else { XUtf8DrawImageString(dpy, w, fontset, gc, x, y, buf, len); x += XUtf8TextWidth(fontset, buf, len); } XUtf8DrawString(dpy, w, fontset, gc, 0, 20, jp_txt, strlen(jp_txt)); XUtf8DrawString(dpy, w, fontset, gc, 50, 90, rtl_txt, strlen(rtl_txt)); XUtf8DrawRtlString(dpy, w, fontset, gc, 50, 90, rtl_txt, strlen(rtl_txt)); buf[len] = 0; printf("'%s' %d %x\n", buf, keysym, keysym); buf[0] = 0; } if (filtered) { printf("Dead key\n"); } } XFreeUtf8FontStruct(dpy, fontset); return 0; }
int main(int argc, char**argv) { char **missing_charset_list; int missing_charset_count; XGCValues xgcv; unsigned long mask; Display* dpy; int scr; Window w, root; XSetWindowAttributes set_attr; int i; XIMStyle *style; static char buf[128]; KeySym keysym = 0; Status status; XWMHints wm_hints; XClassHint class_hints; XIMStyle input_style = 0; char **font_name_list; char *def_string; XFontStruct **font_struct_list; char **font_encoding_list; int nb_font; int len = 0; int no_xim = 0; char **missing_charset_list_return; int missing_charset_count_return; char *def_string_return; if (!setlocale(LC_ALL, "")) puts("locale not supported by C library, locale unchanged"); if (!XSetLocaleModifiers("")) puts("X locale modifiers not supported, using default"); dpy = XOpenDisplay(0); scr = DefaultScreen(dpy); root = RootWindow(dpy, scr); set_attr.event_mask = KeyPressMask|FocusChangeMask; set_attr.background_pixel = WhitePixel(dpy, DefaultScreen(dpy)); set_attr.border_pixel = BlackPixel(dpy, DefaultScreen(dpy)); w = XCreateWindow(dpy, root, 10,10,200,100,0, DefaultDepth(dpy, DefaultScreen(dpy)), InputOutput, DefaultVisual(dpy, DefaultScreen(dpy)), CWEventMask | CWBackPixel | CWBorderPixel, &set_attr); class_hints.res_name = "test"; class_hints.res_class = "Test"; wm_hints.input = True; wm_hints.flags = InputHint; XmbSetWMProperties(dpy, w, "test", "test", NULL, 0, NULL, &wm_hints, &class_hints); XMapWindow(dpy, w); xim_im = XOpenIM(dpy, NULL, "test", "Test"); XGetIMValues(xim_im, XNQueryInputStyle, &xim_styles, NULL, NULL); for (i = 0, style = xim_styles->supported_styles; i < xim_styles->count_styles; i++, style++) { if (*style == (XIMStatusNone|XIMPreeditNone)) { printf("this is not a XIM server !!!\n"); no_xim = 1; } printf("input style : 0x%X\n", *style); } XFree(xim_styles); xim_ic = XCreateIC(xim_im, XNInputStyle, (XIMPreeditNothing | XIMStatusNothing), XNClientWindow, w, XNFocusWindow, w, NULL); XSetICFocus(xim_ic); /*************************************************************** * I don't recommend to use a font base name list similar * to the following one in a real application ;-) ***************************************************************/ fontset = XCreateFontSet(dpy, "-*-*-*-*-*-*-*-*-*-*-*-*-iso8858-3," /* not valid */ "-*-*-medium-r-*-*-*-*-*-*-*-*-iso8859-1," "-*-*-*-*-*-*-*-*-*-*-*-*-iso8859-6," "-*-*-*-*-*-*-*-*-*-*-*-*-iso8859-8," "-*-symbol-*-*-*-*-*-*-*-*-*-*-adobe-fontspecific," "-*-*-*-*-*-*-*-*-*-*-*-*-iso8859-2," "-*-*-*-*-*-*-*-*-*-*-*-*-koi8-1," "-*-*-*-*-*-*-*-*-*-*-*-*-jisx0208.1983-0," "-*-*-*-*-*-*-*-*-*-*-*-*-jisx0212.1990-0," "-*-*-*-*-*-*-*-*-*-*-*-*-big5-0," "-*-*-*-*-*-*-*-*-*-*-*-*-jisx0201.1976-0," "-*-unifont-*-*-*-*-*-*-*-*-*-*-iso10646-1[0x300 0x400_0x500]," "-*-*-*-*-*-*-*-*-*-*-*-*-*-*", &missing_charset_list_return, &missing_charset_count_return, &def_string_return); mask = (GCForeground | GCBackground); xgcv.foreground = BlackPixel(dpy, DefaultScreen(dpy)); xgcv.background = WhitePixel(dpy, DefaultScreen(dpy)); gc = XCreateGC(dpy, w, mask, &xgcv); /***************************************************************/ while (1) { int filtered; static XEvent xevent; static XVaNestedList list1 = 0; int r; XNextEvent(dpy, &xevent); if (xevent.type == KeyPress) { XKeyEvent *e = (XKeyEvent*) &xevent; printf ("0x%X %d\n", e->state, e->keycode); } filtered = XFilterEvent(&xevent, w); if (xevent.type == FocusOut) XUnsetICFocus(xim_ic); if (xevent.type == FocusIn) XSetICFocus(xim_ic); if (xevent.type == KeyPress && !filtered) { len = Xutf8LookupString(xim_ic, &xevent.xkey, buf, 127, &keysym, &status); Xutf8DrawImageString(dpy, w, fontset, gc, x, y, buf, len); Xutf8DrawString(dpy, w, fontset, gc, 0, 20, jp_txt, strlen(jp_txt)); Xutf8DrawString(dpy, w, fontset, gc, 50, 90, rtl_txt, strlen(rtl_txt)); buf[len] = 0; printf("'%s' %d\n", buf, keysym); buf[0] = 0; XCloseIM(xim_im); } if (filtered) { printf("Dead key\n"); } } XFreeFontSet(dpy, fontset); return 0; }
GlobalContext::GlobalContext(int _target_ups, int _target_fps) { thread_context = new thread::ThreadContext; logger::SetThreadName("Main thread"); logger::Info("Distance framework (" DISTANCE_PLATFORM ")\n"); SetTargetFPS(_target_fps); SetTargetUPS(_target_ups); window_count = 0; #if defined(DISTANCE_PLATFORM_LINUX) XSetErrorHandler(XErrorHandler); XSetIOErrorHandler(XIOErrorHandler); setlocale(LC_CTYPE, ""); XSetLocaleModifiers(""); x11_display = XOpenDisplay(nullptr); if (!x11_display) exception::low_level_exception->wrap_throw(exception::LowLevelException::E_X11_OPEN_DISPLAY); logger::Info("X graphics display at %p opened\n", x11_display); x11_wm_delete_message = XInternAtom(x11_display, "WM_DELETE_WINDOW", False); //x11WMAllowedActions = XInternAtom(x11_display, "_NET_WM_ALLOWED_ACTIONS", False); //x11WMActionFullscreen = XInternAtom(x11_display, "_NET_WM_ACTION_FULLSCREEN", False); x11_input_method = XOpenIM(x11_display, nullptr, nullptr, nullptr); if (!x11_input_method) exception::low_level_exception->wrap_throw(exception::LowLevelException::E_X11_OPEN_INPUT_METHOD); XIMStyles *styles = nullptr; if (XGetIMValues(x11_input_method, XNQueryInputStyle, &styles, nullptr) || !styles) exception::low_level_exception->wrap_throw(exception::LowLevelException::E_X11_RETR_INPUT_STYLES); x11_input_method_style = 0; for (int ix = 0; ix != styles->count_styles; ++ix) { XIMStyle thisStyle = styles->supported_styles[ix]; if (thisStyle == (XIMPreeditNothing | XIMStatusNothing)) { x11_input_method_style = thisStyle; break; } } XFree(styles); if (!x11_input_method_style) exception::low_level_exception->wrap_throw(exception::LowLevelException::E_X11_MATCHING_INPUT_STYLE); #elif defined(DISTANCE_PLATFORM_WIN32) win_instance = GetModuleHandle(0); win_window_class.cbSize = sizeof(WNDCLASSEX); win_window_class.style = CS_OWNDC; win_window_class.cbClsExtra = 0; win_window_class.cbWndExtra = 0; win_window_class.lpfnWndProc = graphics::GLWindow::WndProc; win_window_class.hInstance = win_instance; win_window_class.lpszClassName = DISTANCE_WIN_GL_WINDOW_CLASS; win_window_class.hIcon = 0; win_window_class.hCursor = 0; win_window_class.hbrBackground = 0; win_window_class.lpszMenuName = 0; win_window_class.hIconSm = 0; RegisterClassEx(&win_window_class); #endif gl_context = new graphics::GLContext(this); instance = this; }
void X11InputMethod::AttachToXIM(X11Types::Display* display) { if (m_xim != 0) return; if (!SetLocaleModifier(0, 0, FALSE) ) { // Recovery to avoid bug DSK-297409 which really is about a broken distribution OpString8 lc_ctype; lc_ctype.Set(setlocale(LC_CTYPE, 0)); BOOL ok = FALSE; OpAutoVector<OpString8> list; OP_STATUS rc = GetAlternativeLocaleFormat(lc_ctype, list); if (OpStatus::IsError(rc) || list.GetCount()==0) { ok = SetLocaleModifier(0, "C", FALSE); } else { for (UINT32 i=0; !ok && i<list.GetCount(); i++) ok = SetLocaleModifier(0, list.Get(i)->CStr(), FALSE); } if(!ok) { fprintf(stderr, "opera: You appear to have an invalid locale set. This may prevent you from being able to type\n"); return; } } m_xim = XOpenIM(display, NULL, NULL, NULL); if (m_xim == NULL) { // Recovery to avoid bug DSK-304220 (broken XMODIFIERS) SetLocaleModifier("@im=", m_lc_modifier.value.CStr(), TRUE); m_xim = XOpenIM(display, NULL, NULL, NULL); if (m_xim == NULL) { fprintf(stderr, "opera: XOpenIM failed. This may prevent you from being able to type\n"); return; } } { // local scope XIMCallback cb; cb.client_data = (XPointer)this; cb.callback = XIMDestroyCallback; const char * setvalueerr = XSetIMValues(m_xim, XNDestroyCallback, &cb, NULL); if (setvalueerr != 0) fprintf(stderr, "opera: Failed to set XIM destroy callback\n"); } XIMStyles* xim_styles = 0; char* im_values = XGetIMValues(m_xim, XNQueryInputStyle, &xim_styles, NULL); if(im_values != NULL || xim_styles == NULL) { fprintf(stderr, "opera: input method does not support any styles\n"); } if(xim_styles) { unsigned long callbacks = 0; for (int i = 0; i < xim_styles->count_styles; i++) { // We try to find the style with the most support for preedit and status callbacks if ((xim_styles->supported_styles[i] & XIMPreeditCallbacks) && (xim_styles->supported_styles[i] & callbacks) == callbacks) { m_xim_style = xim_styles->supported_styles[i]; callbacks |= XIMPreeditCallbacks; } if ((xim_styles->supported_styles[i] & XIMStatusCallbacks) && (xim_styles->supported_styles[i] & callbacks) == callbacks) { m_xim_style = xim_styles->supported_styles[i]; callbacks |= XIMStatusCallbacks; } if ((xim_styles->supported_styles[i] == (XIMPreeditNothing | XIMStatusNothing)) && !callbacks) { m_xim_style = xim_styles->supported_styles[i]; } } if (m_xim_style == 0) { fprintf(stderr, "opera: input method does not support the style we support\n"); } XFree(xim_styles); } }
/*********************************************************************** * X11DRV Ime creation * * Should always be called with the x11 lock held */ static void X11DRV_OpenIM(Display *display, XPointer ptr, XPointer data) { struct x11drv_thread_data *thread_data = x11drv_thread_data(); XIMStyle ximStyleCallback, ximStyleNone; XIMStyles *ximStyles = NULL; INT i; XIM xim; XIMCallback destroy; xim = XOpenIM(display, NULL, NULL, NULL); if (xim == NULL) { WARN("Could not open input method.\n"); return; } destroy.client_data = NULL; destroy.callback = X11DRV_DestroyIM; if (XSetIMValues(xim, XNDestroyCallback, &destroy, NULL)) { WARN("Could not set destroy callback.\n"); } TRACE("xim = %p\n", xim); TRACE("X display of IM = %p\n", XDisplayOfIM(xim)); TRACE("Using %s locale of Input Method\n", XLocaleOfIM(xim)); XGetIMValues(xim, XNQueryInputStyle, &ximStyles, NULL); if (ximStyles == 0) { WARN("Could not find supported input style.\n"); XCloseIM(xim); return; } else { TRACE("ximStyles->count_styles = %d\n", ximStyles->count_styles); ximStyleRoot = 0; ximStyleNone = 0; ximStyleCallback = 0; for (i = 0; i < ximStyles->count_styles; ++i) { int style = ximStyles->supported_styles[i]; TRACE("ximStyles[%d] = %s%s%s%s%s\n", i, (style&XIMPreeditArea)?"XIMPreeditArea ":"", (style&XIMPreeditCallbacks)?"XIMPreeditCallbacks ":"", (style&XIMPreeditPosition)?"XIMPreeditPosition ":"", (style&XIMPreeditNothing)?"XIMPreeditNothing ":"", (style&XIMPreeditNone)?"XIMPreeditNone ":""); if (!ximStyle && (ximStyles->supported_styles[i] == ximStyleRequest)) { ximStyle = ximStyleRequest; TRACE("Setting Style: ximStyle = ximStyleRequest\n"); } else if (!ximStyleRoot &&(ximStyles->supported_styles[i] == STYLE_ROOT)) { ximStyleRoot = STYLE_ROOT; TRACE("Setting Style: ximStyleRoot = STYLE_ROOT\n"); } else if (!ximStyleCallback &&(ximStyles->supported_styles[i] == STYLE_CALLBACK)) { ximStyleCallback = STYLE_CALLBACK; TRACE("Setting Style: ximStyleCallback = STYLE_CALLBACK\n"); } else if (!ximStyleNone && (ximStyles->supported_styles[i] == STYLE_NONE)) { TRACE("Setting Style: ximStyleNone = STYLE_NONE\n"); ximStyleNone = STYLE_NONE; } } XFree(ximStyles); if (ximStyle == 0) ximStyle = ximStyleRoot; if (ximStyle == 0) ximStyle = ximStyleNone; if (ximStyleCallback == 0) { TRACE("No callback style avalable\n"); ximStyleCallback = ximStyle; } } thread_data->xim = xim; XUnregisterIMInstantiateCallback(display, NULL, NULL, NULL, X11DRV_OpenIM, NULL); wine_tsx11_unlock(); IME_UpdateAssociation(NULL); wine_tsx11_lock(); }
readpw(Display *dpy, const char *pws) #endif { char buf[32], passwd[256]; int num, screen; unsigned int len, llen; KeySym ksym; XEvent ev; XIM im; XIMStyles *im_styles; XIMStyle im_style = 0; char *imvalret; XIC ic; Status status; im = XOpenIM(dpy, NULL, NULL, NULL); if (im == NULL) die("slock: XOpenIM failed"); if(im) { imvalret = XGetIMValues(im, XNQueryInputStyle, &im_styles, NULL); if (imvalret != NULL || im_styles == NULL) { die("slock: input method doesn't support any styles"); } if (im_styles) { im_style = 0; /* for now just pick the first style if it exists */ if (im_styles->count_styles) im_style = im_styles->supported_styles[0]; } if (im_style == 0) { die("slock: input method doesn't support the styles we support"); } XFree(im_styles); } if (im && im_style) { ic = XCreateIC(im, XNInputStyle, im_style, NULL); } len = llen = 0; running = True; /* As "slock" stands for "Simple X display locker", the DPMS settings * had been removed and you can set it with "xset" or some other * utility. This way the user can easily set a customized DPMS * timeout. */ while(running && !XNextEvent(dpy, &ev)) { if(ev.type == KeyPress) { buf[0] = 0; num = Xutf8LookupString(ic, &ev.xkey, buf, sizeof buf, &ksym, &status); switch (status) { case XBufferOverflow: die("slock: XBufferOverflow"); case XLookupNone: continue; case XLookupChars: /* Add the chars to the supposed password */ if (num) { memcpy(passwd + len, buf, num); len += num; if(running != False) XBell(dpy, 100); } break; case XLookupBoth: switch(ksym) { case XK_KP_Enter: case XK_Return: passwd[len] = 0; #ifdef HAVE_BSD_AUTH running = !auth_userokay(getlogin(), NULL, "auth-xlock", passwd); #else running = strcmp(crypt(passwd, pws), pws); #endif if(running != False) XBell(dpy, 100); len = 0; break; case XK_Escape: len = 0; break; case XK_BackSpace: if(len) --len; break; default: if (num) { memcpy(passwd + len, buf, num); len += num; if(running != False) XBell(dpy, 100); } break; } break; case XLookupKeySym: /* Check if ksym is return, enter, escape or backspace */ switch(ksym) { case XK_KP_Enter: case XK_Return: passwd[len] = 0; #ifdef HAVE_BSD_AUTH running = !auth_userokay(getlogin(), NULL, "auth-xlock", passwd); #else running = strcmp(crypt(passwd, pws), pws); #endif if(running != False) XBell(dpy, 100); len = 0; break; case XK_Escape: len = 0; break; case XK_BackSpace: if(len) --len; break; default: break; } } if(llen == 0 && len != 0) { for(screen = 0; screen < nscreens; screen++) { XSetWindowBackground(dpy, locks[screen]->win, locks[screen]->colors[1]); XClearWindow(dpy, locks[screen]->win); } } else if(llen != 0 && len == 0) { for(screen = 0; screen < nscreens; screen++) { XSetWindowBackground(dpy, locks[screen]->win, locks[screen]->colors[0]); XClearWindow(dpy, locks[screen]->win); } } llen = len; } else for(screen = 0; screen < nscreens; screen++) XRaiseWindow(dpy, locks[screen]->win); } if (im != NULL) XCloseIM(im); }
void OS_X11::initialize(const VideoMode& p_desired,int p_video_driver,int p_audio_driver) { last_button_state=0; dpad_last[0]=0; dpad_last[1]=0; xmbstring=NULL; event_id=0; x11_window=0; last_click_ms=0; args=OS::get_singleton()->get_cmdline_args(); current_videomode=p_desired; main_loop=NULL; last_timestamp=0; last_mouse_pos_valid=false; last_keyrelease_time=0; if (get_render_thread_mode()==RENDER_SEPARATE_THREAD) { XInitThreads(); } /** XLIB INITIALIZATION **/ x11_display = XOpenDisplay(NULL); char * modifiers = XSetLocaleModifiers ("@im=none"); ERR_FAIL_COND( modifiers == NULL ); xim = XOpenIM (x11_display, NULL, NULL, NULL); if (xim == NULL) { WARN_PRINT("XOpenIM failed"); xim_style=NULL; } else { ::XIMStyles *xim_styles=NULL; xim_style=0; char *imvalret=NULL; imvalret = XGetIMValues(xim, XNQueryInputStyle, &xim_styles, NULL); if (imvalret != NULL || xim_styles == NULL) { fprintf (stderr, "Input method doesn't support any styles\n"); } if (xim_styles) { xim_style = 0; for (int i=0;i<xim_styles->count_styles;i++) { if (xim_styles->supported_styles[i] == (XIMPreeditNothing | XIMStatusNothing)) { xim_style = xim_styles->supported_styles[i]; break; } } XFree (xim_styles); } } /* char* windowid = getenv("GODOT_WINDOWID"); if (windowid) { //freopen("/home/punto/stdout", "w", stdout); //reopen("/home/punto/stderr", "w", stderr); x11_window = atol(windowid); XWindowAttributes xwa; XGetWindowAttributes(x11_display,x11_window,&xwa); current_videomode.width = xwa.width; current_videomode.height = xwa.height; }; */ // maybe contextgl wants to be in charge of creating the window //print_line("def videomode "+itos(current_videomode.width)+","+itos(current_videomode.height)); #if defined(OPENGL_ENABLED) || defined(LEGACYGL_ENABLED) context_gl = memnew( ContextGL_X11( x11_display, x11_window,current_videomode, false ) ); context_gl->initialize(); if (true) { rasterizer = memnew( RasterizerGLES2 ); } else { //rasterizer = memnew( RasterizerGLES1 ); }; #endif visual_server = memnew( VisualServerRaster(rasterizer) ); if (get_render_thread_mode()!=RENDER_THREAD_UNSAFE) { visual_server =memnew(VisualServerWrapMT(visual_server,get_render_thread_mode()==RENDER_SEPARATE_THREAD)); } // borderless fullscreen window mode if (current_videomode.fullscreen) { // needed for lxde/openbox, possibly others Hints hints; Atom property; hints.flags = 2; hints.decorations = 0; property = XInternAtom(x11_display, "_MOTIF_WM_HINTS", True); XChangeProperty(x11_display, x11_window, property, property, 32, PropModeReplace, (unsigned char *)&hints, 5); XMapRaised(x11_display, x11_window); XWindowAttributes xwa; XGetWindowAttributes(x11_display, DefaultRootWindow(x11_display), &xwa); XMoveResizeWindow(x11_display, x11_window, 0, 0, xwa.width, xwa.height); // code for netwm-compliants XEvent xev; Atom wm_state = XInternAtom(x11_display, "_NET_WM_STATE", False); Atom fullscreen = XInternAtom(x11_display, "_NET_WM_STATE_FULLSCREEN", False); memset(&xev, 0, sizeof(xev)); xev.type = ClientMessage; xev.xclient.window = x11_window; xev.xclient.message_type = wm_state; xev.xclient.format = 32; xev.xclient.data.l[0] = 1; xev.xclient.data.l[1] = fullscreen; xev.xclient.data.l[2] = 0; XSendEvent(x11_display, DefaultRootWindow(x11_display), False, SubstructureNotifyMask, &xev); } // disable resizeable window if (!current_videomode.resizable) { XSizeHints *xsh; xsh = XAllocSizeHints(); xsh->flags = PMinSize | PMaxSize; XWindowAttributes xwa; if (current_videomode.fullscreen) { XGetWindowAttributes(x11_display,DefaultRootWindow(x11_display),&xwa); } else { XGetWindowAttributes(x11_display,x11_window,&xwa); } xsh->min_width = xwa.width; xsh->max_width = xwa.width; xsh->min_height = xwa.height; xsh->max_height = xwa.height; XSetWMNormalHints(x11_display, x11_window, xsh); } AudioDriverManagerSW::get_driver(p_audio_driver)->set_singleton(); if (AudioDriverManagerSW::get_driver(p_audio_driver)->init()!=OK) { ERR_PRINT("Initializing audio failed."); } sample_manager = memnew( SampleManagerMallocSW ); audio_server = memnew( AudioServerSW(sample_manager) ); audio_server->init(); spatial_sound_server = memnew( SpatialSoundServerSW ); spatial_sound_server->init(); spatial_sound_2d_server = memnew( SpatialSound2DServerSW ); spatial_sound_2d_server->init(); ERR_FAIL_COND(!visual_server); ERR_FAIL_COND(x11_window==0); XSetWindowAttributes new_attr; new_attr.event_mask=KeyPressMask | KeyReleaseMask | ButtonPressMask | ButtonReleaseMask | EnterWindowMask | LeaveWindowMask | PointerMotionMask | Button1MotionMask | Button2MotionMask | Button3MotionMask | Button4MotionMask | Button5MotionMask | ButtonMotionMask | KeymapStateMask | ExposureMask | VisibilityChangeMask | StructureNotifyMask | SubstructureNotifyMask | SubstructureRedirectMask | FocusChangeMask | PropertyChangeMask | ColormapChangeMask | OwnerGrabButtonMask; XChangeWindowAttributes(x11_display, x11_window,CWEventMask,&new_attr); XClassHint* classHint; /* set the titlebar name */ XStoreName(x11_display, x11_window, "Godot"); /* set the name and class hints for the window manager to use */ classHint = XAllocClassHint(); if (classHint) { classHint->res_name = "Godot"; classHint->res_class = "Godot"; } XSetClassHint(x11_display, x11_window, classHint); XFree(classHint); wm_delete = XInternAtom(x11_display, "WM_DELETE_WINDOW", true); XSetWMProtocols(x11_display, x11_window, &wm_delete, 1); if (xim && xim_style) { xic = XCreateIC (xim,XNInputStyle, xim_style,XNClientWindow,x11_window,XNFocusWindow, x11_window, (char*)NULL); } else { xic=NULL; WARN_PRINT("XCreateIC couldn't create xic"); } XcursorSetTheme(x11_display,"default"); cursor_size = XcursorGetDefaultSize(x11_display); cursor_theme = XcursorGetTheme(x11_display); if (!cursor_theme) { print_line("not found theme"); cursor_theme="default"; } for(int i=0;i<CURSOR_MAX;i++) { cursors[i]=None; } current_cursor=CURSOR_ARROW; if (cursor_theme) { //print_line("cursor theme: "+String(cursor_theme)); for(int i=0;i<CURSOR_MAX;i++) { static const char *cursor_file[]={ "left_ptr", "xterm", "hand2", "cross", "watch", "left_ptr_watch", "fleur", "hand1", "X_cursor", "sb_v_double_arrow", "sb_h_double_arrow", "size_bdiag", "size_fdiag", "hand1", "sb_v_double_arrow", "sb_h_double_arrow", "question_arrow" }; XcursorImage *img = XcursorLibraryLoadImage(cursor_file[i],cursor_theme,cursor_size); if (img) { cursors[i]=XcursorImageLoadCursor(x11_display,img); //print_line("found cursor: "+String(cursor_file[i])+" id "+itos(cursors[i])); } else { if (OS::is_stdout_verbose()) print_line("failed cursor: "+String(cursor_file[i])); } } } { Pixmap cursormask; XGCValues xgc; GC gc; XColor col; Cursor cursor; cursormask = XCreatePixmap(x11_display, RootWindow(x11_display,DefaultScreen(x11_display)), 1, 1, 1); xgc.function = GXclear; gc = XCreateGC(x11_display, cursormask, GCFunction, &xgc); XFillRectangle(x11_display, cursormask, gc, 0, 0, 1, 1); col.pixel = 0; col.red = 0; col.flags = 4; cursor = XCreatePixmapCursor(x11_display, cursormask, cursormask, &col, &col, 0, 0); XFreePixmap(x11_display, cursormask); XFreeGC(x11_display, gc); if (cursor == None) { ERR_PRINT("FAILED CREATING CURSOR"); } null_cursor=cursor; } set_cursor_shape(CURSOR_BUSY); visual_server->init(); // physics_server = memnew( PhysicsServerSW ); physics_server->init(); physics_2d_server = memnew( Physics2DServerSW ); physics_2d_server->init(); input = memnew( InputDefault ); probe_joystick(); _ensure_data_dir(); net_wm_icon = XInternAtom(x11_display, "_NET_WM_ICON", False); //printf("got map notify\n"); }
static void OpenIM(XawVendorShellExtPart *ve) { int i; char *p, *s, *ns, *end, *pbuf, buf[32]; XIM xim = NULL; XIMStyles *xim_styles; XIMStyle input_style = 0; Boolean found; if (ve->im.open_im == False) return; ve->im.xim = NULL; if (ve->im.input_method == NULL) { if ((p = XSetLocaleModifiers("@im=none")) != NULL && *p) xim = XOpenIM(XtDisplay(ve->parent), NULL, NULL, NULL); } else { /* no fragment can be longer than the whole string */ Cardinal len = strlen (ve->im.input_method) + 5; if (len < sizeof buf) pbuf = buf; else pbuf = XtMalloc (len); if (pbuf == NULL) return; for(ns=s=ve->im.input_method; ns && *s;) { /* skip any leading blanks */ while (*s && isspace(*s)) s++; if (!*s) break; if ((ns = end = strchr(s, ',')) == NULL) end = s + strlen(s); /* If there is a spurious comma end can be the same as s */ if (end > s) { /* strip any trailing blanks */ while (isspace(*(end - 1))) end--; strcpy (pbuf, "@im="); strncat (pbuf, s, end - s); pbuf[end - s + 4] = '\0'; } if ((p = XSetLocaleModifiers(pbuf)) != NULL && *p && (xim = XOpenIM(XtDisplay(ve->parent), NULL, NULL, NULL)) != NULL) break; s = ns + 1; } if (pbuf != buf) XtFree (pbuf); } if (xim == NULL) { if ((p = XSetLocaleModifiers("")) != NULL) { xim = XOpenIM(XtDisplay(ve->parent), NULL, NULL, NULL); } } if (xim == NULL) { XtAppWarning(XtWidgetToApplicationContext(ve->parent), "Input Method Open Failed"); return; } if (XGetIMValues(xim, XNQueryInputStyle, &xim_styles, NULL) || !xim_styles) { XtAppWarning(XtWidgetToApplicationContext(ve->parent), "input method doesn't support any style"); XCloseIM(xim); return; } found = False; for(ns = s = ve->im.preedit_type; s && !found;) { while (*s && isspace(*s)) s++; if (!*s) break; if ((ns = end = strchr(s, ',')) == NULL) end = s + strlen(s); else ns++; if (end > s) while (isspace(*(end - 1))) end--; if (!strncmp(s, "OverTheSpot", end - s)) { input_style = (XIMPreeditPosition | XIMStatusArea); } else if (!strncmp(s, "OffTheSpot", end - s)) { input_style = (XIMPreeditArea | XIMStatusArea); } else if (!strncmp(s, "Root", end - s)) { input_style = (XIMPreeditNothing | XIMStatusNothing); } for (i = 0; (unsigned short)i < xim_styles->count_styles; i++) if (input_style == xim_styles->supported_styles[i]) { ve->ic.input_style = input_style; SetErrCnxt(ve->parent, xim); ve->im.xim = xim; found = True; break; } s = ns; } XFree(xim_styles); if (!found) { XCloseIM(xim); XtAppWarning(XtWidgetToApplicationContext(ve->parent), "input method doesn't support my input style"); } }
se_text_xviewer* se_text_xviewer_create( se_env* env ) { se_text_xviewer* viewer = g_malloc0( sizeof(se_text_xviewer) ); if ( !viewer ) { se_error( "can not malloc a viewer obj" ); } viewer->env = env; int width = 800; int height = 600; viewer->view = XCreateSimpleWindow( env->display, env->root, 0, 0, width, height, 0, BlackPixel(env->display, env->screen), WhitePixel(env->display, env->screen) ); viewer->key_handler = se_text_xviewer_key_event; viewer->mouse_handler = se_text_xviewer_mouse_event; viewer->configure_change_handler = se_text_xviewer_configure_change_handler; viewer->show = se_text_xviewer_show; viewer->repaint = se_text_xviewer_repaint; viewer->redisplay = se_text_xviewer_redisplay; viewer->updateSize = se_text_xviewer_updateSize; se_text_xviewer_draw_create( viewer ); viewer->content = g_malloc0( SE_MAX_COLUMNS * SE_MAX_ROWS ); XIMStyles *im_supported_styles; XIMStyle app_supported_styles; XIMStyle style; XIMStyle best_style; XGetIMValues( env->xim, XNQueryInputStyle, &im_supported_styles, NULL ); app_supported_styles = XIMPreeditNone | XIMPreeditNothing | XIMPreeditArea | XIMStatusNone | XIMStatusNothing | XIMStatusArea; best_style = 0; se_debug( "styles count: %d", im_supported_styles->count_styles ); for(int i=0; i < im_supported_styles->count_styles; i++) { style = im_supported_styles->supported_styles[i]; dump_style( style ); if ((style & app_supported_styles) == style) /* if we can handle it */ best_style = ChooseBetterStyle(style, best_style); } /* if we couldn't support any of them, print an error and exit */ if (best_style == 0) { se_error("commonly supported interaction style."); exit(1); } XFree(im_supported_styles); dump_style( best_style ); viewer->xic = XCreateIC(env->xim, XNInputStyle, best_style, XNClientWindow, viewer->view, NULL); if ( viewer->xic == NULL ) { se_debug(" create xic failed" ); exit(1); } se_debug( "XLocaleOfIM: %s", XLocaleOfIM( env->xim ) ); return viewer; }
int main(int argc, char** args) { int width = 800; int height = 600; Display* display = XOpenDisplay(0); if(!display) { printf("No display available\n"); exit(1); } Window root = DefaultRootWindow(display); int defaultScreen = DefaultScreen(display); int screenBitDepth = 24; XVisualInfo visinfo = {}; if(!XMatchVisualInfo(display, defaultScreen, screenBitDepth, TrueColor, &visinfo)) { printf("No matching visual info\n"); exit(1); } XSetWindowAttributes windowAttr; windowAttr.bit_gravity = StaticGravity; windowAttr.background_pixel = 0; windowAttr.colormap = XCreateColormap(display, root, visinfo.visual, AllocNone); windowAttr.event_mask = StructureNotifyMask | KeyPressMask | KeyReleaseMask; unsigned long attributeMask = CWBitGravity | CWBackPixel | CWColormap | CWEventMask; Window window = XCreateWindow(display, root, 0, 0, width, height, 0, visinfo.depth, InputOutput, visinfo.visual, attributeMask, &windowAttr); if(!window) { printf("Window wasn't created properly\n"); exit(1); } XStoreName(display, window, "Hello, World!"); setSizeHint(display, window, 400, 300, 0, 0); XIM xInputMethod = XOpenIM(display, 0, 0, 0); if(!xInputMethod) { printf("Input Method could not be opened\n"); } XIMStyles* styles = 0; if(XGetIMValues(xInputMethod, XNQueryInputStyle, &styles, NULL) || !styles) { printf("Input Styles could not be retrieved\n"); } XIMStyle bestMatchStyle = 0; for(int i=0; i<styles->count_styles; i++) { XIMStyle thisStyle = styles->supported_styles[i]; if (thisStyle == (XIMPreeditNothing | XIMStatusNothing)) { bestMatchStyle = thisStyle; break; } } XFree(styles); if(!bestMatchStyle) { printf("No matching input style could be determined\n"); } XIC xInputContext = XCreateIC(xInputMethod, XNInputStyle, bestMatchStyle, XNClientWindow, window, XNFocusWindow, window, NULL); if(!xInputContext) { printf("Input Context could not be created\n"); } XMapWindow(display, window); //toggleMaximize(display, window); XFlush(display); int pixelBits = 32; int pixelBytes = pixelBits/8; int windowBufferSize = width*height*pixelBytes; char* mem = (char*)malloc(windowBufferSize); XImage* xWindowBuffer = XCreateImage(display, visinfo.visual, visinfo.depth, ZPixmap, 0, mem, width, height, pixelBits, 0); GC defaultGC = DefaultGC(display, defaultScreen); int sizeChange = 0; int windowOpen = 1; while(windowOpen) { XEvent ev = {}; while(XPending(display) > 0) { XNextEvent(display, &ev); switch(ev.type) { case DestroyNotify: { XDestroyWindowEvent* e = (XDestroyWindowEvent*) &ev; if(e->window == window) { windowOpen = 0; } } break; case ConfigureNotify: { XConfigureEvent* e = (XConfigureEvent*) &ev; width = e->width; height = e->height; sizeChange = 1; } break; case KeyPress: { XKeyPressedEvent* e = (XKeyPressedEvent*) &ev; int symbol = 0; Status status = 0; Xutf8LookupString(xInputContext, e, (char*)&symbol, 4, 0, &status); if(status == XBufferOverflow) { // Should not happen since there are no utf-8 characters larger than 24bits // But something to be aware of when used to directly write to a string buffer printf("Buffer overflow when trying to create keyboard symbol map\n"); } else if(status == XLookupChars) { printf("%s\n", (char*)&symbol); } if(e->keycode == XKeysymToKeycode(display, XK_Left)) printf("left arrow pressed\n"); if(e->keycode == XKeysymToKeycode(display, XK_Right)) printf("right arrow pressed\n"); if(e->keycode == XKeysymToKeycode(display, XK_Up)) printf("up arrow pressed\n"); if(e->keycode == XKeysymToKeycode(display, XK_Down)) printf("down arrow pressed\n"); } break; case KeyRelease: { XKeyPressedEvent* e = (XKeyPressedEvent*) &ev; if(e->keycode == XKeysymToKeycode(display, XK_Left)) printf("left arrow released\n"); if(e->keycode == XKeysymToKeycode(display, XK_Right)) printf("right arrow released\n"); if(e->keycode == XKeysymToKeycode(display, XK_Up)) printf("up arrow released\n"); if(e->keycode == XKeysymToKeycode(display, XK_Down)) printf("down arrow released\n"); } break; } } if(sizeChange) { sizeChange = 0; XDestroyImage(xWindowBuffer); // Free's the memory we malloced; windowBufferSize = width*height*pixelBytes; mem = (char*)malloc(windowBufferSize); xWindowBuffer = XCreateImage(display, visinfo.visual, visinfo.depth, ZPixmap, 0, mem, width, height, pixelBits, 0); } int pitch = width*pixelBytes; for(int y=0; y<height; y++) { char* row = mem+(y*pitch); for(int x=0; x<width; x++) { unsigned int* p = (unsigned int*) (row+(x*pixelBytes)); if(x%16 && y%16) { *p = 0xffffffff; } else { *p = 0; } } } XPutImage(display, window, defaultGC, xWindowBuffer, 0, 0, 0, 0, width, height); }; return 0; }
static void OpenIM( TkDisplay *dispPtr) /* Tk's structure for the display. */ { int i; XIMStyles *stylePtr; XIMStyle bestStyle = 0; if (XSetLocaleModifiers("") == NULL) { return; } dispPtr->inputMethod = XOpenIM(dispPtr->display, NULL, NULL, NULL); if (dispPtr->inputMethod == NULL) { return; } if ((XGetIMValues(dispPtr->inputMethod, XNQueryInputStyle, &stylePtr, NULL) != NULL) || (stylePtr == NULL)) { goto error; } /* * Select the best input style supported by both the IM and Tk. */ for (i = 0; i < stylePtr->count_styles; i++) { XIMStyle thisStyle = stylePtr->supported_styles[i]; if (thisStyle == (XIMPreeditPosition | XIMStatusNothing)) { bestStyle = thisStyle; break; } else if (thisStyle == (XIMPreeditNothing | XIMStatusNothing)) { bestStyle = thisStyle; } } XFree(stylePtr); if (bestStyle == 0) { goto error; } dispPtr->inputStyle = bestStyle; /* * Create an XFontSet for preedit area. */ if (dispPtr->inputStyle & XIMPreeditPosition) { char **missing_list; int missing_count; char *def_string; dispPtr->inputXfs = XCreateFontSet(dispPtr->display, "-*-*-*-R-Normal--14-130-75-75-*-*", &missing_list, &missing_count, &def_string); if (missing_count > 0) { XFreeStringList(missing_list); } } return; error: if (dispPtr->inputMethod) { XCloseIM(dispPtr->inputMethod); dispPtr->inputMethod = NULL; } }
/* x_keyboard_init * Initialise the X11 keyboard driver. */ static int x_keyboard_init(void) { #ifdef ALLEGRO_XWINDOWS_WITH_XIM XIMStyles *xim_styles; XIMStyle xim_style = 0; char *imvalret; int i; #endif if (xkeyboard_installed) return 0; main_pid = getpid(); memcpy(key_names, _keyboard_common_names, sizeof key_names); XLOCK (); #ifdef ALLEGRO_XWINDOWS_WITH_XIM /* Otherwise we are restricted to ISO-8859-1 characters. */ if (setlocale(LC_ALL, "") == NULL) { TRACE(PREFIX_W "Could not set default locale.\n"); } /* TODO: is this needed? modifiers = XSetLocaleModifiers("@im=none"); if (modifiers == NULL) { TRACE(PREFIX_W "XSetLocaleModifiers failed.\n"); } */ xim = XOpenIM(_xwin.display, NULL, NULL, NULL); if (xim == NULL) { TRACE(PREFIX_W "XOpenIM failed.\n"); } if (xim) { imvalret = XGetIMValues(xim, XNQueryInputStyle, &xim_styles, NULL); if (imvalret != NULL || xim_styles == NULL) { TRACE(PREFIX_W "Input method doesn't support any styles.\n"); } if (xim_styles) { xim_style = 0; for (i = 0; i < xim_styles->count_styles; i++) { if (xim_styles->supported_styles[i] == (XIMPreeditNothing | XIMStatusNothing)) { xim_style = xim_styles->supported_styles[i]; break; } } if (xim_style == 0) { TRACE (PREFIX_W "Input method doesn't support the style we support.\n"); } XFree(xim_styles); } } if (xim && xim_style) { xic = XCreateIC(xim, XNInputStyle, xim_style, XNClientWindow, _xwin.window, XNFocusWindow, _xwin.window, NULL); if (xic == NULL) { TRACE (PREFIX_W "XCreateIC failed.\n"); } } #endif _xwin_get_keyboard_mapping(); XUNLOCK(); xkeyboard_installed = 1; return 0; }