static void handle(Display * dpy, Window win, XIC xic, XEvent * e) { switch(e->type) { case ClientMessage: cvInject(CVE_CLOSE, 0, 0); break; case ConfigureNotify: cvInject(CVE_RESIZE, e->xconfigure.width, e->xconfigure.height); break; case ButtonPress: cvInject(CVE_DOWN, mapButton(e->xbutton.button), 0); break; case ButtonRelease: cvInject(CVE_UP, mapButton(e->xbutton.button), 0); break; case MotionNotify: cvInject(CVE_MOTION, e->xmotion.x, e->xmotion.y); break; case KeyPress: { wchar_t buf[64]; KeySym ks; Status st; int i; int n; cvInject(CVE_DOWN, mapkeycode(e->xkey.keycode), 0); n = XwcLookupString(xic, &e->xkey, buf, sizeof(buf) / sizeof(wchar_t), &ks, &st); if (st == XLookupChars || st == XLookupBoth) for (i = 0; i < n; i++) cvInject(CVE_UNICODE, buf[i], 0); } break; case KeyRelease: if (!isAutoRepeat(dpy, win, e)) cvInject(CVE_UP, mapkeycode(e->xkey.keycode), 0); default: break; } }
int _XawImWcLookupString(Widget inwidg, XKeyPressedEvent *event, wchar_t* buffer_return, int bytes_buffer, KeySym *keysym_return) { XawVendorShellExtPart* ve; VendorShellWidget vw; XawIcTableList p; int i, ret; char tmp_buf[64], *tmp_p; wchar_t* buf_p; if ((vw = SearchVendorShell(inwidg)) && (ve = GetExtPart(vw)) && ve->im.xim && (p = GetIcTableShared(inwidg, ve)) && p->xic) { return(XwcLookupString(p->xic, event, buffer_return, bytes_buffer/sizeof(wchar_t), keysym_return, NULL)); } ret = XLookupString( event, tmp_buf, sizeof(tmp_buf), keysym_return, NULL ); for ( i = 0, tmp_p = tmp_buf, buf_p = buffer_return; i < ret; i++ ) { *buf_p++ = _Xaw_atowc(*tmp_p++); } return( ret ); }
void gui_main_loop (void) { XEvent event; struct gui_instance *gi; while (0 == XNextEvent (GUI_display, &event)) { if (0 == (gi = find_instance (event.xany.window))) continue; if (XFilterEvent (&event, gi->window)) continue; if (gi->definition.x11_event) gi->definition.x11_event (gi, &event); switch (event.type) { case KeyPress: gi->last_event = event.xkey.time; if (gi->definition.key_pressed) { wchar_t text[32]; Status status; KeySym key_sym; int len; len = XwcLookupString (gi->xic, &event.xkey, text, sizeof (text) / sizeof (text[0]) - 1, &key_sym, &status); text[len] = 0; if (status == XLookupNone) return; gi->definition.key_pressed (gi, (status == XLookupKeySym || status == XLookupBoth) ? key_sym : 0, (status == XLookupChars || status == XLookupBoth) ? text : NULL, event.xkey.state); } break; case KeyRelease: gi->last_event = event.xkey.time; if (gi->definition.key_released) { KeySym key_sym; key_sym = XLookupKeysym (&event.xkey, 0); gi->definition.key_released (gi, key_sym); } break; case MotionNotify: gi->last_event = event.xmotion.time; if (gi->definition.mouse_moved) gi->definition.mouse_moved (gi, event.xmotion.x, event.xmotion.y); break; case ButtonPress: gi->last_event = event.xbutton.time; if (gi->definition.button_pressed) gi->definition.button_pressed (gi, event.xbutton.button - 1, event.xbutton.state); break; case ButtonRelease: gi->last_event = event.xbutton.time; if (gi->definition.button_released) gi->definition.button_released (gi, event.xbutton.button - 1, event.xbutton.state); break; case ConfigureNotify: while (XCheckTypedWindowEvent (GUI_display, gi->window, ConfigureNotify, &event)) { /* Do nothing */ } if (gi->width == event.xconfigure.width && gi->height == event.xconfigure.height) break; gi->width = event.xconfigure.width; gi->height = event.xconfigure.height; configure_window (gi); XClearArea (GUI_display, gi->window, 0, 0, 0, 0, True); break; case NoExpose: break; case Expose: { int minx = event.xexpose.x; int miny = event.xexpose.y; int maxx = minx + event.xexpose.width; int maxy = miny + event.xexpose.height; while (XCheckTypedWindowEvent (GUI_display, gi->window, Expose, &event)) { if (event.xexpose.x < minx) minx = event.xexpose.x; if (event.xexpose.y < miny) miny = event.xexpose.y; if (event.xexpose.x + event.xexpose.width > maxx) maxx = event.xexpose.x + event.xexpose.width; if (event.xexpose.y + event.xexpose.height > maxx) maxx = event.xexpose.y + event.xexpose.height; } gi->repaint_waiting = 0; if (!gi->back_buffer) configure_window (gi); gi->definition.paint (gi, minx, miny, maxx - minx, maxy - miny); XRenderComposite (GUI_display, PictOpSrc, gi->back_buffer, None, gi->front_buffer, minx, miny, 0, 0, minx, miny, maxx - minx, maxy - miny); } break; case ClientMessage: if (event.xclient.data.l[0] == xa_wm_delete_window) gi->definition.destroy (gi); break; case SelectionRequest: { XSelectionRequestEvent* request; XSelectionEvent response; enum gui_clipboard clipboard; int ret; request = &event.xselectionrequest; if (request->selection == XA_PRIMARY) clipboard = GUI_PRIMARY_SELECTION; else if (request->selection == XA_SECONDARY) clipboard = GUI_SECONDARY_SELECTION; else if (request->selection == xa_clipboard) clipboard = GUI_CLIPBOARD; else break; if (!gi->clipboards[clipboard].length) break; if (request->target != XA_STRING && request->target != xa_utf8_string) break; if (request->property == None) request->property = request->target; response.type = SelectionNotify; response.send_event = True; response.display = GUI_display; response.requestor = request->requestor; response.selection = request->selection; response.target = request->target; response.property = None; response.time = request->time; ret = XChangeProperty (GUI_display, request->requestor, request->property, request->target, 8, PropModeReplace, gi->clipboards[clipboard].data, gi->clipboards[clipboard].length); if (ret != BadAlloc && ret != BadAtom && ret != BadValue && ret != BadWindow) response.property = request->property; XSendEvent (request->display, request->requestor, False, NoEventMask, (XEvent*) &response); } break; case SelectionNotify: { unsigned char* prop; unsigned long nitems, bytes_after; Atom type; int format, result; result = XGetWindowProperty (GUI_display, gi->window, xa_prop_paste, 0, 0, False, AnyPropertyType, &type, &format, &nitems, &bytes_after, &prop); if (result != Success) break; XFree (prop); result = XGetWindowProperty (GUI_display, gi->window, xa_prop_paste, 0, bytes_after, False, AnyPropertyType, &type, &format, &nitems, &bytes_after, &prop); if (result != Success) break; if (gi->definition.paste && type == xa_utf8_string && format == 8) { gi->definition.paste (gi, (const char*) prop, nitems); } XFree (prop); } break; } } }