监听键盘事件而不在X11中消耗它们-键盘挂接

我试图编写一个程序,只要在Ubuntu(KDE)中按下该键,它就会挂接键盘消息以发音每个键的名称。不会干扰程序中键盘的正常操作(只是宣布键名)。

这是我的程序:

#include <X11/Xlib.h>

#include <stdio.h>

#include <stdlib.h>

#include <string.h>

#include <iostream>

using namespace std;

void SendPressKeyEvent(Display *display, XKeyEvent xkey)

{

Window current_focus_window;

int current_focus_revert;

XGetInputFocus(display, &current_focus_window, &current_focus_revert);

xkey.type = KeyPress;

xkey.display = display;

xkey.window = current_focus_window;

xkey.root = DefaultRootWindow(display);

xkey.subwindow = None;

xkey.time = 1000 * time(0);

xkey.x = 0;

xkey.y = 0;

xkey.x_root = 0;

xkey.y_root = 0;

xkey.same_screen = True;

XSendEvent(display, InputFocus, True, KeyPressMask, (XEvent *)(&xkey));

}

void SendReleaseKeyEvent(Display *display, XKeyEvent xkey)

{

Window current_focus_window;

int current_focus_revert;

XGetInputFocus(display, &current_focus_window, &current_focus_revert);

xkey.type = KeyRelease;

xkey.display = display;

xkey.window = current_focus_window;

xkey.root = DefaultRootWindow(display);

xkey.subwindow = None;

xkey.time = 1000 * time(0);

xkey.x = 0;

xkey.y = 0;

xkey.x_root = 0;

xkey.y_root = 0;

xkey.same_screen = True;

XSendEvent(display, InputFocus, True, KeyReleaseMask, (XEvent *)(&xkey));

}

void *TaskCode(void* arg)

{

switch(*(int*)arg)

{

case 38:

system("espeak -v en " "\"a\"");

}

return 0;

}

int main()

{

Display *display = XOpenDisplay(0);

if(display == 0)

exit(1);

XGrabKeyboard(display, DefaultRootWindow(display), True, GrabModeAsync, GrabModeAsync, CurrentTime);

XEvent event;

while(true)

{

XNextEvent(display, &event);

if(event.type == Expose)

{

}

if(event.type == KeyPress)

{

SendPressKeyEvent(display,event.xkey);

if(event.xkey.keycode == 38)

{

pthread_t thread;

int thread_arg = event.xkey.keycode;

pthread_create(&thread,0, TaskCode, (void*) &thread_arg);

}

}

if(event.type == KeyRelease)

SendReleaseKeyEvent(display,event.xkey);

}

XCloseDisplay(display);

}

该程序仅适用于a可以扩展到其他键的键。

但是,当该程序运行时,某些程序(例如Chromium)不会在其编辑框中显示闪烁信号(光标)。同样,所有的KDE热键也被禁用。

如何解决?

回答:

这是我的例子

#include <X11/X.h>

#include <X11/Xlib.h>

#include <X11/Xutil.h>

#include <stdio.h>

#include <ctype.h>

int main ()

{

Display* d = XOpenDisplay(NULL);

Window root = DefaultRootWindow(d);

Window curFocus;

char buf[17];

KeySym ks;

XComposeStatus comp;

int len;

int revert;

XGetInputFocus (d, &curFocus, &revert);

XSelectInput(d, curFocus, KeyPressMask|KeyReleaseMask|FocusChangeMask);

while (1)

{

XEvent ev;

XNextEvent(d, &ev);

switch (ev.type)

{

case FocusOut:

printf ("Focus changed!\n");

printf ("Old focus is %d\n", (int)curFocus);

if (curFocus != root)

XSelectInput(d, curFocus, 0);

XGetInputFocus (d, &curFocus, &revert);

printf ("New focus is %d\n", (int)curFocus);

if (curFocus == PointerRoot)

curFocus = root;

XSelectInput(d, curFocus, KeyPressMask|KeyReleaseMask|FocusChangeMask);

break;

case KeyPress:

printf ("Got key!\n");

len = XLookupString(&ev.xkey, buf, 16, &ks, &comp);

if (len > 0 && isprint(buf[0]))

{

buf[len]=0;

printf("String is: %s\n", buf);

}

else

{

printf ("Key is: %d\n", (int)ks);

}

}

}

}

它不可靠,但在大多数情况下都有效。(它显示的是我正在此框中输入的键)。您可能会调查为什么有时会失败;)原则上它也不能显示热键。热键是获取的密钥,只有一个客户端可以获取获取的密钥。除了加载为此目的而设计的特殊X11扩展(例如XEvIE)以外,这里绝对不能做任何事情。

以上是 监听键盘事件而不在X11中消耗它们-键盘挂接 的全部内容, 来源链接: utcz.com/qa/408805.html

回到顶部