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
This commit is contained in:
Cedric BAIL 2011-12-28 16:10:10 +00:00
parent 8296e98d8b
commit 521c66c9e5
5 changed files with 58 additions and 15 deletions

View File

@ -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);

View File

@ -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;
}

View File

@ -2,6 +2,7 @@
#define __ETHUMB_PRIVATE_H__ 1
#include <Ethumb.h>
#include <Ethumb_Plugin.h>
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__ */

View File

@ -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);

View File

@ -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;