同时捕获输入并发送按键事件

同时捕获输入并发送按键事件

我正在寻找创建一个简单的输入法程序。目前,我可以使用被动按键抓取从任何窗口捕获输入(感谢用户dirkt!)。

另外,我还可以使用 发送按键XTestFakeKeyEvent()

问题是我无法将这两部分放在一起。当发出假按键事件时,它被我的程序接收,而不是具有焦点的预期应用程序。即使我的程序没有被动地获取假事件发出的键码,也会发生这种情况。我怀疑这是因为我从根窗口获取事件,但如果我不这样做,我认为我无法捕获来自其他窗口的输入。

#include <X11/Xlib.h>
#include <X11/keysym.h>
#include <X11/extensions/XTest.h>
#include <stdio.h>

int main()
{
    Display *display;
    Window   rootwindow;
    XEvent   event;

    display = XOpenDisplay(NULL);
    rootwindow = DefaultRootWindow(display);

    XSelectInput(display, rootwindow, KeyPressMask);    

    unsigned int modifiers[] = {
        0, 
        ShiftMask,
        LockMask, //capslock
        Mod2Mask, //numlock
        ShiftMask | LockMask,
        ShiftMask | Mod2Mask,
        LockMask | Mod2Mask,
        LockMask | Mod2Mask | ShiftMask,
    };

    int keys [] = {
        XKeysymToKeycode(display, XK_A),
        XKeysymToKeycode(display, XK_B),
        ...
        XKeysymToKeycode(display, XK_Z)
    };

    int l;
    int m;
    for(l = 0; l < sizeof(keys)/sizeof(int); l++){
        for(m = 0; m < sizeof(modifiers)/sizeof(unsigned int); m++){
            XGrabKey(display, keys[l], modifiers[m], rootwindow, False, GrabModeAsync, GrabModeAsync);
        }
    }

    int repeat = 0;

    while (1) {

        XNextEvent(display, &event);

        if (event.type == KeyPress && event.xkey.send_event == 0) {
            printf("KeyPress: keycode %u state %u send-event %d\n", event.xkey.keycode, event.xkey.state, event.xkey.send_event);
            fflush(stdout);

            if(repeat == 0){ //to avoid infinite loops
                repeat = 1;

                XTestFakeKeyEvent(display, XKeysymToKeycode(display, XK_7), 1, CurrentTime);
                XTestFakeKeyEvent(display, XKeysymToKeycode(display, XK_7), 0, CurrentTime);
            }

        }
    }

    XCloseDisplay(display);
    return 0;
}

相关内容