#include "mouse_inject.h" #include #include "android/input.h" #include "control_msg.h" #include "controller.h" #include "input_events.h" #include "util/intmap.h" #include "util/log.h" /** Downcast mouse processor to sc_mouse_inject */ #define DOWNCAST(MP) container_of(MP, struct sc_mouse_inject, mouse_processor) static enum android_motionevent_buttons convert_mouse_buttons(uint32_t state) { enum android_motionevent_buttons buttons = 0; if (state & SC_MOUSE_BUTTON_LEFT) { buttons |= AMOTION_EVENT_BUTTON_PRIMARY; } if (state & SC_MOUSE_BUTTON_RIGHT) { buttons |= AMOTION_EVENT_BUTTON_SECONDARY; } if (state & SC_MOUSE_BUTTON_MIDDLE) { buttons |= AMOTION_EVENT_BUTTON_TERTIARY; } if (state & SC_MOUSE_BUTTON_X1) { buttons |= AMOTION_EVENT_BUTTON_BACK; } if (state & SC_MOUSE_BUTTON_X2) { buttons |= AMOTION_EVENT_BUTTON_FORWARD; } return buttons; } static enum android_motionevent_action convert_mouse_action(enum sc_action action) { if (action == SC_ACTION_DOWN) { return AMOTION_EVENT_ACTION_DOWN; } assert(action == SC_ACTION_UP); return AMOTION_EVENT_ACTION_UP; } static enum android_motionevent_action convert_touch_action(enum sc_touch_action action) { switch (action) { case SC_TOUCH_ACTION_MOVE: return AMOTION_EVENT_ACTION_MOVE; case SC_TOUCH_ACTION_DOWN: return AMOTION_EVENT_ACTION_DOWN; default: assert(action == SC_TOUCH_ACTION_UP); return AMOTION_EVENT_ACTION_UP; } } static void convert_mouse_motion(const struct sc_mouse_motion_event *event, struct control_msg *msg) { msg->type = CONTROL_MSG_TYPE_INJECT_TOUCH_EVENT; msg->inject_touch_event.action = AMOTION_EVENT_ACTION_MOVE; msg->inject_touch_event.pointer_id = POINTER_ID_MOUSE; msg->inject_touch_event.position = event->position; msg->inject_touch_event.pressure = 1.f; msg->inject_touch_event.buttons = convert_mouse_buttons(event->buttons_state); } static void convert_touch(const struct sc_touch_event *event, struct control_msg *msg) { msg->type = CONTROL_MSG_TYPE_INJECT_TOUCH_EVENT; msg->inject_touch_event.action = convert_touch_action(event->action); msg->inject_touch_event.pointer_id = event->pointer_id; msg->inject_touch_event.position = event->position; msg->inject_touch_event.pressure = event->pressure; msg->inject_touch_event.buttons = 0; } static void convert_mouse_click(const struct sc_mouse_click_event *event, struct control_msg *msg) { msg->type = CONTROL_MSG_TYPE_INJECT_TOUCH_EVENT; msg->inject_touch_event.action = convert_mouse_action(event->action); msg->inject_touch_event.pointer_id = POINTER_ID_MOUSE; msg->inject_touch_event.position = event->position; msg->inject_touch_event.pressure = event->action == SC_ACTION_DOWN ? 1.f : 0.f; msg->inject_touch_event.buttons = convert_mouse_buttons(event->buttons_state); } static void convert_mouse_scroll(const struct sc_mouse_scroll_event *event, struct control_msg *msg) { msg->type = CONTROL_MSG_TYPE_INJECT_SCROLL_EVENT; msg->inject_scroll_event.position = event->position; msg->inject_scroll_event.hscroll = event->hscroll; msg->inject_scroll_event.vscroll = event->vscroll; } static void sc_mouse_processor_process_mouse_motion(struct sc_mouse_processor *mp, const struct sc_mouse_motion_event *event) { struct sc_mouse_inject *mi = DOWNCAST(mp); struct control_msg msg; convert_mouse_motion(event, &msg); if (!controller_push_msg(mi->controller, &msg)) { LOGW("Could not request 'inject mouse motion event'"); } } static void sc_mouse_processor_process_touch(struct sc_mouse_processor *mp, const struct sc_touch_event *event) { struct sc_mouse_inject *mi = DOWNCAST(mp); struct control_msg msg; convert_touch(event, &msg); if (!controller_push_msg(mi->controller, &msg)) { LOGW("Could not request 'inject touch event'"); } } static void sc_mouse_processor_process_mouse_click(struct sc_mouse_processor *mp, const struct sc_mouse_click_event *event) { struct sc_mouse_inject *mi = DOWNCAST(mp); struct control_msg msg; convert_mouse_click(event, &msg); if (!controller_push_msg(mi->controller, &msg)) { LOGW("Could not request 'inject mouse click event'"); } } static void sc_mouse_processor_process_mouse_scroll(struct sc_mouse_processor *mp, const struct sc_mouse_scroll_event *event) { struct sc_mouse_inject *mi = DOWNCAST(mp); struct control_msg msg; convert_mouse_scroll(event, &msg); if (!controller_push_msg(mi->controller, &msg)) { LOGW("Could not request 'inject mouse scroll event'"); } } void sc_mouse_inject_init(struct sc_mouse_inject *mi, struct controller *controller) { mi->controller = controller; static const struct sc_mouse_processor_ops ops = { .process_mouse_motion = sc_mouse_processor_process_mouse_motion, .process_touch = sc_mouse_processor_process_touch, .process_mouse_click = sc_mouse_processor_process_mouse_click, .process_mouse_scroll = sc_mouse_processor_process_mouse_scroll, }; mi->mouse_processor.ops = &ops; }