[英]How to send key event to application using XCB?
How can I send a key press or key release event to a window (the currently active window) from another program using XCB
?如何使用XCB
从另一个程序向窗口(当前活动窗口)发送按键或按键释放事件?
I found some tutorials using XLib
, however I would like to use XCB
.我找到了一些使用XLib
的教程,但是我想使用XCB
。
I guess I will have to call xcb_send_event
, however I have no idea what to pass it as parameters.我想我将不得不调用xcb_send_event
,但是我不知道将它作为参数传递什么。
You should be able to use the XTEST extension to fake input to the active window, using the xcb_test_fake_input() function.您应该能够使用 XTEST 扩展来伪造活动窗口的输入,使用 xcb_test_fake_input() 函数。
#include <xcb/xtest.h>
...
xcb_test_fake_input(c, XCB_KEY_PRESS, keycode, XCB_CURRENT_TIME, XCB_NONE, 0, 0, 0);
xcb_test_fake_input(c, XCB_KEY_RELEASE, keycode, XCB_CURRENT_TIME, XCB_NONE, 0, 0, 0);
See the xte program in xcb/demos for a working example.有关工作示例,请参见xcb/demos 中的 xte 程序。
Possible alternative: xcb_send_event()
可能的替代方案: xcb_send_event()
See: X11R7.7 API Documentation请参阅: X11R7.7 API 文档
Example from there:那里的例子:
/*
* Tell the given window that it was configured to a size of 800x600 pixels.
*/
void my_example(xcb_connection_t* conn, xcb_window_t window) {
//
// Every X11 event is 32 bytes long. Therefore, XCB will copy 32 bytes.
// In order to properly initialize these bytes, we allocate 32 bytes even
// though we only need less for an xcb_configure_notify_event_t
//
xcb_configure_notify_event_t* event = calloc(32, 1);
event->event = window;
event->window = window;
event->response_type = XCB_CONFIGURE_NOTIFY;
event->x = 0;
event->y = 0;
event->width = 800;
event->height = 600;
event->border_width = 0;
event->above_sibling = XCB_NONE;
event->override_redirect = false;
xcb_send_event(conn, false, window, XCB_EVENT_MASK_STRUCTURE_NOTIFY, (char*) event);
xcb_flush(conn);
free(event);
}
With vanilla XCB
(ie. without extensions like XTEST
), using xcb_send_event()
:使用 vanilla XCB
(即没有像XTEST
这样的扩展),使用xcb_send_event()
:
xcb_screen_t* xcb_get_screen(xcb_connection_t* connection, int screen_idx){ // Return a screen from its number!
const xcb_setup_t* setup = xcb_get_setup(connection);
for(xcb_screen_iterator_t screen_it = xcb_setup_roots_iterator(setup); screen_it.rem; --screen_idx, xcb_screen_next(&screen_it))
if(screen_idx==0) return screen_it.data;
return NULL;
}
fdefi void xcb_send_key_press(xcb_connection_t* connection, xcb_window_t root, xcb_window_t window, xcb_keycode_t keycode){ // http://t-sato.in.coocan.jp/xvkbd/events.html
xcb_key_press_event_t ev; memset(&ev,0x00,sizeof(xcb_key_press_event_t));
ev.response_type = XCB_KEY_PRESS;
ev.detail = keycode;
ev.time = XCB_CURRENT_TIME;
ev.root = root;
ev.event = window;
ev.state = 0x0000; // xcb_mod_mask_t: XCB_MOD_MASK_SHIFT XCB_MOD_MASK_LOCK XCB_MOD_MASK_CONTROL XCB_MOD_MASK_1 XCB_MOD_MASK_2 XCB_MOD_MASK_3 XCB_MOD_MASK_4 XCB_MOD_MASK_5 XCB_MOD_MASK_ANY
ev.same_screen = 1;
xcb_send_event(connection, 0/*1*/, window/*XCB_SEND_EVENT_DEST_ITEM_FOCUS*/, XCB_EVENT_MASK_NO_EVENT/*XCB_EVENT_MASK_KEY_PRESS XCB_EVENT_MASK_NO_EVENT*/, (const char*)&ev); // @XCB_SEND_EVENT_DEST_ITEM_FOCUS needs to have @propate set to 1? // every X11 event is 32 bytes
}
int main(){ // תִּשְׂמָ֑ח
int xcb_screen_idx;
xcb_connection_t* xcb_connection = xcb_connect(NULL,&xcb_screen_idx);
xcb_screen_t* xcb_screen = xcb_get_screen(xcb_connection,xcb_screen_idx); // xcb_meta(xcb_connection,xcb_screen_idx);
xcb_get_input_focus_cookie_t get_input_focus_cookie = xcb_get_input_focus_unchecked(xcb_connection);
xcb_get_input_focus_reply_t* get_input_focus_reply = xcb_get_input_focus_reply(xcb_connection, get_input_focus_cookie, NULL);
xcb_send_key_press(xcb_connection, xcb_screen->root, get_input_focus_reply->focus, 0x26);
free(get_input_focus_reply);
xcb_disconnect(xcb_connection);
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.