Как регистрировать события с помощью libxcb-xinput

Я пытаюсь прослушивать события касания (TOUCH_BEGIN, TOUCH_UPDATE, TOUCH_END и TOUCH_OWNERSHIP) в корневом окне.
События касания не интегрированы напрямую в XCB, поэтому мне приходится использовать расширение ввода (libxcb-xinput).

Мне уже удалось настроить прослушиватель событий для событий, поступающих от расширения ввода, но я не могу понять, как регистрировать, какие события я хочу прослушивать.

Я попытался использовать xcb_input_xi_select_events(), однако эта функция принимает параметр типа xcb_input_event_mask_t, тогда как перечисление, содержащее маски событий, имеет тип xcb_input_xi_event_mask_t, и нет очевидного способа их приведения.

По этой причине я думаю, что xcb_input_xi_select_events() - неправильная функция, но я понятия не имею, какую функцию использовать вместо нее.

Мой нерабочий код в настоящее время выглядит так:

xcb_input_event_mask_t mask[] = {
    XCB_INPUT_XI_EVENT_MASK_TOUCH_BEGIN
    | XCB_INPUT_XI_EVENT_MASK_TOUCH_END
    | XCB_INPUT_XI_EVENT_MASK_TOUCH_UPDATE
    | XCB_INPUT_XI_EVENT_MASK_TOUCH_OWNERSHIP
};
xcb_input_xi_select_events(dpy, root, 4, mask);

Ядро выдает предупреждение «большое целое число, неявно усеченное до беззнакового типа» во время компиляции и просто ошибку «Неудачный запрос: (null), (null): 0x000000D5» во время выполнения.

(Я новичок в C и особенно в XCB, поэтому простите за очевидные ошибки)


person freundTech    schedule 22.09.2016    source источник


Ответы (2)


Вам нужно использовать xcb_input_event_mask_t и xcb_input_xi_event_mask_t вместе следующим образом:

struct {
    xcb_input_event_mask_t head;      // describes the subsequent xcb_input_xi_event_mask_t (or an array thereof)
    xcb_input_xi_event_mask_t mask;
} mask;

mask.head.deviceid = XCB_INPUT_DEVICE_ALL;
mask.head.mask_len = sizeof(mask.mask) / sizeof(uint32_t);

mask.mask = XCB_INPUT_XI_EVENT_MASK_TOUCH_BEGIN
| XCB_INPUT_XI_EVENT_MASK_TOUCH_END
| XCB_INPUT_XI_EVENT_MASK_TOUCH_UPDATE
| XCB_INPUT_XI_EVENT_MASK_TOUCH_OWNERSHIP;

xcb_input_xi_select_events(dpy, root, 1, &mask.head);

Отказ от ответственности: я никогда не использовал это. Я нашел один единственный пример использования в сети здесь. Я попытался проверить это использование по источнику xcb_input_xi_select_events здесь, но его код ругательство удалено и не читается. У меня нет ни малейшего представления, как именно люди должны иметь возможность использовать эту библиотеку.

person n. 1.8e9-where's-my-share m.    schedule 25.09.2016
comment
Из чтения комментария к примеру, который вы связали (захват событий ввода неинвазивно с помощью XInput), я бы предположил, что это регистрирует события касания, не препятствуя их получению другими окнами, в то время как моя цель - захватить события, поэтому только другие окна получить их, когда я отклоняю события (извините, я не ясно выразил это в своем вопросе). К настоящему времени я нашел другое решение, которое я опубликую через минуту. Также код xcb-xinput нечитаем, потому что, насколько мне известно, он каким-то образом автоматически генерируется из спецификаций протокола;) - person freundTech; 27.09.2016

Я нашел решение этой проблемы.
Большое спасибо https://github.com/eemikula/touchwm.

const uint32_t mask[] = {
    XCB_INPUT_XI_EVENT_MASK_TOUCH_BEGIN
    | XCB_INPUT_XI_EVENT_MASK_TOUCH_UPDATE
    | XCB_INPUT_XI_EVENT_MASK_TOUCH_END
    | XCB_INPUT_XI_EVENT_MASK_TOUCH_OWNERSHIP
};
const uint32_t modifiers[] = {XCB_INPUT_MODIFIER_MASK_ANY};

xcb_input_xi_passive_grab_device(
    dpy, 
    XCB_CURRENT_TIME, 
    root,
    XCB_CURSOR_NONE,
    0, // detail - as used by XIPassiveGrab
    XCB_INPUT_DEVICE_ALL_MASTER,
    1, // num_modifiers
    1, // mask_len
    XCB_INPUT_GRAB_TYPE_TOUCH_BEGIN,
    XCB_INPUT_GRAB_MODE_22_TOUCH,
    XCB_INPUT_GRAB_MODE_22_ASYNC,
    XCB_INPUT_GRAB_OWNER_NO_OWNER,
    mask,
    modifiers
);

Это выглядит немного загадочно, но это работает.

person freundTech    schedule 27.09.2016
comment
Можете ли вы сказать, что делает xcb_input_xi_passive_grab_device(), особенно в отличие от xcb_input_xi_grab_device()? Это асинхронные команды, и вы должны прочитать детали события отдельной командой, верно? - person jarno; 28.09.2020