From 521c66c9e5f6371fddc34b868744a9716d49f36c Mon Sep 17 00:00:00 2001 From: Cedric BAIL Date: Wed, 28 Dec 2011 16:10:10 +0000 Subject: [PATCH] ethumb: make plugin API fully assynchronous and use it in emotion backend. NOTE: epdf isn't asynchronous at the moment, so no need to fix its ethumb plugin. SVN revision: 66607 --- legacy/ethumb/src/lib/Ethumb_Plugin.h | 3 +- legacy/ethumb/src/lib/ethumb.c | 16 ++++++- legacy/ethumb/src/lib/ethumb_private.h | 4 ++ legacy/ethumb/src/plugins/emotion/emotion.c | 49 ++++++++++++++++----- legacy/ethumb/src/plugins/epdf/epdf.c | 1 + 5 files changed, 58 insertions(+), 15 deletions(-) diff --git a/legacy/ethumb/src/lib/Ethumb_Plugin.h b/legacy/ethumb/src/lib/Ethumb_Plugin.h index 6dda23b390..3eb6f020cd 100644 --- a/legacy/ethumb/src/lib/Ethumb_Plugin.h +++ b/legacy/ethumb/src/lib/Ethumb_Plugin.h @@ -10,7 +10,8 @@ typedef struct _Ethumb_Plugin Ethumb_Plugin; struct _Ethumb_Plugin { const char **extensions; - void (*generate_thumb)(Ethumb *); + void *(*thumb_generate)(Ethumb *); + void (*thumb_cancel)(Ethumb *, void *); }; EAPI void ethumb_calculate_aspect_from_ratio(Ethumb *e, float ia, int *w, int *h); diff --git a/legacy/ethumb/src/lib/ethumb.c b/legacy/ethumb/src/lib/ethumb.c index ecabe9cc02..c097fbe382 100644 --- a/legacy/ethumb/src/lib/ethumb.c +++ b/legacy/ethumb/src/lib/ethumb.c @@ -1185,7 +1185,8 @@ _ethumb_plugin_generate(Ethumb *e) else evas_object_hide(e->img); - plugin->generate_thumb(e); + e->plugin = plugin; + e->pdata = plugin->thumb_generate(e); return EINA_TRUE; } @@ -1519,6 +1520,8 @@ ethumb_finished_callback_call(Ethumb *e, int result) if (e->finished_idler) ecore_idler_del(e->finished_idler); e->finished_idler = ecore_idler_add(_ethumb_finished_idler_cb, e); + e->plugin = NULL; + e->pdata = NULL; } EAPI Eina_Bool @@ -1537,6 +1540,13 @@ ethumb_generate(Ethumb *e, Ethumb_Generate_Cb finished_cb, const void *data, Ein ERR("thumbnail generation already in progress."); return EINA_FALSE; } + if (e->pdata) + { + e->plugin->thumb_cancel(e, e->pdata); + e->pdata = NULL; + e->plugin = NULL; + } + e->finished_cb = finished_cb; e->cb_data = (void *)data; e->cb_data_free = free_data; @@ -1549,9 +1559,9 @@ ethumb_generate(Ethumb *e, Ethumb_Generate_Cb finished_cb, const void *data, Ein } r = _ethumb_plugin_generate(e); + fprintf(stderr, "ethumb generate: %i: %p\n", r, e->pdata); if (r) { - ethumb_finished_callback_call(e, r); return EINA_TRUE; } @@ -1688,6 +1698,8 @@ ethumb_dup(const Ethumb *e) r->cb_data = NULL; r->cb_data_free = NULL; r->cb_result = 0; + r->plugin = NULL; + r->pdata = NULL; return r; } diff --git a/legacy/ethumb/src/lib/ethumb_private.h b/legacy/ethumb/src/lib/ethumb_private.h index 25f2cd354e..49e4de9f67 100644 --- a/legacy/ethumb/src/lib/ethumb_private.h +++ b/legacy/ethumb/src/lib/ethumb_private.h @@ -2,6 +2,7 @@ #define __ETHUMB_PRIVATE_H__ 1 #include +#include typedef struct _Ethumb_Frame Ethumb_Frame; @@ -48,6 +49,9 @@ struct _Ethumb void *cb_data; Eina_Free_Cb cb_data_free; int cb_result; + + void *pdata; + Ethumb_Plugin *plugin; }; #endif /* __ETHUMB_PRIVATE_H__ */ diff --git a/legacy/ethumb/src/plugins/emotion/emotion.c b/legacy/ethumb/src/plugins/emotion/emotion.c index 71918ccf31..560e661e8e 100644 --- a/legacy/ethumb/src/plugins/emotion/emotion.c +++ b/legacy/ethumb/src/plugins/emotion/emotion.c @@ -38,6 +38,9 @@ struct _emotion_plugin int w, h; }; +static Eina_Bool _frame_grab(void *data); +static Eina_Bool _frame_grab_single(void *data); + static void _resize_movie(struct _emotion_plugin *_plugin) { @@ -61,6 +64,17 @@ _resize_movie(struct _emotion_plugin *_plugin) emotion_object_audio_mute_set(_plugin->video, 1); } +static void +_frame_decode_cb(void *data, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) +{ + struct _emotion_plugin *_plugin = data; + + if (_plugin->ef) + _frame_grab(data); + else + _frame_grab_single(data); +} + static void _frame_resized_cb(void *data, Evas_Object *o __UNUSED__, void *event_info __UNUSED__) { @@ -168,6 +182,8 @@ _finish_thumb_generation(struct _emotion_plugin *_plugin, int success) int r = 0; evas_object_smart_callback_del(_plugin->video, "frame_resize", _frame_resized_cb); + evas_object_smart_callback_del(_plugin->video, "frame_decode", + _frame_decode_cb); emotion_object_play_set(_plugin->video, 0); evas_object_del(_plugin->video); if (_plugin->ef) @@ -207,7 +223,7 @@ _frame_grab_single(void *data) emotion_object_play_set(_plugin->video, 0); evas_object_del(_plugin->video); free(_plugin); - + ethumb_finished_callback_call(e, 1); return EINA_FALSE; @@ -294,12 +310,10 @@ _generate_animated_thumb(struct _emotion_plugin *_plugin) fprintf(stderr, "ERROR: could not open '%s'\n", thumb_path); _finish_thumb_generation(_plugin, 0); } - - ecore_timer_add(1.0 / ethumb_video_fps_get(e), _frame_grab, _plugin); } -static void -_generate_thumb(Ethumb *e) +static void * +_thumb_generate(Ethumb *e) { Evas_Object *o; int r; @@ -308,7 +322,7 @@ _generate_thumb(Ethumb *e) struct _emotion_plugin *_plugin = calloc(sizeof(struct _emotion_plugin), 1); o = emotion_object_add(ethumb_evas_get(e)); - r = emotion_object_init(o, "xine"); + r = emotion_object_init(o, NULL); if (!r) { fprintf(stderr, "ERROR: could not start emotion using gstreamer" @@ -316,7 +330,7 @@ _generate_thumb(Ethumb *e) evas_object_del(o); ethumb_finished_callback_call(e, 0); free(_plugin); - return; + return NULL; } _plugin->video = o; @@ -334,6 +348,8 @@ _generate_thumb(Ethumb *e) _plugin->pcount = 1; _resize_movie(_plugin); + evas_object_smart_callback_add(o, "frame_decode", + _frame_decode_cb, _plugin); evas_object_smart_callback_add(o, "frame_resize", _frame_resized_cb, _plugin); evas_object_smart_callback_add(o, "decode_stop", @@ -343,14 +359,22 @@ _generate_thumb(Ethumb *e) { _generate_animated_thumb(_plugin); } - else - { - ecore_timer_add(0.1, _frame_grab_single, _plugin); - } _video_pos_set(_plugin); emotion_object_play_set(o, 1); evas_object_show(o); + + return _plugin; +} + +static void +_thumb_cancel(Ethumb *e __UNUSED__, void *data) +{ + struct _emotion_plugin *_plugin = data; + + if (_plugin->ef) eet_close(_plugin->ef); + evas_object_del(_plugin->video); + free(_plugin); } EAPI Ethumb_Plugin * @@ -361,7 +385,8 @@ ethumb_plugin_get(void) static Ethumb_Plugin plugin = { extensions, - _generate_thumb, + _thumb_generate, + _thumb_cancel }; _log_dom = eina_log_domain_register("ethumb_emotion", EINA_COLOR_GREEN); diff --git a/legacy/ethumb/src/plugins/epdf/epdf.c b/legacy/ethumb/src/plugins/epdf/epdf.c index 82e3b8cf3b..62234a9b50 100644 --- a/legacy/ethumb/src/plugins/epdf/epdf.c +++ b/legacy/ethumb/src/plugins/epdf/epdf.c @@ -76,6 +76,7 @@ ethumb_plugin_get(void) { extensions, _generate_thumb, + NULL /* This plugin is not assynchronous so not possible to cancel it at all */ }; return &plugin;