From cc876e03486f060bd89c41d78a678261f91f871f Mon Sep 17 00:00:00 2001 From: Henrik Rydberg Date: Tue, 29 Mar 2011 10:56:00 +0200 Subject: Introduce test-mtdev A new tool (test-mtdev) is added, showing the usage of gesture frames. Signed-off-by: Henrik Rydberg --- tools/grail-test-mtdev.c | 259 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 259 insertions(+) create mode 100644 tools/grail-test-mtdev.c (limited to 'tools/grail-test-mtdev.c') diff --git a/tools/grail-test-mtdev.c b/tools/grail-test-mtdev.c new file mode 100644 index 0000000..bc87631 --- /dev/null +++ b/tools/grail-test-mtdev.c @@ -0,0 +1,259 @@ +/***************************************************************************** + * + * grail - Gesture Recognition And Instantiation Library + * + * Copyright (C) 2010-2011 Canonical Ltd. + * + * This program is free software: you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation, either version 3 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see . + * + * Authors: + * Henrik Rydberg + * + ****************************************************************************/ + +#define MTDEV_NO_LEGACY_API + +#include +#include +#include +#include +#include +#include +#include + +struct frame_test { + struct evemu_device *evemu; + struct mtdev *mtdev; + utouch_frame_handle fh; + grail_handle ge; +}; + +static int init_evemu(struct frame_test *test, FILE *fp, int fd) +{ + test->evemu = evemu_new(NULL); + if (!test->evemu) + return -1; + if (fp) + return evemu_read(test->evemu, fp) <= 0; + else + return evemu_extract(test->evemu, fd); +} + +static int init_mtdev(struct frame_test *test, int fd) +{ + test->mtdev = mtdev_new_open(fd); + if (!test->mtdev) + return -1; + return 0; +} + +static int init_frame(struct frame_test *test, int fd) +{ + test->fh = utouch_frame_new_engine(100, 32, 100); + if (!test->fh) + return -1; + return utouch_frame_init_mtdev(test->fh, test->evemu); +} + +static int init_grail(struct frame_test *test) +{ + struct grail_coord min = { 0, 0 }; + struct grail_coord max = { 1, 1 }; + test->ge = grail_new(test->fh, 10, 0); + if (!test->ge) + return -1; + grail_set_bbox(test->ge, &min, &max); + return 0; +} + +static void destroy_all(struct frame_test *test) +{ + grail_delete(test->ge); + utouch_frame_delete_engine(test->fh); + if (test->mtdev) + mtdev_close_delete(test->mtdev); + evemu_delete(test->evemu); + memset(test, 0, sizeof(*test)); +} + +static void report_frame(grail_handle ge, + const struct utouch_frame *touch) +{ + const struct grail_frame *frame = grail_pump_frame(ge, touch); + int i; + + if (!frame) + return; + + fprintf(stderr, "ongoing elements: %d\n", frame->num_ongoing); + + for (i = 0; i < frame->num_ongoing; i++) { + const struct grail_element *slot = frame->ongoing[i]; + if (!slot->expect_mask) + continue; + + fprintf(stderr, " element %d\n", i); + fprintf(stderr, " slot: %d\n", slot->slot); + fprintf(stderr, " id: %d\n", slot->id); + fprintf(stderr, " num_touches: %d\n", slot->num_touches); + fprintf(stderr, " expect: %d\n", slot->expect_mask); + fprintf(stderr, " active: %d\n", slot->active_mask); + fprintf(stderr, " start time: %ld\n", slot->start_time); + fprintf(stderr, " center.x: %f\n", slot->center.x); + fprintf(stderr, " center.y: %f\n", slot->center.y); + fprintf(stderr, " velocity.x: %f\n", slot->velocity.x); + fprintf(stderr, " velocity.y: %f\n", slot->velocity.y); + fprintf(stderr, " radius2: %f\n", slot->radius2); + fprintf(stderr, " %+08f %+08f %+08f\n" + " %+08f %+08f %+08f\n" + " %+08f %+08f %+08f\n", + slot->transform[0], slot->transform[1], + slot->transform[2], slot->transform[3], + slot->transform[4], slot->transform[5], + slot->transform[6], slot->transform[7], + slot->transform[8]); + fprintf(stderr, " moveness: %f\n", slot->moveness); + fprintf(stderr, " pivot.x: %f\n", slot->pivot.x); + fprintf(stderr, " pivot.y: %f\n", slot->pivot.y); + fprintf(stderr, " drag.x: %f\n", slot->drag.x); + fprintf(stderr, " drag.y: %f\n", slot->drag.y); + fprintf(stderr, " scale2: %f\n", slot->scale2); + fprintf(stderr, " angle: %f\n", slot->angle); + } +} + +static void loop_device(struct frame_test *test, FILE *fp, int fd) +{ + const struct utouch_frame *frame; + struct input_event ev; + + if (fp) { + struct timeval evtime; + memset(&evtime, 0, sizeof(evtime)); + while (evemu_read_event_realtime(fp, &ev, &evtime) > 0) { + frame = utouch_frame_pump_mtdev(test->fh, &ev); + if (frame) + report_frame(test->ge, frame); + } + } else { + while (!mtdev_idle(test->mtdev, fd, 5000)) { + while (mtdev_get(test->mtdev, fd, &ev, 1) > 0) { + frame = utouch_frame_pump_mtdev(test->fh, &ev); + if (frame) + report_frame(test->ge, frame); + } + } + } +} + +static void report_device_caps(struct frame_test *test) +{ + const struct utouch_surface *s = utouch_frame_get_surface(test->fh); + + fprintf(stderr, "device props:\n"); + if (s->needs_pointer) + fprintf(stderr, "\tpointer\n"); + if (s->is_direct) + fprintf(stderr, "\tdirect\n"); + if (s->is_buttonpad) + fprintf(stderr, "\tbuttonpad\n"); + if (s->is_semi_mt) + fprintf(stderr, "\tsemi_mt\n"); + fprintf(stderr, "device mt events:\n"); + if (s->use_touch_major) + fprintf(stderr, "\ttouch_major\n"); + if (s->use_touch_minor) + fprintf(stderr, "\ttouch_minor\n"); + if (s->use_width_major) + fprintf(stderr, "\twidth_major\n"); + if (s->use_width_minor) + fprintf(stderr, "\twidth_minor\n"); + if (s->use_orientation) + fprintf(stderr, "\torientation\n"); + if (s->use_pressure) + fprintf(stderr, "\tpressure\n"); + if (s->use_distance) + fprintf(stderr, "\tdistance\n"); + + fprintf(stderr, "touch frames: %d\n", + utouch_frame_get_num_frames(test->fh)); + fprintf(stderr, "touch slots: %d\n", + utouch_frame_get_num_slots(test->fh)); +} + +int main(int argc, char *argv[]) +{ + struct frame_test test; + struct stat fs; + FILE *fp = 0; + int fd; + + if (argc < 2) { + fprintf(stderr, "Usage: %s \n", argv[0]); + return -1; + } + + memset(&test, 0, sizeof(test)); + + fd = open(argv[1], O_RDONLY | O_NONBLOCK); + if (fd < 0) { + fprintf(stderr, "error: could not open device\n"); + return -1; + } + if (fstat(fd, &fs)) { + fprintf(stderr, "error: could not stat the device\n"); + return -1; + } + if (!fs.st_rdev) + fp = fdopen(fd, "r"); + + if (!fp && ioctl(fd, EVIOCGRAB, 1)) { + fprintf(stderr, "error: could not grab the device\n"); + return -1; + } + + if (init_evemu(&test, fp, fd)) { + fprintf(stderr, "error: could not describe device\n"); + return -1; + } + if (!utouch_frame_is_supported_mtdev(test.evemu)) { + fprintf(stderr, "error: unsupported device\n"); + return -1; + } + + fprintf(stderr, "device: %s\n", evemu_get_name(test.evemu)); + + if (!fp && init_mtdev(&test, fd)) { + fprintf(stderr, "error: could not init mtdev\n"); + return -1; + } + if (init_frame(&test, fd)) { + fprintf(stderr, "error: could not init frame\n"); + return -1; + } + if (init_grail(&test)) { + fprintf(stderr, "error: could not init grail\n"); + return -1; + } + + report_device_caps(&test); + + loop_device(&test, fp, fd); + + destroy_all(&test); + + if (fs.st_rdev) + ioctl(fd, EVIOCGRAB, 0); + return 0; +} -- cgit v1.2.3