xim.c
来自「具有IDE功能的编辑器」· C语言 代码 · 共 609 行 · 第 1/2 页
C
609 行
#endif}static long destroy_input_context (CWidget * w){ w->input_context = 0; return 0;}void IMDestroyCallback (XIM xim, XPointer client_data, XPointer call_data){ XRegisterIMInstantiateCallback (CDisplay, NULL, NULL, NULL, IMInstantiateCallback, NULL); for_all_widgets ((void *) destroy_input_context, 0, 0); CIC = 0;}/* returns zero on error */XIMStyle get_input_style (void){ int found = 0; char tmp[1024] = "", *s = 0; char *end = 0, *next_s = 0; XIMStyle input_style = 0; XIMStyles *xim_styles = NULL; if (!CIM) { if (option_use_xim) xim_print_error ("Trying to get input_style, but Input Method is null."); return 0; } if (XGetIMValues (CIM, XNQueryInputStyle, &xim_styles, NULL) || !xim_styles) { xim_print_error ("input method doesn't support any style"); return 0; }#ifdef RXVT_SOURCE strncpy (tmp, (rs[Rs_preeditType] ? rs[Rs_preeditType] : "OverTheSpot,OffTheSpot,Root"), sizeof (tmp) - 1);#else strncpy (tmp, "OverTheSpot,OffTheSpot,Root", sizeof (tmp) - 1);#endif for (found = 0, s = tmp; *s && !found; s = next_s + 1) { unsigned short i; for (; *s && isspace (*s); s++); if (!*s) break; for (end = s; (*end && (*end != ',')); end++); for (next_s = end--; ((end >= s) && isspace (*end)); end--); *(end + 1) = '\0'; if (!strcmp (s, "OverTheSpot")) input_style = (XIMPreeditPosition | XIMStatusNothing); else if (!strcmp (s, "OffTheSpot")) input_style = (XIMPreeditArea | XIMStatusArea); else if (!strcmp (s, "Root")) input_style = (XIMPreeditNothing | XIMStatusNothing); for (i = 0; i < xim_styles->count_styles; i++) if (input_style == xim_styles->supported_styles[i]) { found = 1; break; } } XFree (xim_styles); if (found == 0) { xim_print_error ("input method doesn't support my preedit type"); return 0; } if ((input_style != (XIMPreeditNothing | XIMStatusNothing)) && (input_style != (XIMPreeditArea | XIMStatusArea)) && (input_style != (XIMPreeditPosition | XIMStatusNothing))) { xim_print_error ("This program does not support the preedit type"); return 0; } return input_style;}long create_input_context (CWidget * w, XIMStyle input_style){ XVaNestedList preedit_attr = 0; XVaNestedList status_attr = 0; XPoint spot; XRectangle rect, status_rect, needed_rect; XIMCallback ximcallback; unsigned long fg, bg; if (w->kind != C_WINDOW_WIDGET) return 0; if (w->mainid) return 0; if (w->input_context) return 0; if (!CIM) return 1; if (!input_style) return 1; ximcallback.callback = IMDestroyCallback; ximcallback.client_data = NULL; if (input_style & XIMPreeditPosition) { setSize (w, &rect); setPosition (0, w, &spot); setColor (w, &fg, &bg); preedit_attr = XVaCreateNestedList (0, XNArea, &rect, XNSpotLocation, &spot, XNForeground, fg, XNBackground, bg, XNFontSet, current_font->font_set, NULL); } else if (input_style & XIMPreeditArea) { setColor (w, &fg, &bg); /* * The necessary width of preedit area is unknown * until create input context. */ needed_rect.width = 0; setPreeditArea (w, &rect, &status_rect, &needed_rect); preedit_attr = XVaCreateNestedList (0, XNArea, &rect, XNForeground, fg, XNBackground, bg, XNFontSet, current_font->font_set, NULL); status_attr = XVaCreateNestedList (0, XNArea, &status_rect, XNForeground, fg, XNBackground, bg, XNFontSet, current_font->font_set, NULL); } w->input_context = XCreateIC (CIM, XNInputStyle, input_style, XNClientWindow, w->winid, XNFocusWindow, w->winid, XNDestroyCallback, &ximcallback, 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 (!w->input_context) { xim_print_error ("Failed to create input context for widget %s", w->ident); return 1; } return 0;}long set_status_position (CWidget * w){ XIMStyle input_style; XRectangle preedit_rect, status_rect, *needed_rect = 0; XVaNestedList preedit_attr, status_attr; if (!w->input_context) return 0; XGetICValues (w->input_context, XNInputStyle, &input_style, NULL); if (input_style & XIMPreeditArea) { /* Getting the necessary width of preedit area */ status_attr = XVaCreateNestedList (0, XNAreaNeeded, &needed_rect, NULL); XGetICValues (w->input_context, XNStatusAttributes, status_attr, NULL); XFree (status_attr); setPreeditArea (w, &preedit_rect, &status_rect, needed_rect); preedit_attr = XVaCreateNestedList (0, XNArea, &preedit_rect, NULL); status_attr = XVaCreateNestedList (0, XNArea, &status_rect, NULL); XSetICValues (w->input_context, XNPreeditAttributes, preedit_attr, XNStatusAttributes, status_attr, NULL); XFree (preedit_attr); XFree (status_attr); } return 0;}static void IMInstantiateCallback (Display * display, XPointer client_data, XPointer call_data){ char *p; XIMStyle input_style = 0; XIMCallback ximcallback; if (CIC) return; ximcallback.callback = IMDestroyCallback; ximcallback.client_data = NULL;#ifdef RXVT_SOURCE if (rs[Rs_inputMethod] && *rs[Rs_inputMethod]) { strncpy (tmp, option_imput_method, sizeof (tmp) - 1); for (s = tmp; *s; s = next_s + 1) { for (; *s && isspace (*s); s++); if (!*s) break; for (end = s; (*end && (*end != ',')); end++); for (next_s = end--; ((end >= s) && isspace (*end)); end--); *(end + 1) = '\0'; if (*s) { strcpy (buf, "@im="); strncat (buf, s, sizeof (buf) - 4 - 1); if ((p = XSetLocaleModifiers (buf)) != NULL && *p && (CIM = XOpenIM (CDisplay, NULL, NULL, NULL)) != NULL) break; } if (!*next_s) break; } }#endif /* try with XMODIFIERS env. var. */ if (CIM == NULL && (p = XSetLocaleModifiers ("")) != NULL && *p) CIM = XOpenIM (CDisplay, NULL, NULL, NULL); /* try with XMODIFIERS env. var. */ if (CIM == NULL && (p = XSetLocaleModifiers ("@im=control")) != NULL && *p) CIM = XOpenIM (CDisplay, NULL, NULL, NULL); /* try with no modifiers base */ if (CIM == NULL && (p = XSetLocaleModifiers ("@im=none")) != NULL && *p) CIM = XOpenIM (CDisplay, NULL, NULL, NULL); if (!CIM) return;/* got the Input Method, now set up all dialogs */ XSetIMValues (CIM, XNDestroyCallback, &ximcallback, NULL); if (!(input_style = get_input_style ())) { XCloseIM (CIM); CIM = 0; } CPushFont ("editor", 0); if (for_all_widgets ((void *) create_input_context, (void *) input_style, 0)) { input_style = 0; XCloseIM (CIM); CIM = 0; } CPopFont (); if (input_style & XIMPreeditArea) for_all_widgets ((void *) set_status_position, 0, 0);}#elseint option_use_xim = 0;KeySym key_sym_xlat (XEvent * ev, char *x_lat){ static int len = 0; static KeySym keysym = 0; static XComposeStatus compose = {NULL, 0}; static unsigned char kbuf[512] = ""; static Time time = 0; static int valid_keysym = 1; Status status_return = 0; if (x_lat) *x_lat = '\0'; if (ev->type != KeyPress && ev->type != KeyRelease) return 0;/* we mustn't call this twice with the same event */ if (time == ev->xkey.time) goto no_repeat_call; time = ev->xkey.time; keysym = 0; len = 0; if (ev->type == KeyRelease) { len = XLookupString (&ev->xkey, (char *) kbuf, sizeof (kbuf), &keysym, 0); if (!len && (keysym >= 0x0100) && (keysym < 0x0800)) { len = 1; kbuf[0] = (keysym & 0xFF); } } else { keysym = 0; len = XLookupString (&ev->xkey, (char *) kbuf, sizeof (kbuf), &keysym, &compose); if (!len && (keysym >= 0x0100) && (keysym < 0x0800)) { len = 1; kbuf[0] = (keysym & 0xFF); } } no_repeat_call: if (x_lat) { if (len > 0) { if (len > 7) len = 7; memcpy (x_lat, kbuf, len); x_lat[len] = '\0'; } } return valid_keysym ? keysym : 0;}#endif
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?