diff options
author | Gerd Hoffmann <kraxel@redhat.com> | 2013-11-27 10:35:26 +0100 |
---|---|---|
committer | Gerd Hoffmann <kraxel@redhat.com> | 2014-03-05 09:50:17 +0100 |
commit | c8b405b6798e3731eb9a71fcd753745f224ce698 (patch) | |
tree | c36fd8994d4bb05fa33c66b003e0ed27bb8f84ee | |
parent | 8b6b0c59a600d8254a409b837d5358d16e881fd0 (diff) |
input: add core bits of the new input layer
Register and unregister handlers.
Event dispatcher code.
Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
-rw-r--r-- | include/ui/input.h | 32 | ||||
-rw-r--r-- | ui/Makefile.objs | 2 | ||||
-rw-r--r-- | ui/input.c | 83 |
3 files changed, 116 insertions, 1 deletions
diff --git a/include/ui/input.h b/include/ui/input.h new file mode 100644 index 0000000000..3cf3641243 --- /dev/null +++ b/include/ui/input.h @@ -0,0 +1,32 @@ +#ifndef INPUT_H +#define INPUT_H + +#include "qapi-types.h" + +#define INPUT_EVENT_MASK_KEY (1<<INPUT_EVENT_KIND_KEY) +#define INPUT_EVENT_MASK_BTN (1<<INPUT_EVENT_KIND_BTN) +#define INPUT_EVENT_MASK_REL (1<<INPUT_EVENT_KIND_REL) +#define INPUT_EVENT_MASK_ABS (1<<INPUT_EVENT_KIND_ABS) + +typedef struct QemuInputHandler QemuInputHandler; +typedef struct QemuInputHandlerState QemuInputHandlerState; + +typedef void (*QemuInputHandlerEvent)(DeviceState *dev, QemuConsole *src, + InputEvent *evt); +typedef void (*QemuInputHandlerSync)(DeviceState *dev); + +struct QemuInputHandler { + const char *name; + uint32_t mask; + QemuInputHandlerEvent event; + QemuInputHandlerSync sync; +}; + +QemuInputHandlerState *qemu_input_handler_register(DeviceState *dev, + QemuInputHandler *handler); +void qemu_input_handler_activate(QemuInputHandlerState *s); +void qemu_input_handler_unregister(QemuInputHandlerState *s); +void qemu_input_event_send(QemuConsole *src, InputEvent *evt); +void qemu_input_event_sync(void); + +#endif /* INPUT_H */ diff --git a/ui/Makefile.objs b/ui/Makefile.objs index 39ceadcdd8..27af551de2 100644 --- a/ui/Makefile.objs +++ b/ui/Makefile.objs @@ -7,7 +7,7 @@ vnc-obj-$(CONFIG_VNC_SASL) += vnc-auth-sasl.o vnc-obj-$(CONFIG_VNC_WS) += vnc-ws.o vnc-obj-y += vnc-jobs.o -common-obj-y += keymaps.o console.o cursor.o input-legacy.o qemu-pixman.o +common-obj-y += keymaps.o console.o cursor.o input.o input-legacy.o qemu-pixman.o common-obj-$(CONFIG_SPICE) += spice-core.o spice-input.o spice-display.o common-obj-$(CONFIG_SDL) += sdl.o sdl_zoom.o x_keymap.o common-obj-$(CONFIG_COCOA) += cocoa.o diff --git a/ui/input.c b/ui/input.c new file mode 100644 index 0000000000..23c84f7254 --- /dev/null +++ b/ui/input.c @@ -0,0 +1,83 @@ +#include "sysemu/sysemu.h" +#include "qapi-types.h" +#include "ui/input.h" + +struct QemuInputHandlerState { + DeviceState *dev; + QemuInputHandler *handler; + int id; + int events; + QTAILQ_ENTRY(QemuInputHandlerState) node; +}; +static QTAILQ_HEAD(, QemuInputHandlerState) handlers = + QTAILQ_HEAD_INITIALIZER(handlers); + +QemuInputHandlerState *qemu_input_handler_register(DeviceState *dev, + QemuInputHandler *handler) +{ + QemuInputHandlerState *s = g_new0(QemuInputHandlerState, 1); + static int id = 1; + + s->dev = dev; + s->handler = handler; + s->id = id++; + QTAILQ_INSERT_TAIL(&handlers, s, node); + return s; +} + +void qemu_input_handler_activate(QemuInputHandlerState *s) +{ + QTAILQ_REMOVE(&handlers, s, node); + QTAILQ_INSERT_HEAD(&handlers, s, node); +} + +void qemu_input_handler_unregister(QemuInputHandlerState *s) +{ + QTAILQ_REMOVE(&handlers, s, node); + g_free(s); +} + +static QemuInputHandlerState* +qemu_input_find_handler(uint32_t mask) +{ + QemuInputHandlerState *s; + + QTAILQ_FOREACH(s, &handlers, node) { + if (mask & s->handler->mask) { + return s; + } + } + return NULL; +} + +void qemu_input_event_send(QemuConsole *src, InputEvent *evt) +{ + QemuInputHandlerState *s; + + if (!runstate_is_running() && !runstate_check(RUN_STATE_SUSPENDED)) { + return; + } + + s = qemu_input_find_handler(1 << evt->kind); + s->handler->event(s->dev, src, evt); + s->events++; +} + +void qemu_input_event_sync(void) +{ + QemuInputHandlerState *s; + + if (!runstate_is_running() && !runstate_check(RUN_STATE_SUSPENDED)) { + return; + } + + QTAILQ_FOREACH(s, &handlers, node) { + if (!s->events) { + continue; + } + if (s->handler->sync) { + s->handler->sync(s->dev); + } + s->events = 0; + } +} |