Implement keyboard input via font backend abstraction

- WMEKey: add keysym, utf8[8], utf8_len fields
- handle_keyboard_key: translate keycode via xkb_state, fill keysym/utf8,
  route event to focused WINGs view
- W_FontBackend: add lookup_string slot
- wfont_x11.c: implement via W_LookupString (wraps XLookupString)
- wfont_wl.c: implement by reading pre-translated keysym/utf8 from event
- wtextfield.c: use font backend lookup_string (no X11 guards)
This commit is contained in:
Levi Neely 2026-05-13 21:43:24 +02:00
parent 94b45b342e
commit 76080cd2eb
5 changed files with 49 additions and 8 deletions

View File

@ -75,6 +75,9 @@ typedef struct {
unsigned long time;
int x, y;
int x_root, y_root;
unsigned long keysym; /* translated keysym (XKB) */
char utf8[8]; /* UTF-8 text for this key */
int utf8_len; /* length of utf8 text */
} WMEKey;
typedef struct {

View File

@ -203,6 +203,22 @@ wl_draw_image_string(void *sctx, void *handle, WMDrawable d,
tr, tg, tb, ta, tpix, text, len);
}
static int
wl_lookup_string(void *sctx, W_View *view, WMEvent *event,
char *buffer, int buflen, unsigned long *keysym_out)
{
(void)sctx; (void)view;
*keysym_out = event->u.key.keysym;
int len = event->u.key.utf8_len;
if (len > 0 && len < buflen) {
memcpy(buffer, event->u.key.utf8, len);
buffer[len] = '\0';
} else {
len = 0;
}
return len;
}
const W_FontBackend W_FontBackendWL = {
.screen_init = wl_screen_init,
.screen_fini = wl_screen_fini,
@ -211,4 +227,5 @@ const W_FontBackend W_FontBackendWL = {
.text_width = wl_text_width,
.draw_string = wl_draw_string,
.draw_image_string = wl_draw_image_string,
.lookup_string = wl_lookup_string,
};

View File

@ -190,6 +190,16 @@ x11_draw_image_string(void *sctx, void *handle, WMDrawable d,
#endif
}
static int
x11_lookup_string(void *sctx, W_View *view, WMEvent *event,
char *buffer, int buflen, unsigned long *keysym_out)
{
(void)sctx;
if (!event->_x11_raw) { *keysym_out = 0; return 0; }
return W_LookupString(view, &((XEvent *)event->_x11_raw)->xkey,
buffer, buflen, (KeySym *)keysym_out, NULL);
}
const W_FontBackend W_FontBackendX11 = {
.screen_init = x11_screen_init,
.screen_fini = x11_screen_fini,
@ -198,4 +208,5 @@ const W_FontBackend W_FontBackendX11 = {
.text_width = x11_text_width,
.draw_string = x11_draw_string,
.draw_image_string = x11_draw_image_string,
.lookup_string = x11_lookup_string,
};

View File

@ -956,13 +956,9 @@ static void handleTextFieldKeyPress(TextField * tPtr, WMEvent * event)
controled = (event->u.key.state & ControlMask ? True : False);
modified = shifted || controled;
count = event->_x11_raw
? W_LookupString(tPtr->view, &((XEvent *)event->_x11_raw)->xkey, buffer, 63, &ksym, NULL)
: 0;
if (!event->_x11_raw) {
/* Wayland mode: no key translation yet */
return;
}
count = tPtr->view->screen->fontBackend->lookup_string(
tPtr->view->screen->fontBackendCtx, tPtr->view, event,
buffer, 63, &ksym);
buffer[count] = '\0';
switch (ksym) {

View File

@ -1628,7 +1628,13 @@ handle_keyboard_key(struct wl_listener *listener, void *data)
memset(&ev, 0, sizeof(ev));
ev.type = (event->state == WL_KEYBOARD_KEY_STATE_PRESSED)
? WME_KEY_PRESS : WME_KEY_RELEASE;
ev.window = WNATIVE_NONE;
/* Route to focused view */
W_FocusInfo *finfo = wmscr->focusInfo;
W_View *target = (finfo && finfo->focused) ? finfo->focused
: (finfo && finfo->toplevel) ? finfo->toplevel : NULL;
ev.window = target ? (WNativeWindow)target->window : WNATIVE_NONE;
ev.u.key.keycode = keycode;
ev.u.key.state = modifiers;
ev.u.key.time = event->time_msec;
@ -1636,6 +1642,14 @@ handle_keyboard_key(struct wl_listener *listener, void *data)
ev.u.key.y = wl_state.pointer_y;
ev.u.key.x_root = wl_state.pointer_x;
ev.u.key.y_root = wl_state.pointer_y;
/* Translate keycode → keysym + UTF-8 via xkb */
ev.u.key.keysym = xkb_state_key_get_one_sym(kb->xkb_state, keycode);
ev.u.key.utf8_len = xkb_state_key_get_utf8(kb->xkb_state, keycode,
ev.u.key.utf8, sizeof(ev.u.key.utf8));
if (ev.u.key.utf8_len >= (int)sizeof(ev.u.key.utf8))
ev.u.key.utf8_len = 0; /* overflow — discard */
W_WL_EnqueueEvent(wmscr, &ev, NULL);
}