Business
Jobs
  • About Us
  • Solutions
    • Job Postings
      Post your job and receive qualified candidates in 48h.
    • Candidate Assessments
      500+ technical and psychological tests, plus anti-fraud.
    • Headhunting
      Tailor-made executive search from start to finish.
    • Payroll + EOR
      Payroll dispersal and EOR across 15+ LATAM countries.
  • Pricing
  • Jobs

0

200
Views
¿Cómo capturar el evento de cambio de diseño de teclado y obtener un nuevo diseño de teclado actual en Linux?

Ahora, estoy trabajando en el desarrollo de aplicaciones en Linux y quiero capturar el evento de cambio de diseño del teclado (cambiar el diseño del teclado a través de UI/widget/shell/programación, etc.) y obtener/configurar la nueva información de diseño del teclado para continuar con el proceso. Creo que esta no es una pregunta nueva, pero busco en stackoverflow una y otra vez, pero no hay respuesta. ¡Espero poder obtener la respuesta correcta aquí!

La solución principal que quiero aprender se describe aquí. En Windows, el mensaje de Windows WM_INPUTLANGCHANGE podría capturarse en WinProc, que contiene información sobre el diseño del teclado. Y podríamos usar la API GetKeyboardLayout() para obtener información actual sobre el diseño del teclado. Finalmente, si quiero usar mi diseño de teclado preferido, podría usar ActivateKeyboardLayout() para activar el diseño de teclado.

En resumen, espero encontrar los mensajes de notificación y cómo capturar el mensaje en código (es mejor que me muestre un ejemplo) en Linux, la API Obtener diseño de teclado y la API Establecer diseño de teclado en Linux. El lenguaje de desarrollo es C/C++, también.

Gracias por adelantado.

over 4 years ago · Santiago Trujillo
3 answers
Answer question

0

La otra respuesta no me funciona. Se compila y ejecuta, pero el evento MappingNotify no ocurre cuando cambio los diseños. Aquí hay una modificación que funciona para mí.

 #include <stdio.h> #include <X11/Xutil.h> #include <X11/XKBlib.h> int main(int argc, char **argv) { XEvent e; Display *d; if (!(d = XOpenDisplay(NULL))) { fprintf(stderr, "cannot open display\n"); return 1; } XKeysymToKeycode(d, XK_F1); int xkbEventType; XkbQueryExtension(d, 0, &xkbEventType, 0, 0, 0); XkbSelectEvents(d, XkbUseCoreKbd, XkbAllEventsMask, XkbAllEventsMask); XSync(d, False); while (1) { XNextEvent(d, &e); if (e.type == xkbEventType) { XkbEvent* xkbEvent = (XkbEvent*) &e; if (xkbEvent->any.xkb_type == XkbStateNotify) { int lang = xkbEvent->state.group; if (lang == 1) { fprintf(stdout, "1\n"); fflush(stdout); } else { fprintf(stdout, "0\n"); fflush(stdout); } } } } return(0); }

Compilar con:

 gcc -Wall -O2 xmappingnotify.c -o xmappingnotify -lX11

Yo lo uso así:

 xmappingnotify | xargs -I {} my-custom-command {} &

entonces my-custom-command [number_of_the_layout] se ejecuta cuando cambio los diseños. Tengo 2 diseños, xmappingnotify genera "1" para un diseño y "0" para el otro.

over 4 years ago · Santiago Trujillo Report

0

Respuesta para X11:

Detectar cambios a través del evento MappingNotify

Cambiar o consultar el diseño a través de setxkbmap

Aquí hay un ejemplo básico de xlib para detectar eventos de MappingNotify:

 #include <stdio.h> #include <X11/Xlib.h> #include <X11/Xutil.h> #include <X11/keysym.h> int main(int argc, char **argv) { XEvent event; Display *dpy; if (!(dpy = XOpenDisplay(NULL))) { fprintf(stderr, "cannot open display\n"); return 1; } /** * Note: We might never get a MappingNotify event if the * modifier and keymap information was never cached in Xlib. * The next line makes sure that this happens initially. */ XKeysymToKeycode(dpy, XK_F1); while (1) { XNextEvent(dpy, &event); if (event.type == MappingNotify) { XMappingEvent *e = (XMappingEvent *) &event; if (e->request == MappingKeyboard) { fprintf(stderr, "The keyboard mapping was changed!\n"); } XRefreshKeyboardMapping(e); } } return(0); }

Comando construido:

 gcc -Wall -O2 xmappingnotify.c -o xmappingnotify -lX11
over 4 years ago · Santiago Trujillo Report

0

Utilicé la respuesta de @gvlasov como una notificación de diseño de teclado en la barra dwm de Suckless con un parche de diseño de teclado por ventana. Funciona correctamente con respecto al resultado, pero produce demasiados eventos (ctrl, mod, teclas de mayúsculas, presionar y soltar y el movimiento de la rueda de desplazamiento del mouse genera el diseño; el correcto, pero esto no es necesario, solo cuando se cambia el diseño debe devolver el diseño ). Probablemente sea lo mencionado por el comentario de @matanster. Así que hice un cambio que detuvo la salida del movimiento de la rueda del mouse, aunque todavía se produce la salida de las teclas ctrl, mod, shift y pulsaciones. No es ideal, es un poco mejor:

Cambió la línea:

 XkbSelectEvents(d, XkbUseCoreKbd, XkbAllEventsMask, XkbAllEventsMask);

con este:

 XkbSelectEventDetails(d, XkbUseCoreKbd, XkbMapNotifyMask, XkbAllEventsMask, XkbAllEventsMask);

Si alguien tiene alguna idea de cómo obtener resultados / resultados solo en el cambio de diseño del teclado y no en las teclas ctrl, mod, shift, presione y suelte, es bienvenido.


Actualizar, usando esto:

 XkbSelectEventDetails(d, XkbUseCoreKbd, XkbStateNotify, XkbAllStateComponentsMask, XkbGroupStateMask);

Obtuve el resultado esperado. El único evento notificado es el cambio de distribución del teclado, ni las pulsaciones ni las liberaciones de teclas. El único inconveniente en comparación con mi línea anterior es que los cambios de mayúsculas no se notifican, lo que era posible antes.

over 4 years ago · Santiago Trujillo Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Sales
Legal
Terms and conditions Privacy policy
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Show me some job opportunities
There's an error!