diff options
| -rw-r--r-- | INSTALL | 4 | ||||
| -rw-r--r-- | configure.ac | 4 | ||||
| -rw-r--r-- | include/grail-touch.h | 85 | ||||
| -rw-r--r-- | src/Makefile.am | 7 | ||||
| -rw-r--r-- | src/gebuf.h | 4 | ||||
| -rw-r--r-- | src/gestures-drag.c | 6 | ||||
| -rw-r--r-- | src/gestures-pinch.c | 6 | ||||
| -rw-r--r-- | src/gestures-rotate.c | 6 | ||||
| -rw-r--r-- | src/gestures-tapping.c | 4 | ||||
| -rw-r--r-- | src/grail-api.c | 280 | ||||
| -rw-r--r-- | src/grail-event.c | 33 | ||||
| -rw-r--r-- | src/grail-gestures.c | 38 | ||||
| -rw-r--r-- | src/grail-gestures.h | 16 | ||||
| -rw-r--r-- | src/grail-impl.h | 17 | ||||
| -rw-r--r-- | src/grail-inserter.c | 31 | ||||
| -rw-r--r-- | src/grail-inserter.h | 17 | ||||
| -rw-r--r-- | src/grail-recognizer.c | 3 | ||||
| -rw-r--r-- | src/grail-recognizer.h | 3 | ||||
| -rw-r--r-- | src/touch-caps.c | 117 | ||||
| -rw-r--r-- | src/touch-dev.c | 264 | ||||
| -rw-r--r-- | tools/Makefile.am | 2 |
21 files changed, 259 insertions, 688 deletions
| @@ -1,7 +1,7 @@ | |||
| 1 | grail - Gesture Recognition And Instantiation Library | 1 | grail - Gesture Recognition And Instantiation Library |
| 2 | 2 | ||
| 3 | To build, you need to have the autoconf, libtool and mtdev-dev packages | 3 | To build, you need to have the autoconf, libtool, mtdev-dev, |
| 4 | installed. Then, do | 4 | libutouch-evemu-dev and libutouch-frame packages installed. Then, do |
| 5 | 5 | ||
| 6 | ./autogen.sh | 6 | ./autogen.sh |
| 7 | ./configure | 7 | ./configure |
diff --git a/configure.ac b/configure.ac index 0f75818..ceb9258 100644 --- a/configure.ac +++ b/configure.ac | |||
| @@ -22,7 +22,9 @@ AC_PROG_LIBTOOL | |||
| 22 | AC_PROG_CC | 22 | AC_PROG_CC |
| 23 | AC_PROG_INSTALL | 23 | AC_PROG_INSTALL |
| 24 | 24 | ||
| 25 | PKG_CHECK_MODULES([MTDEV], [mtdev >= 1.0]) | 25 | PKG_CHECK_MODULES([MTDEV], [mtdev >= 1.1]) |
| 26 | PKG_CHECK_MODULES([EVEMU], [utouch-evemu >= 1.0]) | ||
| 27 | PKG_CHECK_MODULES([FRAME], [utouch-frame >= 1.0]) | ||
| 26 | 28 | ||
| 27 | AC_CONFIG_FILES([Makefile | 29 | AC_CONFIG_FILES([Makefile |
| 28 | src/Makefile | 30 | src/Makefile |
diff --git a/include/grail-touch.h b/include/grail-touch.h deleted file mode 100644 index 9c63c80..0000000 --- a/include/grail-touch.h +++ /dev/null | |||
| @@ -1,85 +0,0 @@ | |||
| 1 | /***************************************************************************** | ||
| 2 | * | ||
| 3 | * grail - Gesture Recognition And Instantiation Library | ||
| 4 | * | ||
| 5 | * Copyright (C) 2010 Canonical Ltd. | ||
| 6 | * Copyright (C) 2010 Henrik Rydberg <rydberg@bitmath.org> | ||
| 7 | * | ||
| 8 | * This program is free software: you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation, either version 3 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | * This program is distributed in the hope that it will be useful, but | ||
| 14 | * WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
| 16 | * General Public License for more details. | ||
| 17 | * | ||
| 18 | * You should have received a copy of the GNU General Public License along | ||
| 19 | * with this program. If not, see <http://www.gnu.org/licenses/>. | ||
| 20 | * | ||
| 21 | ****************************************************************************/ | ||
| 22 | |||
| 23 | #ifndef _GRAIL_TOUCH_H | ||
| 24 | #define _GRAIL_TOUCH_H | ||
| 25 | |||
| 26 | #include <grail-bits.h> | ||
| 27 | #include <mtdev.h> | ||
| 28 | |||
| 29 | #define DIM_TOUCH 32 | ||
| 30 | #define DIM_TOUCH_BYTES ((DIM_TOUCH + 7) >> 3) | ||
| 31 | |||
| 32 | typedef __u64 touch_time_t; | ||
| 33 | |||
| 34 | struct touch { | ||
| 35 | int active; | ||
| 36 | int slot; | ||
| 37 | int id; | ||
| 38 | int tool_type; | ||
| 39 | int x, y; | ||
| 40 | int touch_major; | ||
| 41 | int touch_minor; | ||
| 42 | int width_major; | ||
| 43 | int width_minor; | ||
| 44 | int orientation; | ||
| 45 | int pressure; | ||
| 46 | }; | ||
| 47 | |||
| 48 | struct touch_frame { | ||
| 49 | int nactive; | ||
| 50 | int ncreate, nmodify, ndestroy; | ||
| 51 | touch_time_t time; | ||
| 52 | grail_mask_t touches[DIM_TOUCH_BYTES]; | ||
| 53 | struct touch *active[DIM_TOUCH]; | ||
| 54 | struct touch touch[DIM_TOUCH]; | ||
| 55 | }; | ||
| 56 | |||
| 57 | struct touch_caps { | ||
| 58 | float min_x, max_x; | ||
| 59 | float min_y, max_y; | ||
| 60 | float min_orient, max_orient; | ||
| 61 | float min_press, max_press; | ||
| 62 | }; | ||
| 63 | |||
| 64 | struct touch_dev { | ||
| 65 | void (*event)(struct touch_dev *dev, const struct input_event *ev); | ||
| 66 | void (*sync)(struct touch_dev *dev, const struct input_event *syn); | ||
| 67 | void *priv; | ||
| 68 | struct mtdev mtdev; | ||
| 69 | struct touch_frame frame; | ||
| 70 | struct touch_caps caps; | ||
| 71 | int slot; | ||
| 72 | int state; | ||
| 73 | }; | ||
| 74 | |||
| 75 | int touch_caps_is_supported(struct touch_dev *dev, int fd); | ||
| 76 | void touch_caps_init(struct touch_dev *dev); | ||
| 77 | float touch_angle(const struct touch_dev *dev, int orientation); | ||
| 78 | float touch_pressure(const struct touch_dev *dev, int pressure); | ||
| 79 | |||
| 80 | int touch_dev_open(struct touch_dev *dev, int fd); | ||
| 81 | int touch_dev_idle(struct touch_dev *dev, int fd, int ms); | ||
| 82 | int touch_dev_pull(struct touch_dev *dev, int fd); | ||
| 83 | void touch_dev_close(struct touch_dev *dev, int fd); | ||
| 84 | |||
| 85 | #endif | ||
diff --git a/src/Makefile.am b/src/Makefile.am index dd2af2b..bb1c4c5 100644 --- a/src/Makefile.am +++ b/src/Makefile.am | |||
| @@ -3,14 +3,14 @@ lib_LTLIBRARIES = libutouch-grail.la | |||
| 3 | libutouch_grail_la_LDFLAGS = \ | 3 | libutouch_grail_la_LDFLAGS = \ |
| 4 | -version-info @LIB_VERSION@ \ | 4 | -version-info @LIB_VERSION@ \ |
| 5 | -lm \ | 5 | -lm \ |
| 6 | $(MTDEV_LIBS) | 6 | $(MTDEV_LIBS) \ |
| 7 | $(EVEMU_LIBS) \ | ||
| 8 | $(FRAME_LIBS) | ||
| 7 | 9 | ||
| 8 | libutouch_grail_la_SOURCES = \ | 10 | libutouch_grail_la_SOURCES = \ |
| 9 | evbuf.h \ | 11 | evbuf.h \ |
| 10 | gebuf.h \ | 12 | gebuf.h \ |
| 11 | grailbuf.h \ | 13 | grailbuf.h \ |
| 12 | touch-dev.c \ | ||
| 13 | touch-caps.c \ | ||
| 14 | grail-bits.c \ | 14 | grail-bits.c \ |
| 15 | grail-inserter.c \ | 15 | grail-inserter.c \ |
| 16 | grail-inserter.h \ | 16 | grail-inserter.h \ |
| @@ -34,5 +34,4 @@ libutouch_grailincludedir = $(includedir) | |||
| 34 | libutouch_grailinclude_HEADERS = \ | 34 | libutouch_grailinclude_HEADERS = \ |
| 35 | $(top_srcdir)/include/grail-bits.h \ | 35 | $(top_srcdir)/include/grail-bits.h \ |
| 36 | $(top_srcdir)/include/grail-types.h \ | 36 | $(top_srcdir)/include/grail-types.h \ |
| 37 | $(top_srcdir)/include/grail-touch.h \ | ||
| 38 | $(top_srcdir)/include/grail.h | 37 | $(top_srcdir)/include/grail.h |
diff --git a/src/gebuf.h b/src/gebuf.h index 460e134..0cd9219 100644 --- a/src/gebuf.h +++ b/src/gebuf.h | |||
| @@ -23,7 +23,7 @@ | |||
| 23 | #ifndef _GRAIL_GESTURE_BUFFER_H | 23 | #ifndef _GRAIL_GESTURE_BUFFER_H |
| 24 | #define _GRAIL_GESTURE_BUFFER_H | 24 | #define _GRAIL_GESTURE_BUFFER_H |
| 25 | 25 | ||
| 26 | #include <grail.h> | 26 | #include "grail-impl.h" |
| 27 | 27 | ||
| 28 | #define DIM_GESTURE_EVENTS 512 | 28 | #define DIM_GESTURE_EVENTS 512 |
| 29 | 29 | ||
| @@ -31,7 +31,7 @@ struct gesture_event { | |||
| 31 | int status; | 31 | int status; |
| 32 | int ntouch; | 32 | int ntouch; |
| 33 | int nprop; | 33 | int nprop; |
| 34 | touch_time_t time; | 34 | utouch_frame_time_t time; |
| 35 | struct grail_coord pos; | 35 | struct grail_coord pos; |
| 36 | grail_prop_t prop[DIM_GRAIL_PROP]; | 36 | grail_prop_t prop[DIM_GRAIL_PROP]; |
| 37 | }; | 37 | }; |
diff --git a/src/gestures-drag.c b/src/gestures-drag.c index 2ced765..05272da 100644 --- a/src/gestures-drag.c +++ b/src/gestures-drag.c | |||
| @@ -35,7 +35,7 @@ static const int getype[DIM_TOUCH + 1] = { | |||
| 35 | 35 | ||
| 36 | static void set_props(const struct gesture_inserter *gin, | 36 | static void set_props(const struct gesture_inserter *gin, |
| 37 | struct combo_model *s, const struct move_model *m, | 37 | struct combo_model *s, const struct move_model *m, |
| 38 | const struct touch_frame *frame) | 38 | const struct utouch_frame *frame) |
| 39 | { | 39 | { |
| 40 | if (m->single) { | 40 | if (m->single) { |
| 41 | s->prop[GRAIL_PROP_DRAG_DX] = | 41 | s->prop[GRAIL_PROP_DRAG_DX] = |
| @@ -59,7 +59,7 @@ static void set_props(const struct gesture_inserter *gin, | |||
| 59 | static const int fm_mask = 0x03; | 59 | static const int fm_mask = 0x03; |
| 60 | 60 | ||
| 61 | int gru_drag(struct grail *ge, | 61 | int gru_drag(struct grail *ge, |
| 62 | const struct touch_frame *frame) | 62 | const struct utouch_frame *frame) |
| 63 | { | 63 | { |
| 64 | struct gesture_recognizer *gru = ge->gru; | 64 | struct gesture_recognizer *gru = ge->gru; |
| 65 | struct combo_model *state = &gru->drag; | 65 | struct combo_model *state = &gru->drag; |
| @@ -89,7 +89,7 @@ int gru_drag(struct grail *ge, | |||
| 89 | } | 89 | } |
| 90 | 90 | ||
| 91 | int gru_windrag(struct grail *ge, | 91 | int gru_windrag(struct grail *ge, |
| 92 | const struct touch_frame *frame) | 92 | const struct utouch_frame *frame) |
| 93 | { | 93 | { |
| 94 | struct gesture_recognizer *gru = ge->gru; | 94 | struct gesture_recognizer *gru = ge->gru; |
| 95 | struct combo_model *state = &gru->windrag; | 95 | struct combo_model *state = &gru->windrag; |
diff --git a/src/gestures-pinch.c b/src/gestures-pinch.c index 45f1cb3..fa8a626 100644 --- a/src/gestures-pinch.c +++ b/src/gestures-pinch.c | |||
| @@ -38,7 +38,7 @@ static const int fm_mask = 0x04; | |||
| 38 | static void set_props(const struct gesture_inserter *gin, | 38 | static void set_props(const struct gesture_inserter *gin, |
| 39 | struct combo_model *s, | 39 | struct combo_model *s, |
| 40 | const struct move_model *m, | 40 | const struct move_model *m, |
| 41 | const struct touch_frame *frame) | 41 | const struct utouch_frame *frame) |
| 42 | { | 42 | { |
| 43 | s->prop[GRAIL_PROP_PINCH_DR] = gin->scale_r * m->fm[FM_R].action_delta; | 43 | s->prop[GRAIL_PROP_PINCH_DR] = gin->scale_r * m->fm[FM_R].action_delta; |
| 44 | s->prop[GRAIL_PROP_PINCH_VR] = gin->scale_r * m->fm[FM_R].velocity; | 44 | s->prop[GRAIL_PROP_PINCH_VR] = gin->scale_r * m->fm[FM_R].velocity; |
| @@ -48,7 +48,7 @@ static void set_props(const struct gesture_inserter *gin, | |||
| 48 | } | 48 | } |
| 49 | 49 | ||
| 50 | int gru_pinch(struct grail *ge, | 50 | int gru_pinch(struct grail *ge, |
| 51 | const struct touch_frame *frame) | 51 | const struct utouch_frame *frame) |
| 52 | { | 52 | { |
| 53 | struct gesture_recognizer *gru = ge->gru; | 53 | struct gesture_recognizer *gru = ge->gru; |
| 54 | struct combo_model *state = &gru->pinch; | 54 | struct combo_model *state = &gru->pinch; |
| @@ -79,7 +79,7 @@ int gru_pinch(struct grail *ge, | |||
| 79 | } | 79 | } |
| 80 | 80 | ||
| 81 | int gru_winpinch(struct grail *ge, | 81 | int gru_winpinch(struct grail *ge, |
| 82 | const struct touch_frame *frame) | 82 | const struct utouch_frame *frame) |
| 83 | { | 83 | { |
| 84 | struct gesture_recognizer *gru = ge->gru; | 84 | struct gesture_recognizer *gru = ge->gru; |
| 85 | struct combo_model *state = &gru->winpinch; | 85 | struct combo_model *state = &gru->winpinch; |
diff --git a/src/gestures-rotate.c b/src/gestures-rotate.c index 8985257..fde0db8 100644 --- a/src/gestures-rotate.c +++ b/src/gestures-rotate.c | |||
| @@ -37,7 +37,7 @@ static const int fm_mask = 0x08; | |||
| 37 | 37 | ||
| 38 | static void set_props(const struct gesture_inserter *gin, | 38 | static void set_props(const struct gesture_inserter *gin, |
| 39 | struct combo_model *s, const struct move_model *m, | 39 | struct combo_model *s, const struct move_model *m, |
| 40 | const struct touch_frame *frame) | 40 | const struct utouch_frame *frame) |
| 41 | { | 41 | { |
| 42 | s->prop[GRAIL_PROP_ROTATE_DA] = m->fm[FM_A].action_delta; | 42 | s->prop[GRAIL_PROP_ROTATE_DA] = m->fm[FM_A].action_delta; |
| 43 | s->prop[GRAIL_PROP_ROTATE_VA] = m->fm[FM_A].velocity; | 43 | s->prop[GRAIL_PROP_ROTATE_VA] = m->fm[FM_A].velocity; |
| @@ -47,7 +47,7 @@ static void set_props(const struct gesture_inserter *gin, | |||
| 47 | } | 47 | } |
| 48 | 48 | ||
| 49 | int gru_rotate(struct grail *ge, | 49 | int gru_rotate(struct grail *ge, |
| 50 | const struct touch_frame *frame) | 50 | const struct utouch_frame *frame) |
| 51 | { | 51 | { |
| 52 | struct gesture_recognizer *gru = ge->gru; | 52 | struct gesture_recognizer *gru = ge->gru; |
| 53 | struct combo_model *state = &gru->rotate; | 53 | struct combo_model *state = &gru->rotate; |
| @@ -78,7 +78,7 @@ int gru_rotate(struct grail *ge, | |||
| 78 | } | 78 | } |
| 79 | 79 | ||
| 80 | int gru_winrotate(struct grail *ge, | 80 | int gru_winrotate(struct grail *ge, |
| 81 | const struct touch_frame *frame) | 81 | const struct utouch_frame *frame) |
| 82 | { | 82 | { |
| 83 | struct gesture_recognizer *gru = ge->gru; | 83 | struct gesture_recognizer *gru = ge->gru; |
| 84 | struct combo_model *state = &gru->winrotate; | 84 | struct combo_model *state = &gru->winrotate; |
diff --git a/src/gestures-tapping.c b/src/gestures-tapping.c index aa8e6d6..6d71642 100644 --- a/src/gestures-tapping.c +++ b/src/gestures-tapping.c | |||
| @@ -30,7 +30,7 @@ static const int fm_mask = 0x07; | |||
| 30 | 30 | ||
| 31 | static void set_props(const struct gesture_inserter *gin, | 31 | static void set_props(const struct gesture_inserter *gin, |
| 32 | struct tapping_model *s, const struct move_model *m, | 32 | struct tapping_model *s, const struct move_model *m, |
| 33 | const struct touch_frame *frame) | 33 | const struct utouch_frame *frame) |
| 34 | { | 34 | { |
| 35 | s->prop[GRAIL_PROP_TAP_DT] = m->time - s->start; | 35 | s->prop[GRAIL_PROP_TAP_DT] = m->time - s->start; |
| 36 | s->prop[GRAIL_PROP_TAP_X] = gin_prop_x(gin, m->fm[FM_X].value); | 36 | s->prop[GRAIL_PROP_TAP_X] = gin_prop_x(gin, m->fm[FM_X].value); |
| @@ -40,7 +40,7 @@ static void set_props(const struct gesture_inserter *gin, | |||
| 40 | } | 40 | } |
| 41 | 41 | ||
| 42 | int gru_tapping(struct grail *ge, | 42 | int gru_tapping(struct grail *ge, |
| 43 | const struct touch_frame *frame) | 43 | const struct utouch_frame *frame) |
| 44 | { | 44 | { |
| 45 | struct gesture_recognizer *gru = ge->gru; | 45 | struct gesture_recognizer *gru = ge->gru; |
| 46 | struct tapping_model *state = &gru->tapping; | 46 | struct tapping_model *state = &gru->tapping; |
diff --git a/src/grail-api.c b/src/grail-api.c index f38ca18..3aca75d 100644 --- a/src/grail-api.c +++ b/src/grail-api.c | |||
| @@ -30,27 +30,124 @@ | |||
| 30 | #include <malloc.h> | 30 | #include <malloc.h> |
| 31 | #include <errno.h> | 31 | #include <errno.h> |
| 32 | 32 | ||
| 33 | static void tp_event(struct touch_dev *dev, | 33 | #define DIM_FRAMES 100 |
| 34 | const struct input_event *ev) | 34 | #define FRAME_RATE 100 |
| 35 | |||
| 36 | void grail_filter_abs_events(struct grail *ge, int usage) | ||
| 35 | { | 37 | { |
| 36 | struct grail *ge = dev->priv; | ||
| 37 | struct grail_impl *x = ge->impl; | 38 | struct grail_impl *x = ge->impl; |
| 38 | if (ev->type == EV_ABS) { | 39 | x->filter_abs = usage; |
| 39 | return; | 40 | } |
| 41 | |||
| 42 | static void init_impl(struct grail_impl *x) | ||
| 43 | { | ||
| 44 | int i; | ||
| 45 | |||
| 46 | if (evemu_has_event(x->evemu, EV_ABS, ABS_X)) { | ||
| 47 | x->emin_x = evemu_get_abs_minimum(x->evemu, ABS_X); | ||
| 48 | x->emin_y = evemu_get_abs_minimum(x->evemu, ABS_Y); | ||
| 49 | x->emax_x = evemu_get_abs_maximum(x->evemu, ABS_X); | ||
| 50 | x->emax_y = evemu_get_abs_maximum(x->evemu, ABS_Y); | ||
| 51 | } else { | ||
| 52 | struct utouch_surface *s = utouch_frame_get_surface(x->fh); | ||
| 53 | x->emin_x = s->min_x; | ||
| 54 | x->emin_y = s->min_y; | ||
| 55 | x->emax_x = s->max_x; | ||
| 56 | x->emax_y = s->max_y; | ||
| 40 | } | 57 | } |
| 41 | if (ev->type == EV_KEY) { | 58 | } |
| 42 | switch (ev->code) { | 59 | |
| 43 | case BTN_TOUCH: | 60 | int grail_open(struct grail *ge, int fd) |
| 44 | case BTN_TOOL_FINGER: | 61 | { |
| 45 | case BTN_TOOL_DOUBLETAP: | 62 | struct grail_impl *x; |
| 46 | case BTN_TOOL_TRIPLETAP: | 63 | int ret; |
| 47 | case BTN_TOOL_QUADTAP: | 64 | x = calloc(1, sizeof(*x)); |
| 48 | return; | 65 | if (!x) |
| 49 | } | 66 | return -ENOMEM; |
| 67 | |||
| 68 | x->evemu = evemu_new(0); | ||
| 69 | if (!x->evemu) { | ||
| 70 | ret = -ENOMEM; | ||
| 71 | goto freemem; | ||
| 50 | } | 72 | } |
| 51 | evbuf_put(&x->evbuf, ev); | 73 | ret = evemu_extract(x->evemu, fd); |
| 74 | if (ret) | ||
| 75 | goto freemem; | ||
| 76 | if (!utouch_frame_is_supported_mtdev(x->evemu)) { | ||
| 77 | ret = -ENODEV; | ||
| 78 | goto freemem; | ||
| 79 | } | ||
| 80 | x->mtdev = mtdev_new_open(fd); | ||
| 81 | if (!x->mtdev) { | ||
| 82 | ret = -ENOMEM; | ||
| 83 | goto freemem; | ||
| 84 | } | ||
| 85 | |||
| 86 | x->fh = utouch_frame_new_engine(DIM_FRAMES, DIM_TOUCH, FRAME_RATE); | ||
| 87 | if (!x->fh) { | ||
| 88 | ret = -ENOMEM; | ||
| 89 | goto freedev; | ||
| 90 | } | ||
| 91 | ret = utouch_frame_init_mtdev(x->fh, x->evemu); | ||
| 92 | if (ret) | ||
| 93 | goto freeframe; | ||
| 94 | |||
| 95 | init_impl(x); | ||
| 96 | ge->impl = x; | ||
| 97 | |||
| 98 | ret = gin_init(ge); | ||
| 99 | if (ret) | ||
| 100 | goto freeframe; | ||
| 101 | |||
| 102 | ret = gru_init(ge); | ||
| 103 | if (ret) | ||
| 104 | goto freegin; | ||
| 105 | |||
| 106 | return 0; | ||
| 107 | freegin: | ||
| 108 | gin_destroy(ge); | ||
| 109 | freeframe: | ||
| 110 | utouch_frame_delete_engine(x->fh); | ||
| 111 | freedev: | ||
| 112 | mtdev_close_delete(x->mtdev); | ||
| 113 | freemem: | ||
| 114 | evemu_delete(x->evemu); | ||
| 115 | free(x); | ||
| 116 | ge->impl = 0; | ||
| 117 | return ret; | ||
| 118 | } | ||
| 119 | |||
| 120 | void grail_close(struct grail *ge, int fd) | ||
| 121 | { | ||
| 122 | struct grail_impl *x = ge->impl; | ||
| 123 | void *status; | ||
| 124 | gru_destroy(ge); | ||
| 125 | gin_destroy(ge); | ||
| 126 | utouch_frame_delete_engine(x->fh); | ||
| 127 | mtdev_close_delete(x->mtdev); | ||
| 128 | evemu_delete(x->evemu); | ||
| 129 | free(x); | ||
| 130 | ge->impl = 0; | ||
| 52 | } | 131 | } |
| 53 | 132 | ||
| 133 | int grail_idle(struct grail *ge, int fd, int ms) | ||
| 134 | { | ||
| 135 | struct grail_impl *x = ge->impl; | ||
| 136 | return mtdev_idle(x->mtdev, fd, ms); | ||
| 137 | } | ||
| 138 | |||
| 139 | void grail_get_units(const struct grail *ge, | ||
| 140 | struct grail_coord *min, struct grail_coord *max) | ||
| 141 | { | ||
| 142 | struct utouch_surface *s = utouch_frame_get_surface(ge->impl->fh); | ||
| 143 | min->x = s->min_x; | ||
| 144 | min->y = s->min_y; | ||
| 145 | max->x = s->max_x; | ||
| 146 | max->y = s->max_y; | ||
| 147 | } | ||
| 148 | |||
| 149 | // legacy glue below | ||
| 150 | |||
| 54 | static void evput(struct grail_impl *x, struct timeval time, | 151 | static void evput(struct grail_impl *x, struct timeval time, |
| 55 | unsigned type, unsigned code, int value) | 152 | unsigned type, unsigned code, int value) |
| 56 | { | 153 | { |
| @@ -76,47 +173,19 @@ static void report_up(struct grail_impl *impl, const struct input_event *syn) | |||
| 76 | impl->report_status = 0; | 173 | impl->report_status = 0; |
| 77 | } | 174 | } |
| 78 | 175 | ||
| 79 | #define SYSCALL(call) while (((call) == -1) && (errno == EINTR)) | ||
| 80 | |||
| 81 | static int getabs(struct input_absinfo *abs, int key, int fd) | ||
| 82 | { | ||
| 83 | int rc; | ||
| 84 | SYSCALL(rc = ioctl(fd, EVIOCGABS(key), abs)); | ||
| 85 | return rc >= 0; | ||
| 86 | } | ||
| 87 | |||
| 88 | static void set_emulation_caps(struct grail_impl *impl, int fd) | ||
| 89 | { | ||
| 90 | struct touch_caps *emu = &impl->emu; | ||
| 91 | struct input_absinfo info; | ||
| 92 | |||
| 93 | memset(emu, 0, sizeof(*emu)); | ||
| 94 | |||
| 95 | if (getabs(&info, ABS_X, fd)) { | ||
| 96 | emu->min_x = info.minimum; | ||
| 97 | emu->max_x = info.maximum; | ||
| 98 | } | ||
| 99 | if (getabs(&info, ABS_Y, fd)) { | ||
| 100 | emu->min_y = info.minimum; | ||
| 101 | emu->max_y = info.maximum; | ||
| 102 | } | ||
| 103 | } | ||
| 104 | |||
| 105 | static void set_pointer(struct grail_impl *impl) | 176 | static void set_pointer(struct grail_impl *impl) |
| 106 | { | 177 | { |
| 107 | struct touch_dev *dev = &impl->dev; | 178 | struct utouch_surface *s = utouch_frame_get_surface(impl->fh); |
| 108 | struct touch_caps *caps = &dev->caps; | 179 | const struct utouch_frame *frame = impl->frame; |
| 109 | struct touch_caps *emu = &impl->emu; | ||
| 110 | struct touch_frame *frame = &dev->frame; | ||
| 111 | int best_x, best_y, best_d = -1; | 180 | int best_x, best_y, best_d = -1; |
| 112 | int i; | 181 | int i; |
| 113 | 182 | ||
| 114 | for (i = 0; i < frame->nactive; i++) { | 183 | for (i = 0; i < frame->num_active; i++) { |
| 115 | struct touch *t = frame->active[i]; | 184 | const struct utouch_contact *t = frame->active[i]; |
| 116 | float u = (t->x - caps->min_x) / (caps->max_x - caps->min_x); | 185 | float u = (t->x - s->min_x) / (s->max_x - s->min_x); |
| 117 | float v = (t->y - caps->min_y) / (caps->max_y - caps->min_y); | 186 | float v = (t->y - s->min_y) / (s->max_y - s->min_y); |
| 118 | int x = emu->min_x + u * (emu->max_x - emu->min_x); | 187 | int x = impl->emin_x + u * (impl->emax_x - impl->emin_x); |
| 119 | int y = emu->min_y + v * (emu->max_y - emu->min_y); | 188 | int y = impl->emin_y + v * (impl->emax_y - impl->emin_y); |
| 120 | int d = abs(x - impl->pointer_x) + abs(y - impl->pointer_y); | 189 | int d = abs(x - impl->pointer_x) + abs(y - impl->pointer_y); |
| 121 | if (best_d < 0 || d < best_d) { | 190 | if (best_d < 0 || d < best_d) { |
| 122 | best_x = x; | 191 | best_x = x; |
| @@ -181,15 +250,18 @@ static void handle_abs_events(struct grail *ge, const struct input_event *syn) | |||
| 181 | } | 250 | } |
| 182 | } | 251 | } |
| 183 | 252 | ||
| 184 | static void tp_sync(struct touch_dev *dev, | 253 | static void report_frame(struct grail *ge, |
| 185 | const struct input_event *syn) | 254 | const struct utouch_frame *frame, |
| 255 | const struct input_event *syn) | ||
| 186 | { | 256 | { |
| 187 | struct grail *ge = dev->priv; | 257 | |
| 188 | struct grail_impl *impl = ge->impl; | 258 | struct grail_impl *impl = ge->impl; |
| 189 | int head = impl->evbuf.head; | 259 | int head = impl->evbuf.head; |
| 190 | struct input_event iev; | 260 | struct input_event iev; |
| 191 | struct grail_event gev; | 261 | struct grail_event gev; |
| 192 | struct touch_frame *frame = &dev->frame; | 262 | |
| 263 | ge->impl->frame = frame; | ||
| 264 | |||
| 193 | gin_frame_begin(ge, frame); | 265 | gin_frame_begin(ge, frame); |
| 194 | gru_recognize(ge, frame); | 266 | gru_recognize(ge, frame); |
| 195 | gin_frame_end(ge, frame); | 267 | gin_frame_end(ge, frame); |
| @@ -211,78 +283,42 @@ static void tp_sync(struct touch_dev *dev, | |||
| 211 | } | 283 | } |
| 212 | } | 284 | } |
| 213 | 285 | ||
| 214 | void grail_filter_abs_events(struct grail *ge, int usage) | 286 | static void grail_pump_mtdev(struct grail *ge, const struct input_event *ev) |
| 215 | { | ||
| 216 | struct grail_impl *x = ge->impl; | ||
| 217 | x->filter_abs = usage; | ||
| 218 | } | ||
| 219 | |||
| 220 | int grail_open(struct grail *ge, int fd) | ||
| 221 | { | ||
| 222 | struct grail_impl *x; | ||
| 223 | int ret; | ||
| 224 | x = calloc(1, sizeof(*x)); | ||
| 225 | if (!x) | ||
| 226 | return -ENOMEM; | ||
| 227 | ge->impl = x; | ||
| 228 | |||
| 229 | ret = touch_dev_open(&x->dev, fd); | ||
| 230 | if (ret) | ||
| 231 | goto freemem; | ||
| 232 | set_emulation_caps(x, fd); | ||
| 233 | x->dev.event = tp_event; | ||
| 234 | x->dev.sync = tp_sync; | ||
| 235 | x->dev.priv = ge; | ||
| 236 | |||
| 237 | ret = gin_init(ge); | ||
| 238 | if (ret) | ||
| 239 | goto freedev; | ||
| 240 | |||
| 241 | ret = gru_init(ge); | ||
| 242 | if (ret) | ||
| 243 | goto freegin; | ||
| 244 | |||
| 245 | return 0; | ||
| 246 | freegin: | ||
| 247 | gin_destroy(ge); | ||
| 248 | freedev: | ||
| 249 | touch_dev_close(&x->dev, fd); | ||
| 250 | freemem: | ||
| 251 | free(x); | ||
| 252 | ge->impl = 0; | ||
| 253 | return ret; | ||
| 254 | } | ||
| 255 | |||
| 256 | void grail_close(struct grail *ge, int fd) | ||
| 257 | { | 287 | { |
| 258 | struct grail_impl *x = ge->impl; | 288 | struct grail_impl *impl = ge->impl; |
| 259 | void *status; | 289 | const struct utouch_frame *frame; |
| 260 | gru_destroy(ge); | ||
| 261 | gin_destroy(ge); | ||
| 262 | touch_dev_close(&x->dev, fd); | ||
| 263 | free(ge->impl); | ||
| 264 | ge->impl = 0; | ||
| 265 | } | ||
| 266 | 290 | ||
| 267 | int grail_idle(struct grail *ge, int fd, int ms) | 291 | if (ev->type == EV_SYN || ev->type == EV_ABS) { |
| 268 | { | 292 | frame = utouch_frame_pump_mtdev(impl->fh, ev); |
| 269 | struct grail_impl *x = ge->impl; | 293 | if (frame) |
| 270 | return touch_dev_idle(&x->dev, fd, ms); | 294 | report_frame(ge, frame, ev); |
| 295 | } else if (ev->type == EV_KEY) { | ||
| 296 | switch (ev->code) { | ||
| 297 | case BTN_TOUCH: | ||
| 298 | case BTN_TOOL_FINGER: | ||
| 299 | case BTN_TOOL_DOUBLETAP: | ||
| 300 | case BTN_TOOL_TRIPLETAP: | ||
| 301 | case BTN_TOOL_QUADTAP: | ||
| 302 | break; | ||
| 303 | default: | ||
| 304 | evbuf_put(&impl->evbuf, ev); | ||
| 305 | break; | ||
| 306 | } | ||
| 307 | } else { | ||
| 308 | evbuf_put(&impl->evbuf, ev); | ||
| 309 | } | ||
| 271 | } | 310 | } |
| 272 | 311 | ||
| 273 | int grail_pull(struct grail *ge, int fd) | 312 | int grail_pull(struct grail *ge, int fd) |
| 274 | { | 313 | { |
| 275 | struct grail_impl *x = ge->impl; | 314 | struct grail_impl *impl = ge->impl; |
| 276 | return touch_dev_pull(&x->dev, fd); | 315 | struct input_event ev; |
| 277 | } | 316 | int ret, count = 0; |
| 278 | 317 | ||
| 279 | void grail_get_units(const struct grail *ge, | 318 | while ((ret = mtdev_get(impl->mtdev, fd, &ev, 1)) > 0) { |
| 280 | struct grail_coord *min, struct grail_coord *max) | 319 | grail_pump_mtdev(ge, &ev); |
| 281 | { | 320 | count++; |
| 282 | const struct touch_caps *caps = &ge->impl->dev.caps; | 321 | } |
| 283 | min->x = caps->min_x; | ||
| 284 | min->y = caps->min_y; | ||
| 285 | max->x = caps->max_x; | ||
| 286 | max->y = caps->max_y; | ||
| 287 | } | ||
| 288 | 322 | ||
| 323 | return count > 0 ? count : ret; | ||
| 324 | } | ||
diff --git a/src/grail-event.c b/src/grail-event.c index 23fdbb3..9c0e437 100644 --- a/src/grail-event.c +++ b/src/grail-event.c | |||
| @@ -28,17 +28,17 @@ | |||
| 28 | #include <math.h> | 28 | #include <math.h> |
| 29 | 29 | ||
| 30 | static void compute_bbox(struct grail_coord *min, struct grail_coord *max, | 30 | static void compute_bbox(struct grail_coord *min, struct grail_coord *max, |
| 31 | const struct touch_frame *frame) | 31 | const struct utouch_frame *frame) |
| 32 | { | 32 | { |
| 33 | float x, y; | 33 | float x, y; |
| 34 | int i; | 34 | int i; |
| 35 | if (frame->nactive < 1) | 35 | if (frame->num_active < 1) |
| 36 | return; | 36 | return; |
| 37 | x = frame->active[0]->x; | 37 | x = frame->active[0]->x; |
| 38 | y = frame->active[0]->y; | 38 | y = frame->active[0]->y; |
| 39 | min->x = max->x = x; | 39 | min->x = max->x = x; |
| 40 | min->y = max->y = y; | 40 | min->y = max->y = y; |
| 41 | for (i = 1; i < frame->nactive; i++) { | 41 | for (i = 1; i < frame->num_active; i++) { |
| 42 | x = frame->active[i]->x; | 42 | x = frame->active[i]->x; |
| 43 | y = frame->active[i]->y; | 43 | y = frame->active[i]->y; |
| 44 | if (x < min->x) | 44 | if (x < min->x) |
| @@ -53,10 +53,10 @@ static void compute_bbox(struct grail_coord *min, struct grail_coord *max, | |||
| 53 | } | 53 | } |
| 54 | 54 | ||
| 55 | int gin_add_contact_props(const struct gesture_inserter *gin, | 55 | int gin_add_contact_props(const struct gesture_inserter *gin, |
| 56 | grail_prop_t *prop, const struct touch_frame *frame) | 56 | grail_prop_t *prop, const struct utouch_frame *frame) |
| 57 | { | 57 | { |
| 58 | struct grail_coord min, max; | 58 | struct grail_coord min, max; |
| 59 | int i, n = 0, ntouch = frame->nactive; | 59 | int i, n = 0, ntouch = frame->num_active; |
| 60 | if (!ntouch) | 60 | if (!ntouch) |
| 61 | return n; | 61 | return n; |
| 62 | if (ntouch > 5) | 62 | if (ntouch > 5) |
| @@ -67,7 +67,7 @@ int gin_add_contact_props(const struct gesture_inserter *gin, | |||
| 67 | prop[n++] = gin_prop_x(gin, max.x); | 67 | prop[n++] = gin_prop_x(gin, max.x); |
| 68 | prop[n++] = gin_prop_y(gin, max.y); | 68 | prop[n++] = gin_prop_y(gin, max.y); |
| 69 | for (i = 0; i < ntouch; i++) { | 69 | for (i = 0; i < ntouch; i++) { |
| 70 | const struct touch *ct = frame->active[i]; | 70 | const struct utouch_contact *ct = frame->active[i]; |
| 71 | prop[n++] = ct->id; | 71 | prop[n++] = ct->id; |
| 72 | prop[n++] = gin_prop_x(gin, ct->x); | 72 | prop[n++] = gin_prop_x(gin, ct->x); |
| 73 | prop[n++] = gin_prop_y(gin, ct->y); | 73 | prop[n++] = gin_prop_y(gin, ct->y); |
| @@ -79,15 +79,15 @@ int gin_get_clients(struct grail *ge, | |||
| 79 | struct grail_client_info *info, int maxinfo, | 79 | struct grail_client_info *info, int maxinfo, |
| 80 | const grail_mask_t* types, int btypes, | 80 | const grail_mask_t* types, int btypes, |
| 81 | const grail_mask_t* span, int bspan, | 81 | const grail_mask_t* span, int bspan, |
| 82 | const struct touch_frame *frame) | 82 | const struct utouch_frame *frame) |
| 83 | { | 83 | { |
| 84 | struct grail_coord pos[DIM_TOUCH]; | 84 | struct grail_coord pos[DIM_TOUCH]; |
| 85 | int i, npos = 0; | 85 | int i, npos = 0; |
| 86 | if (!ge->get_clients) | 86 | if (!ge->get_clients) |
| 87 | return 0; | 87 | return 0; |
| 88 | grail_mask_foreach(i, span, bspan) { | 88 | grail_mask_foreach(i, span, bspan) { |
| 89 | pos[npos].x = gin_prop_x(ge->gin, frame->touch[i].x); | 89 | pos[npos].x = gin_prop_x(ge->gin, frame->slots[i]->x); |
| 90 | pos[npos].y = gin_prop_y(ge->gin, frame->touch[i].y); | 90 | pos[npos].y = gin_prop_y(ge->gin, frame->slots[i]->y); |
| 91 | npos++; | 91 | npos++; |
| 92 | } | 92 | } |
| 93 | return ge->get_clients(ge, info, maxinfo, pos, npos, types, btypes); | 93 | return ge->get_clients(ge, info, maxinfo, pos, npos, types, btypes); |
| @@ -95,7 +95,7 @@ int gin_get_clients(struct grail *ge, | |||
| 95 | 95 | ||
| 96 | void gin_send_event(struct grail *ge, struct slot_state *s, | 96 | void gin_send_event(struct grail *ge, struct slot_state *s, |
| 97 | const struct gesture_event *ev, | 97 | const struct gesture_event *ev, |
| 98 | const struct touch_frame *frame) | 98 | const struct utouch_frame *frame) |
| 99 | { | 99 | { |
| 100 | struct grail_impl *impl = ge->impl; | 100 | struct grail_impl *impl = ge->impl; |
| 101 | const struct gesture_inserter *gin = ge->gin; | 101 | const struct gesture_inserter *gin = ge->gin; |
| @@ -121,15 +121,14 @@ void gin_send_event(struct grail *ge, struct slot_state *s, | |||
| 121 | int grail_get_contacts(const struct grail *ge, | 121 | int grail_get_contacts(const struct grail *ge, |
| 122 | struct grail_contact *touch, int max_touch) | 122 | struct grail_contact *touch, int max_touch) |
| 123 | { | 123 | { |
| 124 | const struct touch_dev *dev = &ge->impl->dev; | ||
| 125 | const struct gesture_inserter *gin = ge->gin; | 124 | const struct gesture_inserter *gin = ge->gin; |
| 126 | const struct touch_frame *frame = &dev->frame; | 125 | const struct utouch_frame *frame = ge->impl->frame; |
| 127 | int i; | 126 | int i; |
| 128 | if (frame->nactive < max_touch) | 127 | if (frame->num_active < max_touch) |
| 129 | max_touch = frame->nactive; | 128 | max_touch = frame->num_active; |
| 130 | for (i = 0; i < max_touch; i++) { | 129 | for (i = 0; i < max_touch; i++) { |
| 131 | struct grail_contact *t = &touch[i]; | 130 | struct grail_contact *t = &touch[i]; |
| 132 | const struct touch *ct = frame->active[i]; | 131 | const struct utouch_contact *ct = frame->active[i]; |
| 133 | t->id = ct->id; | 132 | t->id = ct->id; |
| 134 | t->tool_type = ct->tool_type; | 133 | t->tool_type = ct->tool_type; |
| 135 | t->pos.x = gin_prop_x(gin, ct->x); | 134 | t->pos.x = gin_prop_x(gin, ct->x); |
| @@ -138,8 +137,8 @@ int grail_get_contacts(const struct grail *ge, | |||
| 138 | t->touch_minor = gin->scale_r * ct->touch_minor; | 137 | t->touch_minor = gin->scale_r * ct->touch_minor; |
| 139 | t->width_major = gin->scale_r * ct->width_major; | 138 | t->width_major = gin->scale_r * ct->width_major; |
| 140 | t->width_minor = gin->scale_r * ct->width_minor; | 139 | t->width_minor = gin->scale_r * ct->width_minor; |
| 141 | t->angle = touch_angle(dev, ct->orientation); | 140 | t->angle = ct->orientation; |
| 142 | t->pressure = touch_pressure(dev, ct->pressure); | 141 | t->pressure = ct->pressure; |
| 143 | } | 142 | } |
| 144 | return max_touch; | 143 | return max_touch; |
| 145 | } | 144 | } |
diff --git a/src/grail-gestures.c b/src/grail-gestures.c index ed937a4..035a199 100644 --- a/src/grail-gestures.c +++ b/src/grail-gestures.c | |||
| @@ -31,15 +31,15 @@ static const grail_time_t SAMPLE_MS = 10; | |||
| 31 | static const float EPS = 1e-3; | 31 | static const float EPS = 1e-3; |
| 32 | 32 | ||
| 33 | static void compute_position(float *x, float *y, | 33 | static void compute_position(float *x, float *y, |
| 34 | const struct touch_frame *frame) | 34 | const struct utouch_frame *frame) |
| 35 | { | 35 | { |
| 36 | int i, n = frame->nactive; | 36 | int i, n = frame->num_active; |
| 37 | *x = 0; | 37 | *x = 0; |
| 38 | *y = 0; | 38 | *y = 0; |
| 39 | if (n < 1) | 39 | if (n < 1) |
| 40 | return; | 40 | return; |
| 41 | for (i = 0; i < n; i++) { | 41 | for (i = 0; i < n; i++) { |
| 42 | const struct touch *t = frame->active[i]; | 42 | const struct utouch_contact *t = frame->active[i]; |
| 43 | *x += t->x; | 43 | *x += t->x; |
| 44 | *y += t->y; | 44 | *y += t->y; |
| 45 | } | 45 | } |
| @@ -48,14 +48,14 @@ static void compute_position(float *x, float *y, | |||
| 48 | } | 48 | } |
| 49 | 49 | ||
| 50 | static float compute_radius(float x, float y, | 50 | static float compute_radius(float x, float y, |
| 51 | const struct touch_frame *frame) | 51 | const struct utouch_frame *frame) |
| 52 | { | 52 | { |
| 53 | int i, n = frame->nactive; | 53 | int i, n = frame->num_active; |
| 54 | float r = 0, r2 = 0; | 54 | float r = 0, r2 = 0; |
| 55 | if (n < 2) | 55 | if (n < 2) |
| 56 | return r; | 56 | return r; |
| 57 | for (i = 0; i < n; i++) { | 57 | for (i = 0; i < n; i++) { |
| 58 | const struct touch *t = frame->active[i]; | 58 | const struct utouch_contact *t = frame->active[i]; |
| 59 | float dx = t->x - x; | 59 | float dx = t->x - x; |
| 60 | float dy = t->y - y; | 60 | float dy = t->y - y; |
| 61 | r2 += dx * dx + dy * dy; | 61 | r2 += dx * dx + dy * dy; |
| @@ -66,16 +66,15 @@ static float compute_radius(float x, float y, | |||
| 66 | } | 66 | } |
| 67 | 67 | ||
| 68 | static float compute_rotation(float x, float y, float r, | 68 | static float compute_rotation(float x, float y, float r, |
| 69 | const struct touch_frame *prev, | 69 | const struct utouch_frame *frame) |
| 70 | const struct touch_frame *frame) | ||
| 71 | { | 70 | { |
| 72 | int i, n = frame->nactive; | 71 | int i, n = frame->num_active; |
| 73 | float da = 0, darc2 = 0; | 72 | float da = 0, darc2 = 0; |
| 74 | if (n < 2) | 73 | if (n < 2) |
| 75 | return da; | 74 | return da; |
| 76 | for (i = 0; i < n; i++) { | 75 | for (i = 0; i < n; i++) { |
| 77 | const struct touch *t = frame->active[i]; | 76 | const struct utouch_contact *t = frame->active[i]; |
| 78 | const struct touch *ot = &prev->touch[t->slot]; | 77 | const struct utouch_contact *ot = t->prev; |
| 79 | float dx = t->x - x; | 78 | float dx = t->x - x; |
| 80 | float dy = t->y - y; | 79 | float dy = t->y - y; |
| 81 | float mx = t->x - ot->x; | 80 | float mx = t->x - ot->x; |
| @@ -142,13 +141,13 @@ static void move_update(struct move_model *m, int i, float x, grail_time_t t) | |||
| 142 | 141 | ||
| 143 | void gru_init_motion(struct grail *ge) | 142 | void gru_init_motion(struct grail *ge) |
| 144 | { | 143 | { |
| 145 | struct touch_caps *caps = &ge->impl->dev.caps; | 144 | struct utouch_surface *s = utouch_frame_get_surface(ge->impl->fh); |
| 146 | struct gesture_recognizer *gru = ge->gru; | 145 | struct gesture_recognizer *gru = ge->gru; |
| 147 | struct move_model *m = &gru->move; | 146 | struct move_model *m = &gru->move; |
| 148 | float D[DIM_FM]; | 147 | float D[DIM_FM]; |
| 149 | int i; | 148 | int i; |
| 150 | D[FM_X] = caps->max_x - caps->min_x; | 149 | D[FM_X] = s->max_x - s->min_x; |
| 151 | D[FM_Y] = caps->max_y - caps->min_y; | 150 | D[FM_Y] = s->max_y - s->min_y; |
| 152 | D[FM_R] = sqrt(D[FM_X] * D[FM_X] + D[FM_Y] * D[FM_Y]); | 151 | D[FM_R] = sqrt(D[FM_X] * D[FM_X] + D[FM_Y] * D[FM_Y]); |
| 153 | D[FM_A] = 2 * M_PI; | 152 | D[FM_A] = 2 * M_PI; |
| 154 | for (i = 0; i < DIM_FM; i++) { | 153 | for (i = 0; i < DIM_FM; i++) { |
| @@ -159,14 +158,15 @@ void gru_init_motion(struct grail *ge) | |||
| 159 | } | 158 | } |
| 160 | 159 | ||
| 161 | void gru_motion(struct grail *ge, | 160 | void gru_motion(struct grail *ge, |
| 162 | const struct touch_frame *frame) | 161 | const struct utouch_frame *frame) |
| 163 | { | 162 | { |
| 164 | struct gesture_recognizer *gru = ge->gru; | 163 | struct gesture_recognizer *gru = ge->gru; |
| 165 | struct move_model *m = &gru->move; | 164 | struct move_model *m = &gru->move; |
| 166 | grail_time_t t = frame->time; | 165 | grail_time_t t = frame->time; |
| 167 | float x, y, r, a; | 166 | float x, y, r, a; |
| 167 | |||
| 168 | compute_position(&x, &y, frame); | 168 | compute_position(&x, &y, frame); |
| 169 | if (frame->ncreate || frame->ndestroy) { | 169 | if (frame->prev->revision != frame->revision) { |
| 170 | r = compute_radius(x, y, frame); | 170 | r = compute_radius(x, y, frame); |
| 171 | a = 0; | 171 | a = 0; |
| 172 | move_reset(m, FM_X, x, t); | 172 | move_reset(m, FM_X, x, t); |
| @@ -175,7 +175,7 @@ void gru_motion(struct grail *ge, | |||
| 175 | move_reset(m, FM_A, a, t); | 175 | move_reset(m, FM_A, a, t); |
| 176 | m->single = 0; | 176 | m->single = 0; |
| 177 | m->multi = 0; | 177 | m->multi = 0; |
| 178 | } else if (frame->nactive < 2) { | 178 | } else if (frame->num_active < 2) { |
| 179 | r = 0; | 179 | r = 0; |
| 180 | a = 0; | 180 | a = 0; |
| 181 | move_update(m, FM_X, x, t); | 181 | move_update(m, FM_X, x, t); |
| @@ -190,7 +190,7 @@ void gru_motion(struct grail *ge, | |||
| 190 | r = compute_radius(x, y, frame); | 190 | r = compute_radius(x, y, frame); |
| 191 | r = move_filter(&m->fm[FM_R], r); | 191 | r = move_filter(&m->fm[FM_R], r); |
| 192 | a = m->fm[FM_A].value; | 192 | a = m->fm[FM_A].value; |
| 193 | a += compute_rotation(x, y, r, &gru->frame, frame); | 193 | a += compute_rotation(x, y, r, frame); |
| 194 | a = move_filter(&m->fm[FM_A], a); | 194 | a = move_filter(&m->fm[FM_A], a); |
| 195 | move_update(m, FM_X, x, t); | 195 | move_update(m, FM_X, x, t); |
| 196 | move_update(m, FM_Y, y, t); | 196 | move_update(m, FM_Y, y, t); |
| @@ -199,7 +199,7 @@ void gru_motion(struct grail *ge, | |||
| 199 | m->single = 0; | 199 | m->single = 0; |
| 200 | m->multi = 1; | 200 | m->multi = 1; |
| 201 | } | 201 | } |
| 202 | m->ntouch = frame->nactive; | 202 | m->ntouch = frame->num_active; |
| 203 | m->time = t; | 203 | m->time = t; |
| 204 | } | 204 | } |
| 205 | 205 | ||
diff --git a/src/grail-gestures.h b/src/grail-gestures.h index 27108e9..69dd7e4 100644 --- a/src/grail-gestures.h +++ b/src/grail-gestures.h | |||
| @@ -61,7 +61,7 @@ struct move_model { | |||
| 61 | 61 | ||
| 62 | void gru_init_motion(struct grail *ge); | 62 | void gru_init_motion(struct grail *ge); |
| 63 | void gru_motion(struct grail *ge, | 63 | void gru_motion(struct grail *ge, |
| 64 | const struct touch_frame *frame); | 64 | const struct utouch_frame *frame); |
| 65 | void gru_event(struct grail *ge, int gid, | 65 | void gru_event(struct grail *ge, int gid, |
| 66 | const struct move_model *move, | 66 | const struct move_model *move, |
| 67 | const grail_prop_t *prop, int nprop); | 67 | const grail_prop_t *prop, int nprop); |
| @@ -77,11 +77,11 @@ struct combo_model { | |||
| 77 | }; | 77 | }; |
| 78 | 78 | ||
| 79 | int gru_drag(struct grail *ge, | 79 | int gru_drag(struct grail *ge, |
| 80 | const struct touch_frame *frame); | 80 | const struct utouch_frame *frame); |
| 81 | int gru_pinch(struct grail *ge, | 81 | int gru_pinch(struct grail *ge, |
| 82 | const struct touch_frame *frame); | 82 | const struct utouch_frame *frame); |
| 83 | int gru_rotate(struct grail *ge, | 83 | int gru_rotate(struct grail *ge, |
| 84 | const struct touch_frame *frame); | 84 | const struct utouch_frame *frame); |
| 85 | 85 | ||
| 86 | static inline int out_of_bounds(const struct combo_model *s, | 86 | static inline int out_of_bounds(const struct combo_model *s, |
| 87 | const struct move_model *m) | 87 | const struct move_model *m) |
| @@ -90,11 +90,11 @@ static inline int out_of_bounds(const struct combo_model *s, | |||
| 90 | } | 90 | } |
| 91 | 91 | ||
| 92 | int gru_windrag(struct grail *ge, | 92 | int gru_windrag(struct grail *ge, |
| 93 | const struct touch_frame *frame); | 93 | const struct utouch_frame *frame); |
| 94 | int gru_winpinch(struct grail *ge, | 94 | int gru_winpinch(struct grail *ge, |
| 95 | const struct touch_frame *frame); | 95 | const struct utouch_frame *frame); |
| 96 | int gru_winrotate(struct grail *ge, | 96 | int gru_winrotate(struct grail *ge, |
| 97 | const struct touch_frame *frame); | 97 | const struct utouch_frame *frame); |
| 98 | 98 | ||
| 99 | struct tapping_model { | 99 | struct tapping_model { |
| 100 | grail_time_t start, end; | 100 | grail_time_t start, end; |
| @@ -105,7 +105,7 @@ struct tapping_model { | |||
| 105 | }; | 105 | }; |
| 106 | 106 | ||
| 107 | int gru_tapping(struct grail *ge, | 107 | int gru_tapping(struct grail *ge, |
| 108 | const struct touch_frame *frame); | 108 | const struct utouch_frame *frame); |
| 109 | 109 | ||
| 110 | #endif | 110 | #endif |
| 111 | 111 | ||
diff --git a/src/grail-impl.h b/src/grail-impl.h index 2859186..dcbaedd 100644 --- a/src/grail-impl.h +++ b/src/grail-impl.h | |||
| @@ -23,15 +23,26 @@ | |||
| 23 | #ifndef _GRAIL_IMPL_H | 23 | #ifndef _GRAIL_IMPL_H |
| 24 | #define _GRAIL_IMPL_H | 24 | #define _GRAIL_IMPL_H |
| 25 | 25 | ||
| 26 | #include <grail-touch.h> | 26 | #define MTDEV_NO_LEGACY_API |
| 27 | #define GRAIL_NO_LEGACY_API | ||
| 28 | |||
| 29 | #include <grail.h> | ||
| 30 | #include <utouch/frame-mtdev.h> | ||
| 27 | #include "evbuf.h" | 31 | #include "evbuf.h" |
| 28 | #include "grailbuf.h" | 32 | #include "grailbuf.h" |
| 29 | 33 | ||
| 34 | #define DIM_TOUCH 32 | ||
| 35 | #define DIM_TOUCH_BYTES ((DIM_TOUCH + 7) >> 3) | ||
| 36 | |||
| 30 | struct grail_impl { | 37 | struct grail_impl { |
| 31 | struct touch_dev dev; | 38 | struct evemu_device *evemu; |
| 32 | struct touch_caps emu; | 39 | struct mtdev *mtdev; |
| 40 | utouch_frame_handle fh; | ||
| 41 | const struct utouch_frame *frame; | ||
| 33 | struct evbuf evbuf; | 42 | struct evbuf evbuf; |
| 34 | struct grailbuf gbuf; | 43 | struct grailbuf gbuf; |
| 44 | float emin_x, emin_y; | ||
| 45 | float emax_x, emax_y; | ||
| 35 | int filter_abs; | 46 | int filter_abs; |
| 36 | int pointer_status; | 47 | int pointer_status; |
| 37 | int pointer_x, pointer_y; | 48 | int pointer_x, pointer_y; |
diff --git a/src/grail-inserter.c b/src/grail-inserter.c index 847995a..6f9a034 100644 --- a/src/grail-inserter.c +++ b/src/grail-inserter.c | |||
| @@ -40,7 +40,7 @@ static int find_gslot(const struct gesture_inserter *gin, int gid) | |||
| 40 | 40 | ||
| 41 | // todo: spanning tree for multi-user case | 41 | // todo: spanning tree for multi-user case |
| 42 | static void setup_new_gestures(struct grail *ge, | 42 | static void setup_new_gestures(struct grail *ge, |
| 43 | const struct touch_frame *frame) | 43 | const struct utouch_frame *frame) |
| 44 | { | 44 | { |
| 45 | struct gesture_inserter *gin = ge->gin; | 45 | struct gesture_inserter *gin = ge->gin; |
| 46 | grail_mask_t types[DIM_GRAIL_TYPE_BYTES]; | 46 | grail_mask_t types[DIM_GRAIL_TYPE_BYTES]; |
| @@ -100,14 +100,14 @@ void gin_destroy(struct grail *ge) | |||
| 100 | ge->gin = NULL; | 100 | ge->gin = NULL; |
| 101 | } | 101 | } |
| 102 | 102 | ||
| 103 | void gin_frame_begin(struct grail *ge, const struct touch_frame *frame) | 103 | void gin_frame_begin(struct grail *ge, const struct utouch_frame *frame) |
| 104 | { | 104 | { |
| 105 | struct gesture_inserter *gin = ge->gin; | 105 | struct gesture_inserter *gin = ge->gin; |
| 106 | memset(gin->types, 0, sizeof(gin->types)); | 106 | memset(gin->types, 0, sizeof(gin->types)); |
| 107 | gin->time = frame->time; | 107 | gin->time = frame->time; |
| 108 | } | 108 | } |
| 109 | 109 | ||
| 110 | void gin_frame_end(struct grail *ge, const struct touch_frame *frame) | 110 | void gin_frame_end(struct grail *ge, const struct utouch_frame *frame) |
| 111 | { | 111 | { |
| 112 | struct gesture_inserter *gin = ge->gin; | 112 | struct gesture_inserter *gin = ge->gin; |
| 113 | int i, hold = 0, discard = 0; | 113 | int i, hold = 0, discard = 0; |
| @@ -151,11 +151,12 @@ void gin_frame_end(struct grail *ge, const struct touch_frame *frame) | |||
| 151 | } | 151 | } |
| 152 | } | 152 | } |
| 153 | 153 | ||
| 154 | int gin_gid_begin_select(struct grail *ge, int type, int priority, | 154 | int gin_gid_begin(struct grail *ge, int type, int priority, |
| 155 | const grail_mask_t *span, int nspan) | 155 | const struct utouch_frame *frame) |
| 156 | { | 156 | { |
| 157 | struct gesture_inserter *gin = ge->gin; | 157 | struct gesture_inserter *gin = ge->gin; |
| 158 | struct slot_state *s; | 158 | struct slot_state *s; |
| 159 | int slot; | ||
| 159 | int i = grail_mask_get_first(gin->unused, sizeof(gin->unused)); | 160 | int i = grail_mask_get_first(gin->unused, sizeof(gin->unused)); |
| 160 | if (i < 0) | 161 | if (i < 0) |
| 161 | return -1; | 162 | return -1; |
| @@ -165,7 +166,8 @@ int gin_gid_begin_select(struct grail *ge, int type, int priority, | |||
| 165 | s->id = gin->gestureid++ & MAX_GESTURE_ID; | 166 | s->id = gin->gestureid++ & MAX_GESTURE_ID; |
| 166 | s->status = GRAIL_STATUS_BEGIN; | 167 | s->status = GRAIL_STATUS_BEGIN; |
| 167 | s->nclient = 0; | 168 | s->nclient = 0; |
| 168 | memcpy(s->span, span, nspan); | 169 | for (slot = 0; slot < DIM_TOUCH; slot++) |
| 170 | grail_mask_modify(s->span, slot, frame->slots[slot]->active); | ||
| 169 | gebuf_clear(&s->buf); | 171 | gebuf_clear(&s->buf); |
| 170 | grail_mask_clear(gin->unused, i); | 172 | grail_mask_clear(gin->unused, i); |
| 171 | grail_mask_set(gin->fresh, i); | 173 | grail_mask_set(gin->fresh, i); |
| @@ -173,13 +175,6 @@ int gin_gid_begin_select(struct grail *ge, int type, int priority, | |||
| 173 | return s->id; | 175 | return s->id; |
| 174 | } | 176 | } |
| 175 | 177 | ||
| 176 | int gin_gid_begin(struct grail *ge, int type, int priority, | ||
| 177 | const struct touch_frame *frame) | ||
| 178 | { | ||
| 179 | return gin_gid_begin_select(ge, type, priority, | ||
| 180 | frame->touches, sizeof(frame->touches)); | ||
| 181 | } | ||
| 182 | |||
| 183 | void gin_gid_discard(struct grail *ge, int gid) | 178 | void gin_gid_discard(struct grail *ge, int gid) |
| 184 | { | 179 | { |
| 185 | struct gesture_inserter *gin = ge->gin; | 180 | struct gesture_inserter *gin = ge->gin; |
| @@ -248,18 +243,18 @@ void grail_set_bbox(struct grail *ge, | |||
| 248 | const struct grail_coord *tmin, | 243 | const struct grail_coord *tmin, |
| 249 | const struct grail_coord *tmax) | 244 | const struct grail_coord *tmax) |
| 250 | { | 245 | { |
| 251 | struct touch_caps *caps = &ge->impl->dev.caps; | 246 | struct utouch_surface *s = utouch_frame_get_surface(ge->impl->fh); |
| 252 | struct gesture_inserter *gin = ge->gin; | 247 | struct gesture_inserter *gin = ge->gin; |
| 253 | double tx, ty, dx, dy, sx, sy; | 248 | double tx, ty, dx, dy, sx, sy; |
| 254 | tx = tmax->x - tmin->x; | 249 | tx = tmax->x - tmin->x; |
| 255 | ty = tmax->y - tmin->y; | 250 | ty = tmax->y - tmin->y; |
| 256 | dx = caps->max_x - caps->min_x; | 251 | dx = s->max_x - s->min_x; |
| 257 | dy = caps->max_y - caps->min_y; | 252 | dy = s->max_y - s->min_y; |
| 258 | sx = tx / dx; | 253 | sx = tx / dx; |
| 259 | sy = ty / dy; | 254 | sy = ty / dy; |
| 260 | gin->scale_x = sx; | 255 | gin->scale_x = sx; |
| 261 | gin->scale_y = sy; | 256 | gin->scale_y = sy; |
| 262 | gin->scale_r = sqrt((tx * tx + ty * ty) / (dx * dx + dy * dy)); | 257 | gin->scale_r = sqrt((tx * tx + ty * ty) / (dx * dx + dy * dy)); |
| 263 | gin->trans_x = tmin->x - caps->min_x * sx; | 258 | gin->trans_x = tmin->x - s->min_x * sx; |
| 264 | gin->trans_y = tmin->y - caps->min_y * sy; | 259 | gin->trans_y = tmin->y - s->min_y * sy; |
| 265 | } | 260 | } |
diff --git a/src/grail-inserter.h b/src/grail-inserter.h index 9baecb7..3b8cd77 100644 --- a/src/grail-inserter.h +++ b/src/grail-inserter.h | |||
| @@ -23,8 +23,7 @@ | |||
| 23 | #ifndef _GRAIL_INSERTER_H | 23 | #ifndef _GRAIL_INSERTER_H |
| 24 | #define _GRAIL_INSERTER_H | 24 | #define _GRAIL_INSERTER_H |
| 25 | 25 | ||
| 26 | #include <grail-touch.h> | 26 | #include "grail-impl.h" |
| 27 | #include <grail.h> | ||
| 28 | #include "gebuf.h" | 27 | #include "gebuf.h" |
| 29 | 28 | ||
| 30 | #define DIM_EV_TYPE EV_CNT | 29 | #define DIM_EV_TYPE EV_CNT |
| @@ -69,27 +68,25 @@ static inline float gin_prop_y(const struct gesture_inserter *gin, float y) | |||
| 69 | } | 68 | } |
| 70 | 69 | ||
| 71 | int gin_add_contact_props(const struct gesture_inserter *gin, | 70 | int gin_add_contact_props(const struct gesture_inserter *gin, |
| 72 | grail_prop_t *prop, const struct touch_frame *frame); | 71 | grail_prop_t *prop, const struct utouch_frame *frame); |
| 73 | 72 | ||
| 74 | int gin_get_clients(struct grail *ge, | 73 | int gin_get_clients(struct grail *ge, |
| 75 | struct grail_client_info *info, int maxinfo, | 74 | struct grail_client_info *info, int maxinfo, |
| 76 | const grail_mask_t* types, int btypes, | 75 | const grail_mask_t* types, int btypes, |
| 77 | const grail_mask_t* span, int bspan, | 76 | const grail_mask_t* span, int bspan, |
| 78 | const struct touch_frame *frame); | 77 | const struct utouch_frame *frame); |
| 79 | void gin_send_event(struct grail *ge, struct slot_state *s, | 78 | void gin_send_event(struct grail *ge, struct slot_state *s, |
| 80 | const struct gesture_event *ev, | 79 | const struct gesture_event *ev, |
| 81 | const struct touch_frame *frame); | 80 | const struct utouch_frame *frame); |
| 82 | 81 | ||
| 83 | int gin_init(struct grail *ge); | 82 | int gin_init(struct grail *ge); |
| 84 | void gin_destroy(struct grail *ge); | 83 | void gin_destroy(struct grail *ge); |
| 85 | 84 | ||
| 86 | void gin_frame_begin(struct grail *ge, const struct touch_frame *frame); | 85 | void gin_frame_begin(struct grail *ge, const struct utouch_frame *frame); |
| 87 | void gin_frame_end(struct grail *ge, const struct touch_frame *frame); | 86 | void gin_frame_end(struct grail *ge, const struct utouch_frame *frame); |
| 88 | 87 | ||
| 89 | int gin_gid_begin_select(struct grail *ge, int type, int priority, | ||
| 90 | const grail_mask_t *span, int nspan); | ||
| 91 | int gin_gid_begin(struct grail *ge, int type, int priority, | 88 | int gin_gid_begin(struct grail *ge, int type, int priority, |
| 92 | const struct touch_frame *frame); | 89 | const struct utouch_frame *frame); |
| 93 | void gin_gid_discard(struct grail *ge, int gid); | 90 | void gin_gid_discard(struct grail *ge, int gid); |
| 94 | 91 | ||
| 95 | void gin_gid_event(struct grail *ge, int gid, | 92 | void gin_gid_event(struct grail *ge, int gid, |
diff --git a/src/grail-recognizer.c b/src/grail-recognizer.c index 932f28a..fb0ae85 100644 --- a/src/grail-recognizer.c +++ b/src/grail-recognizer.c | |||
| @@ -42,7 +42,7 @@ void gru_destroy(struct grail *ge) | |||
| 42 | ge->gru = NULL; | 42 | ge->gru = NULL; |
| 43 | } | 43 | } |
| 44 | 44 | ||
| 45 | void gru_recognize(struct grail *ge, const struct touch_frame *frame) | 45 | void gru_recognize(struct grail *ge, const struct utouch_frame *frame) |
| 46 | { | 46 | { |
| 47 | if (!ge->gin || !ge->gru) | 47 | if (!ge->gin || !ge->gru) |
| 48 | return; | 48 | return; |
| @@ -54,5 +54,4 @@ void gru_recognize(struct grail *ge, const struct touch_frame *frame) | |||
| 54 | gru_winpinch(ge, frame); | 54 | gru_winpinch(ge, frame); |
| 55 | gru_winrotate(ge, frame); | 55 | gru_winrotate(ge, frame); |
| 56 | gru_tapping(ge, frame); | 56 | gru_tapping(ge, frame); |
| 57 | ge->gru->frame = *frame; | ||
| 58 | } | 57 | } |
diff --git a/src/grail-recognizer.h b/src/grail-recognizer.h index 1a9edd1..56e5b8d 100644 --- a/src/grail-recognizer.h +++ b/src/grail-recognizer.h | |||
| @@ -26,7 +26,6 @@ | |||
| 26 | #include "grail-gestures.h" | 26 | #include "grail-gestures.h" |
| 27 | 27 | ||
| 28 | struct gesture_recognizer { | 28 | struct gesture_recognizer { |
| 29 | struct touch_frame frame; | ||
| 30 | struct move_model move; | 29 | struct move_model move; |
| 31 | struct combo_model drag; | 30 | struct combo_model drag; |
| 32 | struct combo_model pinch; | 31 | struct combo_model pinch; |
| @@ -38,7 +37,7 @@ struct gesture_recognizer { | |||
| 38 | }; | 37 | }; |
| 39 | 38 | ||
| 40 | int gru_init(struct grail *ge); | 39 | int gru_init(struct grail *ge); |
| 41 | void gru_recognize(struct grail *ge, const struct touch_frame *frame); | 40 | void gru_recognize(struct grail *ge, const struct utouch_frame *frame); |
| 42 | void gru_destroy(struct grail *ge); | 41 | void gru_destroy(struct grail *ge); |
| 43 | 42 | ||
| 44 | #endif | 43 | #endif |
diff --git a/src/touch-caps.c b/src/touch-caps.c deleted file mode 100644 index f99b0d7..0000000 --- a/src/touch-caps.c +++ /dev/null | |||
| @@ -1,117 +0,0 @@ | |||
| 1 | /***************************************************************************** | ||
| 2 | * | ||
| 3 | * grail - Gesture Recognition And Instantiation Library | ||
| 4 | * | ||
| 5 | * Copyright (C) 2010 Canonical Ltd. | ||
| 6 | * Copyright (C) 2010 Henrik Rydberg <rydberg@bitmath.org> | ||
| 7 | * | ||
| 8 | * This program is free software: you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation, either version 3 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | * This program is distributed in the hope that it will be useful, but | ||
| 14 | * WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
| 16 | * General Public License for more details. | ||
| 17 | * | ||
| 18 | * You should have received a copy of the GNU General Public License along | ||
| 19 | * with this program. If not, see <http://www.gnu.org/licenses/>. | ||
| 20 | * | ||
| 21 | ****************************************************************************/ | ||
| 22 | |||
| 23 | #include <grail-touch.h> | ||
| 24 | #include <errno.h> | ||
| 25 | #include <math.h> | ||
| 26 | |||
| 27 | /* see mtdev-mapping.h */ | ||
| 28 | #define MTDEV_POSITION_X 5 | ||
| 29 | #define MTDEV_POSITION_Y 6 | ||
| 30 | #define MTDEV_ORIENTATION 4 | ||
| 31 | #define MTDEV_PRESSURE 10 | ||
| 32 | |||
| 33 | #define SYSCALL(call) while (((call) == -1) && (errno == EINTR)) | ||
| 34 | |||
| 35 | static const int bits_per_long = 8 * sizeof(long); | ||
| 36 | |||
| 37 | static inline int nlongs(int nbit) | ||
| 38 | { | ||
| 39 | return (nbit + bits_per_long - 1) / bits_per_long; | ||
| 40 | } | ||
| 41 | |||
| 42 | static inline int getbit(const unsigned long *map, int key) | ||
| 43 | { | ||
| 44 | return (map[key / bits_per_long] >> (key % bits_per_long)) & 0x01; | ||
| 45 | } | ||
| 46 | |||
| 47 | int touch_caps_is_supported(struct touch_dev *dev, int fd) | ||
| 48 | { | ||
| 49 | unsigned long keybits[nlongs(KEY_MAX)]; | ||
| 50 | unsigned long absbits[nlongs(ABS_MAX)]; | ||
| 51 | unsigned long relbits[nlongs(REL_CNT)]; | ||
| 52 | int rc; | ||
| 53 | |||
| 54 | SYSCALL(rc = ioctl(fd, EVIOCGBIT(EV_KEY, sizeof(keybits)), keybits)); | ||
| 55 | if (rc < 0) | ||
| 56 | return 0; | ||
| 57 | SYSCALL(rc = ioctl(fd, EVIOCGBIT(EV_ABS, sizeof(absbits)), absbits)); | ||
| 58 | if (rc < 0) | ||
| 59 | return 0; | ||
| 60 | SYSCALL(rc = ioctl(fd, EVIOCGBIT(EV_REL, sizeof(relbits)), relbits)); | ||
| 61 | if (rc < 0) | ||
| 62 | return 0; | ||
| 63 | |||
| 64 | /* only support pure absolute devices at this time */ | ||
| 65 | if (getbit(relbits, REL_X) || getbit(relbits, REL_Y)) | ||
| 66 | return 0; | ||
| 67 | |||
| 68 | if (dev->mtdev.caps.has_mtdata) | ||
| 69 | return 1; | ||
| 70 | |||
| 71 | return getbit(absbits, ABS_X) && | ||
| 72 | getbit(absbits, ABS_Y) && | ||
| 73 | getbit(keybits, BTN_TOUCH) && | ||
| 74 | getbit(keybits, BTN_TOOL_DOUBLETAP); | ||
| 75 | } | ||
| 76 | |||
| 77 | void touch_caps_init(struct touch_dev *dev) | ||
| 78 | { | ||
| 79 | const struct mtdev_caps *mt = &dev->mtdev.caps; | ||
| 80 | struct touch_caps *caps = &dev->caps; | ||
| 81 | caps->min_x = mt->abs[MTDEV_POSITION_X].minimum; | ||
| 82 | caps->max_x = mt->abs[MTDEV_POSITION_X].maximum; | ||
| 83 | caps->min_y = mt->abs[MTDEV_POSITION_Y].minimum; | ||
| 84 | caps->max_y = mt->abs[MTDEV_POSITION_Y].maximum; | ||
| 85 | caps->min_orient = mt->abs[MTDEV_ORIENTATION].minimum; | ||
| 86 | caps->max_orient = mt->abs[MTDEV_ORIENTATION].maximum; | ||
| 87 | caps->min_press = mt->abs[MTDEV_PRESSURE].minimum; | ||
| 88 | caps->max_press = mt->abs[MTDEV_PRESSURE].maximum; | ||
| 89 | if (caps->min_x == caps->max_x) { | ||
| 90 | caps->min_x = 0; | ||
| 91 | caps->max_x = 1024; | ||
| 92 | } | ||
| 93 | if (caps->min_y == caps->max_y) { | ||
| 94 | caps->min_y = 0; | ||
| 95 | caps->max_y = 768; | ||
| 96 | } | ||
| 97 | if (caps->min_orient == caps->max_orient) | ||
| 98 | caps->max_orient = 1; | ||
| 99 | if (caps->min_orient + caps->max_orient != 0) | ||
| 100 | caps->min_orient = -caps->max_orient; | ||
| 101 | if (caps->min_press == caps->max_press) { | ||
| 102 | caps->min_press = 0; | ||
| 103 | caps->max_press = 256; | ||
| 104 | } | ||
| 105 | } | ||
| 106 | |||
| 107 | float touch_angle(const struct touch_dev *dev, int orient) | ||
| 108 | { | ||
| 109 | const struct touch_caps *caps = &dev->caps; | ||
| 110 | return orient / caps->max_orient * M_PI_2; | ||
| 111 | } | ||
| 112 | |||
| 113 | float touch_pressure(const struct touch_dev *dev, int press) | ||
| 114 | { | ||
| 115 | const struct touch_caps *caps = &dev->caps; | ||
| 116 | return (press - caps->min_press) / (caps->max_press - caps->min_press); | ||
| 117 | } | ||
diff --git a/src/touch-dev.c b/src/touch-dev.c deleted file mode 100644 index d8e192e..0000000 --- a/src/touch-dev.c +++ /dev/null | |||
| @@ -1,264 +0,0 @@ | |||
| 1 | /***************************************************************************** | ||
| 2 | * | ||
| 3 | * grail - Gesture Recognition And Instantiation Library | ||
| 4 | * | ||
| 5 | * Copyright (C) 2010 Canonical Ltd. | ||
| 6 | * Copyright (C) 2010 Henrik Rydberg <rydberg@bitmath.org> | ||
| 7 | * | ||
| 8 | * This program is free software: you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation, either version 3 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | * | ||
| 13 | * This program is distributed in the hope that it will be useful, but | ||
| 14 | * WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
| 16 | * General Public License for more details. | ||
| 17 | * | ||
| 18 | * You should have received a copy of the GNU General Public License along | ||
| 19 | * with this program. If not, see <http://www.gnu.org/licenses/>. | ||
| 20 | * | ||
| 21 | ****************************************************************************/ | ||
| 22 | |||
| 23 | #include <grail-touch.h> | ||
| 24 | #include <malloc.h> | ||
| 25 | #include <string.h> | ||
| 26 | #include <errno.h> | ||
| 27 | |||
| 28 | /* see mtdev-mapping.h */ | ||
| 29 | #define MTDEV_TOUCH_MINOR 1 | ||
| 30 | |||
| 31 | #define SET_PROP(name, value) \ | ||
| 32 | if (t->name != value) { \ | ||
| 33 | t->name = value; \ | ||
| 34 | frame->nmodify++; \ | ||
| 35 | } | ||
| 36 | |||
| 37 | static void finish_touch(struct touch_dev *dev, struct touch_frame *frame) | ||
| 38 | { | ||
| 39 | struct touch *t = &frame->touch[dev->slot]; | ||
| 40 | if (t->touch_major && !t->touch_minor || | ||
| 41 | !dev->mtdev.caps.has_abs[MTDEV_TOUCH_MINOR]) | ||
| 42 | SET_PROP(touch_minor, t->touch_major); | ||
| 43 | if (dev->state > 0) { | ||
| 44 | t->active = 1; | ||
| 45 | grail_mask_set(frame->touches, dev->slot); | ||
| 46 | frame->ncreate++; | ||
| 47 | } | ||
| 48 | if (dev->state < 0) { | ||
| 49 | t->active = 0; | ||
| 50 | grail_mask_clear(frame->touches, dev->slot); | ||
| 51 | frame->ndestroy++; | ||
| 52 | } | ||
| 53 | dev->state = 0; | ||
| 54 | } | ||
| 55 | |||
| 56 | static void finish_legacy(struct touch_dev *dev, struct touch_frame *frame) | ||
| 57 | { | ||
| 58 | static int trkid; | ||
| 59 | int i; | ||
| 60 | for (i = 0; i < frame->nactive; i++) { | ||
| 61 | struct touch *t = &frame->touch[i]; | ||
| 62 | t->active = 1; | ||
| 63 | if (t->id < 0) { | ||
| 64 | t->id = trkid++ & 0xffff; | ||
| 65 | frame->ncreate++; | ||
| 66 | } | ||
| 67 | if (i > 0) { | ||
| 68 | SET_PROP(x, frame->touch[0].x); | ||
| 69 | SET_PROP(y, frame->touch[0].y); | ||
| 70 | SET_PROP(pressure, frame->touch[0].pressure); | ||
| 71 | } | ||
| 72 | grail_mask_set(frame->touches, i); | ||
| 73 | } | ||
| 74 | for (i = frame->nactive; i < DIM_TOUCH; i++) { | ||
| 75 | struct touch *t = &frame->touch[i]; | ||
| 76 | t->active = 0; | ||
| 77 | if (t->id >= 0) { | ||
| 78 | t->id = -1; | ||
| 79 | frame->ndestroy++; | ||
| 80 | } | ||
| 81 | grail_mask_clear(frame->touches, i); | ||
| 82 | } | ||
| 83 | } | ||
| 84 | |||
| 85 | static void finish_packet(struct touch_dev *dev, | ||
| 86 | const struct input_event *syn) | ||
| 87 | { | ||
| 88 | static const touch_time_t ms = 1000; | ||
| 89 | struct touch_frame *frame = &dev->frame; | ||
| 90 | int i, nslot = 0; | ||
| 91 | if (dev->mtdev.caps.has_mtdata) | ||
| 92 | finish_touch(dev, frame); | ||
| 93 | else | ||
| 94 | finish_legacy(dev, frame); | ||
| 95 | grail_mask_foreach(i, frame->touches, DIM_TOUCH_BYTES) | ||
| 96 | frame->active[nslot++] = &frame->touch[i]; | ||
| 97 | frame->nactive = nslot; | ||
| 98 | frame->time = syn->time.tv_usec / ms + syn->time.tv_sec * ms; | ||
| 99 | if (dev->sync) | ||
| 100 | dev->sync(dev, syn); | ||
| 101 | frame->ncreate = 0; | ||
| 102 | frame->nmodify = 0; | ||
| 103 | frame->ndestroy = 0; | ||
| 104 | } | ||
| 105 | |||
| 106 | static int handle_abs_event(struct touch_dev *dev, | ||
| 107 | const struct input_event *ev) | ||
| 108 | { | ||
| 109 | struct touch_frame *frame = &dev->frame; | ||
| 110 | struct touch *t = &frame->touch[dev->slot]; | ||
| 111 | switch (ev->code) { | ||
| 112 | case ABS_X: | ||
| 113 | if (dev->mtdev.caps.has_mtdata) | ||
| 114 | return 0; | ||
| 115 | SET_PROP(x, ev->value); | ||
| 116 | return 0; | ||
| 117 | case ABS_Y: | ||
| 118 | if (dev->mtdev.caps.has_mtdata) | ||
| 119 | return 0; | ||
| 120 | SET_PROP(y, ev->value); | ||
| 121 | return 0; | ||
| 122 | case ABS_PRESSURE: | ||
| 123 | if (dev->mtdev.caps.has_mtdata) | ||
| 124 | return 0; | ||
| 125 | SET_PROP(pressure, ev->value); | ||
| 126 | return 0; | ||
| 127 | case ABS_MT_SLOT: | ||
| 128 | if (ev->value >= 0 && ev->value < DIM_TOUCH) { | ||
| 129 | if (dev->slot != ev->value) | ||
| 130 | finish_touch(dev, frame); | ||
| 131 | dev->slot = ev->value; | ||
| 132 | t = &frame->touch[dev->slot]; | ||
| 133 | } | ||
| 134 | return 1; | ||
| 135 | case ABS_MT_POSITION_X: | ||
| 136 | SET_PROP(x, ev->value); | ||
| 137 | return 1; | ||
| 138 | case ABS_MT_POSITION_Y: | ||
| 139 | SET_PROP(y, ev->value); | ||
| 140 | return 1; | ||
| 141 | case ABS_MT_TOUCH_MAJOR: | ||
| 142 | SET_PROP(touch_major, ev->value); | ||
| 143 | return 1; | ||
| 144 | case ABS_MT_TOUCH_MINOR: | ||
| 145 | SET_PROP(touch_minor, ev->value); | ||
| 146 | return 1; | ||
| 147 | case ABS_MT_WIDTH_MAJOR: | ||
| 148 | SET_PROP(width_major, ev->value); | ||
| 149 | return 1; | ||
| 150 | case ABS_MT_WIDTH_MINOR: | ||
| 151 | SET_PROP(width_minor, ev->value); | ||
| 152 | return 1; | ||
| 153 | case ABS_MT_ORIENTATION: | ||
| 154 | SET_PROP(orientation, ev->value); | ||
| 155 | return 1; | ||
| 156 | case ABS_MT_PRESSURE: | ||
| 157 | SET_PROP(pressure, ev->value); | ||
| 158 | return 1; | ||
| 159 | case ABS_MT_TOOL_TYPE: | ||
| 160 | SET_PROP(tool_type, ev->value); | ||
| 161 | return 1; | ||
| 162 | case ABS_MT_TRACKING_ID: | ||
| 163 | if (t->id != ev->value) { | ||
| 164 | if (t->id != MT_ID_NULL) { | ||
| 165 | dev->state = -1; | ||
| 166 | finish_touch(dev, frame); | ||
| 167 | } | ||
| 168 | if (ev->value != MT_ID_NULL) | ||
| 169 | dev->state = 1; | ||
| 170 | t->id = ev->value; | ||
| 171 | } | ||
| 172 | return 1; | ||
| 173 | default: | ||
| 174 | return 0; | ||
| 175 | } | ||
| 176 | } | ||
| 177 | |||
| 178 | static int handle_key_event(struct touch_dev *dev, | ||
| 179 | const struct input_event *ev) | ||
| 180 | { | ||
| 181 | struct touch_frame *frame = &dev->frame; | ||
| 182 | if (dev->mtdev.caps.has_mtdata) | ||
| 183 | return 0; | ||
| 184 | switch (ev->code) { | ||
| 185 | case BTN_TOUCH: | ||
| 186 | if (ev->value && !frame->nactive) | ||
| 187 | frame->nactive = 1; | ||
| 188 | else if (!ev->value && frame->nactive) | ||
| 189 | frame->nactive = 0; | ||
| 190 | return 0; | ||
| 191 | case BTN_TOOL_FINGER: | ||
| 192 | if (ev->value) | ||
| 193 | frame->nactive = 1; | ||
| 194 | return 0; | ||
| 195 | case BTN_TOOL_DOUBLETAP: | ||
| 196 | if (ev->value) | ||
| 197 | frame->nactive = 2; | ||
| 198 | return 0; | ||
| 199 | case BTN_TOOL_TRIPLETAP: | ||
| 200 | if (ev->value) | ||
| 201 | frame->nactive = 3; | ||
| 202 | return 0; | ||
| 203 | case BTN_TOOL_QUADTAP: | ||
| 204 | if (ev->value) | ||
| 205 | frame->nactive = 4; | ||
| 206 | return 0; | ||
| 207 | default: | ||
| 208 | return 0; | ||
| 209 | } | ||
| 210 | } | ||
| 211 | |||
| 212 | int touch_dev_open(struct touch_dev *dev, int fd) | ||
| 213 | { | ||
| 214 | struct touch_frame *frame = &dev->frame; | ||
| 215 | int ret, i; | ||
| 216 | memset(dev, 0, sizeof(*dev)); | ||
| 217 | for (i = 0; i < DIM_TOUCH; i++) { | ||
| 218 | struct touch *t = &frame->touch[i]; | ||
| 219 | t->slot = i; | ||
| 220 | t->id = MT_ID_NULL; | ||
| 221 | } | ||
| 222 | ret = mtdev_open(&dev->mtdev, fd); | ||
| 223 | if (!ret && !touch_caps_is_supported(dev, fd)) | ||
| 224 | ret = -ENODEV; | ||
| 225 | if (ret) | ||
| 226 | goto error; | ||
| 227 | touch_caps_init(dev); | ||
| 228 | return 0; | ||
| 229 | error: | ||
| 230 | return ret; | ||
| 231 | } | ||
| 232 | |||
| 233 | int touch_dev_idle(struct touch_dev *dev, int fd, int ms) | ||
| 234 | { | ||
| 235 | return mtdev_idle(&dev->mtdev, fd, ms); | ||
| 236 | } | ||
| 237 | |||
| 238 | int touch_dev_pull(struct touch_dev *dev, int fd) | ||
| 239 | { | ||
| 240 | struct input_event ev; | ||
| 241 | int ret, count = 0, consumed; | ||
| 242 | while ((ret = mtdev_get(&dev->mtdev, fd, &ev, 1)) > 0) { | ||
| 243 | consumed = 0; | ||
| 244 | if (ev.type == EV_SYN) { | ||
| 245 | if (ev.code == SYN_REPORT) | ||
| 246 | finish_packet(dev, &ev); | ||
| 247 | consumed++; | ||
| 248 | } else if (ev.type == EV_ABS) { | ||
| 249 | consumed += handle_abs_event(dev, &ev); | ||
| 250 | } else if (ev.type == EV_KEY) { | ||
| 251 | consumed += handle_key_event(dev, &ev); | ||
| 252 | } | ||
| 253 | if (!consumed && dev->event) | ||
| 254 | dev->event(dev, &ev); | ||
| 255 | count++; | ||
| 256 | } | ||
| 257 | return count > 0 ? count : ret; | ||
| 258 | } | ||
| 259 | |||
| 260 | void touch_dev_close(struct touch_dev *dev, int fd) | ||
| 261 | { | ||
| 262 | mtdev_close(&dev->mtdev); | ||
| 263 | memset(dev, 0, sizeof(*dev)); | ||
| 264 | } | ||
diff --git a/tools/Makefile.am b/tools/Makefile.am index ae6866c..303f70d 100644 --- a/tools/Makefile.am +++ b/tools/Makefile.am | |||
| @@ -4,4 +4,4 @@ INCLUDES=-I$(top_srcdir)/include/ | |||
| 4 | 4 | ||
| 5 | grail_gesture_SOURCES = grail-gesture.c | 5 | grail_gesture_SOURCES = grail-gesture.c |
| 6 | grail_gesture_LDFLAGS = -L$(top_builddir)/src/.libs/ \ | 6 | grail_gesture_LDFLAGS = -L$(top_builddir)/src/.libs/ \ |
| 7 | -lutouch-grail -lmtdev -lm | 7 | -lutouch-grail -lutouch-frame -lutouch-evemu -lmtdev -lm |
