From 54175998d538e0b2173fc023bb822f1e6536e58f Mon Sep 17 00:00:00 2001 From: Woochanlee Date: Tue, 14 May 2019 16:37:20 +0900 Subject: [PATCH] Gesture Manager: Add gestures and fix gesture managing, recognizer logic. Summary: https://phab.enlightenment.org/T7544 Provides a way for a user to get a gesture manager, recognizer instance. Supports different recognizer properties for each target(Eo). Gesture, Touch Class Life-cycle re-implementation. for supporting multiple touches. Add below gestures. efl_canvas_gesture_tap efl_canvas_gesture_double_tap efl_canvas_gesture_triple_tap efl_canvas_gesture_long_tap efl_canvas_gesture_momentum efl_canvas_gesture_zoom efl_canvas_gesture_flick Test Plan: Simple test -> test_gesture_framework.c More test cases will upload. Reviewers: woohyun, smohanty, segfaultxavi, Jaehyun_Cho Reviewed By: Jaehyun_Cho Subscribers: Jaehyun_Cho, segfaultxavi, cedric Tags: #efl, #do_not_merge Differential Revision: https://phab.enlightenment.org/D7579 --- src/Makefile_Evas.am | 40 +- src/bin/elementary/test_gesture_framework.c | 281 ++++++++++++-- src/lib/evas/Evas_Eo.h | 29 +- src/lib/evas/canvas/efl_canvas_object.eo | 6 +- src/lib/evas/canvas/evas_callbacks.c | 6 +- src/lib/evas/canvas/evas_object_main.c | 9 + src/lib/evas/gesture/efl_canvas_gesture.c | 19 +- src/lib/evas/gesture/efl_canvas_gesture.eo | 20 +- .../gesture/efl_canvas_gesture_double_tap.c | 18 + .../gesture/efl_canvas_gesture_double_tap.eo | 9 + .../evas/gesture/efl_canvas_gesture_flick.c | 30 ++ .../evas/gesture/efl_canvas_gesture_flick.eo | 20 + .../gesture/efl_canvas_gesture_long_tap.c | 8 +- .../gesture/efl_canvas_gesture_long_tap.eo | 5 +- .../evas/gesture/efl_canvas_gesture_manager.c | 241 +++++++++--- .../gesture/efl_canvas_gesture_manager.eo | 8 +- .../gesture/efl_canvas_gesture_momentum.c | 24 ++ .../gesture/efl_canvas_gesture_momentum.eo | 16 + .../evas/gesture/efl_canvas_gesture_private.h | 141 ++++++- .../gesture/efl_canvas_gesture_recognizer.c | 10 + .../gesture/efl_canvas_gesture_recognizer.eo | 15 +- ...efl_canvas_gesture_recognizer_double_tap.c | 191 ++++++++++ ...fl_canvas_gesture_recognizer_double_tap.eo | 22 ++ .../efl_canvas_gesture_recognizer_flick.c | 354 ++++++++++++++++++ .../efl_canvas_gesture_recognizer_flick.eo | 9 + .../efl_canvas_gesture_recognizer_long_tap.c | 151 +++++--- .../efl_canvas_gesture_recognizer_long_tap.eo | 16 +- .../efl_canvas_gesture_recognizer_momentum.c | 197 ++++++++++ .../efl_canvas_gesture_recognizer_momentum.eo | 9 + .../efl_canvas_gesture_recognizer_tap.c | 56 ++- .../efl_canvas_gesture_recognizer_tap.eo | 3 +- ...efl_canvas_gesture_recognizer_triple_tap.c | 191 ++++++++++ ...fl_canvas_gesture_recognizer_triple_tap.eo | 22 ++ .../efl_canvas_gesture_recognizer_zoom.c | 275 ++++++++++++++ .../efl_canvas_gesture_recognizer_zoom.eo | 9 + src/lib/evas/gesture/efl_canvas_gesture_tap.c | 3 +- .../evas/gesture/efl_canvas_gesture_tap.eo | 5 +- .../evas/gesture/efl_canvas_gesture_touch.c | 102 +++-- .../evas/gesture/efl_canvas_gesture_touch.eo | 18 +- .../gesture/efl_canvas_gesture_triple_tap.c | 18 + .../gesture/efl_canvas_gesture_triple_tap.eo | 9 + .../evas/gesture/efl_canvas_gesture_types.eot | 13 + .../evas/gesture/efl_canvas_gesture_zoom.c | 35 ++ .../evas/gesture/efl_canvas_gesture_zoom.eo | 19 + src/lib/evas/gesture/efl_gesture_events.eo | 13 + src/lib/evas/gesture/meson.build | 50 +-- 46 files changed, 2473 insertions(+), 272 deletions(-) create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_double_tap.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_double_tap.eo create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_flick.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_flick.eo create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_momentum.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_momentum.eo create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.eo create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_flick.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_flick.eo create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.eo create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.eo create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.eo create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_triple_tap.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_triple_tap.eo create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_zoom.c create mode 100644 src/lib/evas/gesture/efl_canvas_gesture_zoom.eo create mode 100644 src/lib/evas/gesture/efl_gesture_events.eo diff --git a/src/Makefile_Evas.am b/src/Makefile_Evas.am index 95ec86e756..9abbe585a3 100644 --- a/src/Makefile_Evas.am +++ b/src/Makefile_Evas.am @@ -59,16 +59,25 @@ evas_gesture_eolian_pub_files = \ lib/evas/gesture/efl_canvas_gesture.eo \ lib/evas/gesture/efl_canvas_gesture_tap.eo \ lib/evas/gesture/efl_canvas_gesture_long_tap.eo \ + lib/evas/gesture/efl_canvas_gesture_double_tap.eo \ + lib/evas/gesture/efl_canvas_gesture_triple_tap.eo \ + lib/evas/gesture/efl_canvas_gesture_momentum.eo \ + lib/evas/gesture/efl_canvas_gesture_flick.eo \ + lib/evas/gesture/efl_canvas_gesture_zoom.eo \ lib/evas/gesture/efl_canvas_gesture_recognizer.eo \ + lib/evas/gesture/efl_canvas_gesture_recognizer_tap.eo \ + lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.eo \ + lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.eo \ + lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.eo \ + lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.eo \ + lib/evas/gesture/efl_canvas_gesture_recognizer_flick.eo \ + lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.eo \ lib/evas/gesture/efl_canvas_gesture_manager.eo \ + lib/evas/gesture/efl_gesture_events.eo \ $(NULL) evas_canvas_eolian_priv_files = \ - lib/evas/include/evas_ector_buffer.eo - -evas_gesture_eolian_priv_files = \ - lib/evas/gesture/efl_canvas_gesture_recognizer_tap.eo \ - lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.eo + lib/evas/include/evas_ector_buffer.eo evas_canvas_eolian_type_files = \ lib/evas/canvas/evas_canvas3d_types.eot \ @@ -80,9 +89,6 @@ evas_gesture_eolian_type_files = \ evas_canvas_eolian_priv_c = $(evas_canvas_eolian_priv_files:%.eo=%.eo.c) evas_canvas_eolian_priv_h = $(evas_canvas_eolian_priv_files:%.eo=%.eo.h) -evas_gesture_eolian_priv_c = $(evas_gesture_eolian_priv_files:%.eo=%.eo.c) -evas_gesture_eolian_priv_h = $(evas_gesture_eolian_priv_files:%.eo=%.eo.h) - evas_canvas_eolian_pub_c = $(evas_canvas_eolian_pub_files:%.eo=%.eo.c) evas_canvas_eolian_pub_h = $(evas_canvas_eolian_pub_files:%.eo=%.eo.h) \ $(evas_canvas_eolian_type_files:%.eot=%.eot.h) @@ -97,13 +103,15 @@ evas_eolian_files = $(evas_canvas_eolian_pub_files) \ $(evas_gesture_eolian_type_files) evas_eolian_internal_files = $(evas_canvas_eolian_priv_files) \ - $(evas_gesture_eolian_priv_files) + $(evas_eolian_legacy_files) evas_eolian_c = $(evas_canvas_eolian_pub_c) $(evas_canvas_eolian_priv_c) \ - $(evas_gesture_eolian_pub_c) $(evas_gesture_eolian_priv_c) + $(evas_gesture_eolian_pub_c) \ + $(evas_eolian_legacy_c) evas_eolian_h = $(evas_canvas_eolian_pub_h) $(evas_canvas_eolian_priv_h) \ - $(evas_gesture_eolian_pub_h) $(evas_gesture_eolian_priv_h) + $(evas_gesture_eolian_pub_h) \ + $(evas_eolian_legacy_h) BUILT_SOURCES += \ $(evas_eolian_c) \ @@ -319,9 +327,19 @@ lib/evas/gesture/efl_canvas_gesture_touch.c \ lib/evas/gesture/efl_canvas_gesture.c \ lib/evas/gesture/efl_canvas_gesture_tap.c \ lib/evas/gesture/efl_canvas_gesture_long_tap.c \ +lib/evas/gesture/efl_canvas_gesture_double_tap.c \ +lib/evas/gesture/efl_canvas_gesture_triple_tap.c \ +lib/evas/gesture/efl_canvas_gesture_momentum.c \ +lib/evas/gesture/efl_canvas_gesture_flick.c \ +lib/evas/gesture/efl_canvas_gesture_zoom.c \ lib/evas/gesture/efl_canvas_gesture_recognizer.c \ lib/evas/gesture/efl_canvas_gesture_recognizer_tap.c \ lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.c \ +lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.c \ +lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.c \ +lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.c \ +lib/evas/gesture/efl_canvas_gesture_recognizer_flick.c \ +lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.c \ lib/evas/gesture/efl_canvas_gesture_manager.c \ lib/evas/common/region.c \ lib/evas/common/region.h \ diff --git a/src/bin/elementary/test_gesture_framework.c b/src/bin/elementary/test_gesture_framework.c index ada28bc50f..5e2e935e49 100644 --- a/src/bin/elementary/test_gesture_framework.c +++ b/src/bin/elementary/test_gesture_framework.c @@ -175,25 +175,19 @@ _color_and_icon_set(infra_data *infra, char *name, int n, int max, static void finger_tap_start(void *data , Efl_Canvas_Gesture *tap) { - Eina_Vector2 pos = efl_gesture_hotspot_get(tap); + Eina_Position2D pos = efl_gesture_hotspot_get(tap); _color_and_icon_set(data, TAP_NAME, 1, MAX_TAP, START_COLOR); - printf("Tap Gesture started x,y=<%f,%f> \n", pos.x, pos.y); -} - -static void -finger_tap_update(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) -{ - _color_and_icon_set(data, TAP_NAME, 1, MAX_TAP, UPDATE_COLOR); + printf("Tap Gesture started x,y=<%d,%d> \n", pos.x, pos.y); } static void finger_tap_end(void *data , Efl_Canvas_Gesture *tap) { - Eina_Vector2 pos = efl_gesture_hotspot_get(tap); + Eina_Position2D pos = efl_gesture_hotspot_get(tap); _color_and_icon_set(data, TAP_NAME, 1, MAX_TAP, END_COLOR); - printf("Tap Gesture ended x,y=<%f,%f> \n", pos.x, pos.y); + printf("Tap Gesture ended x,y=<%d,%d> \n", pos.x, pos.y); } static void @@ -203,13 +197,148 @@ finger_tap_abort(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) printf("Tap Aborted\n"); } +static void +finger_flick_start(void *data , Efl_Canvas_Gesture *tap) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + + _color_and_icon_set(data, FLICK_NAME, 1, MAX_TAP, START_COLOR); + printf("Flick Gesture started x,y=<%d,%d> \n", pos.x, pos.y); +} + +static void +finger_flick_end(void *data , Efl_Canvas_Gesture *tap) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + double angle = efl_gesture_flick_angle_get(tap); + + _color_and_icon_set(data, FLICK_NAME, 1, MAX_TAP, END_COLOR); + printf("Flick Gesture ended x,y=<%d,%d> angle=<%f>\n", pos.x, pos.y, angle); +} + +static void +finger_flick_abort(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) +{ + _color_and_icon_set(data, FLICK_NAME, 1, MAX_TAP, ABORT_COLOR); + printf("Flick Aborted\n"); +} + +static void +finger_momentum_start(void *data , Efl_Canvas_Gesture *tap) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + unsigned int t = efl_gesture_timestamp_get(tap); + + _color_and_icon_set(data, MOMENTUM_NAME, 1, MAX_TAP, START_COLOR); + printf("Momentum Gesture started x,y=<%d,%d> time=<%d>\n", pos.x, pos.y, t); +} + +static void +finger_momentum_update(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + Eina_Vector2 m = efl_gesture_momentum_get(tap); + unsigned int t = efl_gesture_timestamp_get(tap); + + _color_and_icon_set(data, MOMENTUM_NAME, 1, MAX_TAP, UPDATE_COLOR); + printf("Momentum Gesture updated x,y=<%d,%d> momentum=<%f %f> time=<%d>\n", + pos.x, pos.y, m.x, m.y, t); +} + +static void +finger_momentum_end(void *data , Efl_Canvas_Gesture *tap) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + Eina_Vector2 m = efl_gesture_momentum_get(tap); + unsigned int t = efl_gesture_timestamp_get(tap); + + _color_and_icon_set(data, MOMENTUM_NAME, 1, MAX_TAP, END_COLOR); + printf("Momentum Gesture ended x,y=<%d,%d> momentum=<%f %f> time=<%d>\n", + pos.x, pos.y, m.x, m.y, t); +} + +static void +finger_momentum_abort(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) +{ + _color_and_icon_set(data, MOMENTUM_NAME, 1, MAX_TAP, ABORT_COLOR); + printf("Momentum Aborted\n"); +} + +static void +finger_triple_tap_start(void *data , Efl_Canvas_Gesture *tap) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + + _color_and_icon_set(data, TRIPLE_TAP_NAME, 1, MAX_TAP, START_COLOR); + printf("Triple Tap Gesture started x,y=<%d,%d> \n", pos.x, pos.y); +} + +static void +finger_triple_tap_update(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + + _color_and_icon_set(data, TRIPLE_TAP_NAME, 1, MAX_TAP, UPDATE_COLOR); + printf("Triple Tap Gesture updated x,y=<%d,%d> \n", pos.x, pos.y); +} + +static void +finger_triple_tap_end(void *data , Efl_Canvas_Gesture *tap) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + + _color_and_icon_set(data, TRIPLE_TAP_NAME, 1, MAX_TAP, END_COLOR); + printf("Triple Tap Gesture ended x,y=<%d,%d> \n", pos.x, pos.y); +} + +static void +finger_triple_tap_abort(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) +{ + _color_and_icon_set(data, TRIPLE_TAP_NAME, 1, MAX_TAP, ABORT_COLOR); + printf("Triple Tap Aborted\n"); +} + +static void +finger_double_tap_start(void *data , Efl_Canvas_Gesture *tap) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + + _color_and_icon_set(data, DOUBLE_TAP_NAME, 1, MAX_TAP, START_COLOR); + printf("Double Tap Gesture started x,y=<%d,%d> \n", pos.x, pos.y); +} + +static void +finger_double_tap_update(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + + _color_and_icon_set(data, DOUBLE_TAP_NAME, 1, MAX_TAP, UPDATE_COLOR); + printf("Double Tap Gesture updated x,y=<%d,%d> \n", pos.x, pos.y); +} + +static void +finger_double_tap_end(void *data , Efl_Canvas_Gesture *tap) +{ + Eina_Position2D pos = efl_gesture_hotspot_get(tap); + + _color_and_icon_set(data, DOUBLE_TAP_NAME, 1, MAX_TAP, END_COLOR); + printf("Double Tap Gesture ended x,y=<%d,%d> \n", pos.x, pos.y); +} + +static void +finger_double_tap_abort(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) +{ + _color_and_icon_set(data, DOUBLE_TAP_NAME, 1, MAX_TAP, ABORT_COLOR); + printf("Double Tap Aborted\n"); +} + static void finger_long_tap_start(void *data , Efl_Canvas_Gesture *tap) { - Eina_Vector2 pos = efl_gesture_hotspot_get(tap); + Eina_Position2D pos = efl_gesture_hotspot_get(tap); _color_and_icon_set(data, LONG_TAP_NAME, 1, MAX_TAP, START_COLOR); - printf("Long Tap Gesture started x,y=<%f,%f> \n", pos.x, pos.y); + printf("Long Tap Gesture started x,y=<%d,%d> \n", pos.x, pos.y); } static void @@ -222,10 +351,10 @@ finger_long_tap_update(void *data , Efl_Canvas_Gesture *tap EINA_UNUSED) static void finger_long_tap_end(void *data , Efl_Canvas_Gesture *tap) { - Eina_Vector2 pos = efl_gesture_hotspot_get(tap); + Eina_Position2D pos = efl_gesture_hotspot_get(tap); _color_and_icon_set(data, LONG_TAP_NAME, 1, MAX_TAP, END_COLOR); - printf("Long Tap Gesture ended x,y=<%f,%f> \n",pos.x, pos.y); + printf("Long Tap Gesture ended x,y=<%d,%d> \n",pos.x, pos.y); } static void @@ -244,9 +373,6 @@ tap_gesture_cb(void *data , const Efl_Event *ev) case EFL_GESTURE_STARTED: finger_tap_start(data, g); break; - case EFL_GESTURE_UPDATED: - finger_tap_update(data, g); - break; case EFL_GESTURE_CANCELED: finger_tap_abort(data, g); break; @@ -258,6 +384,95 @@ tap_gesture_cb(void *data , const Efl_Event *ev) } } +static void +flick_gesture_cb(void *data , const Efl_Event *ev) +{ + Efl_Canvas_Gesture *g = ev->info; + switch(efl_gesture_state_get(g)) + { + case EFL_GESTURE_STARTED: + finger_flick_start(data, g); + break; + case EFL_GESTURE_CANCELED: + finger_flick_abort(data, g); + break; + case EFL_GESTURE_FINISHED: + finger_flick_end(data, g); + break; + default: + break; + } +} + +static void +momentum_gesture_cb(void *data , const Efl_Event *ev) +{ + Efl_Canvas_Gesture *g = ev->info; + switch(efl_gesture_state_get(g)) + { + case EFL_GESTURE_STARTED: + finger_momentum_start(data, g); + break; + case EFL_GESTURE_UPDATED: + finger_momentum_update(data, g); + break; + case EFL_GESTURE_CANCELED: + finger_momentum_abort(data, g); + break; + case EFL_GESTURE_FINISHED: + finger_momentum_end(data, g); + break; + default: + break; + } +} + +static void +triple_tap_gesture_cb(void *data , const Efl_Event *ev) +{ + Efl_Canvas_Gesture *g = ev->info; + switch(efl_gesture_state_get(g)) + { + case EFL_GESTURE_STARTED: + finger_triple_tap_start(data, g); + break; + case EFL_GESTURE_UPDATED: + finger_triple_tap_update(data, g); + break; + case EFL_GESTURE_CANCELED: + finger_triple_tap_abort(data, g); + break; + case EFL_GESTURE_FINISHED: + finger_triple_tap_end(data, g); + break; + default: + break; + } +} + +static void +double_tap_gesture_cb(void *data , const Efl_Event *ev) +{ + Efl_Canvas_Gesture *g = ev->info; + switch(efl_gesture_state_get(g)) + { + case EFL_GESTURE_STARTED: + finger_double_tap_start(data, g); + break; + case EFL_GESTURE_UPDATED: + finger_double_tap_update(data, g); + break; + case EFL_GESTURE_CANCELED: + finger_double_tap_abort(data, g); + break; + case EFL_GESTURE_FINISHED: + finger_double_tap_end(data, g); + break; + default: + break; + } +} + static void long_tap_gesture_cb(void *data , const Efl_Event *ev) { @@ -313,12 +528,23 @@ create_gesture_box(Evas_Object *win, icon_properties *icons, return bx; } +void +_tb_resize(void *data, Evas *e EINA_UNUSED, Evas_Object *obj, void *event_info EINA_UNUSED) +{ + int w,h; + + evas_object_geometry_get(obj, NULL, NULL, &w, &h); + evas_object_resize(data, w, h); + evas_object_color_set(data, 0, 0, 0, 0); + evas_object_show(data); +} + void test_gesture_framework(void *data EINA_UNUSED, Evas_Object *obj EINA_UNUSED, void *event_info EINA_UNUSED) { Evas_Object *win, *tb, *lb, *bx; - Evas_Object *r; /* Gesture layer transparent object */ + Evas_Object *r, *target; /* Gesture layer transparent object */ infra_data *infra = _infra_data_alloc(); @@ -336,6 +562,9 @@ test_gesture_framework(void *data EINA_UNUSED, Evas_Object *obj EINA_UNUSED, evas_object_show(tb); evas_object_show(bx); + target = evas_object_rectangle_add(evas_object_evas_get(win)); + evas_object_event_callback_add(win, EVAS_CALLBACK_RESIZE, _tb_resize, target); + /* Box of Tap icon and label */ bx = create_gesture_box(win, infra->icons, 0, TAP_NAME, "Tap"); elm_table_pack(tb, bx, 0, 0, 1, 1); @@ -458,15 +687,13 @@ test_gesture_framework(void *data EINA_UNUSED, Evas_Object *obj EINA_UNUSED, evas_object_show(lb); /* END - Building icons table */ - r = evas_object_rectangle_add(evas_object_evas_get(win)); - evas_object_move(r, 250, 300); - evas_object_color_set(r, 0, 0, 255, 255); - evas_object_resize(r, 70, 70); - evas_object_show(r); - - // LISTEN FOR TAP GESTURE - efl_event_callback_add(r, EFL_EVENT_GESTURE_TAP, tap_gesture_cb, infra); - efl_event_callback_add(r, EFL_EVENT_GESTURE_LONG_TAP, long_tap_gesture_cb, infra); + // LISTEN FOR GESTURES + efl_event_callback_add(target, EFL_EVENT_GESTURE_TAP, tap_gesture_cb, infra); + efl_event_callback_add(target, EFL_EVENT_GESTURE_LONG_TAP, long_tap_gesture_cb, infra); + efl_event_callback_add(target, EFL_EVENT_GESTURE_DOUBLE_TAP, double_tap_gesture_cb, infra); + efl_event_callback_add(target, EFL_EVENT_GESTURE_TRIPLE_TAP, triple_tap_gesture_cb, infra); + efl_event_callback_add(target, EFL_EVENT_GESTURE_MOMENTUM, momentum_gesture_cb, infra); + efl_event_callback_add(target, EFL_EVENT_GESTURE_FLICK, flick_gesture_cb, infra); /* Update color state 20 times a second */ infra->colortimer = ecore_timer_add(0.05, _icon_color_set_cb, infra->icons); diff --git a/src/lib/evas/Evas_Eo.h b/src/lib/evas/Evas_Eo.h index a4f611e201..f3bcb6eb32 100644 --- a/src/lib/evas/Evas_Eo.h +++ b/src/lib/evas/Evas_Eo.h @@ -187,6 +187,27 @@ struct _Efl_Canvas_Object_Animation_Event #include "canvas/efl_canvas_animation_types.eot.h" +#include "gesture/efl_canvas_gesture_types.eot.h" +#include "gesture/efl_canvas_gesture_touch.eo.h" +#include "gesture/efl_canvas_gesture.eo.h" +#include "gesture/efl_canvas_gesture_tap.eo.h" +#include "gesture/efl_canvas_gesture_long_tap.eo.h" +#include "gesture/efl_canvas_gesture_double_tap.eo.h" +#include "gesture/efl_canvas_gesture_triple_tap.eo.h" +#include "gesture/efl_canvas_gesture_momentum.eo.h" +#include "gesture/efl_canvas_gesture_flick.eo.h" +#include "gesture/efl_canvas_gesture_zoom.eo.h" +#include "gesture/efl_canvas_gesture_recognizer.eo.h" +#include "gesture/efl_canvas_gesture_recognizer_tap.eo.h" +#include "gesture/efl_canvas_gesture_recognizer_long_tap.eo.h" +#include "gesture/efl_canvas_gesture_recognizer_double_tap.eo.h" +#include "gesture/efl_canvas_gesture_recognizer_triple_tap.eo.h" +#include "gesture/efl_canvas_gesture_recognizer_momentum.eo.h" +#include "gesture/efl_canvas_gesture_recognizer_flick.eo.h" +#include "gesture/efl_canvas_gesture_recognizer_zoom.eo.h" +#include "gesture/efl_canvas_gesture_manager.eo.h" +#include "gesture/efl_gesture_events.eo.h" + #include "canvas/efl_canvas_object.eo.h" #include "canvas/efl_canvas_animation.eo.h" @@ -442,11 +463,3 @@ typedef void (Evas_Canvas3D_Surface_Func)(Evas_Real *out_x, #include "canvas/efl_input_hold.eo.h" #include "canvas/efl_input_interface.eo.h" #include "canvas/efl_input_focus.eo.h" - -# include "gesture/efl_canvas_gesture_types.eot.h" -# include "gesture/efl_canvas_gesture_touch.eo.h" -# include "gesture/efl_canvas_gesture.eo.h" -# include "gesture/efl_canvas_gesture_tap.eo.h" -# include "gesture/efl_canvas_gesture_long_tap.eo.h" -# include "gesture/efl_canvas_gesture_recognizer.eo.h" -# include "gesture/efl_canvas_gesture_manager.eo.h" diff --git a/src/lib/evas/canvas/efl_canvas_object.eo b/src/lib/evas/canvas/efl_canvas_object.eo index 9a5f89dbe8..6cd64ea713 100644 --- a/src/lib/evas/canvas/efl_canvas_object.eo +++ b/src/lib/evas/canvas/efl_canvas_object.eo @@ -8,7 +8,7 @@ struct Efl.Event_Animator_Tick { abstract Efl.Canvas.Object extends Efl.Loop_Consumer implements Efl.Gfx.Entity, Efl.Gfx.Color, Efl.Gfx.Stack, Efl.Input.Interface, Efl.Gfx.Hint, - Efl.Gfx.Mapping, Efl.Ui.I18n, Efl.Canvas.Pointer + Efl.Gfx.Mapping, Efl.Ui.I18n, Efl.Canvas.Pointer, Efl.Gesture.Events { [[Efl canvas object abstract class @@ -494,6 +494,10 @@ abstract Efl.Canvas.Object extends Efl.Loop_Consumer implements Efl.Gfx.Entity, return: bool; [[$true if the coords are inside the object, $false otherwise]] } } + gesture_manager_get @beta { + [[Returns current canvas's gesture manager]] + return: const(Efl.Canvas.Gesture_Manager); [[The gesture manager]] + } } implements { Efl.Object.constructor; diff --git a/src/lib/evas/canvas/evas_callbacks.c b/src/lib/evas/canvas/evas_callbacks.c index dcd3338dd6..0e9be65f05 100644 --- a/src/lib/evas/canvas/evas_callbacks.c +++ b/src/lib/evas/canvas/evas_callbacks.c @@ -811,8 +811,7 @@ _check_event_catcher_add(void *data, const Efl_Event *event) for (i = 0; array[i].desc != NULL; i++) { - if (obj->layer->evas->gesture_manager && - _efl_canvas_gesture_manager_watches(array[i].desc)) + if (obj->layer->evas->gesture_manager) { if (!gd) gd = _efl_canvas_gesture_manager_private_data_get(obj->layer->evas->gesture_manager); @@ -853,8 +852,7 @@ _check_event_catcher_del(void *data, const Efl_Event *event) for (i = 0; array[i].desc != NULL; i++) { - if (obj->layer->evas->gesture_manager && - _efl_canvas_gesture_manager_watches(array[i].desc)) + if (obj->layer->evas->gesture_manager) { if (!gd) gd = _efl_canvas_gesture_manager_private_data_get(obj->layer->evas->gesture_manager); diff --git a/src/lib/evas/canvas/evas_object_main.c b/src/lib/evas/canvas/evas_object_main.c index 07193790ba..35556cbf77 100644 --- a/src/lib/evas/canvas/evas_object_main.c +++ b/src/lib/evas/canvas/evas_object_main.c @@ -258,6 +258,15 @@ end: return efl_finalize(efl_super(eo_obj, MY_CLASS)); } +EOLIAN const Efl_Canvas_Gesture_Manager * +_efl_canvas_object_gesture_manager_get(Eo *eo_obj EINA_UNUSED, Evas_Object_Protected_Data *pd) +{ + if (!pd->layer || !pd->layer->evas) + return NULL; + + return (pd->layer->evas)->gesture_manager; +} + void evas_object_change_reset(Evas_Object_Protected_Data *obj) { diff --git a/src/lib/evas/gesture/efl_canvas_gesture.c b/src/lib/evas/gesture/efl_canvas_gesture.c index 7386a90396..9017f822b5 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture.c +++ b/src/lib/evas/gesture/efl_canvas_gesture.c @@ -21,16 +21,29 @@ _efl_canvas_gesture_state_set(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Data *pd, } EOLIAN static void -_efl_canvas_gesture_hotspot_set(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Data *pd, Eina_Vector2 hotspot) +_efl_canvas_gesture_hotspot_set(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Data *pd, Eina_Position2D hotspot) { pd->hotspot = hotspot; } -EOLIAN static Eina_Vector2 +EOLIAN static Eina_Position2D _efl_canvas_gesture_hotspot_get(const Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Data *pd) { return pd->hotspot; } -#include "efl_canvas_gesture.eo.c" \ No newline at end of file +EOLIAN static void +_efl_canvas_gesture_timestamp_set(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Data *pd, unsigned int timestamp) +{ + pd->timestamp = timestamp; +} + + +EOLIAN static unsigned int +_efl_canvas_gesture_timestamp_get(const Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Data *pd) +{ + return pd->timestamp; +} + +#include "efl_canvas_gesture.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture.eo b/src/lib/evas/gesture/efl_canvas_gesture.eo index eafb1d983a..2a097d5fad 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture.eo +++ b/src/lib/evas/gesture/efl_canvas_gesture.eo @@ -2,7 +2,13 @@ import efl_canvas_gesture_types; abstract @beta Efl.Canvas.Gesture extends Efl.Object { - [[EFL Gesture abstract class]] + [[EFL Gesture abstract class + + A gesture class defines a method that spcific gesture event and privides information + about the gesture's type, state, and associated pointer information. + + For cetain gesture types, additional methods are defined to provide meaningful gesture + information to the user.]] c_prefix: efl_gesture; methods { @property type { @@ -30,7 +36,17 @@ abstract @beta Efl.Canvas.Gesture extends Efl.Object set { } values { - hotspot: Eina.Vector2;[[hotspot co-ordinate]] + hotspot: Eina.Position2D;[[hotspot co-ordinate]] + } + } + @property timestamp { + [[This property holds the timestamp of the current gesture.]] + get { + } + set { + } + values { + timestamp: uint;[[The timestamp]] } } } diff --git a/src/lib/evas/gesture/efl_canvas_gesture_double_tap.c b/src/lib/evas/gesture/efl_canvas_gesture_double_tap.c new file mode 100644 index 0000000000..971d49e3b6 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_double_tap.c @@ -0,0 +1,18 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_DOUBLE_TAP_CLASS + +EOLIAN static Efl_Object * +_efl_canvas_gesture_double_tap_efl_object_constructor(Eo *obj, void *pd EINA_UNUSED) +{ + Efl_Canvas_Gesture_Data *gd; + + obj = efl_constructor(efl_super(obj, MY_CLASS)); + + gd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_CLASS); + gd->type = EFL_EVENT_GESTURE_DOUBLE_TAP; + + return obj; +} + +#include "efl_canvas_gesture_double_tap.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_double_tap.eo b/src/lib/evas/gesture/efl_canvas_gesture_double_tap.eo new file mode 100644 index 0000000000..39d84b86f2 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_double_tap.eo @@ -0,0 +1,9 @@ +class @beta Efl.Canvas.Gesture_Double_Tap extends Efl.Canvas.Gesture +{ + [[EFL Gesture Double Tap class]] + data: null; + c_prefix: efl_gesture_double_tap; + implements { + Efl.Object.constructor; + } +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_flick.c b/src/lib/evas/gesture/efl_canvas_gesture_flick.c new file mode 100644 index 0000000000..1095a84652 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_flick.c @@ -0,0 +1,30 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_FLICK_CLASS + +EOLIAN static Efl_Object * +_efl_canvas_gesture_flick_efl_object_constructor(Eo *obj, Efl_Canvas_Gesture_Flick_Data *pd EINA_UNUSED) +{ + Efl_Canvas_Gesture_Data *gd; + + obj = efl_constructor(efl_super(obj, MY_CLASS)); + + gd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_CLASS); + gd->type = EFL_EVENT_GESTURE_FLICK; + + return obj; +} + +EOLIAN static Eina_Vector2 +_efl_canvas_gesture_flick_momentum_get(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Flick_Data *pd) +{ + return pd->momentum; +} + +EOLIAN static double +_efl_canvas_gesture_flick_angle_get(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Flick_Data *pd) +{ + return pd->angle; +} + +#include "efl_canvas_gesture_flick.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_flick.eo b/src/lib/evas/gesture/efl_canvas_gesture_flick.eo new file mode 100644 index 0000000000..7e87c55f71 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_flick.eo @@ -0,0 +1,20 @@ +import eina_types; + +class @beta Efl.Canvas.Gesture_Flick extends Efl.Canvas.Gesture +{ + [[EFL Gesture Flick class]] + c_prefix: efl_gesture_flick; + methods { + momentum_get { + [[Gets flick gesture momentum value]] + return: Eina.Vector2; [[The momentum vector]] + } + angle_get { + [[Gets flick direction angle]] + return: double; [[The angle value]] + } + } + implements { + Efl.Object.constructor; + } +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_long_tap.c b/src/lib/evas/gesture/efl_canvas_gesture_long_tap.c index 099893a58e..21f0055414 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_long_tap.c +++ b/src/lib/evas/gesture/efl_canvas_gesture_long_tap.c @@ -2,9 +2,8 @@ #define MY_CLASS EFL_CANVAS_GESTURE_LONG_TAP_CLASS - EOLIAN static Efl_Object * -_efl_canvas_gesture_long_tap_efl_object_constructor(Eo *obj, Efl_Canvas_Gesture_Long_Tap_Data *pd EINA_UNUSED) +_efl_canvas_gesture_long_tap_efl_object_constructor(Eo *obj, void *pd EINA_UNUSED) { Efl_Canvas_Gesture_Data *gd; @@ -16,11 +15,8 @@ _efl_canvas_gesture_long_tap_efl_object_constructor(Eo *obj, Efl_Canvas_Gesture_ } EOLIAN static void -_efl_canvas_gesture_long_tap_efl_object_destructor(Eo *obj, Efl_Canvas_Gesture_Long_Tap_Data *pd) +_efl_canvas_gesture_long_tap_efl_object_destructor(Eo *obj, void *pd EINA_UNUSED) { - if (pd->timeout) - ecore_timer_del(pd->timeout); - efl_destructor(efl_super(obj, MY_CLASS)); } diff --git a/src/lib/evas/gesture/efl_canvas_gesture_long_tap.eo b/src/lib/evas/gesture/efl_canvas_gesture_long_tap.eo index 1a690b0d65..79c5c6d0e6 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_long_tap.eo +++ b/src/lib/evas/gesture/efl_canvas_gesture_long_tap.eo @@ -1,11 +1,8 @@ class @beta Efl.Canvas.Gesture_Long_Tap extends Efl.Canvas.Gesture { [[EFL Gesture Long Tap class]] + data: null; c_prefix: efl_gesture_long_tap; - event_prefix: efl; - events { - gesture,long_tap: Efl.Canvas.Gesture; [[Event for tap gesture]] - } implements { Efl.Object.constructor; Efl.Object.destructor; diff --git a/src/lib/evas/gesture/efl_canvas_gesture_manager.c b/src/lib/evas/gesture/efl_canvas_gesture_manager.c index b174e49b7b..86960046ff 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_manager.c +++ b/src/lib/evas/gesture/efl_canvas_gesture_manager.c @@ -4,25 +4,25 @@ typedef struct _Object_Gesture { - Eo *object; - const Efl_Event_Description *type; + Eo *object; + const Efl_Event_Description *type; Efl_Canvas_Gesture *gesture; Efl_Canvas_Gesture_Recognizer *recognizer; -}Object_Gesture; +} Object_Gesture; typedef struct _Efl_Canvas_Gesture_Manager_Data { - // keeps track of all the gesture request for a particular target + //Keeps track of all the gesture request for a particular target Eina_Hash *m_gesture_contex; // (*target, *event_desc) - // keeps all the event directed to this particular object from touch_begin till touch_end + //Keeps all the event directed to this particular object from touch_begin till touch_end Eina_Hash *m_object_events; // (*target, *efl_gesture_touch) - // keeps all the recognizer registered to gesture manager + //Keeps all the recognizer registered to gesture manager Eina_Hash *m_recognizers; // (*gesture_type, *recognizer) - // keeps track of all current object gestures. + //Keeps track of all current object gestures. Eina_List *m_object_gestures; //(List of *object_gesture) - // lazy deletion of gestures + //Lazy deletion of gestures Eina_List *m_gestures_to_delete; - + //Kepps config values for gesture recognize Eina_Hash *m_config; } Efl_Canvas_Gesture_Manager_Data; @@ -65,13 +65,18 @@ _efl_canvas_gesture_manager_efl_object_constructor(Eo *obj, Efl_Canvas_Gesture_M pd->m_config = eina_hash_string_superfast_new(EINA_FREE_CB(eina_value_free)); + //Register all types of recognizers at very first time. efl_gesture_manager_recognizer_register(obj, efl_add(EFL_CANVAS_GESTURE_RECOGNIZER_TAP_CLASS, obj)); efl_gesture_manager_recognizer_register(obj, efl_add(EFL_CANVAS_GESTURE_RECOGNIZER_LONG_TAP_CLASS, obj)); + efl_gesture_manager_recognizer_register(obj, efl_add(EFL_CANVAS_GESTURE_RECOGNIZER_DOUBLE_TAP_CLASS, obj)); + efl_gesture_manager_recognizer_register(obj, efl_add(EFL_CANVAS_GESTURE_RECOGNIZER_TRIPLE_TAP_CLASS, obj)); + efl_gesture_manager_recognizer_register(obj, efl_add(EFL_CANVAS_GESTURE_RECOGNIZER_MOMENTUM_CLASS, obj)); + efl_gesture_manager_recognizer_register(obj, efl_add(EFL_CANVAS_GESTURE_RECOGNIZER_FLICK_CLASS, obj)); + efl_gesture_manager_recognizer_register(obj, efl_add(EFL_CANVAS_GESTURE_RECOGNIZER_ZOOM_CLASS, obj)); return obj; } - EOLIAN static Eina_Value * _efl_canvas_gesture_manager_config_get(const Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Manager_Data *pd, const char *name) { @@ -84,6 +89,22 @@ _efl_canvas_gesture_manager_config_set(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_M Eina_Value *v = eina_value_new(eina_value_type_get(value)); eina_value_copy(value, v); eina_hash_add(pd->m_config, name, v); + + //Sets recognizer class property. + if (!strcmp(name, "glayer_tap_finger_size")) + { + int finger_size; + Efl_Canvas_Gesture_Recognizer *r; + Efl_Canvas_Gesture_Recognizer_Data *rd; + + eina_value_get(value, &finger_size); + + const Efl_Event_Description *type = EFL_EVENT_GESTURE_TAP; + + r = eina_hash_find(pd->m_recognizers, &type); + rd = efl_data_scope_get(r, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + rd->finger_size = finger_size; + } } EOLIAN static void @@ -109,11 +130,11 @@ void _efl_canvas_gesture_manager_callback_add_hook(void *data, Eo *target, const Efl_Event_Description *type) { Efl_Canvas_Gesture_Manager_Data *pd = data; - // if there is a recognizer registered for that event then add it to the gesture context + //If there is a recognizer registered for that event then add it to the gesture context Efl_Canvas_Gesture_Recognizer *recognizer = eina_hash_find (pd->m_recognizers, &type); if (recognizer) { - // add it to the gesture context. + //Add it to the gesture context. eina_hash_list_append(pd->m_gesture_contex, &target, type); } } @@ -122,7 +143,7 @@ void _efl_canvas_gesture_manager_callback_del_hook(void *data, Eo *target, const Efl_Event_Description *type) { Efl_Canvas_Gesture_Manager_Data *pd = data; - // if there is a recognizer registered for that event then add it to the gesture context + //If there is a recognizer registered for that event then add it to the gesture context Efl_Canvas_Gesture_Recognizer *recognizer = eina_hash_find (pd->m_recognizers, &type); if (recognizer) { @@ -148,28 +169,39 @@ _efl_canvas_gesture_manager_filter_event(Eo *obj, Eo *target, void *event) gesture_context = eina_hash_find(pd->m_gesture_contex, &target); if (gesture_context) { - // get the touch event for this particular widget - touch_event = eina_hash_find(pd->m_object_events, &target); - if (!touch_event) - { - touch_event = efl_add_ref(EFL_CANVAS_GESTURE_TOUCH_CLASS, NULL); - eina_hash_add(pd->m_object_events, &target, touch_event); - } - - efl_gesture_touch_point_record(touch_event, pointer_data->tool, pointer_data->cur, - pointer_data->timestamp, pointer_data->action); - - if (efl_gesture_touch_state_get(touch_event) == EFL_GESTURE_TOUCH_UNKNOWN) - return; - EINA_LIST_FOREACH(gesture_context, l, gesture_type) { + //Check there is already created event exist or not. + touch_event = eina_hash_find(pd->m_object_events, &gesture_type); + + if (!touch_event) + { + touch_event = efl_add_ref(EFL_CANVAS_GESTURE_TOUCH_CLASS, NULL); + eina_hash_add(pd->m_object_events, &gesture_type, touch_event); + } + + efl_gesture_touch_point_record(touch_event, pointer_data->tool, pointer_data->cur, + pointer_data->timestamp, pointer_data->action); + + //This is for handling the case that mouse event pairs dont match. + //Such as the case of canceling gesture recognition after a mouse down. + if (efl_gesture_touch_state_get(touch_event) == EFL_GESTURE_TOUCH_UNKNOWN) + continue; + recognizer = eina_hash_find(pd->m_recognizers, &gesture_type); + + //If the gesture canceled or already finished by recognizer. gesture = _get_state(pd, target, recognizer, gesture_type); if (!gesture) continue; + + //Gesture detecting. recog_result = efl_gesture_recognizer_recognize(recognizer, gesture, target, touch_event); recog_state = recog_result & EFL_GESTURE_RESULT_MASK; + + Efl_Canvas_Gesture_Recognizer_Data *rd = + efl_data_scope_get(recognizer, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + if (recog_state == EFL_GESTURE_TRIGGER) { if (efl_gesture_state_get(gesture) == EFL_GESTURE_NONE) @@ -188,53 +220,57 @@ _efl_canvas_gesture_manager_filter_event(Eo *obj, Eo *target, void *event) else if (recog_state == EFL_GESTURE_CANCEL) { if (efl_gesture_state_get(gesture) != EFL_GESTURE_NONE) - { - efl_gesture_state_set(gesture, EFL_GESTURE_CANCELED); - } + efl_gesture_state_set(gesture, EFL_GESTURE_CANCELED); else - continue; + { + //Need to recognize events that occur consecutively + //in a mouse-down state. + if (rd->continues) + continue; + } } else if (recog_state == EFL_GESTURE_IGNORE) { continue; } + + efl_gesture_timestamp_set(gesture, efl_gesture_touch_cur_timestamp_get(touch_event)); efl_event_callback_call(target, gesture_type, gesture); - } - if (efl_gesture_touch_state_get(touch_event) == EFL_GESTURE_TOUCH_END) - { - EINA_LIST_FOREACH(gesture_context, l, gesture_type) - _cleanup_cached_gestures(pd, target, gesture_type); + //If the current event recognizes the gesture continuously, dont delete gesture. + if (((recog_state == EFL_GESTURE_FINISH) || (recog_state == EFL_GESTURE_CANCEL)) && + !rd->continues) + { + _cleanup_cached_gestures(pd, target, gesture_type); + eina_hash_del(pd->m_object_events, &gesture_type, NULL); + //FIXME: delete it by object not list. + _cleanup_object(pd->m_gestures_to_delete); + pd->m_gestures_to_delete = NULL; - eina_hash_del(pd->m_object_events, &target, NULL); - // free gesture_to_delete list - _cleanup_object(pd->m_gestures_to_delete); - pd->m_gestures_to_delete = NULL; + } } } } -EOLIAN static const Efl_Event_Description * +EOLIAN static void _efl_canvas_gesture_manager_recognizer_register(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Manager_Data *pd, Efl_Canvas_Gesture_Recognizer *recognizer) { Efl_Canvas_Gesture_Recognizer_Data *rpd; - Efl_Canvas_Gesture *dummy = efl_gesture_recognizer_create(recognizer, 0); + Efl_Canvas_Gesture *dummy = efl_gesture_recognizer_add(recognizer, NULL); if (!dummy) - return NULL; + return; const Efl_Event_Description *type = efl_gesture_type_get(dummy); - // Add the recognizer to the m_recognizers + //Add the recognizer to the m_recognizers eina_hash_add(pd->m_recognizers, &type, efl_ref(recognizer)); - // update the manager + //Update the manager rpd = efl_data_scope_get(recognizer, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); rpd->manager = obj; efl_del(dummy); - - return type; } EOLIAN static void @@ -248,19 +284,19 @@ _efl_canvas_gesture_manager_recognizer_unregister(Eo *obj EINA_UNUSED, Efl_Canva if (!recognizer) return; - // find the type of the recognizer - dummy = efl_gesture_recognizer_create(recognizer, 0); + //Find the type of the recognizer + dummy = efl_gesture_recognizer_add(recognizer, 0); if (!dummy)return; type = efl_gesture_type_get(dummy); efl_del(dummy); - // check if its already registered + //Check if its already registered recognizer = eina_hash_find(pd->m_recognizers, &type); if (!recognizer) return; - // remove that gesture from the list of object gestures + //Remove that gesture from the list of object gestures EINA_LIST_FOREACH_SAFE(pd->m_object_gestures, l, l_next, object_gesture) { if (object_gesture->type == type) @@ -270,9 +306,71 @@ _efl_canvas_gesture_manager_recognizer_unregister(Eo *obj EINA_UNUSED, Efl_Canva pd->m_object_gestures = eina_list_remove_list(pd->m_object_gestures, l); } } + eina_hash_del(pd->m_recognizers, &type, NULL); } +static Efl_Canvas_Gesture_Recognizer * +_find_match_recognizer(Efl_Canvas_Gesture_Manager_Data *pd, Efl_Canvas_Gesture_Recognizer_Type type) +{ + const Efl_Event_Description *event_type; + + switch (type) + { + case EFL_GESTURE_TAP: + { + event_type = EFL_EVENT_GESTURE_TAP; + break; + } + case EFL_GESTURE_DOUBLETAP: + { + event_type = EFL_EVENT_GESTURE_DOUBLE_TAP; + break; + } + case EFL_GESTURE_TRIPLETAP: + { + event_type = EFL_EVENT_GESTURE_TRIPLE_TAP; + break; + } + case EFL_GESTURE_LONGTAP: + { + event_type = EFL_EVENT_GESTURE_LONG_TAP; + break; + } + case EFL_GESTURE_MOMENTUM: + { + event_type = EFL_EVENT_GESTURE_MOMENTUM; + break; + } + case EFL_GESTURE_FLICK: + { + event_type = EFL_EVENT_GESTURE_FLICK; + break; + } + case EFL_GESTURE_ZOOM: + { + event_type = EFL_EVENT_GESTURE_ZOOM; + break; + } + default: + return NULL; + } + + return eina_hash_find(pd->m_recognizers, &event_type); +} + +EOLIAN static const Efl_Canvas_Gesture_Recognizer * +_efl_canvas_gesture_manager_recognizer_get(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Manager_Data *pd, + Efl_Canvas_Gesture_Recognizer_Type type) +{ + Efl_Canvas_Gesture_Recognizer *recognizer = _find_match_recognizer(pd, type); + + if (recognizer) + return recognizer; + else + return NULL; +} + // EOLIAN static void // _efl_canvas_gesture_manager_ungrab_all(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Manager_Data *pd, // Eo *target) @@ -291,7 +389,7 @@ _efl_canvas_gesture_manager_recognizer_unregister(Eo *obj EINA_UNUSED, Efl_Canva // eina_hash_del(pd->m_gesture_contex, &target, NULL); // } -// get or create a gesture object that will represent the state for a given object, used by the recognizer +//Get or create a gesture object that will represent the state for a given object, used by the recognizer Efl_Canvas_Gesture* _get_state(Efl_Canvas_Gesture_Manager_Data *pd, Eo *target, Efl_Canvas_Gesture_Recognizer *recognizer, const Efl_Event_Description *type) @@ -299,9 +397,11 @@ _get_state(Efl_Canvas_Gesture_Manager_Data *pd, Eina_List *l; Object_Gesture *object_gesture; Efl_Canvas_Gesture *gesture; + Efl_Canvas_Gesture_Recognizer_Data *rd = + efl_data_scope_get(recognizer, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); - // if the widget is being deleted we should be careful not to - // create a new state. + //If the widget is being deleted we should be careful not to + //Create a new state. if (efl_destructed_is(target)) return 0; @@ -310,19 +410,27 @@ _get_state(Efl_Canvas_Gesture_Manager_Data *pd, { if (object_gesture->object == target && object_gesture->recognizer == recognizer && - object_gesture->type == type) + object_gesture->type == type) { - // the gesture is already processed waiting for cleanup - if ((efl_gesture_state_get(object_gesture->gesture) == EFL_GESTURE_FINISHED) || - (efl_gesture_state_get(object_gesture->gesture) == EFL_GESTURE_CANCELED)) - return NULL; + //The gesture is already processed waiting for cleanup + if (((efl_gesture_state_get(object_gesture->gesture) == EFL_GESTURE_FINISHED) || + (efl_gesture_state_get(object_gesture->gesture) == EFL_GESTURE_CANCELED)) && + (!rd->continues)) + { + _cleanup_cached_gestures(pd, target, type); + eina_hash_del(pd->m_object_events, &type, NULL); + _cleanup_object(pd->m_gestures_to_delete); + pd->m_gestures_to_delete = NULL; + return NULL; + } return object_gesture->gesture; } } - gesture = efl_gesture_recognizer_create(recognizer, target); + gesture = efl_gesture_recognizer_add(recognizer, target); if (!gesture) return 0; + object_gesture = calloc(1, sizeof(Object_Gesture)); object_gesture->object = target; object_gesture->recognizer = recognizer; @@ -343,7 +451,7 @@ _cleanup_cached_gestures(Efl_Canvas_Gesture_Manager_Data *pd, EINA_LIST_FOREACH_SAFE(pd->m_object_gestures, l, l_next, object_gesture) { - if ( (object_gesture->type == type) && (target == object_gesture->object)) + if ((object_gesture->type == type) && (target == object_gesture->object)) { pd->m_gestures_to_delete = eina_list_append(pd->m_gestures_to_delete, object_gesture->gesture); free(object_gesture); @@ -371,4 +479,15 @@ _efl_canvas_gesture_manager_watches(const Efl_Event_Description *ev) return EINA_FALSE; } +void +efl_gesture_manager_gesture_clean_up(Eo *obj, Eo *target, const Efl_Event_Description *type) +{ + Efl_Canvas_Gesture_Manager_Data *pd = efl_data_scope_get(obj, MY_CLASS); + + _cleanup_cached_gestures(pd, target, type); + eina_hash_del(pd->m_object_events, &type, NULL); + _cleanup_object(pd->m_gestures_to_delete); + pd->m_gestures_to_delete = NULL; +} + #include "efl_canvas_gesture_manager.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_manager.eo b/src/lib/evas/gesture/efl_canvas_gesture_manager.eo index a39318aea0..d626ca16de 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_manager.eo +++ b/src/lib/evas/gesture/efl_canvas_gesture_manager.eo @@ -8,7 +8,6 @@ class @beta Efl.Canvas.Gesture_Manager extends Efl.Object params { @in recognizer: Efl.Canvas.Gesture_Recognizer; [[The gesture recognizer object]] } - return: ptr(const(Efl.Event_Description)); [[Returns the Efl.Event_Description type the recognizer supports]] } recognizer_unregister { [[This function is called to unregister a Efl.Canvas.Gesture_Recognizer]] @@ -16,6 +15,13 @@ class @beta Efl.Canvas.Gesture_Manager extends Efl.Object @in recognizer: Efl.Canvas.Gesture_Recognizer; [[The gesture recognizer object]] } } + recognizer_get { + [[Gets event type's recognizer]] + params { + @in gesture_type: Efl.Canvas.Gesture_Recognizer_Type; [[The gesture type]] + } + return: const(Efl.Canvas.Gesture_Recognizer); [[The gesture recognizer]] + } @property config { [[This property holds the config value for the recognizer]] set { diff --git a/src/lib/evas/gesture/efl_canvas_gesture_momentum.c b/src/lib/evas/gesture/efl_canvas_gesture_momentum.c new file mode 100644 index 0000000000..e7eb34ad2b --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_momentum.c @@ -0,0 +1,24 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_MOMENTUM_CLASS + +EOLIAN static Efl_Object * +_efl_canvas_gesture_momentum_efl_object_constructor(Eo *obj, Efl_Canvas_Gesture_Momentum_Data *pd EINA_UNUSED) +{ + Efl_Canvas_Gesture_Data *gd; + + obj = efl_constructor(efl_super(obj, MY_CLASS)); + + gd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_CLASS); + gd->type = EFL_EVENT_GESTURE_MOMENTUM; + + return obj; +} + +EOLIAN static Eina_Vector2 +_efl_canvas_gesture_momentum_momentum_get(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Momentum_Data *pd) +{ + return pd->momentum; +} + +#include "efl_canvas_gesture_momentum.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_momentum.eo b/src/lib/evas/gesture/efl_canvas_gesture_momentum.eo new file mode 100644 index 0000000000..c5aebcb5d2 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_momentum.eo @@ -0,0 +1,16 @@ +import eina_types; + +class @beta Efl.Canvas.Gesture_Momentum extends Efl.Canvas.Gesture +{ + [[EFL Gesture Momentum class]] + c_prefix: efl_gesture_momentum; + methods { + momentum_get { + [[Gets momentum value]] + return: Eina.Vector2; [[The momentum vector]] + } + } + implements { + Efl.Object.constructor; + } +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_private.h b/src/lib/evas/gesture/efl_canvas_gesture_private.h index c09fd26779..e1de45cb78 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_private.h +++ b/src/lib/evas/gesture/efl_canvas_gesture_private.h @@ -6,37 +6,154 @@ #define EFL_INTERNAL_UNSTABLE #include "interfaces/efl_common_internal.h" +#include "efl_gesture_events.eo.c" + #include -//private gesture classes -#include "efl_canvas_gesture_recognizer_tap.eo.h" -#include "efl_canvas_gesture_recognizer_long_tap.eo.h" +void efl_gesture_manager_gesture_clean_up(Eo *obj, Eo *target, const Efl_Event_Description *type); +typedef struct _Efl_Canvas_Gesture_Manager_Data Efl_Canvas_Gesture_Manager_Data; typedef struct _Efl_Canvas_Gesture_Recognizer_Data Efl_Canvas_Gesture_Recognizer_Data; +typedef struct _Efl_Canvas_Gesture_Recognizer_Tap_Data Efl_Canvas_Gesture_Recognizer_Tap_Data; +typedef struct _Efl_Canvas_Gesture_Recognizer_Long_Tap_Data Efl_Canvas_Gesture_Recognizer_Long_Tap_Data; +typedef struct _Efl_Canvas_Gesture_Recognizer_Double_Tap_Data Efl_Canvas_Gesture_Recognizer_Double_Tap_Data; +typedef struct _Efl_Canvas_Gesture_Recognizer_Triple_Tap_Data Efl_Canvas_Gesture_Recognizer_Triple_Tap_Data; +typedef struct _Efl_Canvas_Gesture_Recognizer_Momentum_Data Efl_Canvas_Gesture_Recognizer_Momentum_Data; +typedef struct _Efl_Canvas_Gesture_Recognizer_Flick_Data Efl_Canvas_Gesture_Recognizer_Flick_Data; +typedef struct _Efl_Canvas_Gesture_Recognizer_Zoom_Data Efl_Canvas_Gesture_Recognizer_Zoom_Data; typedef struct _Efl_Canvas_Gesture_Data Efl_Canvas_Gesture_Data; -typedef struct _Efl_Canvas_Gesture_Tap_Data Efl_Canvas_Gesture_Tap_Data; -typedef struct _Efl_Canvas_Gesture_Long_Tap_Data Efl_Canvas_Gesture_Long_Tap_Data; +typedef struct _Efl_Canvas_Gesture_Momentum_Data Efl_Canvas_Gesture_Momentum_Data; +typedef struct _Efl_Canvas_Gesture_Flick_Data Efl_Canvas_Gesture_Flick_Data; +typedef struct _Efl_Canvas_Gesture_Zoom_Data Efl_Canvas_Gesture_Zoom_Data; + +typedef struct _Pointer_Data +{ + struct + { + Eina_Position2D pos; + unsigned int timestamp; + } start, prev, cur; + int id; + Efl_Pointer_Action action; +} Pointer_Data; + +typedef struct _Efl_Canvas_Gesture_Touch_Data +{ + Efl_Canvas_Gesture_Touch_State state; + Eina_Hash *touch_points; + int touch_down; + Eina_Bool multi_touch; + Eo *target; +} Efl_Canvas_Gesture_Touch_Data; struct _Efl_Canvas_Gesture_Recognizer_Data { - Eo *manager; // keeps a reference of the manager + Eo *manager; // keeps a reference of the manager + Eo *gesture; + int finger_size; + Eina_Bool continues; +}; + +struct _Efl_Canvas_Gesture_Recognizer_Tap_Data +{ + Eo *target; + Eo *gesture; + Ecore_Timer *timeout; +}; + +struct _Efl_Canvas_Gesture_Recognizer_Long_Tap_Data +{ + Eina_List *target_timeout; + Eo *target; + Efl_Canvas_Gesture *gesture; + Ecore_Timer *timeout; + double start_timeout; + Eina_Bool is_timeout; +}; + +struct _Efl_Canvas_Gesture_Recognizer_Double_Tap_Data +{ + Eina_List *target_timeout; + Eo *target; + Eo *gesture; + Ecore_Timer *timeout; + double start_timeout; + Eina_Bool is_timeout; + int tap_count; +}; + +struct _Efl_Canvas_Gesture_Recognizer_Triple_Tap_Data +{ + Eina_List *target_timeout; + Eo *target; + Eo *gesture; + Ecore_Timer *timeout; + double start_timeout; + Eina_Bool is_timeout; + int tap_count; +}; + +struct _Efl_Canvas_Gesture_Recognizer_Momentum_Data +{ + Eina_Position2D st_line; + Eina_Position2D end_line; + unsigned int t_st; + unsigned int t_end; + int xdir; + int ydir; + Eina_Bool touched; +}; + +struct _Efl_Canvas_Gesture_Recognizer_Flick_Data +{ + Eina_Position2D st_line; + unsigned int t_st; + unsigned int t_end; + int line_length; + double line_angle; + Eina_Bool touched; +}; + +struct _Efl_Canvas_Gesture_Recognizer_Zoom_Data +{ + Pointer_Data zoom_st; + Pointer_Data zoom_st1; + + Pointer_Data zoom_mv; + Pointer_Data zoom_mv1; + + Evas_Coord zoom_base; /* Holds gap between fingers on + * zoom-start */ + double zoom_distance_tolerance; + double zoom_finger_factor; + double zoom_step; + double next_step; + Eina_Bool calc_temp; }; struct _Efl_Canvas_Gesture_Data { const Efl_Event_Description *type; - Efl_Canvas_Gesture_State state; - Eina_Vector2 hotspot; + Efl_Canvas_Gesture_State state; + Eina_Position2D hotspot; + unsigned int timestamp; }; -struct _Efl_Canvas_Gesture_Tap_Data +struct _Efl_Canvas_Gesture_Momentum_Data { + Eina_Vector2 momentum; }; -struct _Efl_Canvas_Gesture_Long_Tap_Data +struct _Efl_Canvas_Gesture_Flick_Data { - Ecore_Timer *timeout; - Eina_Bool is_timeout; + Eina_Vector2 momentum; + double angle; +}; + +struct _Efl_Canvas_Gesture_Zoom_Data +{ + double radius; + double zoom; }; #endif diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer.c b/src/lib/evas/gesture/efl_canvas_gesture_recognizer.c index eac5f1cecf..8a83e2f945 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_recognizer.c +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer.c @@ -2,6 +2,7 @@ #define MY_CLASS EFL_CANVAS_GESTURE_RECOGNIZER_CLASS +#define EFL_GESTURE_TAP_FINGER_SIZE 10 EOLIAN static Eina_Value * _efl_canvas_gesture_recognizer_config_get(const Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Recognizer_Data *pd, const char *name) { @@ -15,4 +16,13 @@ _efl_canvas_gesture_recognizer_reset(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Rec } +EOLIAN static Efl_Object * +_efl_canvas_gesture_recognizer_efl_object_constructor(Eo *obj, Efl_Canvas_Gesture_Recognizer_Data *pd) +{ + obj = efl_constructor(efl_super(obj, MY_CLASS)); + + pd->finger_size = EFL_GESTURE_TAP_FINGER_SIZE; + + return obj; +} #include "efl_canvas_gesture_recognizer.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer.eo b/src/lib/evas/gesture/efl_canvas_gesture_recognizer.eo index 857408913b..aaee7d29b1 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_recognizer.eo +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer.eo @@ -2,10 +2,18 @@ import efl_canvas_gesture_types; abstract @beta Efl.Canvas.Gesture_Recognizer extends Efl.Object { - [[EFL Gesture Recognizer abstract class]] + [[EFL Gesture Recognizer abstract class + + The gesture recognizer class grabs events that occur on the target + object that user register to see if a particluar gesture has occurred. + + Uesr can adjust the config value involved in gesture recognition + through the method provided by the gesture recognizer. + + The default config values follow the system default config value.]] c_prefix: efl_gesture_recognizer; methods { - create @pure_virtual { + add @pure_virtual { [[This function is called to create a new Efl.Canvas.Gesture object for the given target]] params { @in target: Efl.Object; [[The target widget]] @@ -44,4 +52,7 @@ abstract @beta Efl.Canvas.Gesture_Recognizer extends Efl.Object } } } + implements { + Efl.Object.constructor; + } } diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.c b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.c new file mode 100644 index 0000000000..1656bb633f --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.c @@ -0,0 +1,191 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_RECOGNIZER_DOUBLE_TAP_CLASS + +#define TAP_TIME_OUT 0.33 + +EOLIAN static Efl_Canvas_Gesture * +_efl_canvas_gesture_recognizer_double_tap_efl_canvas_gesture_recognizer_add(Eo *obj, Efl_Canvas_Gesture_Recognizer_Double_Tap_Data *pd EINA_UNUSED, Efl_Object *target EINA_UNUSED) +{ + return efl_add(EFL_CANVAS_GESTURE_DOUBLE_TAP_CLASS, obj); +} + +EOLIAN static void +_efl_canvas_gesture_recognizer_double_tap_efl_object_destructor(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Double_Tap_Data *pd) +{ + if (pd->timeout) + ecore_timer_del(pd->timeout); + + efl_destructor(efl_super(obj, MY_CLASS)); +} + +static Eina_Bool +_tap_timeout_cb(void *data) +{ + Efl_Canvas_Gesture_Recognizer_Data *rd; + Efl_Canvas_Gesture_Recognizer_Double_Tap_Data *pd; + + rd = efl_data_scope_get(data, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + pd = efl_data_scope_get(data, EFL_CANVAS_GESTURE_RECOGNIZER_DOUBLE_TAP_CLASS); + + efl_gesture_state_set(pd->gesture, EFL_GESTURE_CANCELED); + efl_event_callback_call(pd->target, EFL_EVENT_GESTURE_DOUBLE_TAP, pd->gesture); + + efl_gesture_manager_gesture_clean_up(rd->manager, pd->target, EFL_EVENT_GESTURE_DOUBLE_TAP); + + pd->timeout = NULL; + pd->tap_count = 0; + + return ECORE_CALLBACK_CANCEL; +} + +EOLIAN static Efl_Canvas_Gesture_Recognizer_Result +_efl_canvas_gesture_recognizer_double_tap_efl_canvas_gesture_recognizer_recognize(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Double_Tap_Data *pd, + Efl_Canvas_Gesture *gesture, Efl_Object *watched, + Efl_Canvas_Gesture_Touch *event) +{ + double length; + double timeout = TAP_TIME_OUT; + Eina_Position2D pos; + Eina_Vector2 dist; + Efl_Canvas_Gesture_Recognizer_Result result = EFL_GESTURE_CANCEL; + Efl_Canvas_Gesture_Recognizer_Data *rd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + + pd->target = watched; + pd->gesture = gesture; + + if (!pd->start_timeout) + { + double time; + Eina_Value *val = efl_gesture_recognizer_config_get(obj, "glayer_doublee_tap_timeout"); + + if (val) + { + eina_value_get(val, &time); + pd->start_timeout = timeout = time; + } + } + else + timeout = pd->start_timeout; + + switch (efl_gesture_touch_state_get(event)) + { + case EFL_GESTURE_TOUCH_BEGIN: + { + pos = efl_gesture_touch_start_point_get(event); + efl_gesture_hotspot_set(gesture, pos); + + if (pd->timeout) + ecore_timer_reset(pd->timeout); + else + pd->timeout = ecore_timer_add(timeout, _tap_timeout_cb, obj); + + result = EFL_GESTURE_TRIGGER; + + break; + } + + case EFL_GESTURE_TOUCH_UPDATE: + { + result = EFL_GESTURE_IGNORE; + + if (efl_gesture_state_get(gesture) != EFL_GESTURE_NONE && + !efl_gesture_touch_multi_touch_get(event)) + { + dist = efl_gesture_touch_distance(event, 0); + length = fabs(dist.x) + fabs(dist.y); + + if (length > rd->finger_size) + { + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + pd->timeout = NULL; + } + + result = EFL_GESTURE_CANCEL; + + pd->tap_count = 0; + } + } + + break; + } + case EFL_GESTURE_TOUCH_END: + { + + if (efl_gesture_state_get(gesture) != EFL_GESTURE_NONE && + !efl_gesture_touch_multi_touch_get(event)) + { + dist = efl_gesture_touch_distance(event, 0); + length = fabs(dist.x) + fabs(dist.y); + + if (length <= rd->finger_size) + { + pd->tap_count++; + if (pd->tap_count == 1) + { + if (pd->timeout) + ecore_timer_reset(pd->timeout); + + result = EFL_GESTURE_TRIGGER; + } + else + { + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + pd->timeout = NULL; + } + + if (efl_gesture_touch_state_get(event) == EFL_GESTURE_TOUCH_END) + result = EFL_GESTURE_FINISH; + else + result = EFL_GESTURE_TRIGGER; + + pd->tap_count = 0; + } + } + else + { + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + pd->timeout = NULL; + } + + result = EFL_GESTURE_CANCEL; + + pd->tap_count = 0; + } + } + + break; + } + + default: + + break; + } + + return result; +} + +EOLIAN static double +_efl_canvas_gesture_recognizer_double_tap_timeout_get(const Eo *obj EINA_UNUSED, + Efl_Canvas_Gesture_Recognizer_Double_Tap_Data *pd) +{ + return pd->start_timeout; +} + +EOLIAN static void +_efl_canvas_gesture_recognizer_double_tap_timeout_set(Eo *obj EINA_UNUSED, + Efl_Canvas_Gesture_Recognizer_Double_Tap_Data *pd, + double time) +{ + pd->start_timeout = time; +} + +#include "efl_canvas_gesture_recognizer_double_tap.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.eo b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.eo new file mode 100644 index 0000000000..9f3ab0a93c --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_double_tap.eo @@ -0,0 +1,22 @@ +class @beta Efl.Canvas.Gesture_Recognizer_Double_Tap extends Efl.Canvas.Gesture_Recognizer +{ + [[EFL Gesture Recognizer Double Tap class]] + c_prefix: efl_gesture_recognizer_double_tap; + methods { + @property timeout { + [[Sets the time between taps to be recognized as a double tap]] + set { + } + get { + } + values { + time: double; [[Allowed time gap value]] + } + } + } + implements { + Efl.Object.destructor; + Efl.Canvas.Gesture_Recognizer.add; + Efl.Canvas.Gesture_Recognizer.recognize; + } +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_flick.c b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_flick.c new file mode 100644 index 0000000000..4968c61b34 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_flick.c @@ -0,0 +1,354 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_RECOGNIZER_FLICK_CLASS + +#define MOMENTUM_TIMEOUT 50 +#define THUMBSCROLL_FRICTION 0.95 +#define THUMBSCROLL_MOMENTUM_THRESHOLD 100.0 +#define EFL_GESTURE_MINIMUM_MOMENTUM 0.001 + +#define RAD2DEG(x) ((x) * 57.295779513) +#define DEG2RAD(x) ((x) / 57.295779513) + +EOLIAN static Efl_Canvas_Gesture * +_efl_canvas_gesture_recognizer_flick_efl_canvas_gesture_recognizer_add(Eo *obj, Efl_Canvas_Gesture_Recognizer_Flick_Data *pd EINA_UNUSED, Efl_Object *target EINA_UNUSED) +{ + return efl_add(EFL_CANVAS_GESTURE_FLICK_CLASS, obj); +} + +static void +_momentum_set(Eo *obj, + Efl_Canvas_Gesture_Flick_Data *fd, + Eina_Position2D v1, + Eina_Position2D v2, + unsigned int t1, + unsigned int t2) +{ + Evas_Coord velx = 0, vely = 0, vel; + Evas_Coord dx = v2.x - v1.x; + Evas_Coord dy = v2.y - v1.y; + int dt = t2 - t1; + Eina_Value *tf, *tmt; + double thumbscroll_friction, thumbscroll_momentum_threshold; + + if (dt > 0) + { + velx = (dx * 1000) / dt; + vely = (dy * 1000) / dt; + } + + vel = sqrt((velx * velx) + (vely * vely)); + + tf = efl_gesture_recognizer_config_get(obj, "thumbscroll_friction"); + if (tf) eina_value_get(tf, &thumbscroll_friction); + else thumbscroll_friction = THUMBSCROLL_FRICTION; + + tmt = efl_gesture_recognizer_config_get(obj, "thumbscroll_momentum_threshold"); + if (tmt) eina_value_get(tmt, &thumbscroll_momentum_threshold); + else thumbscroll_momentum_threshold = THUMBSCROLL_MOMENTUM_THRESHOLD; + + if ((thumbscroll_friction > 0.0) && + (vel > thumbscroll_momentum_threshold)) /* report + * momentum */ + { + fd->momentum.x = velx; + fd->momentum.y = vely; + } + else + { + fd->momentum.x = 0; + fd->momentum.y = 0; + } +} + +static void +_single_line_process(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Flick_Data *pd, + Efl_Canvas_Gesture *gesture, + Efl_Canvas_Gesture_Flick_Data *fd, + Efl_Canvas_Gesture_Touch *event) +{ + switch (efl_gesture_touch_state_get(event)) + { + case EFL_GESTURE_TOUCH_BEGIN: + case EFL_GESTURE_TOUCH_UPDATE: + if (!pd->t_st) + { + pd->st_line = efl_gesture_touch_cur_point_get(event); + pd->t_st = efl_gesture_touch_cur_timestamp_get(event); + + efl_gesture_hotspot_set(gesture, pd->st_line); + + return; + } + + break; + + case EFL_GESTURE_TOUCH_END: + { + if (!pd->t_st) return; + + pd->t_end = efl_gesture_touch_cur_timestamp_get(event); + + break; + } + + default: + + return; + } + + _momentum_set(obj, fd, pd->st_line, efl_gesture_touch_cur_point_get(event), + pd->t_st, efl_gesture_touch_cur_timestamp_get(event)); +} + +static double +_angle_get(Evas_Coord xx1, + Evas_Coord yy1, + Evas_Coord xx2, + Evas_Coord yy2) +{ + double a, xx, yy, rt = (-1); + + xx = abs(xx2 - xx1); + yy = abs(yy2 - yy1); + + if (((int)xx) && ((int)yy)) + { + rt = a = RAD2DEG(atan(yy / xx)); + if (xx1 < xx2) + { + if (yy1 < yy2) rt = 360 - a; + else rt = a; + } + else + { + if (yy1 < yy2) rt = 180 + a; + else rt = 180 - a; + } + } + + if (rt < 0) /* Do this only if rt is not set */ + { + if (((int)xx)) /* Horizontal line */ + { + if (xx2 < xx1) rt = 180; + else rt = 0.0; + } + else + { /* Vertical line */ + if (yy2 < yy1) rt = 90; + else rt = 270; + } + } + + /* Now we want to change from: + * 90 0 + * original circle 180 0 We want: 270 90 + * 270 180 + */ + rt = 450 - rt; + if (rt >= 360) rt -= 360; + + return rt; +} + + +static void +_vector_get(Eina_Position2D v1, + Eina_Position2D v2, + int *l, + double *a) +{ + int xx, yy; + + xx = (int)(v2.x - v1.x); + yy = (int)(v2.y - v1.y); + *l = (int)sqrt((xx * xx) + (yy * yy)); + *a = _angle_get((int)v1.x, (int)v1.y, (int)v2.x, (int)v2.y); +} + +EOLIAN static Efl_Canvas_Gesture_Recognizer_Result +_efl_canvas_gesture_recognizer_flick_efl_canvas_gesture_recognizer_recognize(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Flick_Data *pd, + Efl_Canvas_Gesture *gesture, Efl_Object *watched, + Efl_Canvas_Gesture_Touch *event) +{ + double angle; + Eina_Value *val; + unsigned char glayer_continues_enable; + Efl_Canvas_Gesture_Recognizer_Result result = EFL_GESTURE_CANCEL; + Eina_Bool touch_up = EINA_FALSE; + Efl_Canvas_Gesture_Flick_Data *fd = efl_data_scope_get(gesture, EFL_CANVAS_GESTURE_FLICK_CLASS); + Efl_Canvas_Gesture_Recognizer_Data *rd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + + val = efl_gesture_recognizer_config_get(obj, "glayer_continues_enable"); + if (val) eina_value_get(val, &glayer_continues_enable); + else glayer_continues_enable = 1; + + //We need to cover events that occur continuously in the mouse down state + //without mouse up. + //Recognizing the gesture again, even though it was canceled during gesture + //recognition. + if (efl_gesture_state_get(gesture) == EFL_GESTURE_CANCELED) + efl_gesture_state_set(gesture, EFL_GESTURE_NONE); + + if (efl_gesture_touch_state_get(event) == EFL_GESTURE_TOUCH_END) + touch_up = EINA_TRUE; + + //This is to handle a case with a mouse click on the target object. + if (efl_gesture_touch_state_get(event) == EFL_GESTURE_TOUCH_END && !pd->touched) + efl_gesture_manager_gesture_clean_up(rd->manager, watched, EFL_EVENT_GESTURE_FLICK); + + if (glayer_continues_enable && !pd->touched) + { + pd->touched = EINA_TRUE; + pd->line_angle = -1.0; + rd->continues = EINA_TRUE; + + return EFL_GESTURE_IGNORE; + } + + _single_line_process(obj, pd, gesture, fd, event); + _vector_get(pd->st_line, efl_gesture_touch_cur_point_get(event), + &pd->line_length, &angle); + + if (pd->t_st) + { + if (pd->line_angle >= 0.0) + { + double line_distance_tolerance, line_angular_tolerance; + double a = fabs(angle - pd->line_angle); + double d = (tan(DEG2RAD(a))) * pd->line_length; + + val = efl_gesture_recognizer_config_get(obj, "glayer_line_distance_tolerance"); + if (val) eina_value_get(val, &line_distance_tolerance); + else line_distance_tolerance = 3.0; + + line_distance_tolerance *= rd->finger_size; + + val = efl_gesture_recognizer_config_get(obj, "glayer_line_angular_tolerance"); + if (val) eina_value_get(val, &line_angular_tolerance); + else line_angular_tolerance = 20.0; + + if ((d > line_distance_tolerance) || + (a > line_angular_tolerance)) + { + memset(pd, 0, sizeof(Efl_Canvas_Gesture_Recognizer_Flick_Data)); + + if (touch_up) rd->continues = EINA_FALSE; + + return EFL_GESTURE_CANCEL; + } + + /* We may finish line if momentum is zero */ + if (glayer_continues_enable) + { + /* This is for continues-gesture */ + /* Finish line on zero momentum for continues gesture */ + if ((!fd->momentum.x) && (!fd->momentum.y)) + pd->t_end = efl_gesture_touch_cur_timestamp_get(event); + } + } + else + { + double line_min_length; + + val = efl_gesture_recognizer_config_get(obj, "glayer_line_min_length"); + if (val) eina_value_get(val, &line_min_length); + else line_min_length = 1.0; + + line_min_length *= rd->finger_size; + + if (pd->line_length >= line_min_length) + fd->angle = pd->line_angle = angle; + + } + + if (pd->t_end) + { + if (pd->line_angle < 0.0) + { + memset(pd, 0, sizeof(Efl_Canvas_Gesture_Recognizer_Flick_Data)); + + if (touch_up) rd->continues = EINA_FALSE; + + return EFL_GESTURE_CANCEL; + } + } + } + + unsigned int tm_end = efl_gesture_touch_cur_timestamp_get(event); + if (pd->t_end) + { + if (pd->t_end < tm_end) + tm_end = pd->t_end; + } + + unsigned int time_limit_ms; + val = efl_gesture_recognizer_config_get(obj, "glayer_flick_time_limit_ms"); + if (val) eina_value_get(val, &time_limit_ms); + else time_limit_ms = 120; + + if ((tm_end - pd->t_st) > time_limit_ms) + { + memset(pd, 0, sizeof(Efl_Canvas_Gesture_Recognizer_Flick_Data)); + + if (touch_up) rd->continues = EINA_FALSE; + + return EFL_GESTURE_CANCEL; + } + + switch (efl_gesture_touch_state_get(event)) + { + case EFL_GESTURE_TOUCH_BEGIN: + case EFL_GESTURE_TOUCH_UPDATE: + { + if (pd->t_st) + { + if (glayer_continues_enable && pd->t_end) + { + result = EFL_GESTURE_FINISH; + } + else + { + result = EFL_GESTURE_TRIGGER; + } + } + break; + } + + case EFL_GESTURE_TOUCH_END: + { + if (!pd->t_st) + { + pd->touched = EINA_FALSE; + rd->continues = EINA_FALSE; + + return EFL_GESTURE_CANCEL; + } + if (pd->t_st && pd->t_end) + { + rd->continues = EINA_FALSE; + + result = EFL_GESTURE_FINISH; + } + + efl_gesture_hotspot_set(gesture, efl_gesture_touch_cur_point_get(event)); + + memset(pd, 0, sizeof(Efl_Canvas_Gesture_Recognizer_Flick_Data)); + + rd->continues = EINA_FALSE; + + break; + } + + default: + + break; + } + + return result; +} + +#include "efl_canvas_gesture_recognizer_flick.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_flick.eo b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_flick.eo new file mode 100644 index 0000000000..c7103ad33f --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_flick.eo @@ -0,0 +1,9 @@ +class @beta Efl.Canvas.Gesture_Recognizer_Flick extends Efl.Canvas.Gesture_Recognizer +{ + [[EFL Gesture Recognizer Flick Class]] + c_prefix: efl_gesture_recognizer_flick; + implements { + Efl.Canvas.Gesture_Recognizer.add; + Efl.Canvas.Gesture_Recognizer.recognize; + } +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.c b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.c index 9f5463cf49..8f6773588b 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.c +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.c @@ -2,36 +2,71 @@ #define MY_CLASS EFL_CANVAS_GESTURE_RECOGNIZER_LONG_TAP_CLASS -#define LONG_TAP_TIME_OUT 0.2 +#define EFL_GESTURE_LONG_TAP_TIME_OUT 1.2 EOLIAN static Efl_Canvas_Gesture * -_efl_canvas_gesture_recognizer_long_tap_efl_canvas_gesture_recognizer_create(Eo *obj, void *pd EINA_UNUSED, - Efl_Object *target EINA_UNUSED) +_efl_canvas_gesture_recognizer_long_tap_efl_canvas_gesture_recognizer_add(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Long_Tap_Data *pd EINA_UNUSED, + Efl_Object *target EINA_UNUSED) { return efl_add(EFL_CANVAS_GESTURE_LONG_TAP_CLASS, obj); } +EOLIAN static void +_efl_canvas_gesture_recognizer_long_tap_efl_object_destructor(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Long_Tap_Data *pd) +{ + if (pd->timeout) + ecore_timer_del(pd->timeout); + + efl_destructor(efl_super(obj, MY_CLASS)); +} + static Eina_Bool _long_tap_timeout_cb(void *data) { - Efl_Canvas_Gesture_Long_Tap_Data *ltp = data; + Efl_Canvas_Gesture_Recognizer_Long_Tap_Data *pd = data; /* FIXME: Needs to propagate this event back to evas! */ - ltp->is_timeout = EINA_TRUE; + pd->is_timeout = EINA_TRUE; + + efl_gesture_state_set(pd->gesture, EFL_GESTURE_UPDATED); + efl_event_callback_call(pd->target, EFL_EVENT_GESTURE_LONG_TAP, pd->gesture); return ECORE_CALLBACK_RENEW; } EOLIAN static Efl_Canvas_Gesture_Recognizer_Result -_efl_canvas_gesture_recognizer_long_tap_efl_canvas_gesture_recognizer_recognize(Eo *obj EINA_UNUSED, - void *pd EINA_UNUSED, - Efl_Canvas_Gesture *gesture, Efl_Object *watched EINA_UNUSED, - Efl_Canvas_Gesture_Touch *event) +_efl_canvas_gesture_recognizer_long_tap_efl_canvas_gesture_recognizer_recognize(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Long_Tap_Data *pd, + Efl_Canvas_Gesture *gesture, + Efl_Object *watched, + Efl_Canvas_Gesture_Touch *event) { double length; // Manhattan distance - Eina_Vector2 pos, dist; + double timeout = EFL_GESTURE_LONG_TAP_TIME_OUT; + Eina_Position2D pos; + Eina_Vector2 dist; Efl_Canvas_Gesture_Recognizer_Result result = EFL_GESTURE_CANCEL; - Efl_Canvas_Gesture_Long_Tap_Data *ltp = efl_data_scope_get(gesture, EFL_CANVAS_GESTURE_LONG_TAP_CLASS); + Efl_Canvas_Gesture_Recognizer_Data *rd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + + pd->target = watched; + pd->gesture = gesture; + + if (!pd->start_timeout) + { + double time; + Eina_Value *val = efl_gesture_recognizer_config_get(obj, "glayer_long_tap_start_timeout"); + + if (val) + { + eina_value_get(val, &time); + pd->start_timeout = timeout = time; + } + } + else + timeout = pd->start_timeout; + switch (efl_gesture_touch_state_get(event)) { @@ -39,49 +74,56 @@ _efl_canvas_gesture_recognizer_long_tap_efl_canvas_gesture_recognizer_recognize( { pos = efl_gesture_touch_start_point_get(event); efl_gesture_hotspot_set(gesture, pos); - if (ltp->timeout) - ecore_timer_del(ltp->timeout); - ltp->timeout = ecore_timer_add(LONG_TAP_TIME_OUT, - _long_tap_timeout_cb, ltp); - result = EFL_GESTURE_MAYBE; + + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + } + pd->timeout = ecore_timer_add(timeout, + _long_tap_timeout_cb, pd); + + result = EFL_GESTURE_TRIGGER; + break; } + case EFL_GESTURE_TOUCH_UPDATE: { - if (!efl_gesture_touch_multi_touch_get(event)) + dist = efl_gesture_touch_distance(event, 0); + length = fabs(dist.x) + fabs(dist.y); + + if ((efl_gesture_touch_multi_touch_get(event)) || (length > rd->finger_size)) { - dist = efl_gesture_touch_distance(event, 0); - length = fabs(dist.x) + fabs(dist.y); - if (length <= 50) // FIXME config! + if (pd->timeout) { - if (ltp->is_timeout) - { - ltp->is_timeout = EINA_FALSE; - result = EFL_GESTURE_TRIGGER; - } - else - { - result = EFL_GESTURE_MAYBE; - } - } - else - { - result = EFL_GESTURE_CANCEL; + ecore_timer_del(pd->timeout); + pd->timeout = NULL; } + + result = EFL_GESTURE_CANCEL; } + else + { + result = EFL_GESTURE_MAYBE; + } + break; } + case EFL_GESTURE_TOUCH_END: { - if (ltp->timeout) - ecore_timer_del(ltp->timeout); - ltp->timeout = NULL; + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + pd->timeout = NULL; + } + if (efl_gesture_state_get(gesture) != EFL_GESTURE_NONE && !efl_gesture_touch_multi_touch_get(event)) { dist = efl_gesture_touch_distance(event, 0); length = fabs(dist.x) + fabs(dist.y); - if (length <= 50 && ltp->is_timeout) // FIXME config! + if (length <= rd->finger_size && pd->is_timeout) { result = EFL_GESTURE_FINISH; } @@ -90,26 +132,45 @@ _efl_canvas_gesture_recognizer_long_tap_efl_canvas_gesture_recognizer_recognize( result = EFL_GESTURE_CANCEL; } } + break; } + default: + break; } + return result; } EOLIAN static void _efl_canvas_gesture_recognizer_long_tap_efl_canvas_gesture_recognizer_reset(Eo *obj, - void *pd EINA_UNUSED, - Efl_Canvas_Gesture *gesture) + Efl_Canvas_Gesture_Recognizer_Long_Tap_Data *pd, + Efl_Canvas_Gesture *gesture) { - Efl_Canvas_Gesture_Long_Tap_Data *ltp; - ltp = efl_data_scope_get(gesture, EFL_CANVAS_GESTURE_LONG_TAP_CLASS); - if (ltp->timeout) - ecore_timer_del(ltp->timeout); - ltp->timeout = NULL; - ltp->is_timeout = EINA_FALSE; + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + pd->timeout = NULL; + } + pd->is_timeout = EINA_FALSE; efl_gesture_recognizer_reset(efl_super(obj, MY_CLASS), gesture); } +EOLIAN static double +_efl_canvas_gesture_recognizer_long_tap_timeout_get(const Eo *obj EINA_UNUSED, + Efl_Canvas_Gesture_Recognizer_Long_Tap_Data *pd) +{ + return pd->start_timeout; +} + +EOLIAN static void +_efl_canvas_gesture_recognizer_long_tap_timeout_set(Eo *obj EINA_UNUSED, + Efl_Canvas_Gesture_Recognizer_Long_Tap_Data *pd, + double time) +{ + pd->start_timeout = time; +} + #include "efl_canvas_gesture_recognizer_long_tap.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.eo b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.eo index 8094655f13..7c8df2cfeb 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.eo +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_long_tap.eo @@ -1,10 +1,22 @@ class @beta Efl.Canvas.Gesture_Recognizer_Long_Tap extends Efl.Canvas.Gesture_Recognizer { [[EFL Gesture Recognizer Long Tap class]] - data: null; c_prefix: efl_gesture_recognizer_long_tap; + methods { + @property timeout { + [[Sets the holding time to be recognized as a long tap.]] + set { + } + get { + } + values { + time: double; [[Allowed time gap value]] + } + } + } implements { - Efl.Canvas.Gesture_Recognizer.create; + Efl.Object.destructor; + Efl.Canvas.Gesture_Recognizer.add; Efl.Canvas.Gesture_Recognizer.recognize; Efl.Canvas.Gesture_Recognizer.reset; } diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.c b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.c new file mode 100644 index 0000000000..34c9030ad3 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.c @@ -0,0 +1,197 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_RECOGNIZER_MOMENTUM_CLASS + +#define MOMENTUM_TIMEOUT 50 +#define THUMBSCROLL_FRICTION 0.95 +#define THUMBSCROLL_MOMENTUM_THRESHOLD 100.0 +#define EFL_GESTURE_MINIMUM_MOMENTUM 0.001 + +EOLIAN static Efl_Canvas_Gesture * +_efl_canvas_gesture_recognizer_momentum_efl_canvas_gesture_recognizer_add(Eo *obj, Efl_Canvas_Gesture_Recognizer_Momentum_Data *pd EINA_UNUSED, Efl_Object *target EINA_UNUSED) +{ + return efl_add(EFL_CANVAS_GESTURE_MOMENTUM_CLASS, obj); +} + +static void +_momentum_set(Eo *obj, + Efl_Canvas_Gesture_Momentum_Data *md, + Eina_Position2D v1, + Eina_Position2D v2, + unsigned int t1, + unsigned int t2) +{ + Evas_Coord velx = 0, vely = 0, vel; + Evas_Coord dx = v2.x - v1.x; + Evas_Coord dy = v2.y - v1.y; + int dt = t2 - t1; + Eina_Value *tf, *tmt; + double thumbscroll_friction, thumbscroll_momentum_threshold; + + if (dt > 0) + { + velx = (dx * 1000) / dt; + vely = (dy * 1000) / dt; + } + + vel = sqrt((velx * velx) + (vely * vely)); + + tf = efl_gesture_recognizer_config_get(obj, "thumbscroll_friction"); + if (tf) eina_value_get(tf, &thumbscroll_friction); + else thumbscroll_friction = THUMBSCROLL_FRICTION; + + tmt = efl_gesture_recognizer_config_get(obj, "thumbscroll_momentum_threshold"); + if (tmt) eina_value_get(tmt, &thumbscroll_momentum_threshold); + else thumbscroll_momentum_threshold = THUMBSCROLL_MOMENTUM_THRESHOLD; + + if ((thumbscroll_friction > 0.0) && + (vel > thumbscroll_momentum_threshold)) /* report + * momentum */ + { + md->momentum.x = velx; + md->momentum.y = vely; + } + else + { + md->momentum.x = 0; + md->momentum.y = 0; + } +} + +static int +_direction_get(Evas_Coord xx1, + Evas_Coord xx2) +{ + if (xx2 < xx1) return -1; + if (xx2 > xx1) return 1; + + return 0; +} + +EOLIAN static Efl_Canvas_Gesture_Recognizer_Result +_efl_canvas_gesture_recognizer_momentum_efl_canvas_gesture_recognizer_recognize(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Momentum_Data *pd, + Efl_Canvas_Gesture *gesture, Efl_Object *watched EINA_UNUSED, + Efl_Canvas_Gesture_Touch *event) +{ + Eina_Value *val; + unsigned char glayer_continues_enable; + Efl_Canvas_Gesture_Recognizer_Result result = EFL_GESTURE_CANCEL; + Efl_Canvas_Gesture_Momentum_Data *md = efl_data_scope_get(gesture, EFL_CANVAS_GESTURE_MOMENTUM_CLASS); + + val = efl_gesture_recognizer_config_get(obj, "glayer_continues_enable"); + if (val) eina_value_get(val, &glayer_continues_enable); + else glayer_continues_enable = 1; + + //Check the touched to ignore very first event. + //It does not have any meanging of this gesture. + if (glayer_continues_enable && !pd->touched) + { + pd->touched = EINA_TRUE; + + return EFL_GESTURE_IGNORE; + } + + switch (efl_gesture_touch_state_get(event)) + { + case EFL_GESTURE_TOUCH_BEGIN: + case EFL_GESTURE_TOUCH_UPDATE: + { + if (!pd->t_st) + { + if (efl_gesture_touch_state_get(event) == EFL_GESTURE_TOUCH_BEGIN || + glayer_continues_enable) + { + pd->t_st = pd->t_end = efl_gesture_touch_cur_timestamp_get(event); + + pd->st_line = pd->end_line = + efl_gesture_touch_start_point_get(event); + + efl_gesture_hotspot_set(gesture, pd->st_line); + + return EFL_GESTURE_TRIGGER; + } + } + + if ((efl_gesture_touch_cur_timestamp_get(event) - MOMENTUM_TIMEOUT) > + pd->t_end) + { + pd->st_line = efl_gesture_touch_cur_point_get(event); + pd->t_st = efl_gesture_touch_cur_timestamp_get(event); + pd->xdir = pd->ydir = 0; + } + else + { + int xdir, ydir; + Eina_Position2D cur_p = efl_gesture_touch_cur_point_get(event); + + xdir = _direction_get(pd->end_line.x, cur_p.x); + ydir = _direction_get(pd->end_line.y, cur_p.y); + + if (xdir && (xdir != pd->xdir)) + { + pd->st_line.x = pd->end_line.x; + pd->t_st = pd->t_end; + pd->xdir = xdir; + } + + if (ydir && (ydir != pd->ydir)) + { + pd->st_line.y = pd->end_line.y; + pd->t_st = pd->t_end; + pd->ydir = ydir; + } + } + + pd->end_line = efl_gesture_touch_cur_point_get(event); + pd->t_end = efl_gesture_touch_cur_timestamp_get(event); + efl_gesture_hotspot_set(gesture, pd->end_line); + + _momentum_set(obj, md, pd->st_line, efl_gesture_touch_cur_point_get(event), + pd->t_st, efl_gesture_touch_cur_timestamp_get(event)); + + result = EFL_GESTURE_TRIGGER; + + break; + } + + case EFL_GESTURE_TOUCH_END: + { + if (!pd->t_st) + { + pd->touched = EINA_FALSE; + + return EFL_GESTURE_CANCEL; + } + + if ((efl_gesture_touch_cur_timestamp_get(event) - MOMENTUM_TIMEOUT) > pd->t_end) + { + pd->st_line = efl_gesture_touch_cur_point_get(event); + pd->t_st = efl_gesture_touch_cur_timestamp_get(event); + pd->xdir = pd->ydir = 0; + } + + pd->end_line = efl_gesture_touch_cur_point_get(event); + pd->t_end = efl_gesture_touch_cur_timestamp_get(event); + efl_gesture_hotspot_set(gesture, pd->end_line); + + if ((abs(md->momentum.x) > EFL_GESTURE_MINIMUM_MOMENTUM) || + (abs(md->momentum.y) > EFL_GESTURE_MINIMUM_MOMENTUM)) + result = EFL_GESTURE_FINISH; + else + result = EFL_GESTURE_CANCEL; + + memset(pd, 0, sizeof(Efl_Canvas_Gesture_Recognizer_Momentum_Data)); + + break; + } + + default: + + break; + } + + return result; +} + +#include "efl_canvas_gesture_recognizer_momentum.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.eo b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.eo new file mode 100644 index 0000000000..1ae250dbba --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_momentum.eo @@ -0,0 +1,9 @@ +class @beta Efl.Canvas.Gesture_Recognizer_Momentum extends Efl.Canvas.Gesture_Recognizer +{ + [[EFL Gesture Recognizer Momentum class]] + c_prefix: efl_gesture_recognizer_momentum; + implements { + Efl.Canvas.Gesture_Recognizer.add; + Efl.Canvas.Gesture_Recognizer.recognize; + } +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_tap.c b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_tap.c index 2e4a5a6b76..8f53a0585a 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_tap.c +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_tap.c @@ -2,22 +2,45 @@ #define MY_CLASS EFL_CANVAS_GESTURE_RECOGNIZER_TAP_CLASS +//FIXME: It doesnt have matched config value. +// may using dobule tap timeout value? +#define EFL_GESTURE_TAP_TIME_OUT 0.33 + EOLIAN static Efl_Canvas_Gesture * -_efl_canvas_gesture_recognizer_tap_efl_canvas_gesture_recognizer_create(Eo *obj, void *pd EINA_UNUSED, - Efl_Object *target EINA_UNUSED) +_efl_canvas_gesture_recognizer_tap_efl_canvas_gesture_recognizer_add(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Tap_Data *pd EINA_UNUSED, + Efl_Object *target EINA_UNUSED) { return efl_add(EFL_CANVAS_GESTURE_TAP_CLASS, obj); } +static Eina_Bool +_tap_timeout_cb(void *data) +{ + Efl_Canvas_Gesture_Recognizer_Tap_Data *pd = data; + + efl_gesture_state_set(pd->gesture, EFL_GESTURE_CANCELED); + efl_event_callback_call(pd->target, EFL_EVENT_GESTURE_TAP, pd->gesture); + + return ECORE_CALLBACK_CANCEL; +} + + EOLIAN static Efl_Canvas_Gesture_Recognizer_Result -_efl_canvas_gesture_recognizer_tap_efl_canvas_gesture_recognizer_recognize(Eo *obj EINA_UNUSED, - void *pd EINA_UNUSED, - Efl_Canvas_Gesture *gesture, Efl_Object *watched EINA_UNUSED, - Efl_Canvas_Gesture_Touch *event EINA_UNUSED) +_efl_canvas_gesture_recognizer_tap_efl_canvas_gesture_recognizer_recognize(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Tap_Data *pd, + Efl_Canvas_Gesture *gesture, + Efl_Object *watched, + Efl_Canvas_Gesture_Touch *event) { double length; - Eina_Vector2 pos, dist; + Eina_Position2D pos; + Eina_Vector2 dist; Efl_Canvas_Gesture_Recognizer_Result result = EFL_GESTURE_CANCEL; + Efl_Canvas_Gesture_Recognizer_Data *rd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + + pd->target = watched; + pd->gesture = gesture; switch (efl_gesture_touch_state_get(event)) { @@ -25,18 +48,31 @@ _efl_canvas_gesture_recognizer_tap_efl_canvas_gesture_recognizer_recognize(Eo *o { pos = efl_gesture_touch_start_point_get(event); efl_gesture_hotspot_set(gesture, pos); + + if (pd->timeout) + ecore_timer_del(pd->timeout); + pd->timeout = ecore_timer_add(EFL_GESTURE_TAP_TIME_OUT, _tap_timeout_cb, pd); + result = EFL_GESTURE_TRIGGER; + break; } + case EFL_GESTURE_TOUCH_UPDATE: case EFL_GESTURE_TOUCH_END: { + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + pd->timeout = NULL; + } + if (efl_gesture_state_get(gesture) != EFL_GESTURE_NONE && !efl_gesture_touch_multi_touch_get(event)) { dist = efl_gesture_touch_distance(event, 0); length = fabs(dist.x) + fabs(dist.y); - if (length <= 50) // FIXME config! + if (length <= rd->finger_size) { if (efl_gesture_touch_state_get(event) == EFL_GESTURE_TOUCH_END) result = EFL_GESTURE_FINISH; @@ -44,11 +80,15 @@ _efl_canvas_gesture_recognizer_tap_efl_canvas_gesture_recognizer_recognize(Eo *o result = EFL_GESTURE_TRIGGER; } } + break; } + default: + break; } + return result; } diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_tap.eo b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_tap.eo index 65ae8c0c10..d7aabc7cdb 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_tap.eo +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_tap.eo @@ -1,10 +1,9 @@ class @beta Efl.Canvas.Gesture_Recognizer_Tap extends Efl.Canvas.Gesture_Recognizer { [[EFL Gesture Recognizer Tap class]] - data: null; c_prefix: efl_gesture_recognizer_tap; implements { - Efl.Canvas.Gesture_Recognizer.create; + Efl.Canvas.Gesture_Recognizer.add; Efl.Canvas.Gesture_Recognizer.recognize; } } diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.c b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.c new file mode 100644 index 0000000000..cd54d45886 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.c @@ -0,0 +1,191 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_RECOGNIZER_TRIPLE_TAP_CLASS + +#define TAP_TIME_OUT 0.33 + +EOLIAN static Efl_Canvas_Gesture * +_efl_canvas_gesture_recognizer_triple_tap_efl_canvas_gesture_recognizer_add(Eo *obj, Efl_Canvas_Gesture_Recognizer_Triple_Tap_Data *pd EINA_UNUSED, Efl_Object *target EINA_UNUSED) +{ + return efl_add(EFL_CANVAS_GESTURE_TRIPLE_TAP_CLASS, obj); +} + +EOLIAN static void +_efl_canvas_gesture_recognizer_triple_tap_efl_object_destructor(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Triple_Tap_Data *pd) +{ + if (pd->timeout) + ecore_timer_del(pd->timeout); + + efl_destructor(efl_super(obj, MY_CLASS)); +} + +static Eina_Bool +_tap_timeout_cb(void *data) +{ + Efl_Canvas_Gesture_Recognizer_Data *rd; + Efl_Canvas_Gesture_Recognizer_Triple_Tap_Data *pd; + + rd = efl_data_scope_get(data, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + pd = efl_data_scope_get(data, EFL_CANVAS_GESTURE_RECOGNIZER_TRIPLE_TAP_CLASS); + + efl_gesture_state_set(pd->gesture, EFL_GESTURE_CANCELED); + efl_event_callback_call(pd->target, EFL_EVENT_GESTURE_TRIPLE_TAP, pd->gesture); + + efl_gesture_manager_gesture_clean_up(rd->manager, pd->target, EFL_EVENT_GESTURE_TRIPLE_TAP); + + pd->timeout = NULL; + pd->tap_count = 0; + + return ECORE_CALLBACK_CANCEL; +} + +EOLIAN static Efl_Canvas_Gesture_Recognizer_Result +_efl_canvas_gesture_recognizer_triple_tap_efl_canvas_gesture_recognizer_recognize(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Triple_Tap_Data *pd, + Efl_Canvas_Gesture *gesture, Efl_Object *watched, + Efl_Canvas_Gesture_Touch *event) +{ + double length; + double timeout = TAP_TIME_OUT; + Eina_Position2D pos; + Eina_Vector2 dist; + Efl_Canvas_Gesture_Recognizer_Result result = EFL_GESTURE_CANCEL; + Efl_Canvas_Gesture_Recognizer_Data *rd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + + pd->target = watched; + pd->gesture = gesture; + + if (!pd->start_timeout) + { + double time; + Eina_Value *val = efl_gesture_recognizer_config_get(obj, "glayer_doublee_tap_timeout"); + + if (val) + { + eina_value_get(val, &time); + pd->start_timeout = timeout = time; + } + } + else + timeout = pd->start_timeout; + + switch (efl_gesture_touch_state_get(event)) + { + case EFL_GESTURE_TOUCH_BEGIN: + { + pos = efl_gesture_touch_start_point_get(event); + efl_gesture_hotspot_set(gesture, pos); + + if (pd->timeout) + ecore_timer_reset(pd->timeout); + else + pd->timeout = ecore_timer_add(timeout, _tap_timeout_cb, obj); + + result = EFL_GESTURE_TRIGGER; + + break; + } + + case EFL_GESTURE_TOUCH_UPDATE: + { + result = EFL_GESTURE_IGNORE; + + if (efl_gesture_state_get(gesture) != EFL_GESTURE_NONE && + !efl_gesture_touch_multi_touch_get(event)) + { + dist = efl_gesture_touch_distance(event, 0); + length = fabs(dist.x) + fabs(dist.y); + + if (length > rd->finger_size) + { + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + pd->timeout = NULL; + } + + result = EFL_GESTURE_CANCEL; + + pd->tap_count = 0; + } + } + + break; + } + case EFL_GESTURE_TOUCH_END: + { + + if (efl_gesture_state_get(gesture) != EFL_GESTURE_NONE && + !efl_gesture_touch_multi_touch_get(event)) + { + dist = efl_gesture_touch_distance(event, 0); + length = fabs(dist.x) + fabs(dist.y); + + if (length <= rd->finger_size) + { + pd->tap_count++; + if (pd->tap_count < 3) + { + if (pd->timeout) + ecore_timer_reset(pd->timeout); + + result = EFL_GESTURE_TRIGGER; + } + else + { + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + pd->timeout = NULL; + } + + if (efl_gesture_touch_state_get(event) == EFL_GESTURE_TOUCH_END) + result = EFL_GESTURE_FINISH; + else + result = EFL_GESTURE_TRIGGER; + + pd->tap_count = 0; + } + } + else + { + if (pd->timeout) + { + ecore_timer_del(pd->timeout); + pd->timeout = NULL; + } + + result = EFL_GESTURE_CANCEL; + + pd->tap_count = 0; + } + } + + break; + } + + default: + + break; + } + + return result; +} + +EOLIAN static double +_efl_canvas_gesture_recognizer_triple_tap_timeout_get(const Eo *obj EINA_UNUSED, + Efl_Canvas_Gesture_Recognizer_Triple_Tap_Data *pd) +{ + return pd->start_timeout; +} + +EOLIAN static void +_efl_canvas_gesture_recognizer_triple_tap_timeout_set(Eo *obj EINA_UNUSED, + Efl_Canvas_Gesture_Recognizer_Triple_Tap_Data *pd, + double time) +{ + pd->start_timeout = time; +} + +#include "efl_canvas_gesture_recognizer_triple_tap.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.eo b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.eo new file mode 100644 index 0000000000..2ed02bb047 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_triple_tap.eo @@ -0,0 +1,22 @@ +class @beta Efl.Canvas.Gesture_Recognizer_Triple_Tap extends Efl.Canvas.Gesture_Recognizer +{ + [[EFL Gesture Recognizer Triple Tap class]] + c_prefix: efl_gesture_recognizer_triple_tap; + methods { + @property timeout { + [[Sets the time between taps to be recognized as a double tap.]] + set { + } + get { + } + values { + time: double; [[Time value.]] + } + } + } + implements { + Efl.Object.destructor; + Efl.Canvas.Gesture_Recognizer.add; + Efl.Canvas.Gesture_Recognizer.recognize; + } +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.c b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.c new file mode 100644 index 0000000000..190e476312 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.c @@ -0,0 +1,275 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_RECOGNIZER_ZOOM_CLASS + +static Evas_Coord +_finger_gap_length_get(Evas_Coord xx1, + Evas_Coord yy1, + Evas_Coord xx2, + Evas_Coord yy2, + Evas_Coord *x, + Evas_Coord *y) +{ + double a, b, xx, yy, gap; + xx = abs(xx2 - xx1); + yy = abs(yy2 - yy1); + gap = sqrt((xx * xx) + (yy * yy)); + + /* START - Compute zoom center point */ + /* The triangle defined as follows: + * B + * / | + * / | + * gap / | a + * / | + * A-----C + * b + * http://en.wikipedia.org/wiki/Trigonometric_functions + *************************************/ + if (((int)xx) && ((int)yy)) + { + double A = atan((yy / xx)); + a = (Evas_Coord)((gap / 2) * sin(A)); + b = (Evas_Coord)((gap / 2) * cos(A)); + *x = (Evas_Coord)((xx2 > xx1) ? (xx1 + b) : (xx2 + b)); + *y = (Evas_Coord)((yy2 > yy1) ? (yy1 + a) : (yy2 + a)); + } + else + { + if ((int)xx) /* horiz line, take half width */ + { + *x = (Evas_Coord)((xx1 + xx2) / 2); + *y = (Evas_Coord)(yy1); + } + + if ((int)yy) /* vert line, take half width */ + { + *x = (Evas_Coord)(xx1); + *y = (Evas_Coord)((yy1 + yy2) / 2); + } + } + /* END - Compute zoom center point */ + + return (Evas_Coord)gap; +} + +static double +_zoom_compute(Efl_Canvas_Gesture_Recognizer_Zoom_Data *pd, + Efl_Canvas_Gesture_Zoom_Data *zd, + Evas_Coord xx1, + Evas_Coord yy1, + Evas_Coord xx2, + Evas_Coord yy2, + double zoom_finger_factor) +{ + double rt = 1.0; + //TODO: Enable below code if the zoom momentum is need + //unsigned int tm_end = (pd->zoom_mv.cur.timestamp > pd->zoom_mv1.cur.timestamp) ? + // pd->zoom_mv.cur.timestamp : pd->zoom_mv1.cur.timestamp; + + int x,y; //Hot spot + Evas_Coord diam = _finger_gap_length_get(xx1, yy1, xx2, yy2, + &x, &y); + + zd->radius = diam / 2; + + if (!pd->zoom_base) + { + pd->zoom_base = diam; + return zd->zoom; + } + + if (pd->zoom_distance_tolerance) /* zoom tolerance <> ZERO, means + * zoom action NOT started yet */ + { + /* avoid jump with zoom value when break tolerance */ + if (diam < (pd->zoom_base - pd->zoom_distance_tolerance)) + { + pd->zoom_base -= pd->zoom_distance_tolerance; + pd->zoom_distance_tolerance = 0; + } + + /* avoid jump with zoom value when break tolerance */ + if (diam > (pd->zoom_base + pd->zoom_distance_tolerance)) + { + pd->zoom_base += pd->zoom_distance_tolerance; + pd->zoom_distance_tolerance = 0; + } + + return rt; + } + + /* We use factor only on the difference between gap-base */ + /* if gap=120, base=100, we get ((120-100)/100)=0.2*factor */ + rt = ((1.0) + ((((float)diam - (float)pd->zoom_base) / + (float)pd->zoom_base) * zoom_finger_factor)); + + //TODO: Enable below code if the zoom momentum is need + /* Momentum: zoom per second: */ + //zd->momentum = _zoom_momentum_get(st, tm_end, rt); + + return rt; +} + +EOLIAN static Efl_Canvas_Gesture * +_efl_canvas_gesture_recognizer_zoom_efl_canvas_gesture_recognizer_add(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Zoom_Data *pd EINA_UNUSED, + Efl_Object *target EINA_UNUSED) +{ + return efl_add(EFL_CANVAS_GESTURE_ZOOM_CLASS, obj); +} + +EOLIAN static Efl_Canvas_Gesture_Recognizer_Result +_efl_canvas_gesture_recognizer_zoom_efl_canvas_gesture_recognizer_recognize(Eo *obj, + Efl_Canvas_Gesture_Recognizer_Zoom_Data *pd, + Efl_Canvas_Gesture *gesture, + Efl_Object *watched, + Efl_Canvas_Gesture_Touch *event) +{ + int id1 = 0; + int id2 = 1; + Eina_Value *val; + unsigned char zoom_finger_enable; + unsigned char glayer_continues_enable; + Efl_Canvas_Gesture_Recognizer_Result result = EFL_GESTURE_CANCEL; + Efl_Canvas_Gesture_Zoom_Data *zd = efl_data_scope_get(gesture, EFL_CANVAS_GESTURE_ZOOM_CLASS); + Efl_Canvas_Gesture_Touch_Data *td = efl_data_scope_get(event, EFL_CANVAS_GESTURE_TOUCH_CLASS); + Efl_Canvas_Gesture_Recognizer_Data *rd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_RECOGNIZER_CLASS); + + //FIXME: Wheel zoom test first here. + + val = efl_gesture_recognizer_config_get(obj, "glayer_continues_enable"); + if (val) eina_value_get(val, &glayer_continues_enable); + else glayer_continues_enable = 1; + + val = efl_gesture_recognizer_config_get(obj, "glayer_zoom_finger_enable"); + if (val) eina_value_get(val, &zoom_finger_enable); + else zoom_finger_enable = 1; + + val = efl_gesture_recognizer_config_get(obj, "glayer_zoom_finger_factor"); + if (val) eina_value_get(val, &pd->zoom_finger_factor); + else pd->zoom_finger_factor = 1.0; + + rd->continues = EINA_TRUE; + + if (!pd->zoom_distance_tolerance && !pd->calc_temp) + { + pd->calc_temp = EINA_TRUE; + val = efl_gesture_recognizer_config_get(obj, "glayer_zoom_distance_tolerance"); + if (val) eina_value_get(val, &pd->zoom_distance_tolerance); + else pd->zoom_distance_tolerance = 1.0; + + pd->zoom_distance_tolerance *= rd->finger_size; + } + + switch (efl_gesture_touch_state_get(event)) + { + case EFL_GESTURE_TOUCH_UPDATE: + { + if ((!glayer_continues_enable) && (!pd->zoom_st.cur.timestamp)) + { + return EFL_GESTURE_IGNORE; + } + EINA_FALLTHROUGH; + } + case EFL_GESTURE_TOUCH_BEGIN: + { + if (td->touch_down > 2) + { + return EFL_GESTURE_CANCEL; + } + + if (!pd->zoom_st.cur.timestamp) /* Now scan touched-devices list + * and find other finger */ + { + if (!efl_gesture_touch_multi_touch_get(event)) + return EFL_GESTURE_IGNORE; + + Pointer_Data *p1 = eina_hash_find(td->touch_points, &id1); + Pointer_Data *p2 = eina_hash_find(td->touch_points, &id2); + + memcpy(&pd->zoom_st, p2, sizeof(Pointer_Data)); + memcpy(&pd->zoom_st1, p1, sizeof(Pointer_Data)); + + memcpy(&pd->zoom_mv, p2, sizeof(Pointer_Data)); + memcpy(&pd->zoom_mv1, p1, sizeof(Pointer_Data)); + + int x,y; //Hot spot + zd->zoom = 1.0; + pd->zoom_base = _finger_gap_length_get(pd->zoom_st1.cur.pos.x, + pd->zoom_st1.cur.pos.y, + pd->zoom_st.cur.pos.x, + pd->zoom_st.cur.pos.y, + &x, &y); + + zd->radius = pd->zoom_base / 2; + + if ((efl_gesture_state_get(gesture) != EFL_GESTURE_STARTED) && + (efl_gesture_state_get(gesture) != EFL_GESTURE_UPDATED)) + return EFL_GESTURE_TRIGGER; + + return EFL_GESTURE_CANCEL; + } + + Pointer_Data *p2 = eina_hash_find(td->touch_points, &id2); + if (p2->id == pd->zoom_mv.id) + memcpy(&pd->zoom_mv, p2, sizeof(Pointer_Data)); + else if (p2->id == pd->zoom_mv1.id) + memcpy(&pd->zoom_mv1, p2, sizeof(Pointer_Data)); + + zd->zoom = _zoom_compute(pd, zd, pd->zoom_mv.cur.pos.x, + pd->zoom_mv.cur.pos.y, pd->zoom_mv1.cur.pos.x, + pd->zoom_mv1.cur.pos.y, pd->zoom_finger_factor); + + + if (!pd->zoom_distance_tolerance) + { + double d = zd->zoom - pd->next_step; + + if (d < 0.0) d = (-d); + + if (d >= pd->zoom_step) + { + pd->next_step = zd->zoom; + + return EFL_GESTURE_TRIGGER; + } + } + + return EFL_GESTURE_IGNORE; + } + case EFL_GESTURE_TOUCH_END: + { + if (td->touch_down == 0) + { + rd->continues = EINA_FALSE; + + memset(pd, 0, sizeof(Efl_Canvas_Gesture_Recognizer_Zoom_Data)); + efl_gesture_manager_gesture_clean_up(rd->manager, watched, EFL_EVENT_GESTURE_ZOOM); + + return EFL_GESTURE_IGNORE; + } + if ((pd->zoom_base) && (pd->zoom_distance_tolerance == 0)) + { + memset(pd, 0, sizeof(Efl_Canvas_Gesture_Recognizer_Zoom_Data)); + + return EFL_GESTURE_FINISH; + } + + if (efl_gesture_state_get(gesture) != EFL_GESTURE_NONE) + { + memset(pd, 0, sizeof(Efl_Canvas_Gesture_Recognizer_Zoom_Data)); + + return EFL_GESTURE_CANCEL; + } + } + + default: + + break; + } + + return result; +} + +#include "efl_canvas_gesture_recognizer_zoom.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.eo b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.eo new file mode 100644 index 0000000000..350614c50c --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_recognizer_zoom.eo @@ -0,0 +1,9 @@ +class @beta Efl.Canvas.Gesture_Recognizer_Zoom extends Efl.Canvas.Gesture_Recognizer +{ + [[EFL Gesture Recognizer Zoom class]] + c_prefix: efl_gesture_recognizer_zoom; + implements { + Efl.Canvas.Gesture_Recognizer.add; + Efl.Canvas.Gesture_Recognizer.recognize; + } +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_tap.c b/src/lib/evas/gesture/efl_canvas_gesture_tap.c index aca24a9dbd..d777bebba1 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_tap.c +++ b/src/lib/evas/gesture/efl_canvas_gesture_tap.c @@ -2,9 +2,8 @@ #define MY_CLASS EFL_CANVAS_GESTURE_TAP_CLASS - EOLIAN static Efl_Object * -_efl_canvas_gesture_tap_efl_object_constructor(Eo *obj, Efl_Canvas_Gesture_Tap_Data *pd EINA_UNUSED) +_efl_canvas_gesture_tap_efl_object_constructor(Eo *obj, void *pd EINA_UNUSED) { Efl_Canvas_Gesture_Data *gd; diff --git a/src/lib/evas/gesture/efl_canvas_gesture_tap.eo b/src/lib/evas/gesture/efl_canvas_gesture_tap.eo index a994b90abe..bd6daba234 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_tap.eo +++ b/src/lib/evas/gesture/efl_canvas_gesture_tap.eo @@ -1,11 +1,8 @@ class @beta Efl.Canvas.Gesture_Tap extends Efl.Canvas.Gesture { [[EFL Gesture Tap class]] + data: null; c_prefix: efl_gesture_tap; - event_prefix: efl; - events { - gesture,tap: Efl.Canvas.Gesture; [[Event for tap gesture]] - } implements { Efl.Object.constructor; } diff --git a/src/lib/evas/gesture/efl_canvas_gesture_touch.c b/src/lib/evas/gesture/efl_canvas_gesture_touch.c index 9f997f59e6..4a5f5ca422 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_touch.c +++ b/src/lib/evas/gesture/efl_canvas_gesture_touch.c @@ -2,29 +2,9 @@ #define MY_CLASS EFL_CANVAS_GESTURE_TOUCH_CLASS -typedef struct _Pointer_Data -{ - struct - { - Eina_Vector2 pos; - double timestamp; - } start, prev, cur; - Efl_Pointer_Action action; -} Pointer_Data; - -typedef struct _Efl_Canvas_Gesture_Touch_Data -{ - Efl_Canvas_Gesture_Touch_State state; - Eina_Hash *touch_points; - int touch_down; - Eina_Bool multi_touch; - Eo *target; -} Efl_Canvas_Gesture_Touch_Data; - - -// This event object accumulates all the touch points -// that are directed to a particular object from the -// first finger down to the last finger up +//This event object accumulates all the touch points +//that are directed to a particular object from the +//first finger down to the last finger up static void _hash_free_cb(Pointer_Data *point) { @@ -63,40 +43,52 @@ _efl_canvas_gesture_touch_state_get(const Eo *obj EINA_UNUSED, Efl_Canvas_Gestur EOLIAN static void _efl_canvas_gesture_touch_point_record(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Touch_Data *pd, - int id, Eina_Vector2 pos, double timestamp, Efl_Pointer_Action action) + int id, Eina_Vector2 pos, unsigned int timestamp, Efl_Pointer_Action action) { Pointer_Data *point = eina_hash_find(pd->touch_points, &id); + Eina_Position2D _pos = { pos.x, pos.y }; if (action == EFL_POINTER_ACTION_DOWN) - pd->touch_down++; + { + pd->touch_down++; + //TODO: Need to handle 2 or more case. + if (pd->touch_down == 2) + pd->multi_touch = EINA_TRUE; + } else if ((action == EFL_POINTER_ACTION_UP) || (action == EFL_POINTER_ACTION_CANCEL)) - pd->touch_down--; - EINA_SAFETY_ON_FALSE_GOTO(pd->touch_down >= 0, bad_fingers); + { + pd->touch_down--; + if (pd->multi_touch && pd->touch_down == 1) + pd->multi_touch = EINA_FALSE; + } + + if (pd->touch_down < 0) goto finished_touch; if (point) { - // the point already exists. update the cur and prev point + //The point already exists. update the cur and prev point point->prev = point->cur; - point->cur.pos = pos; + point->cur.pos = _pos; point->cur.timestamp = timestamp; } else { - // new finger + //New finger if (!id && (action != EFL_POINTER_ACTION_DOWN)) { - // discard any other event + //Discard any other event return; } point = calloc(1, sizeof(Pointer_Data)); if (!point) return; - point->start.pos = point->prev.pos = point->cur.pos = pos; + point->start.pos = point->prev.pos = point->cur.pos = _pos; point->start.timestamp = point->prev.timestamp = point->cur.timestamp = timestamp; + point->id = id; - // add to the hash + //Add to the hash eina_hash_add(pd->touch_points, &id, point); - // FIXME: finger_list was broken + //FIXME: finger_list was broken if (id) pd->multi_touch = EINA_TRUE; } @@ -106,7 +98,7 @@ _efl_canvas_gesture_touch_point_record(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_T { pd->state = EFL_GESTURE_TOUCH_BEGIN; } - else if ((action == EFL_POINTER_ACTION_UP) && (pd->touch_down == 0)) + else if (action == EFL_POINTER_ACTION_UP) { pd->state = EFL_GESTURE_TOUCH_END; } @@ -116,8 +108,7 @@ _efl_canvas_gesture_touch_point_record(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_T } return; -bad_fingers: - ERR("Inconsistent touch events received!"); +finished_touch: _touch_points_reset(pd); } @@ -127,12 +118,12 @@ _efl_canvas_gesture_touch_multi_touch_get(const Eo *obj EINA_UNUSED, Efl_Canvas_ return pd->multi_touch; } -EOLIAN static Eina_Vector2 +EOLIAN static Eina_Position2D _efl_canvas_gesture_touch_start_point_get(const Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Touch_Data *pd) { int tool = 0; Pointer_Data *point = eina_hash_find(pd->touch_points, &tool); - Eina_Vector2 vec = { 0, 0 }; + Eina_Position2D vec = { 0, 0 }; if (!point) return vec; @@ -140,16 +131,43 @@ _efl_canvas_gesture_touch_start_point_get(const Eo *obj EINA_UNUSED, Efl_Canvas_ return point->start.pos; } +EOLIAN static Eina_Position2D +_efl_canvas_gesture_touch_cur_point_get(const Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Touch_Data *pd) +{ + int tool = 0; + Pointer_Data *point = eina_hash_find(pd->touch_points, &tool); + Eina_Position2D vec = { 0, 0 }; + + if (!point) + return vec; + + return point->cur.pos; +} + +EOLIAN static unsigned int +_efl_canvas_gesture_touch_cur_timestamp_get(const Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Touch_Data *pd) +{ + int tool = 0; + Pointer_Data *point = eina_hash_find(pd->touch_points, &tool); + + if (!point) + return 0; + + return point->cur.timestamp; +} + EOLIAN static Eina_Vector2 _efl_canvas_gesture_touch_delta(const Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Touch_Data *pd, int tool) { Pointer_Data *point = eina_hash_find(pd->touch_points, &tool); Eina_Vector2 vec = { 0, 0 }; + Eina_Vector2 v1 = { point->cur.pos.x, point->cur.pos.y }; + Eina_Vector2 v2 = { point->prev.pos.x, point->prev.pos.y }; if (!point) return vec; - eina_vector2_subtract(&vec, &point->cur.pos, &point->prev.pos); + eina_vector2_subtract(&vec, &v1, &v2); return vec; } @@ -158,11 +176,13 @@ _efl_canvas_gesture_touch_distance(const Eo *obj EINA_UNUSED, Efl_Canvas_Gesture { Pointer_Data *point = eina_hash_find(pd->touch_points, &tool); Eina_Vector2 vec = { 0, 0 }; + Eina_Vector2 v1 = { point->cur.pos.x, point->cur.pos.y }; + Eina_Vector2 v2 = { point->start.pos.x, point->start.pos.y }; if (!point) return vec; - eina_vector2_subtract(&vec, &point->cur.pos, &point->start.pos); + eina_vector2_subtract(&vec, &v1, &v2); return vec; } diff --git a/src/lib/evas/gesture/efl_canvas_gesture_touch.eo b/src/lib/evas/gesture/efl_canvas_gesture_touch.eo index 4109b47de4..8b78e192de 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_touch.eo +++ b/src/lib/evas/gesture/efl_canvas_gesture_touch.eo @@ -13,7 +13,7 @@ class @beta Efl.Canvas.Gesture_Touch extends Efl.Object params { @in tool : int; [[The finger id ]] @in pos : Eina.Vector2; [[Position of the event]] - @in timestamp : double; [[The timestamp of the event]] + @in timestamp : uint; [[The timestamp of the event]] @in action : Efl.Pointer.Action; [[action of the event]] } } @@ -36,7 +36,21 @@ class @beta Efl.Canvas.Gesture_Touch extends Efl.Object [[Returns the first touch point.]] get {} values { - pos: Eina.Vector2; [[The start position.]] + pos: Eina.Position2D; [[The start position.]] + } + } + @property cur_point { + [[Returns the current touch point.]] + get {} + values { + pos: Eina.Position2D; [[The current position.]] + } + } + @property cur_timestamp { + [[Returns the timestamp.]] + get {} + values { + time: uint; [[The timestamp.]] } } @property multi_touch { diff --git a/src/lib/evas/gesture/efl_canvas_gesture_triple_tap.c b/src/lib/evas/gesture/efl_canvas_gesture_triple_tap.c new file mode 100644 index 0000000000..5a6bb2f126 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_triple_tap.c @@ -0,0 +1,18 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_TRIPLE_TAP_CLASS + +EOLIAN static Efl_Object * +_efl_canvas_gesture_triple_tap_efl_object_constructor(Eo *obj, void *pd EINA_UNUSED) +{ + Efl_Canvas_Gesture_Data *gd; + + obj = efl_constructor(efl_super(obj, MY_CLASS)); + + gd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_CLASS); + gd->type = EFL_EVENT_GESTURE_TRIPLE_TAP; + + return obj; +} + +#include "efl_canvas_gesture_triple_tap.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_triple_tap.eo b/src/lib/evas/gesture/efl_canvas_gesture_triple_tap.eo new file mode 100644 index 0000000000..bab59c68fa --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_triple_tap.eo @@ -0,0 +1,9 @@ +class @beta Efl.Canvas.Gesture_Triple_Tap extends Efl.Canvas.Gesture +{ + [[EFL Gesture Triple Tap class]] + data: null; + c_prefix: efl_gesture_triple_tap; + implements { + Efl.Object.constructor; + } +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_types.eot b/src/lib/evas/gesture/efl_canvas_gesture_types.eot index 8be4528405..96a2ff6293 100644 --- a/src/lib/evas/gesture/efl_canvas_gesture_types.eot +++ b/src/lib/evas/gesture/efl_canvas_gesture_types.eot @@ -31,3 +31,16 @@ enum @beta Efl.Canvas.Gesture_Recognizer_Result cancel = 0x0010, [[The event made it clear that it is not a gesture. If the gesture recognizer was in Triggered state before, then the gesture is canceled.]] result_mask = 0x00ff, [[The gesture result mask]] } + +enum @beta Efl.Canvas.Gesture_Recognizer_Type +{ + [[ This enum type describes the state of a touch event. ]] + legacy: efl_gesture; + tap = 0, + doubleTap, + tripleTap, + longTap, + momentum, + flick, + zoom, +} diff --git a/src/lib/evas/gesture/efl_canvas_gesture_zoom.c b/src/lib/evas/gesture/efl_canvas_gesture_zoom.c new file mode 100644 index 0000000000..3ac4ffcbf4 --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_zoom.c @@ -0,0 +1,35 @@ +#include "efl_canvas_gesture_private.h" + +#define MY_CLASS EFL_CANVAS_GESTURE_ZOOM_CLASS + +EOLIAN static Efl_Object * +_efl_canvas_gesture_zoom_efl_object_constructor(Eo *obj, Efl_Canvas_Gesture_Zoom_Data *pd EINA_UNUSED) +{ + Efl_Canvas_Gesture_Data *gd; + + obj = efl_constructor(efl_super(obj, MY_CLASS)); + gd = efl_data_scope_get(obj, EFL_CANVAS_GESTURE_CLASS); + gd->type = EFL_EVENT_GESTURE_ZOOM; + + return obj; +} + +EOLIAN static void +_efl_canvas_gesture_zoom_efl_object_destructor(Eo *obj, Efl_Canvas_Gesture_Zoom_Data *pd EINA_UNUSED) +{ + efl_destructor(efl_super(obj, MY_CLASS)); +} + +EOLIAN static double +_efl_canvas_gesture_zoom_radius_get(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Zoom_Data *pd) +{ + return pd->radius; +} + +EOLIAN static double +_efl_canvas_gesture_zoom_zoom_get(Eo *obj EINA_UNUSED, Efl_Canvas_Gesture_Zoom_Data *pd) +{ + return pd->zoom; +} + +#include "efl_canvas_gesture_zoom.eo.c" diff --git a/src/lib/evas/gesture/efl_canvas_gesture_zoom.eo b/src/lib/evas/gesture/efl_canvas_gesture_zoom.eo new file mode 100644 index 0000000000..1cb7f7d48b --- /dev/null +++ b/src/lib/evas/gesture/efl_canvas_gesture_zoom.eo @@ -0,0 +1,19 @@ +class @beta Efl.Canvas.Gesture_Zoom extends Efl.Canvas.Gesture +{ + [[EFL Gesture Zoom class]] + c_prefix: efl_gesture_zoom; + methods { + radius_get { + [[Gets zoom center point reported to user]] + return: double; [[The radius value]] + } + zoom_get { + [[Gets zoom value. (1.0 means no zoom)]] + return: double; [[The zoom value]] + } + } + implements { + Efl.Object.constructor; + Efl.Object.destructor; + } +} diff --git a/src/lib/evas/gesture/efl_gesture_events.eo b/src/lib/evas/gesture/efl_gesture_events.eo new file mode 100644 index 0000000000..376b51ef4b --- /dev/null +++ b/src/lib/evas/gesture/efl_gesture_events.eo @@ -0,0 +1,13 @@ +interface @beta Efl.Gesture.Events +{ + event_prefix: efl; + events { + gesture,tap: Efl.Canvas.Gesture_Tap; [[Event for tap gesture]] + gesture,double_tap: Efl.Canvas.Gesture_Double_Tap; [[Event for double tap gesture]] + gesture,triple_tap: Efl.Canvas.Gesture_Triple_Tap; [[Event for triple tap gesture]] + gesture,long_tap: Efl.Canvas.Gesture_Long_Tap; [[Event for long tap gesture]] + gesture,momentum: Efl.Canvas.Gesture_Momentum; [[Event for momentum gesture]] + gesture,flick: Efl.Canvas.Gesture_Flick; [[Event for flick gesture]] + gesture,zoom: Efl.Canvas.Gesture_Zoom; [[Event for zoom gesture]] + } +} diff --git a/src/lib/evas/gesture/meson.build b/src/lib/evas/gesture/meson.build index 3765a0b67d..3c7847aeac 100644 --- a/src/lib/evas/gesture/meson.build +++ b/src/lib/evas/gesture/meson.build @@ -2,9 +2,22 @@ pub_eo_files = [ 'efl_canvas_gesture_touch.eo', 'efl_canvas_gesture.eo', 'efl_canvas_gesture_tap.eo', + 'efl_canvas_gesture_double_tap.eo', + 'efl_canvas_gesture_triple_tap.eo', 'efl_canvas_gesture_long_tap.eo', + 'efl_canvas_gesture_momentum.eo', + 'efl_canvas_gesture_flick.eo', + 'efl_canvas_gesture_zoom.eo', 'efl_canvas_gesture_recognizer.eo', - 'efl_canvas_gesture_manager.eo' + 'efl_canvas_gesture_recognizer_tap.eo', + 'efl_canvas_gesture_recognizer_double_tap.eo', + 'efl_canvas_gesture_recognizer_triple_tap.eo', + 'efl_canvas_gesture_recognizer_long_tap.eo', + 'efl_canvas_gesture_recognizer_momentum.eo', + 'efl_canvas_gesture_recognizer_flick.eo', + 'efl_canvas_gesture_recognizer_zoom.eo', + 'efl_canvas_gesture_manager.eo', + 'efl_gesture_events.eo' ] evas_gesture_eo_files = pub_eo_files @@ -16,28 +29,7 @@ foreach eo_file : pub_eo_files depfile : eo_file + '.d', install : true, install_dir : join_paths(dir_package_include, 'gesture'), - command : eolian_gen + [ '-I', meson.current_source_dir(), eolian_include_directories, - '-o', 'h:' + join_paths(meson.current_build_dir(), eo_file + '.h'), - '-o', 'c:' + join_paths(meson.current_build_dir(), eo_file + '.c'), - '-o', 'd:' + join_paths(meson.current_build_dir(), eo_file + '.d'), - '-gchd', '@INPUT@']) -endforeach - -pub_evas_eo_files += files(pub_eo_files) - -pub_eo_files = [ - 'efl_canvas_gesture_recognizer_tap.eo', - 'efl_canvas_gesture_recognizer_long_tap.eo' -] - -foreach eo_file : pub_eo_files - pub_eo_file_target += custom_target('eolian_gen_' + eo_file, - input : eo_file, - output : [eo_file + '.h'], - depfile : eo_file + '.d', - install : false, - install_dir : join_paths(dir_package_include, 'gesture'), - command : eolian_gen + [ '-I', meson.current_source_dir(), eolian_include_directories, + command : [eolian_gen, '-I', meson.current_source_dir(), eolian_include_directories, '-o', 'h:' + join_paths(meson.current_build_dir(), eo_file + '.h'), '-o', 'c:' + join_paths(meson.current_build_dir(), eo_file + '.c'), '-o', 'd:' + join_paths(meson.current_build_dir(), eo_file + '.d'), @@ -59,7 +51,7 @@ foreach eo_file : pub_eo_types_files depfile : eo_file + '.d', install : true, install_dir : join_paths(dir_package_include, 'gesture'), - command : eolian_gen + [ '-I', meson.current_source_dir(), eolian_include_directories, + command : [eolian_gen, '-I', meson.current_source_dir(), eolian_include_directories, '-o', 'h:' + join_paths(meson.current_build_dir(), eo_file + '.h'), '-o', 'd:' + join_paths(meson.current_build_dir(), eo_file + '.d'), '-ghd', '@INPUT@']) @@ -69,10 +61,20 @@ evas_src += files([ 'efl_canvas_gesture_touch.c', 'efl_canvas_gesture.c', 'efl_canvas_gesture_tap.c', + 'efl_canvas_gesture_double_tap.c', + 'efl_canvas_gesture_triple_tap.c', 'efl_canvas_gesture_long_tap.c', + 'efl_canvas_gesture_momentum.c', + 'efl_canvas_gesture_flick.c', + 'efl_canvas_gesture_zoom.c', 'efl_canvas_gesture_recognizer.c', 'efl_canvas_gesture_recognizer_tap.c', + 'efl_canvas_gesture_recognizer_double_tap.c', + 'efl_canvas_gesture_recognizer_triple_tap.c', 'efl_canvas_gesture_recognizer_long_tap.c', + 'efl_canvas_gesture_recognizer_momentum.c', + 'efl_canvas_gesture_recognizer_flick.c', + 'efl_canvas_gesture_recognizer_zoom.c', 'efl_canvas_gesture_manager.c', ])