From fa09a2322396febfa958d4717edaab1c3c07bbb8 Mon Sep 17 00:00:00 2001 From: Carsten Haitzler Date: Fri, 11 Dec 2009 08:12:58 +0000 Subject: [PATCH] flip widget! first go at it and still primitive. will expand! for flipping between 2 bits of content (front and back). SVN revision: 44352 --- src/bin/test_flip.c | 48 ++++++++++--- src/lib/Elementary.h.in | 11 +-- src/lib/elm_flip.c | 178 ++++++++++++++++++++++++++++++++++++++++++++++-- src/lib/elm_genlist.c | 23 ++++++- src/lib/elm_layout.c | 2 +- 5 files changed, 238 insertions(+), 24 deletions(-) diff --git a/src/bin/test_flip.c b/src/bin/test_flip.c index 8f19466..63ff33c 100644 --- a/src/bin/test_flip.c +++ b/src/bin/test_flip.c @@ -5,13 +5,36 @@ void my_fl_1(void *data, Evas_Object *obj, void *event_info) { Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_ROTATE_Y_CENTER_AXIS); +} + +void +my_fl_2(void *data, Evas_Object *obj, void *event_info) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_ROTATE_X_CENTER_AXIS); +} + +void +my_fl_3(void *data, Evas_Object *obj, void *event_info) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_ROTATE_XZ_CENTER_AXIS); +} + +void +my_fl_4(void *data, Evas_Object *obj, void *event_info) +{ + Evas_Object *fl = data; + elm_flip_go(fl, ELM_FLIP_ROTATE_YZ_CENTER_AXIS); } void test_flip(void *data, Evas_Object *obj, void *event_info) { Evas_Object *win, *bg, *bx, *bx2, *fl, *o, *bt; - + char buf[PATH_MAX]; + win = elm_win_add(NULL, "flip", ELM_WIN_BASIC); elm_win_title_set(win, "Flip"); elm_win_autodel_set(win, 1); @@ -26,28 +49,31 @@ test_flip(void *data, Evas_Object *obj, void *event_info) elm_win_resize_object_add(win, bx); evas_object_show(bx); -#if 0 // working on it +#if 1 // working on it fl = elm_flip_add(win); evas_object_size_hint_align_set(fl, EVAS_HINT_FILL, EVAS_HINT_FILL); evas_object_size_hint_weight_set(fl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); elm_box_pack_end(bx, fl); - o = elm_button_add(win); - elm_button_label_set(o, "Front"); + o = elm_bg_add(win); evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, "sky_01.jpg"); + elm_bg_file_set(o, buf, NULL); elm_flip_content_front_set(fl, o); evas_object_show(o); - o = elm_button_add(win); - elm_button_label_set(o, "Back"); + o = elm_bg_add(win); evas_object_size_hint_weight_set(o, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); - elm_flip_content_front_set(fl, o); + snprintf(buf, sizeof(buf), "%s/images/%s", PACKAGE_DATA_DIR, "rock_01.jpg"); + elm_bg_file_set(o, buf, NULL); + elm_flip_content_back_set(fl, o); evas_object_show(o); evas_object_show(fl); bx2 = elm_box_add(win); + elm_box_horizontal_set(bx2, 1); evas_object_size_hint_align_set(bx2, EVAS_HINT_FILL, EVAS_HINT_FILL); evas_object_size_hint_weight_set(bx2, EVAS_HINT_EXPAND, 0.0); @@ -61,7 +87,7 @@ test_flip(void *data, Evas_Object *obj, void *event_info) bt = elm_button_add(win); elm_button_label_set(bt, "2"); - evas_object_smart_callback_add(bt, "clicked", my_fl_1, fl); + evas_object_smart_callback_add(bt, "clicked", my_fl_2, fl); evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); elm_box_pack_end(bx2, bt); @@ -69,7 +95,7 @@ test_flip(void *data, Evas_Object *obj, void *event_info) bt = elm_button_add(win); elm_button_label_set(bt, "3"); - evas_object_smart_callback_add(bt, "clicked", my_fl_1, fl); + evas_object_smart_callback_add(bt, "clicked", my_fl_3, fl); evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); elm_box_pack_end(bx2, bt); @@ -77,7 +103,7 @@ test_flip(void *data, Evas_Object *obj, void *event_info) bt = elm_button_add(win); elm_button_label_set(bt, "4"); - evas_object_smart_callback_add(bt, "clicked", my_fl_1, fl); + evas_object_smart_callback_add(bt, "clicked", my_fl_4, fl); evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); elm_box_pack_end(bx2, bt); @@ -87,7 +113,7 @@ test_flip(void *data, Evas_Object *obj, void *event_info) evas_object_show(bx2); #endif - evas_object_resize(win, 300, 300); + evas_object_resize(win, 320, 480); evas_object_show(win); } #endif diff --git a/src/lib/Elementary.h.in b/src/lib/Elementary.h.in index 97feb88..2c139a2 100644 --- a/src/lib/Elementary.h.in +++ b/src/lib/Elementary.h.in @@ -462,7 +462,7 @@ extern "C" { EAPI Eina_Bool elm_layout_file_set(Evas_Object *obj, const char *file, const char *group); EAPI void elm_layout_content_set(Evas_Object *obj, const char *swallow, Evas_Object *content); EAPI Evas_Object *elm_layout_edje_get(const Evas_Object *obj); - EAPI void elm_layout_sizing_eval(const Evas_Object *obj); + EAPI void elm_layout_sizing_eval(Evas_Object *obj); /* smart callbacks called: */ @@ -851,6 +851,7 @@ extern "C" { EAPI void elm_genlist_always_select_mode_set(Evas_Object *obj, Eina_Bool always_select); EAPI void elm_genlist_no_select_mode_set(Evas_Object *obj, Eina_Bool no_select); EAPI void elm_genlist_compress_mode_set(Evas_Object *obj, Eina_Bool compress); + EAPI void elm_genlist_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce); /* available item styles: * default * default_style - The text part is a textblock @@ -1122,7 +1123,7 @@ extern "C" { EAPI void elm_panel_orient_set(Evas_Object *obj, Elm_Panel_Orient orient); EAPI void elm_panel_content_set(Evas_Object *obj, Evas_Object *content); -#if 0 // working on it +#if 1 // working on it // flip types: // rotate around y axis 180 degrees // rotate around x axis 180 degrees @@ -1143,8 +1144,10 @@ extern "C" { // light x, y, z typedef enum _Elm_Flip_Mode { - ELM_FLIP_ROTATE_Y CENTER_AXIS, - ELM_FLIP_ROTATE_X_CENTER_AXIS + ELM_FLIP_ROTATE_Y_CENTER_AXIS, + ELM_FLIP_ROTATE_X_CENTER_AXIS, + ELM_FLIP_ROTATE_XZ_CENTER_AXIS, + ELM_FLIP_ROTATE_YZ_CENTER_AXIS } Elm_Flip_Mode; EAPI Evas_Object *elm_flip_add(Evas_Object *parent); diff --git a/src/lib/elm_flip.c b/src/lib/elm_flip.c index 2a30a59..245d654 100644 --- a/src/lib/elm_flip.c +++ b/src/lib/elm_flip.c @@ -1,9 +1,8 @@ #include #include "elm_priv.h" -#if 0 // working on it +#if 1 // working on it -// fixme: on configure of widget smart obj - reconfigure front + back and maps /** * @defgroup Flip Flip * @@ -15,9 +14,13 @@ typedef struct _Widget_Data Widget_Data; struct _Widget_Data { + Ecore_Animator *animator; + double start, len; + Elm_Flip_Mode mode; struct { Evas_Object *content; } front, back; + Eina_Bool state : 1; }; static void _del_hook(Evas_Object *obj); @@ -30,6 +33,7 @@ static void _del_hook(Evas_Object *obj) { Widget_Data *wd = elm_widget_data_get(obj); + if (wd->animator) ecore_animator_del(wd->animator); free(wd); } @@ -94,6 +98,161 @@ _sub_del(void *data, Evas_Object *obj, void *event_info) } } +static int +_flip(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + double t = ecore_loop_time_get() - wd->start; + Evas_Coord x, y, w, h; + double p, deg; + Evas_Map *mf, *mb; + Evas_Coord cx, cy, cz, px, py, foc; + int lx, ly, lz, lr, lg, lb, lar, lag, lab; + if (!wd->animator) return 0; + t = t / wd->len; + if (t > 1.0) t = 1.0; + + evas_object_geometry_get(obj, &x, &y, &w, &h); + + + mf = evas_map_new(4); + evas_map_smooth_set(mf, 0); + mb = evas_map_new(4); + evas_map_smooth_set(mb, 0); + + if (wd->front.content) + evas_map_util_points_populate_from_object_full(mf, wd->front.content, 0); + if (wd->back.content) + evas_map_util_points_populate_from_object_full(mb, wd->back.content, 0); + + cx = x + (w / 2); + cy = y + (h / 2); + + px = x + (w / 2); + py = y + (h / 2); + foc = 2048; + + lx = cx; + ly = cy; + lz = -10000; + lr = 255; + lg = 255; + lb = 255; + lar = 0; + lag = 0; + lab = 0; + + switch (wd->mode) + { + case ELM_FLIP_ROTATE_Y_CENTER_AXIS: + p = 1.0 - t; + p = 1.0 - (p * p); + if (wd->state) deg = 180.0 * p; + else deg = 180 + (180.0 * p); + evas_map_util_3d_rotate(mf, 0.0, deg, 0.0, cx, cy, 0); + evas_map_util_3d_rotate(mb, 0.0, deg + 180.0, 0.0, cx, cy, 0); + break; + case ELM_FLIP_ROTATE_X_CENTER_AXIS: + p = 1.0 - t; + p = 1.0 - (p * p); + if (wd->state) deg = 180.0 * p; + else deg = 180 + (180.0 * p); + evas_map_util_3d_rotate(mf, deg, 0.0, 0.0, cx, cy, 0); + evas_map_util_3d_rotate(mb, deg + 180.0, 0.0, 0.0, cx, cy, 0); + break; + case ELM_FLIP_ROTATE_XZ_CENTER_AXIS: + p = 1.0 - t; + p = 1.0 - (p * p); + if (wd->state) deg = 180.0 * p; + else deg = 180 + (180.0 * p); + evas_map_util_3d_rotate(mf, deg, 0.0, deg, cx, cy, 0); + evas_map_util_3d_rotate(mb, deg + 180.0, 0.0, deg + 180.0, cx, cy, 0); + break; + case ELM_FLIP_ROTATE_YZ_CENTER_AXIS: + p = 1.0 - t; + p = 1.0 - (p * p); + if (wd->state) deg = 180.0 * p; + else deg = 180 + (180.0 * p); + evas_map_util_3d_rotate(mf, 0.0, deg, deg, cx, cy, 0); + evas_map_util_3d_rotate(mb, 0.0, deg + 180.0, deg + 180.0, cx, cy, 0); + break; + default: + break; + } + + + if (wd->front.content) + { + evas_map_util_3d_lighting(mf, lx, ly, lz, lr, lg, lb, lar, lag, lab); + evas_map_util_3d_perspective(mf, px, py, 0, foc); + evas_object_map_set(wd->front.content, mf); + evas_object_map_enable_set(wd->front.content, 1); + if (evas_map_util_clockwise_get(mf)) evas_object_show(wd->front.content); + else evas_object_hide(wd->front.content); + } + + if (wd->back.content) + { + evas_map_util_3d_lighting(mb, lx, ly, lz, lr, lg, lb, lar, lag, lab); + evas_map_util_3d_perspective(mb, px, py, 0, foc); + evas_object_map_set(wd->back.content, mb); + evas_object_map_enable_set(wd->back.content, 1); + if (evas_map_util_clockwise_get(mb)) evas_object_show(wd->back.content); + else evas_object_hide(wd->back.content); + } + + evas_map_free(mf); + evas_map_free(mb); + + if (t >= 1.0) + { + evas_object_map_enable_set(wd->front.content, 0); + evas_object_map_enable_set(wd->back.content, 0); + wd->animator = NULL; + wd->state = !wd->state; + evas_object_smart_callback_call(obj, "animate,done", NULL); + return 0; + } + return 1; +} + +static void +_configure(Evas_Object *obj) +{ + Widget_Data *wd = elm_widget_data_get(obj); + Evas_Coord x, y, w, h; + evas_object_geometry_get(obj, &x, &y, &w, &h); + if (wd->front.content) + { + evas_object_move(wd->front.content, x, y); + evas_object_resize(wd->front.content, w, h); + } + if (wd->back.content) + { + evas_object_move(wd->back.content, x, y); + evas_object_resize(wd->back.content, w, h); + } + _flip(obj); +} + +static void +_move(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + _configure(obj); +} + +static void +_resize(void *data, Evas *e, Evas_Object *obj, void *event_info) +{ + _configure(obj); +} + +static int +_animate(void *data) +{ + return _flip(data); +} + /** * Add a new flip to the parent * @@ -119,7 +278,11 @@ elm_flip_add(Evas_Object *parent) elm_widget_theme_hook_set(obj, _theme_hook); evas_object_smart_callback_add(obj, "sub-object-del", _sub_del, obj); - + evas_object_event_callback_add(obj, EVAS_CALLBACK_MOVE, _move, NULL); + evas_object_event_callback_add(obj, EVAS_CALLBACK_RESIZE, _resize, NULL); + + wd->state = 1; + _sizing_eval(obj); return obj; } @@ -154,6 +317,7 @@ elm_flip_content_front_set(Evas_Object *obj, Evas_Object *content) } //XXX use clips if (!elm_flip_front_get(obj)) evas_object_hide(wd->front.content); + _configure(obj); } /** @@ -186,6 +350,7 @@ elm_flip_content_back_set(Evas_Object *obj, Evas_Object *content) } //XXX use clips if (elm_flip_front_get(obj)) evas_object_hide(wd->back.content); + _configure(obj); } /** @@ -200,8 +365,7 @@ EAPI Eina_Bool elm_flip_front_get(Evas_Object *obj) { Widget_Data *wd = elm_widget_data_get(obj); - //XXX retunr if front is showing or not - return 1; + return wd->state; } EAPI void @@ -214,5 +378,9 @@ EAPI void elm_flip_go(Evas_Object *obj, Elm_Flip_Mode mode) { Widget_Data *wd = elm_widget_data_get(obj); + if (!wd->animator) wd->animator = ecore_animator_add(_animate, obj); + wd->mode = mode; + wd->start = ecore_loop_time_get(); + wd->len = 0.5; } #endif diff --git a/src/lib/elm_genlist.c b/src/lib/elm_genlist.c index d7577ef..ed888f0 100644 --- a/src/lib/elm_genlist.c +++ b/src/lib/elm_genlist.c @@ -2637,7 +2637,6 @@ EAPI void elm_genlist_always_select_mode_set(Evas_Object *obj, Eina_Bool always_select) { Widget_Data *wd = elm_widget_data_get(obj); - wd->always_select = always_select; } @@ -2656,12 +2655,11 @@ EAPI void elm_genlist_no_select_mode_set(Evas_Object *obj, Eina_Bool no_select) { Widget_Data *wd = elm_widget_data_get(obj); - wd->no_select = no_select; } /** - * Set compress mode mode + * Set compress mode * * This will enable the compress mode where items are "compressed" horizontally * to fit the genlist scrollable viewport width. @@ -2677,3 +2675,22 @@ elm_genlist_compress_mode_set(Evas_Object *obj, Eina_Bool compress) Widget_Data *wd = elm_widget_data_get(obj); wd->compress = compress; } + +/** + * Set bounce mode + * + * This will enable or disable the scroller bounce mode for the gnelist. See + * elm_scroller_bounce_set() for details + * + * @param obj The genlist object + * @param h_bounce Allow bounce horizontally + * @param v_bounce Allow bounce vertically + * + * @ingroup Genlist + */ +EAPI void +elm_genlist_bounce_set(Evas_Object *obj, Eina_Bool h_bounce, Eina_Bool v_bounce) +{ + Widget_Data *wd = elm_widget_data_get(obj); + elm_smart_scroller_bounce_allow_set(wd->scr, h_bounce, v_bounce); +} diff --git a/src/lib/elm_layout.c b/src/lib/elm_layout.c index a7184de..bd0daad 100644 --- a/src/lib/elm_layout.c +++ b/src/lib/elm_layout.c @@ -257,7 +257,7 @@ elm_layout_edje_get(const Evas_Object *obj) * @ingroup Layout */ EAPI void -elm_layout_sizing_eval(const Evas_Object *obj) +elm_layout_sizing_eval(Evas_Object *obj) { Widget_Data *wd = elm_widget_data_get(obj); _request_sizing_eval(obj); -- 2.7.4