evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
|
2016-03-14 03:38:44 -07:00
|
|
|
#include "evas_image_private.h"
|
2008-11-04 01:19:35 -08:00
|
|
|
|
2017-08-07 07:34:33 -07:00
|
|
|
#define MY_CLASS EFL_CANVAS_IMAGE_INTERNAL_CLASS
|
2013-11-07 03:16:01 -08:00
|
|
|
#define MY_CLASS_NAME "Evas_Image"
|
2013-01-28 22:36:23 -08:00
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
/* private magic number for image objects */
|
|
|
|
static const char o_type[] = "image";
|
|
|
|
|
2014-11-12 17:40:16 -08:00
|
|
|
const char *o_image_type = o_type;
|
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
/* private methods for image objects */
|
2017-08-07 07:34:33 -07:00
|
|
|
static Evas_Coord evas_object_image_figure_x_fill(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj, Evas_Coord start, Evas_Coord size, Evas_Coord *size_ret);
|
|
|
|
static Evas_Coord evas_object_image_figure_y_fill(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj, Evas_Coord start, Evas_Coord size, Evas_Coord *size_ret);
|
|
|
|
|
|
|
|
static void evas_object_image_init(Evas_Object *eo_obj);
|
|
|
|
static void evas_object_image_render(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data,
|
|
|
|
void *engine, void *output, void *context, void *surface,
|
|
|
|
int x, int y, Eina_Bool do_async);
|
|
|
|
static void _evas_image_render(Eo *eo_obj, Evas_Object_Protected_Data *obj,
|
|
|
|
void *engine, void *output, void *context, void *surface,
|
|
|
|
int x, int y, int l, int t, int r, int b, Eina_Bool skip_map, Eina_Bool do_async);
|
|
|
|
static void evas_object_image_free(Evas_Object *eo_obj,
|
|
|
|
Evas_Object_Protected_Data *obj);
|
|
|
|
static void evas_object_image_render_pre(Evas_Object *eo_obj,
|
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data);
|
|
|
|
static void evas_object_image_render_post(Evas_Object *eo_obj,
|
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data);
|
2012-10-08 18:58:41 -07:00
|
|
|
|
2017-08-07 07:34:33 -07:00
|
|
|
static void *evas_object_image_engine_data_get(Evas_Object *eo_obj);
|
|
|
|
|
|
|
|
static int evas_object_image_is_opaque(Evas_Object *eo_obj,
|
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data);
|
|
|
|
static int evas_object_image_was_opaque(Evas_Object *eo_obj,
|
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data);
|
|
|
|
static int evas_object_image_is_inside(Evas_Object *eo_obj,
|
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data,
|
|
|
|
Evas_Coord x, Evas_Coord y);
|
|
|
|
static int evas_object_image_has_opaque_rect(Evas_Object *eo_obj,
|
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data);
|
|
|
|
static int evas_object_image_get_opaque_rect(Evas_Object *eo_obj,
|
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data,
|
|
|
|
Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h);
|
|
|
|
static int evas_object_image_can_map(Evas_Object *eo_obj);
|
|
|
|
static void evas_object_image_render_prepare(Evas_Object *obj, Evas_Object_Protected_Data *pd, Eina_Bool do_async);
|
|
|
|
|
|
|
|
static void evas_object_image_filled_resize_listener(void *data, Evas *eo_e, Evas_Object *eo_obj, void *einfo);
|
2008-05-18 20:13:16 -07:00
|
|
|
|
2018-10-22 08:20:28 -07:00
|
|
|
static int evas_object_image_is_on_plane(Evas_Object *obj EINA_UNUSED, Evas_Object_Protected_Data *pd EINA_UNUSED, void *type_private_data);
|
2018-10-22 08:22:26 -07:00
|
|
|
static int evas_object_image_plane_changed(Evas_Object *obj EINA_UNUSED, Evas_Object_Protected_Data *pd EINA_UNUSED, void *type_private_data);
|
2007-05-06 04:29:37 -07:00
|
|
|
static const Evas_Object_Func object_func =
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
|
|
|
/* methods (compulsory) */
|
2012-10-08 18:58:41 -07:00
|
|
|
NULL,
|
2017-08-07 07:34:33 -07:00
|
|
|
evas_object_image_render,
|
|
|
|
evas_object_image_render_pre,
|
|
|
|
evas_object_image_render_post,
|
|
|
|
evas_object_image_engine_data_get,
|
|
|
|
/* these are optional. NULL = nothing */
|
|
|
|
NULL,
|
|
|
|
NULL,
|
|
|
|
evas_object_image_is_opaque,
|
|
|
|
evas_object_image_was_opaque,
|
|
|
|
evas_object_image_is_inside,
|
|
|
|
NULL,
|
|
|
|
NULL,
|
|
|
|
evas_object_image_has_opaque_rect,
|
|
|
|
evas_object_image_get_opaque_rect,
|
|
|
|
evas_object_image_can_map,
|
2018-10-22 08:20:28 -07:00
|
|
|
evas_object_image_render_prepare, // render_prepare
|
|
|
|
evas_object_image_is_on_plane,
|
2018-10-22 08:22:26 -07:00
|
|
|
evas_object_image_plane_changed
|
2002-11-08 00:02:15 -08:00
|
|
|
};
|
|
|
|
|
2013-01-23 17:50:57 -08:00
|
|
|
static const Evas_Object_Image_Load_Opts default_load_opts = {
|
2017-08-07 07:34:33 -07:00
|
|
|
0, 0.0, 0, 0, { 0, 0, 0, 0 }, { 0, 0, 0, 0, 0, 0, 0, 0 }, 0
|
2013-01-23 17:50:57 -08:00
|
|
|
};
|
|
|
|
|
2013-01-25 04:15:38 -08:00
|
|
|
static const Evas_Object_Image_Pixels default_pixels = {
|
2017-08-07 07:34:33 -07:00
|
|
|
NULL, { NULL, NULL }, NULL, { 0, NULL, NULL, NULL, NULL, NULL, NULL, NULL }, ~0x0
|
2013-01-25 04:15:38 -08:00
|
|
|
};
|
|
|
|
|
2013-01-27 16:28:53 -08:00
|
|
|
static const Evas_Object_Image_State default_state = {
|
2017-08-07 07:34:33 -07:00
|
|
|
{ 0, 0, 0, 0 }, // fill
|
|
|
|
{ 0, 0, 0 }, // image
|
|
|
|
{ 1.0, 0, 0, 0, 0, 1 }, // border
|
|
|
|
NULL, NULL, NULL, //source, defmap, scene
|
2017-10-04 21:01:35 -07:00
|
|
|
NULL, //f
|
2017-08-07 07:34:33 -07:00
|
|
|
NULL, //key
|
|
|
|
0, //frame
|
|
|
|
EVAS_COLORSPACE_ARGB8888,
|
|
|
|
EVAS_IMAGE_ORIENT_NONE,
|
|
|
|
|
|
|
|
EINA_TRUE, // smooth
|
|
|
|
EINA_FALSE, // has_alpha
|
|
|
|
EINA_FALSE, // opaque_valid
|
2017-10-04 21:01:35 -07:00
|
|
|
EINA_FALSE // opaque
|
2013-01-27 16:28:53 -08:00
|
|
|
};
|
|
|
|
|
2013-01-23 17:50:57 -08:00
|
|
|
Eina_Cow *evas_object_image_load_opts_cow = NULL;
|
2013-01-25 04:15:38 -08:00
|
|
|
Eina_Cow *evas_object_image_pixels_cow = NULL;
|
2013-01-27 16:28:53 -08:00
|
|
|
Eina_Cow *evas_object_image_state_cow = NULL;
|
2013-01-25 04:15:38 -08:00
|
|
|
|
2016-11-14 18:22:14 -08:00
|
|
|
static void
|
2016-11-21 02:36:29 -08:00
|
|
|
evas_object_image_render_prepare(Evas_Object *eo_obj EINA_UNUSED, Evas_Object_Protected_Data *obj EINA_UNUSED, Eina_Bool do_async EINA_UNUSED)
|
2016-11-14 18:22:14 -08:00
|
|
|
{
|
2016-11-21 02:36:29 -08:00
|
|
|
#if 0
|
2016-11-14 18:22:14 -08:00
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
|
|
|
|
|
|
|
// if image data not loaded or in texture then upload
|
2017-10-04 21:01:35 -07:00
|
|
|
if ((o->cur->f) || (o->written) || (o->cur->frame != 0))
|
2016-11-14 18:22:14 -08:00
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
if (o->engine_data) ENFN->image_prepare(ENC, o->engine_data);
|
2016-11-14 18:22:14 -08:00
|
|
|
}
|
2016-11-16 19:28:52 -08:00
|
|
|
#endif
|
2016-11-14 18:22:14 -08:00
|
|
|
// XXX: if image is a proxy, PREPEND to prerender list in evas canvas
|
|
|
|
}
|
|
|
|
|
2017-08-25 10:51:40 -07:00
|
|
|
static void *
|
|
|
|
_evas_object_image_output_find(Evas_Object_Protected_Data *obj)
|
|
|
|
{
|
|
|
|
Efl_Canvas_Output *output;
|
|
|
|
Eina_List *l;
|
|
|
|
const Eina_Rectangle geometry = {
|
|
|
|
obj->cur->geometry.x,
|
|
|
|
obj->cur->geometry.y,
|
|
|
|
obj->cur->geometry.w,
|
|
|
|
obj->cur->geometry.h
|
|
|
|
};
|
|
|
|
|
|
|
|
EINA_LIST_FOREACH(obj->layer->evas->outputs, l, output)
|
|
|
|
{
|
|
|
|
if (eina_rectangles_intersect(&output->geometry, &geometry))
|
|
|
|
return output->output;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Always return an output, as evas rely on that even if the object is out of screen.
|
|
|
|
output = eina_list_data_get(obj->layer->evas->outputs);
|
|
|
|
return output->output;
|
|
|
|
}
|
|
|
|
|
2016-03-14 03:38:44 -07:00
|
|
|
void
|
2016-03-07 21:11:07 -08:00
|
|
|
_evas_image_cleanup(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj, Evas_Image_Data *o)
|
2011-10-02 20:28:52 -07:00
|
|
|
{
|
2014-10-28 22:15:11 -07:00
|
|
|
/* Eina_Cow doesn't know if the resulting memory has changed, better check
|
|
|
|
before we change it */
|
|
|
|
if (o->cur->opaque_valid)
|
2013-03-12 05:58:19 -07:00
|
|
|
{
|
2014-10-28 22:15:11 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque_valid = 0;
|
|
|
|
}
|
2014-10-28 22:15:11 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-03-12 05:58:19 -07:00
|
|
|
}
|
|
|
|
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
if ((o->preload & EVAS_IMAGE_PRELOADING) && (o->engine_data))
|
2011-10-02 20:28:52 -07:00
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
o->preload = EVAS_IMAGE_PRELOAD_NONE;
|
|
|
|
ENFN->image_data_preload_cancel(ENC, o->engine_data, eo_obj, EINA_FALSE);
|
2011-10-02 20:28:52 -07:00
|
|
|
}
|
2016-03-07 21:11:07 -08:00
|
|
|
if (o->cur->source) _evas_image_proxy_unset(eo_obj, obj, o);
|
|
|
|
if (o->cur->scene) _evas_image_3d_unset(eo_obj, obj, o);
|
2011-10-02 20:28:52 -07:00
|
|
|
}
|
|
|
|
|
2013-01-25 04:15:38 -08:00
|
|
|
static Eina_Bool
|
2015-05-20 06:56:45 -07:00
|
|
|
_init_cow(void)
|
2013-01-25 04:15:38 -08:00
|
|
|
{
|
2013-01-27 16:28:53 -08:00
|
|
|
if (!evas_object_image_load_opts_cow ||
|
|
|
|
!evas_object_image_pixels_cow ||
|
|
|
|
!evas_object_image_state_cow)
|
2013-01-25 04:15:38 -08:00
|
|
|
{
|
|
|
|
evas_object_image_load_opts_cow = eina_cow_add("Evas_Object_Image load opts",
|
|
|
|
sizeof (Evas_Object_Image_Load_Opts),
|
|
|
|
8,
|
2013-04-02 01:10:35 -07:00
|
|
|
&default_load_opts,
|
|
|
|
EINA_TRUE);
|
2013-01-25 04:15:38 -08:00
|
|
|
evas_object_image_pixels_cow = eina_cow_add("Evas_Object_Image pixels",
|
|
|
|
sizeof (Evas_Object_Image_Pixels),
|
|
|
|
8,
|
2013-04-02 01:10:35 -07:00
|
|
|
&default_pixels,
|
|
|
|
EINA_TRUE);
|
2013-01-27 16:28:53 -08:00
|
|
|
evas_object_image_state_cow = eina_cow_add("Evas_Object_Image states",
|
|
|
|
sizeof (Evas_Object_Image_State),
|
|
|
|
8,
|
2013-04-02 01:10:35 -07:00
|
|
|
&default_state,
|
|
|
|
EINA_TRUE);
|
2013-01-25 04:15:38 -08:00
|
|
|
}
|
2013-01-27 16:28:53 -08:00
|
|
|
if (!evas_object_image_load_opts_cow ||
|
|
|
|
!evas_object_image_pixels_cow ||
|
|
|
|
!evas_object_image_state_cow)
|
2013-01-25 04:15:38 -08:00
|
|
|
{
|
2015-05-20 06:56:45 -07:00
|
|
|
ERR("Failed to init cow.");
|
2013-01-25 04:15:38 -08:00
|
|
|
return EINA_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
return EINA_TRUE;
|
|
|
|
}
|
|
|
|
|
2015-05-19 03:41:27 -07:00
|
|
|
EOLIAN static Eo *
|
2016-08-10 07:23:04 -07:00
|
|
|
_efl_canvas_image_internal_efl_object_constructor(Eo *eo_obj, Evas_Image_Data *o)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2013-01-27 16:28:53 -08:00
|
|
|
Evas_Colorspace cspace;
|
2002-11-08 00:02:15 -08:00
|
|
|
|
2016-08-15 06:44:41 -07:00
|
|
|
eo_obj = efl_constructor(efl_super(eo_obj, MY_CLASS));
|
2013-09-24 21:32:56 -07:00
|
|
|
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_image_init(eo_obj);
|
2013-01-23 17:50:57 -08:00
|
|
|
|
2015-05-20 06:56:45 -07:00
|
|
|
if (!_init_cow())
|
2015-05-19 03:41:27 -07:00
|
|
|
return NULL;
|
2013-01-23 17:50:57 -08:00
|
|
|
|
|
|
|
o->load_opts = eina_cow_alloc(evas_object_image_load_opts_cow);
|
2013-01-25 04:15:38 -08:00
|
|
|
o->pixels = eina_cow_alloc(evas_object_image_pixels_cow);
|
2013-01-27 16:28:53 -08:00
|
|
|
o->cur = eina_cow_alloc(evas_object_image_state_cow);
|
|
|
|
o->prev = eina_cow_alloc(evas_object_image_state_cow);
|
2013-04-28 23:30:37 -07:00
|
|
|
o->proxy_src_clip = EINA_TRUE;
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2017-08-25 10:51:10 -07:00
|
|
|
cspace = ENFN->image_colorspace_get(ENC, o->engine_data);
|
2015-06-18 05:45:21 -07:00
|
|
|
if (cspace != o->cur->cspace)
|
2013-01-27 16:28:53 -08:00
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
state_write->cspace = cspace;
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
}
|
2015-05-19 03:41:27 -07:00
|
|
|
|
|
|
|
return eo_obj;
|
2012-10-08 18:58:41 -07:00
|
|
|
}
|
|
|
|
|
2016-03-01 22:44:12 -08:00
|
|
|
EOLIAN static Eo *
|
2016-08-10 07:23:04 -07:00
|
|
|
_efl_canvas_image_internal_efl_object_finalize(Eo *eo_obj, Evas_Image_Data *o)
|
2016-03-01 22:44:12 -08:00
|
|
|
{
|
|
|
|
if (!o->filled_set)
|
2016-03-17 19:50:48 -07:00
|
|
|
efl_gfx_fill_auto_set(eo_obj, EINA_TRUE);
|
2016-08-15 06:44:41 -07:00
|
|
|
return efl_finalize(efl_super(eo_obj, MY_CLASS));
|
2016-03-01 22:44:12 -08:00
|
|
|
}
|
|
|
|
|
2016-03-07 21:11:07 -08:00
|
|
|
void
|
2017-10-04 21:01:35 -07:00
|
|
|
_evas_image_init_set(const Eina_File *f, const char *key,
|
2017-08-07 07:34:33 -07:00
|
|
|
Eo *eo_obj, Evas_Object_Protected_Data *obj, Evas_Image_Data *o,
|
|
|
|
Evas_Image_Load_Opts *lo)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-03-07 21:11:07 -08:00
|
|
|
if (o->cur->source) _evas_image_proxy_unset(eo_obj, obj, o);
|
|
|
|
if (o->cur->scene) _evas_image_3d_unset(eo_obj, obj, o);
|
2013-12-26 23:56:30 -08:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
2017-10-04 21:01:35 -07:00
|
|
|
Eina_File *tmp = state_write->f;
|
2017-08-07 07:34:33 -07:00
|
|
|
|
2017-10-04 21:01:35 -07:00
|
|
|
state_write->f = NULL;
|
|
|
|
|
|
|
|
if (f) state_write->f = eina_file_dup(f);
|
|
|
|
eina_file_close(tmp);
|
|
|
|
|
|
|
|
eina_stringshare_replace(&state_write->key, key);
|
2017-08-07 07:34:33 -07:00
|
|
|
state_write->opaque_valid = 0;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2017-10-04 21:01:35 -07:00
|
|
|
if (o->prev->f != NULL || o->prev->key != NULL)
|
2013-01-27 16:28:53 -08:00
|
|
|
{
|
2013-07-11 00:03:01 -07:00
|
|
|
EINA_COW_WRITE_BEGIN(evas_object_image_state_cow, o->prev, Evas_Object_Image_State, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
2017-10-04 21:01:35 -07:00
|
|
|
state_write->f = NULL;
|
2017-08-07 07:34:33 -07:00
|
|
|
state_write->key = NULL;
|
|
|
|
}
|
2013-07-11 00:03:01 -07:00
|
|
|
EINA_COW_WRITE_END(evas_object_image_state_cow, o->prev, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
}
|
2014-04-14 03:03:47 -07:00
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
if (o->engine_data)
|
2009-09-27 20:51:21 -07:00
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
if (o->preload & EVAS_IMAGE_PRELOADING)
|
2011-05-02 20:20:02 -07:00
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
o->preload = EVAS_IMAGE_PRELOAD_NONE;
|
|
|
|
ENFN->image_data_preload_cancel(ENC, o->engine_data, eo_obj, EINA_FALSE);
|
2011-05-02 20:20:02 -07:00
|
|
|
}
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_free(ENC, o->engine_data);
|
2009-09-27 20:51:21 -07:00
|
|
|
}
|
2019-04-18 06:05:31 -07:00
|
|
|
o->engine_data = NULL;
|
2019-03-04 10:36:57 -08:00
|
|
|
o->load_error = EFL_GFX_IMAGE_LOAD_ERROR_NONE;
|
2019-04-18 06:05:31 -07:00
|
|
|
if (!lo) return;
|
2017-01-01 05:15:24 -08:00
|
|
|
lo->emile.scale_down_by = o->load_opts->scale_down_by;
|
|
|
|
lo->emile.dpi = o->load_opts->dpi;
|
|
|
|
lo->emile.w = o->load_opts->w;
|
|
|
|
lo->emile.h = o->load_opts->h;
|
|
|
|
lo->emile.region.x = o->load_opts->region.x;
|
|
|
|
lo->emile.region.y = o->load_opts->region.y;
|
|
|
|
lo->emile.region.w = o->load_opts->region.w;
|
|
|
|
lo->emile.region.h = o->load_opts->region.h;
|
|
|
|
lo->emile.scale_load.src_x = o->load_opts->scale_load.src_x;
|
|
|
|
lo->emile.scale_load.src_y = o->load_opts->scale_load.src_y;
|
|
|
|
lo->emile.scale_load.src_w = o->load_opts->scale_load.src_w;
|
|
|
|
lo->emile.scale_load.src_h = o->load_opts->scale_load.src_h;
|
|
|
|
lo->emile.scale_load.dst_w = o->load_opts->scale_load.dst_w;
|
|
|
|
lo->emile.scale_load.dst_h = o->load_opts->scale_load.dst_h;
|
|
|
|
lo->emile.scale_load.smooth = o->load_opts->scale_load.smooth;
|
|
|
|
lo->emile.scale_load.scale_hint = o->load_opts->scale_load.scale_hint;
|
|
|
|
lo->emile.orientation = o->load_opts->orientation;
|
|
|
|
lo->emile.degree = 0;
|
|
|
|
lo->skip_head = o->skip_head;
|
2013-05-07 23:37:37 -07:00
|
|
|
}
|
|
|
|
|
2016-03-07 21:11:07 -08:00
|
|
|
void
|
|
|
|
_evas_image_done_set(Eo *eo_obj, Evas_Object_Protected_Data *obj, Evas_Image_Data *o)
|
2013-05-07 23:37:37 -07:00
|
|
|
{
|
|
|
|
Eina_Bool resize_call = EINA_FALSE;
|
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
if (o->engine_data)
|
|
|
|
{
|
2012-09-04 01:42:38 -07:00
|
|
|
int w, h;
|
|
|
|
int stride;
|
2017-01-01 22:22:04 -08:00
|
|
|
Evas_Image_Orient orient;
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_size_get(ENC, o->engine_data, &w, &h);
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_stride_get)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_stride_get(ENC, o->engine_data, &stride);
|
2012-09-04 01:42:38 -07:00
|
|
|
else
|
|
|
|
stride = w * 4;
|
2017-08-25 10:51:10 -07:00
|
|
|
orient = ENFN->image_orient_get(ENC, o->engine_data);
|
2014-03-19 19:10:43 -07:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
state_write->has_alpha = ENFN->image_alpha_get(ENC, o->engine_data);
|
|
|
|
state_write->cspace = ENFN->image_colorspace_get(ENC, o->engine_data);
|
2017-08-07 07:34:33 -07:00
|
|
|
|
|
|
|
if ((o->cur->image.w != w) || (o->cur->image.h != h))
|
|
|
|
resize_call = EINA_TRUE;
|
|
|
|
|
|
|
|
state_write->image.w = w;
|
|
|
|
state_write->image.h = h;
|
|
|
|
state_write->image.stride = stride;
|
|
|
|
state_write->orient = orient;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2019-03-04 10:36:57 -08:00
|
|
|
if (o->load_error == EFL_GFX_IMAGE_LOAD_ERROR_NONE)
|
|
|
|
o->load_error = EFL_GFX_IMAGE_LOAD_ERROR_GENERIC;
|
2012-09-04 21:20:42 -07:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->has_alpha = EINA_TRUE;
|
|
|
|
state_write->cspace = EVAS_COLORSPACE_ARGB8888;
|
|
|
|
|
|
|
|
if ((state_write->image.w != 0) || (state_write->image.h != 0))
|
|
|
|
resize_call = EINA_TRUE;
|
|
|
|
|
|
|
|
state_write->image.w = 0;
|
|
|
|
state_write->image.h = 0;
|
|
|
|
state_write->image.stride = 0;
|
|
|
|
state_write->orient = EVAS_IMAGE_ORIENT_NONE;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
2017-05-23 23:07:21 -07:00
|
|
|
o->file_size.w = 0;
|
|
|
|
o->file_size.h = 0;
|
2013-06-12 22:09:28 -07:00
|
|
|
o->written = EINA_FALSE;
|
2012-09-04 01:56:46 -07:00
|
|
|
o->changed = EINA_TRUE;
|
2012-10-08 18:58:41 -07:00
|
|
|
if (resize_call) evas_object_inform_call_image_resize(eo_obj);
|
|
|
|
evas_object_change(eo_obj, obj);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2016-04-05 18:46:04 -07:00
|
|
|
void
|
|
|
|
_evas_image_orientation_set(Eo *eo_obj, Evas_Image_Data *o, Evas_Image_Orient orient)
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
int iw, ih;
|
|
|
|
|
|
|
|
if (o->cur->orient == orient) return;
|
|
|
|
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
if ((o->preload & EVAS_IMAGE_PRELOADING) && (o->engine_data))
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
o->preload = EVAS_IMAGE_PRELOAD_NONE;
|
|
|
|
ENFN->image_data_preload_cancel(ENC, o->engine_data, eo_obj, EINA_TRUE);
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
}
|
|
|
|
|
2015-09-20 19:05:58 -07:00
|
|
|
if (o->engine_data)
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
{
|
|
|
|
int stride = 0;
|
|
|
|
|
2017-08-25 10:51:10 -07:00
|
|
|
o->engine_data = ENFN->image_orient_set(ENC, o->engine_data, orient);
|
2017-08-07 07:34:33 -07:00
|
|
|
if (o->engine_data)
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_size_get(ENC, o->engine_data, &iw, &ih);
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
|
|
|
|
if (ENFN->image_stride_get)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_stride_get(ENC, o->engine_data, &stride);
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
else
|
2017-06-12 10:10:23 -07:00
|
|
|
stride = iw * 4;
|
|
|
|
|
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->image.w = iw;
|
|
|
|
state_write->image.h = ih;
|
|
|
|
state_write->orient = orient;
|
|
|
|
state_write->image.stride = stride;
|
|
|
|
}
|
2017-06-12 10:10:23 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
o->written = EINA_TRUE;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
o->changed = EINA_TRUE;
|
|
|
|
evas_object_change(eo_obj, obj);
|
|
|
|
}
|
|
|
|
|
2016-04-05 18:46:04 -07:00
|
|
|
EOLIAN static void
|
2019-07-12 01:22:16 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_orientable_image_orientation_set(Eo *obj, Evas_Image_Data *o, Efl_Gfx_Image_Orientation efl_orient)
|
2016-04-05 18:46:04 -07:00
|
|
|
{
|
2019-05-22 11:16:16 -07:00
|
|
|
// This array takes an Efl_Gfx_Image_Orientation and turns it into an Elm_Image_Orient
|
2019-05-20 08:51:56 -07:00
|
|
|
static const Evas_Image_Orient evas_orient[16] = {
|
2019-05-22 11:16:16 -07:00
|
|
|
EVAS_IMAGE_ORIENT_NONE, // EFL_GFX_IMAGE_ORIENTATION_NONE
|
|
|
|
EVAS_IMAGE_ORIENT_90, // EFL_GFX_IMAGE_ORIENTATION_RIGHT
|
|
|
|
EVAS_IMAGE_ORIENT_180, // EFL_GFX_IMAGE_ORIENTATION_DOWN
|
|
|
|
EVAS_IMAGE_ORIENT_270, // EFL_GFX_IMAGE_ORIENTATION_LEFT
|
|
|
|
EVAS_IMAGE_FLIP_HORIZONTAL, // EFL_GFX_IMAGE_ORIENTATION_NONE + FLIP_HOR
|
|
|
|
EVAS_IMAGE_FLIP_TRANSPOSE, // EFL_GFX_IMAGE_ORIENTATION_RIGHT + FLIP_HOR
|
|
|
|
EVAS_IMAGE_FLIP_VERTICAL, // EFL_GFX_IMAGE_ORIENTATION_DOWN + FLIP_HOR
|
|
|
|
EVAS_IMAGE_FLIP_TRANSVERSE, // EFL_GFX_IMAGE_ORIENTATION_LEFT + FLIP_HOR
|
|
|
|
EVAS_IMAGE_FLIP_VERTICAL, // EFL_GFX_IMAGE_ORIENTATION_NONE + FLIP_VER
|
|
|
|
EVAS_IMAGE_FLIP_TRANSVERSE, // EFL_GFX_IMAGE_ORIENTATION_RIGHT + FLIP_VER
|
|
|
|
EVAS_IMAGE_FLIP_HORIZONTAL, // EFL_GFX_IMAGE_ORIENTATION_DOWN + FLIP_VER
|
|
|
|
EVAS_IMAGE_FLIP_TRANSPOSE, // EFL_GFX_IMAGE_ORIENTATION_LEFT + FLIP_VER
|
|
|
|
EVAS_IMAGE_ORIENT_180, // EFL_GFX_IMAGE_ORIENTATION_NONE + FLIP_HOR + FLIP_VER
|
|
|
|
EVAS_IMAGE_ORIENT_270, // EFL_GFX_IMAGE_ORIENTATION_RIGHT + FLIP_HOR + FLIP_VER
|
|
|
|
EVAS_IMAGE_ORIENT_0, // EFL_GFX_IMAGE_ORIENTATION_DOWN + FLIP_HOR + FLIP_VER
|
|
|
|
EVAS_IMAGE_ORIENT_90 // EFL_GFX_IMAGE_ORIENTATION_LEFT + FLIP_HOR + FLIP_VER
|
2019-05-20 08:51:56 -07:00
|
|
|
};
|
|
|
|
EINA_SAFETY_ON_FALSE_RETURN(efl_orient >= 0 && efl_orient < 16);
|
2016-04-05 18:46:04 -07:00
|
|
|
|
2019-05-20 08:51:56 -07:00
|
|
|
o->orient_value = efl_orient;
|
|
|
|
_evas_image_orientation_set(obj, o, evas_orient[efl_orient]);
|
2016-04-05 18:46:04 -07:00
|
|
|
}
|
|
|
|
|
2019-05-22 11:16:16 -07:00
|
|
|
EOLIAN static Efl_Gfx_Image_Orientation
|
2019-07-12 01:22:16 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_orientable_image_orientation_get(const Eo *obj EINA_UNUSED, Evas_Image_Data *o)
|
2016-04-05 18:46:04 -07:00
|
|
|
{
|
|
|
|
return o->orient_value;
|
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2016-08-10 07:23:04 -07:00
|
|
|
_efl_canvas_image_internal_efl_object_dbg_info_get(Eo *eo_obj, Evas_Image_Data *o, Efl_Dbg_Info *root)
|
2013-01-28 22:36:23 -08:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
efl_dbg_info_get(efl_super(eo_obj, MY_CLASS), root);
|
|
|
|
Efl_Dbg_Info *group = EFL_DBG_INFO_LIST_APPEND(root, MY_CLASS_NAME);
|
2013-01-28 22:36:23 -08:00
|
|
|
|
|
|
|
const char *file, *key;
|
2017-10-04 21:01:35 -07:00
|
|
|
file = eina_file_filename_get(o->cur->f);
|
2013-07-23 23:49:39 -07:00
|
|
|
key = o->cur->key;
|
|
|
|
|
2016-08-15 06:44:41 -07:00
|
|
|
EFL_DBG_INFO_APPEND(group, "Image File", EINA_VALUE_TYPE_STRING, file);
|
|
|
|
EFL_DBG_INFO_APPEND(group, "Key", EINA_VALUE_TYPE_STRING, key);
|
|
|
|
EFL_DBG_INFO_APPEND(group, "Source", EINA_VALUE_TYPE_UINT64,
|
2017-08-07 07:34:33 -07:00
|
|
|
(uint64_t)(uintptr_t)evas_object_image_source_get(eo_obj));
|
2013-01-28 22:36:23 -08:00
|
|
|
}
|
|
|
|
|
2019-05-30 11:22:42 -07:00
|
|
|
static Eina_Rect
|
|
|
|
_efl_canvas_image_internal_efl_gfx_image_content_region_get(const Eo *eo_obj, Evas_Image_Data *o)
|
|
|
|
{
|
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
|
|
|
Eina_Rect r;
|
|
|
|
|
|
|
|
r.x = o->cur->border.l;
|
|
|
|
r.y = o->cur->border.t;
|
|
|
|
r.w = obj->cur->geometry.w - o->cur->border.l - o->cur->border.r;
|
|
|
|
r.h = obj->cur->geometry.h - o->cur->border.t - o->cur->border.b;
|
|
|
|
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_border_set(Eo *eo_obj, Evas_Image_Data *o, int l, int r, int t, int b)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2012-10-08 18:58:41 -07:00
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
if (l < 0) l = 0;
|
|
|
|
if (r < 0) r = 0;
|
|
|
|
if (t < 0) t = 0;
|
|
|
|
if (b < 0) b = 0;
|
2013-01-27 16:28:53 -08:00
|
|
|
if ((o->cur->border.l == l) &&
|
|
|
|
(o->cur->border.r == r) &&
|
|
|
|
(o->cur->border.t == t) &&
|
|
|
|
(o->cur->border.b == b)) return;
|
|
|
|
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->border.l = l;
|
|
|
|
state_write->border.r = r;
|
|
|
|
state_write->border.t = t;
|
|
|
|
state_write->border.b = b;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2012-09-04 01:56:46 -07:00
|
|
|
o->changed = EINA_TRUE;
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_change(eo_obj, obj);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_border_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o, int *l, int *r, int *t, int *b)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2013-01-27 16:28:53 -08:00
|
|
|
if (l) *l = o->cur->border.l;
|
|
|
|
if (r) *r = o->cur->border.r;
|
|
|
|
if (t) *t = o->cur->border.t;
|
|
|
|
if (b) *b = o->cur->border.b;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_border_center_fill_set(Eo *eo_obj, Evas_Image_Data *o, Efl_Gfx_Border_Fill_Mode _fill)
|
2005-03-31 03:39:55 -08:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2017-08-07 07:34:33 -07:00
|
|
|
Evas_Border_Fill_Mode fill = (Evas_Border_Fill_Mode)_fill;
|
2016-03-02 03:46:11 -08:00
|
|
|
|
2013-01-27 16:28:53 -08:00
|
|
|
if (fill == o->cur->border.fill) return;
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
state_write->border.fill = fill;
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2012-09-04 01:56:46 -07:00
|
|
|
o->changed = EINA_TRUE;
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_change(eo_obj, obj);
|
2005-03-31 03:39:55 -08:00
|
|
|
}
|
|
|
|
|
2016-03-02 03:46:11 -08:00
|
|
|
EOLIAN static Efl_Gfx_Border_Fill_Mode
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_border_center_fill_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
return (Efl_Gfx_Border_Fill_Mode)o->cur->border.fill;
|
2012-10-08 18:58:41 -07:00
|
|
|
}
|
2008-12-12 14:36:47 -08:00
|
|
|
|
2019-05-13 08:45:13 -07:00
|
|
|
static void
|
|
|
|
_toggle_fill_listener(Eo *eo_obj, Evas_Image_Data *o)
|
|
|
|
{
|
|
|
|
if (!o->filled)
|
|
|
|
evas_object_event_callback_del(eo_obj, EVAS_CALLBACK_RESIZE,
|
|
|
|
evas_object_image_filled_resize_listener);
|
|
|
|
else
|
|
|
|
evas_object_event_callback_add(eo_obj, EVAS_CALLBACK_RESIZE,
|
|
|
|
evas_object_image_filled_resize_listener,
|
|
|
|
NULL);
|
|
|
|
}
|
|
|
|
|
2016-03-01 22:44:12 -08:00
|
|
|
EOLIAN static void
|
2017-08-07 07:34:33 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_fill_fill_auto_set(Eo *eo_obj, Evas_Image_Data *o, Eina_Bool setting)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2019-05-13 08:45:13 -07:00
|
|
|
Eina_Size2D sz;
|
2008-12-12 14:36:47 -08:00
|
|
|
setting = !!setting;
|
2016-03-01 22:44:12 -08:00
|
|
|
o->filled_set = 1;
|
2008-12-12 14:36:47 -08:00
|
|
|
if (o->filled == setting) return;
|
|
|
|
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2008-12-12 14:36:47 -08:00
|
|
|
o->filled = setting;
|
|
|
|
|
2019-05-13 08:45:13 -07:00
|
|
|
_toggle_fill_listener(eo_obj, o);
|
2008-12-12 14:36:47 -08:00
|
|
|
|
2019-05-13 08:45:13 -07:00
|
|
|
if (!o->filled) return;
|
|
|
|
|
|
|
|
sz = efl_gfx_entity_size_get(eo_obj);
|
|
|
|
_evas_image_fill_set(eo_obj, o, 0, 0, sz.w, sz.h);
|
2008-12-12 14:36:47 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static Eina_Bool
|
2018-04-17 11:09:44 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_fill_fill_auto_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
return o->filled;
|
2010-02-20 22:21:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_border_scale_set(Eo *eo_obj, Evas_Image_Data *o, double scale)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2017-01-06 09:57:46 -08:00
|
|
|
if (EINA_DBL_EQ(scale, o->cur->border.scale)) return;
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
state_write->border.scale = scale;
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2012-09-04 01:56:46 -07:00
|
|
|
o->changed = EINA_TRUE;
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_change(eo_obj, obj);
|
2010-02-20 22:21:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static double
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_border_scale_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
return o->cur->border.scale;
|
2005-03-31 03:39:55 -08:00
|
|
|
}
|
|
|
|
|
2016-03-17 19:29:55 -07:00
|
|
|
void
|
|
|
|
_evas_image_fill_set(Eo *eo_obj, Evas_Image_Data *o, int x, int y, int w, int h)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2005-05-21 19:49:50 -07:00
|
|
|
|
2009-09-23 21:55:01 -07:00
|
|
|
if (w == 0) return;
|
|
|
|
if (h == 0) return;
|
2012-07-19 22:41:25 -07:00
|
|
|
if (w < 0) w = -w;
|
|
|
|
if (h < 0) h = -h;
|
|
|
|
|
2013-01-27 16:28:53 -08:00
|
|
|
if ((o->cur->fill.x == x) &&
|
|
|
|
(o->cur->fill.y == y) &&
|
|
|
|
(o->cur->fill.w == w) &&
|
|
|
|
(o->cur->fill.h == h)) return;
|
|
|
|
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->fill.x = x;
|
|
|
|
state_write->fill.y = y;
|
|
|
|
state_write->fill.w = w;
|
|
|
|
state_write->fill.h = h;
|
|
|
|
state_write->opaque_valid = 0;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2012-09-04 01:56:46 -07:00
|
|
|
o->changed = EINA_TRUE;
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_change(eo_obj, obj);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2016-03-17 19:29:55 -07:00
|
|
|
EOLIAN static void
|
2017-09-13 19:59:44 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_fill_fill_set(Eo *eo_obj, Evas_Image_Data *o, Eina_Rect fill)
|
2016-03-17 19:29:55 -07:00
|
|
|
{
|
|
|
|
// Should (0,0,0,0) reset the filled flag to true?
|
|
|
|
o->filled = EINA_FALSE;
|
|
|
|
o->filled_set = EINA_TRUE;
|
2019-05-13 08:45:13 -07:00
|
|
|
_toggle_fill_listener(eo_obj, o);
|
2017-09-13 01:41:20 -07:00
|
|
|
_evas_image_fill_set(eo_obj, o, fill.x, fill.y, fill.w, fill.h);
|
2016-03-17 19:29:55 -07:00
|
|
|
}
|
|
|
|
|
2017-09-13 19:59:44 -07:00
|
|
|
EOLIAN static Eina_Rect
|
2018-04-17 11:09:44 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_fill_fill_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2017-09-13 19:59:44 -07:00
|
|
|
return (Eina_Rect) o->cur->fill;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2017-09-18 04:56:45 -07:00
|
|
|
EOLIAN static Eina_Size2D
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_image_size_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2017-05-23 23:07:21 -07:00
|
|
|
{
|
2017-09-18 04:49:56 -07:00
|
|
|
return EINA_SIZE2D(o->file_size.w, o->file_size.h);
|
2017-05-23 23:07:21 -07:00
|
|
|
}
|
|
|
|
|
2017-09-18 04:16:33 -07:00
|
|
|
EOLIAN static Eina_Size2D
|
2018-04-17 11:09:44 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_view_view_size_get(const Eo *eo_obj, Evas_Image_Data *o)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2015-05-27 19:11:56 -07:00
|
|
|
int uvw, uvh;
|
|
|
|
Evas_Object_Protected_Data *source = NULL;
|
|
|
|
Evas_Object_Protected_Data *obj;
|
|
|
|
|
2016-08-15 06:44:41 -07:00
|
|
|
obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2015-05-27 19:11:56 -07:00
|
|
|
if (o->cur->source)
|
2016-08-15 06:44:41 -07:00
|
|
|
source = efl_data_scope_get(o->cur->source, EFL_CANVAS_OBJECT_CLASS);
|
2015-05-27 19:11:56 -07:00
|
|
|
|
|
|
|
if (o->cur->scene)
|
|
|
|
{
|
|
|
|
uvw = obj->data_3d->w;
|
|
|
|
uvh = obj->data_3d->h;
|
|
|
|
}
|
|
|
|
else if (!o->cur->source)
|
|
|
|
{
|
|
|
|
uvw = o->cur->image.w;
|
|
|
|
uvh = o->cur->image.h;
|
|
|
|
}
|
|
|
|
else if (source->proxy->surface && !source->proxy->redraw)
|
|
|
|
{
|
|
|
|
uvw = source->proxy->w;
|
|
|
|
uvh = source->proxy->h;
|
|
|
|
}
|
|
|
|
else if (source->type == o_type &&
|
2016-08-15 06:44:41 -07:00
|
|
|
((Evas_Image_Data *)efl_data_scope_get(o->cur->source, MY_CLASS))->engine_data)
|
2015-05-27 19:11:56 -07:00
|
|
|
{
|
|
|
|
uvw = source->cur->geometry.w;
|
|
|
|
uvh = source->cur->geometry.h;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
uvw = source->proxy->w;
|
|
|
|
uvh = source->proxy->h;
|
|
|
|
}
|
|
|
|
|
2017-09-18 04:16:33 -07:00
|
|
|
return EINA_SIZE2D(uvw, uvh);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2017-09-18 03:30:30 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_buffer_buffer_update_add(Eo *eo_obj, Evas_Image_Data *o, const Eina_Rect *region)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2012-10-08 18:58:41 -07:00
|
|
|
Eina_Rectangle *r;
|
2019-04-02 10:24:04 -07:00
|
|
|
Eo *eo_obj2;
|
|
|
|
Eina_List *l;
|
2017-09-18 03:30:30 -07:00
|
|
|
int x, y, w, h;
|
2012-12-15 18:01:11 -08:00
|
|
|
int cnt;
|
2012-10-08 18:58:41 -07:00
|
|
|
|
2017-09-18 03:30:30 -07:00
|
|
|
if (region)
|
|
|
|
{
|
|
|
|
x = region->x;
|
|
|
|
y = region->y;
|
|
|
|
w = region->w;
|
|
|
|
h = region->h;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
x = y = 0;
|
|
|
|
w = o->cur->image.w;
|
|
|
|
h = o->cur->image.h;
|
|
|
|
}
|
|
|
|
|
2013-01-27 16:28:53 -08:00
|
|
|
RECTS_CLIP_TO_RECT(x, y, w, h, 0, 0, o->cur->image.w, o->cur->image.h);
|
2017-08-07 07:34:33 -07:00
|
|
|
if ((w <= 0) || (h <= 0)) return;
|
2017-03-28 00:09:34 -07:00
|
|
|
if (obj->cur->snapshot)
|
2017-03-29 21:52:48 -07:00
|
|
|
{
|
|
|
|
obj->snapshot_no_obscure = EINA_TRUE;
|
|
|
|
evas_object_change(eo_obj, obj);
|
|
|
|
return;
|
|
|
|
}
|
2013-06-12 22:09:28 -07:00
|
|
|
if (!o->written) return;
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2013-01-25 04:15:38 -08:00
|
|
|
cnt = eina_list_count(o->pixels->pixel_updates);
|
2017-08-07 07:34:33 -07:00
|
|
|
if (cnt == 1) // detect single blob case already there to do a nop
|
|
|
|
{
|
|
|
|
if ((r = o->pixels->pixel_updates->data)) // already a single full rect there.
|
|
|
|
{
|
2013-06-28 01:25:30 -07:00
|
|
|
if ((r->x == 0) && (r->y == 0) && (r->w == o->cur->image.w) && (r->h == o->cur->image.h))
|
2012-12-15 18:01:11 -08:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
}
|
2015-10-02 00:32:05 -07:00
|
|
|
if ((cnt >= 512) ||
|
2017-08-07 07:34:33 -07:00
|
|
|
(((x == 0) && (y == 0) && (w == o->cur->image.w) && (h == o->cur->image.h)))) // too many update rects - just make a single blob update
|
|
|
|
{
|
2013-01-25 04:15:38 -08:00
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
EINA_LIST_FREE(pixi_write->pixel_updates, r)
|
|
|
|
eina_rectangle_free(r);
|
|
|
|
NEW_RECT(r, 0, 0, o->cur->image.w, o->cur->image.h);
|
|
|
|
if (r) pixi_write->pixel_updates = eina_list_append(pixi_write->pixel_updates, r);
|
|
|
|
}
|
2013-01-25 04:15:38 -08:00
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
2012-12-15 18:01:11 -08:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
NEW_RECT(r, x, y, w, h);
|
2013-01-25 04:15:38 -08:00
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
if (r) pixi_write->pixel_updates = eina_list_append(pixi_write->pixel_updates, r);
|
2013-01-25 04:15:38 -08:00
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
2012-12-15 18:01:11 -08:00
|
|
|
}
|
2014-04-14 03:03:47 -07:00
|
|
|
|
2012-09-04 01:56:46 -07:00
|
|
|
o->changed = EINA_TRUE;
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_change(eo_obj, obj);
|
2019-04-02 10:24:04 -07:00
|
|
|
|
|
|
|
EINA_LIST_FOREACH(obj->proxy->proxies, l, eo_obj2)
|
|
|
|
{
|
|
|
|
Evas_Object_Protected_Data *obj2 = efl_data_scope_get(eo_obj2, EFL_CANVAS_OBJECT_CLASS);
|
|
|
|
evas_object_change(eo_obj2, obj2);
|
|
|
|
}
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2016-06-09 01:30:05 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_buffer_alpha_set(Eo *eo_obj, Evas_Image_Data *o, Eina_Bool has_alpha)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2012-10-08 18:58:41 -07:00
|
|
|
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
if ((o->preload & EVAS_IMAGE_PRELOADING) && (o->engine_data))
|
2011-05-02 20:20:02 -07:00
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
o->preload = EVAS_IMAGE_PRELOAD_NONE;
|
|
|
|
ENFN->image_data_preload_cancel(ENC, o->engine_data, eo_obj, EINA_TRUE);
|
2011-05-02 20:20:02 -07:00
|
|
|
}
|
2015-07-01 23:41:06 -07:00
|
|
|
|
|
|
|
has_alpha = !!has_alpha;
|
|
|
|
if (has_alpha == o->cur->has_alpha)
|
2002-11-08 00:02:15 -08:00
|
|
|
return;
|
2015-07-01 23:41:06 -07:00
|
|
|
|
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->has_alpha = has_alpha;
|
|
|
|
state_write->opaque_valid = 0;
|
|
|
|
}
|
2015-07-01 23:41:06 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
if (o->engine_data)
|
2010-05-21 00:10:45 -07:00
|
|
|
{
|
2010-08-19 00:32:44 -07:00
|
|
|
int stride = 0;
|
2011-03-14 03:53:37 -07:00
|
|
|
|
2017-08-25 10:51:10 -07:00
|
|
|
o->engine_data = ENFN->image_alpha_set(ENC, o->engine_data, o->cur->has_alpha);
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_scale_hint_set)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_scale_hint_set(ENC, o->engine_data, o->scale_hint);
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_content_hint_set)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_content_hint_set(ENC, o->engine_data, o->content_hint);
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_stride_get)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_stride_get(ENC, o->engine_data, &stride);
|
2010-08-19 00:32:44 -07:00
|
|
|
else
|
2014-10-22 02:34:51 -07:00
|
|
|
stride = o->cur->image.w * 4;
|
|
|
|
|
2013-01-27 16:28:53 -08:00
|
|
|
if (o->cur->image.stride != stride)
|
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
state_write->image.stride = stride;
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
}
|
2013-06-12 22:09:28 -07:00
|
|
|
o->written = EINA_TRUE;
|
2010-05-21 00:10:45 -07:00
|
|
|
}
|
2017-09-18 03:30:30 -07:00
|
|
|
efl_gfx_buffer_update_add(eo_obj, NULL);
|
2013-01-27 16:28:53 -08:00
|
|
|
EVAS_OBJECT_WRITE_IMAGE_FREE_FILE_AND_KEY(o);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static Eina_Bool
|
2018-04-17 11:09:44 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_buffer_alpha_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
return o->cur->has_alpha;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_smooth_scale_set(Eo *eo_obj, Evas_Image_Data *o, Eina_Bool smooth_scale)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2012-10-08 18:58:41 -07:00
|
|
|
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2013-01-27 16:28:53 -08:00
|
|
|
if (((smooth_scale) && (o->cur->smooth_scale)) ||
|
|
|
|
((!smooth_scale) && (!o->cur->smooth_scale)))
|
2002-11-08 00:02:15 -08:00
|
|
|
return;
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
state_write->smooth_scale = smooth_scale;
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2012-09-04 01:56:46 -07:00
|
|
|
o->changed = EINA_TRUE;
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_change(eo_obj, obj);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static Eina_Bool
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_smooth_scale_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
return o->cur->smooth_scale;
|
2012-10-08 18:58:41 -07:00
|
|
|
}
|
2005-05-21 19:49:50 -07:00
|
|
|
|
2016-03-02 02:39:41 -08:00
|
|
|
EOLIAN static double
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_ratio_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2016-03-02 02:39:41 -08:00
|
|
|
{
|
|
|
|
if (!o->cur->image.h) return 1.0;
|
2017-08-07 07:34:33 -07:00
|
|
|
return (double)o->cur->image.w / (double)o->cur->image.h;
|
2016-03-02 02:39:41 -08:00
|
|
|
}
|
|
|
|
|
2019-03-04 10:36:57 -08:00
|
|
|
EOLIAN static Eina_Error
|
2019-02-27 10:17:09 -08:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_image_load_error_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
|
|
|
{
|
|
|
|
return o->load_error;
|
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static Eina_Bool
|
2019-02-27 10:17:35 -08:00
|
|
|
_efl_canvas_image_internal_efl_file_save_save(const Eo *eo_obj, Evas_Image_Data *o, const char *file, const char *key, const Efl_File_Save_Info *info)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
|
|
|
int quality = 80, compress = 9, ok = 0;
|
2019-02-27 10:17:35 -08:00
|
|
|
const char *encoding = NULL;
|
2015-07-01 19:52:16 -07:00
|
|
|
Image_Entry *ie;
|
2015-10-30 00:41:32 -07:00
|
|
|
Evas_Colorspace cspace = EVAS_COLORSPACE_ARGB8888;
|
2016-12-20 00:56:09 -08:00
|
|
|
Evas_Colorspace want_cspace = EVAS_COLORSPACE_ARGB8888;
|
2017-03-28 00:09:34 -07:00
|
|
|
Evas_Object_Protected_Data *obj;
|
|
|
|
Eina_Bool unmap_it = EINA_FALSE;
|
2019-05-02 04:50:24 -07:00
|
|
|
Eina_Bool tofree = EINA_FALSE;
|
2017-03-28 00:09:34 -07:00
|
|
|
int imagew, imageh, uvw, uvh;
|
|
|
|
Eina_Rw_Slice slice = {};
|
|
|
|
DATA32 *data = NULL;
|
2017-08-25 10:51:40 -07:00
|
|
|
void *pixels;
|
|
|
|
void *output;
|
2015-06-29 23:37:55 -07:00
|
|
|
|
2017-03-28 00:09:34 -07:00
|
|
|
obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2017-03-27 22:40:29 -07:00
|
|
|
|
2017-03-28 00:09:34 -07:00
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(file, EINA_FALSE);
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2015-06-29 23:37:55 -07:00
|
|
|
|
2017-08-25 10:51:40 -07:00
|
|
|
output = _evas_object_image_output_find(obj);
|
|
|
|
pixels = _evas_image_pixels_get((Eo *)eo_obj, obj, ENC, output, NULL, NULL,
|
2017-05-12 15:03:05 -07:00
|
|
|
0, 0,
|
2017-03-28 00:09:34 -07:00
|
|
|
&imagew, &imageh, &uvw, &uvh, EINA_TRUE, EINA_TRUE);
|
|
|
|
if (!pixels) goto no_pixels;
|
2015-06-29 23:37:55 -07:00
|
|
|
|
2017-08-25 10:51:10 -07:00
|
|
|
cspace = ENFN->image_file_colorspace_get(ENC, pixels);
|
2016-12-20 00:56:09 -08:00
|
|
|
want_cspace = cspace;
|
2019-02-27 10:17:35 -08:00
|
|
|
if (info)
|
2005-11-10 22:09:46 -08:00
|
|
|
{
|
2019-02-27 10:17:35 -08:00
|
|
|
encoding = info->encoding;
|
|
|
|
quality = info->quality;
|
|
|
|
compress = info->compression;
|
|
|
|
}
|
2015-10-30 00:41:32 -07:00
|
|
|
|
2019-02-27 10:17:35 -08:00
|
|
|
if (encoding)
|
|
|
|
{
|
|
|
|
const char *ext = strrchr(file, '.');
|
|
|
|
if (ext && !strcasecmp(ext, ".tgv"))
|
2016-12-20 00:56:09 -08:00
|
|
|
{
|
2019-02-27 10:17:35 -08:00
|
|
|
if (!strcmp(encoding, "auto"))
|
|
|
|
want_cspace = cspace;
|
|
|
|
else if (!strcmp(encoding, "etc1"))
|
|
|
|
want_cspace = EVAS_COLORSPACE_ETC1;
|
|
|
|
else if (!strcmp(encoding, "etc2"))
|
2015-10-30 00:41:32 -07:00
|
|
|
{
|
2019-02-27 10:17:35 -08:00
|
|
|
if (!ENFN->image_alpha_get(ENC, pixels))
|
|
|
|
want_cspace = EVAS_COLORSPACE_RGB8_ETC2;
|
|
|
|
else
|
|
|
|
want_cspace = EVAS_COLORSPACE_RGBA8_ETC2_EAC;
|
2015-10-30 00:41:32 -07:00
|
|
|
}
|
2019-02-27 10:17:35 -08:00
|
|
|
else if (!strcmp(encoding, "etc1+alpha"))
|
|
|
|
want_cspace = EVAS_COLORSPACE_ETC1_ALPHA;
|
2015-10-30 00:41:32 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2016-12-20 00:56:09 -08:00
|
|
|
if (ENFN->image_data_direct_get && (o->cur->orient == EVAS_IMAGE_ORIENT_NONE))
|
2015-10-30 00:41:32 -07:00
|
|
|
{
|
2016-12-20 00:56:09 -08:00
|
|
|
Evas_Colorspace cs;
|
2017-03-28 00:09:34 -07:00
|
|
|
Eina_Slice sl;
|
2016-12-20 00:56:09 -08:00
|
|
|
|
2019-05-02 04:50:24 -07:00
|
|
|
ok = ENFN->image_data_direct_get(ENC, pixels, 0, &sl, &cs, EINA_TRUE, &tofree);
|
2017-03-28 00:09:34 -07:00
|
|
|
if (ok && (cs == want_cspace))
|
2017-08-07 07:34:33 -07:00
|
|
|
data = (DATA32 *)sl.mem;
|
2016-12-20 00:56:09 -08:00
|
|
|
}
|
|
|
|
|
2017-03-28 00:09:34 -07:00
|
|
|
if (!data)
|
2015-10-30 00:41:32 -07:00
|
|
|
{
|
2017-03-28 00:09:34 -07:00
|
|
|
int stride;
|
2015-10-30 00:41:32 -07:00
|
|
|
|
2017-03-28 00:09:34 -07:00
|
|
|
cspace = EVAS_COLORSPACE_ARGB8888;
|
2017-08-25 10:51:10 -07:00
|
|
|
ok = ENFN->image_data_map(ENC, &pixels, &slice, &stride, 0, 0, imagew, imageh,
|
2017-03-28 00:09:34 -07:00
|
|
|
cspace, EFL_GFX_BUFFER_ACCESS_MODE_READ, 0);
|
|
|
|
if (!ok || !slice.mem) goto no_pixels;
|
|
|
|
unmap_it = EINA_TRUE;
|
|
|
|
data = slice.mem;
|
|
|
|
|
|
|
|
if (stride != (imagew * 4))
|
|
|
|
WRN("Invalid stride: saved image may look wrong!");
|
2015-10-30 00:41:32 -07:00
|
|
|
}
|
|
|
|
|
2015-07-01 19:52:16 -07:00
|
|
|
ie = evas_cache_image_data(evas_common_image_cache_get(),
|
2015-10-30 00:41:32 -07:00
|
|
|
imagew, imageh, data, o->cur->has_alpha, cspace);
|
2015-07-01 19:52:16 -07:00
|
|
|
if (ie)
|
2005-11-10 22:09:46 -08:00
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
RGBA_Image *im = (RGBA_Image *)ie;
|
2008-05-18 20:13:16 -07:00
|
|
|
|
2016-12-20 00:56:09 -08:00
|
|
|
ok = evas_common_save_image_to_file(im, file, key, quality, compress, encoding);
|
2015-07-01 19:52:16 -07:00
|
|
|
evas_cache_image_drop(ie);
|
2005-11-10 22:09:46 -08:00
|
|
|
}
|
2016-12-20 00:56:09 -08:00
|
|
|
else ok = EINA_FALSE;
|
2015-07-01 19:52:16 -07:00
|
|
|
|
2017-03-28 00:09:34 -07:00
|
|
|
if (unmap_it)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_data_unmap(ENC, pixels, &slice);
|
2014-06-16 23:29:51 -07:00
|
|
|
|
2019-05-02 04:50:24 -07:00
|
|
|
if (tofree) free(data);
|
|
|
|
|
2017-03-28 00:09:34 -07:00
|
|
|
if (!ok) ERR("Image save failed.");
|
2014-03-12 07:28:40 -07:00
|
|
|
return ok;
|
2017-03-28 00:09:34 -07:00
|
|
|
|
|
|
|
no_pixels:
|
|
|
|
ERR("Could not get image pixels for saving.");
|
|
|
|
return EINA_FALSE;
|
2005-11-10 22:09:46 -08:00
|
|
|
}
|
|
|
|
|
2016-03-02 03:46:11 -08:00
|
|
|
EOLIAN static Efl_Gfx_Colorspace
|
2018-04-17 11:09:44 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_buffer_colorspace_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
return (Efl_Gfx_Colorspace)o->cur->cspace;
|
2012-10-08 18:58:41 -07:00
|
|
|
}
|
|
|
|
|
2013-10-27 18:26:32 -07:00
|
|
|
static void
|
|
|
|
_on_image_native_surface_del(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *einfo EINA_UNUSED)
|
|
|
|
{
|
|
|
|
evas_object_image_native_surface_set(obj, NULL);
|
|
|
|
}
|
|
|
|
|
2016-03-08 23:21:08 -08:00
|
|
|
Eina_Bool
|
|
|
|
_evas_image_native_surface_set(Eo *eo_obj, Evas_Native_Surface *surf)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2013-10-27 18:26:32 -07:00
|
|
|
evas_object_event_callback_del_full
|
|
|
|
(eo_obj, EVAS_CALLBACK_DEL, _on_image_native_surface_del, NULL);
|
|
|
|
if (surf) // We need to unset native surf on del to remove shared hash refs
|
|
|
|
evas_object_event_callback_add
|
2017-08-07 07:34:33 -07:00
|
|
|
(eo_obj, EVAS_CALLBACK_DEL, _on_image_native_surface_del, NULL);
|
2012-10-08 18:58:41 -07:00
|
|
|
|
2017-06-21 13:06:01 -07:00
|
|
|
o->can_scanout = EINA_FALSE;
|
|
|
|
|
2012-12-21 09:30:44 -08:00
|
|
|
evas_render_rendering_wait(obj->layer->evas);
|
2016-03-07 21:11:07 -08:00
|
|
|
_evas_image_cleanup(eo_obj, obj, o);
|
2016-03-08 23:21:08 -08:00
|
|
|
if (!ENFN->image_native_set) return EINA_FALSE;
|
2010-12-06 01:02:16 -08:00
|
|
|
if ((surf) &&
|
|
|
|
((surf->version < 2) ||
|
2016-03-08 23:21:08 -08:00
|
|
|
(surf->version > EVAS_NATIVE_SURFACE_VERSION))) return EINA_FALSE;
|
2017-08-25 10:51:10 -07:00
|
|
|
o->engine_data = ENFN->image_native_set(ENC, o->engine_data, surf);
|
2017-06-21 13:06:01 -07:00
|
|
|
|
|
|
|
if (surf && surf->version > 4)
|
|
|
|
{
|
|
|
|
switch (surf->type)
|
|
|
|
{
|
|
|
|
case EVAS_NATIVE_SURFACE_WL_DMABUF:
|
|
|
|
if (surf->data.wl_dmabuf.scanout.handler)
|
|
|
|
o->can_scanout = EINA_TRUE;
|
|
|
|
break;
|
2017-08-07 07:34:33 -07:00
|
|
|
|
2017-06-21 13:06:01 -07:00
|
|
|
default:
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
2017-08-07 07:34:33 -07:00
|
|
|
return o->engine_data != NULL;
|
2006-12-09 00:52:08 -08:00
|
|
|
}
|
|
|
|
|
2016-03-08 23:21:08 -08:00
|
|
|
Evas_Native_Surface *
|
|
|
|
_evas_image_native_surface_get(const Evas_Object *eo_obj)
|
2009-05-07 06:29:56 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
2016-03-08 23:21:08 -08:00
|
|
|
Evas_Native_Surface *surf = NULL;
|
2012-10-08 18:58:41 -07:00
|
|
|
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_native_get)
|
2017-08-25 10:51:10 -07:00
|
|
|
surf = ENFN->image_native_get(ENC, o->engine_data);
|
2012-10-08 18:58:41 -07:00
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
return surf;
|
2012-10-08 18:58:41 -07:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_scale_hint_set(Eo *eo_obj, Evas_Image_Data *o, Efl_Gfx_Image_Scale_Hint hint)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2010-08-11 23:02:15 -07:00
|
|
|
if (o->scale_hint == hint) return;
|
2009-05-07 06:29:56 -07:00
|
|
|
o->scale_hint = hint;
|
2010-08-18 22:18:17 -07:00
|
|
|
if (o->engine_data)
|
|
|
|
{
|
2010-08-19 00:32:44 -07:00
|
|
|
int stride = 0;
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_scale_hint_set)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_scale_hint_set(ENC, o->engine_data, o->scale_hint);
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_stride_get)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_stride_get(ENC, o->engine_data, &stride);
|
2010-08-19 00:32:44 -07:00
|
|
|
else
|
2014-10-22 02:34:51 -07:00
|
|
|
stride = o->cur->image.w * 4;
|
2013-01-27 16:28:53 -08:00
|
|
|
|
|
|
|
if (o->cur->image.stride != stride)
|
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
state_write->image.stride = stride;
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
}
|
2010-08-18 22:18:17 -07:00
|
|
|
}
|
2009-05-07 06:29:56 -07:00
|
|
|
}
|
|
|
|
|
2018-04-19 04:26:59 -07:00
|
|
|
EOLIAN static Efl_Gfx_Image_Scale_Hint
|
|
|
|
_efl_canvas_image_internal_efl_gfx_image_scale_hint_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-03-10 20:59:14 -08:00
|
|
|
return o->scale_hint;
|
2012-10-08 18:58:41 -07:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2018-04-19 04:26:59 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_image_content_hint_set(Eo *eo_obj, Evas_Image_Data *o, Efl_Gfx_Image_Content_Hint hint)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2010-08-11 23:02:15 -07:00
|
|
|
if (o->content_hint == hint) return;
|
2010-03-06 20:19:17 -08:00
|
|
|
o->content_hint = hint;
|
2010-08-18 22:18:17 -07:00
|
|
|
if (o->engine_data)
|
|
|
|
{
|
2010-08-19 00:32:44 -07:00
|
|
|
int stride = 0;
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_content_hint_set)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_content_hint_set(ENC, o->engine_data, o->content_hint);
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_stride_get)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_stride_get(ENC, o->engine_data, &stride);
|
2010-08-19 00:32:44 -07:00
|
|
|
else
|
2014-10-22 02:34:51 -07:00
|
|
|
stride = o->cur->image.w * 4;
|
2013-01-27 16:28:53 -08:00
|
|
|
|
|
|
|
if (o->cur->image.stride != stride)
|
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
state_write->image.stride = stride;
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2013-01-27 16:28:53 -08:00
|
|
|
}
|
2010-08-18 22:18:17 -07:00
|
|
|
}
|
2010-03-06 20:19:17 -08:00
|
|
|
}
|
|
|
|
|
2018-04-19 04:26:59 -07:00
|
|
|
EOLIAN static Efl_Gfx_Image_Content_Hint
|
|
|
|
_efl_canvas_image_internal_efl_gfx_image_content_hint_get(const Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
return o->content_hint;
|
2012-10-08 18:58:41 -07:00
|
|
|
}
|
|
|
|
|
2016-03-15 00:19:12 -07:00
|
|
|
void
|
|
|
|
_evas_image_unload(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj, Eina_Bool dirty)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o;
|
2012-09-04 21:20:42 -07:00
|
|
|
Eina_Bool resize_call = EINA_FALSE;
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2016-08-15 06:44:41 -07:00
|
|
|
o = efl_data_scope_get(eo_obj, MY_CLASS);
|
2017-10-04 21:01:35 -07:00
|
|
|
if ((!o->cur->f) ||
|
2004-09-21 21:54:39 -07:00
|
|
|
(o->pixels_checked_out > 0)) return;
|
2012-10-08 18:58:41 -07:00
|
|
|
|
2015-02-10 03:44:38 -08:00
|
|
|
evas_object_async_block(obj);
|
2009-05-10 15:42:09 -07:00
|
|
|
if (dirty)
|
|
|
|
{
|
|
|
|
if (o->engine_data)
|
2017-08-25 10:51:10 -07:00
|
|
|
o->engine_data = ENFN->image_dirty_region(ENC, o->engine_data,
|
2017-08-07 07:34:33 -07:00
|
|
|
0, 0,
|
|
|
|
o->cur->image.w, o->cur->image.h);
|
2009-05-10 15:42:09 -07:00
|
|
|
}
|
2002-11-08 00:02:15 -08:00
|
|
|
if (o->engine_data)
|
2010-12-24 08:04:27 -08:00
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
if (o->preload & EVAS_IMAGE_PRELOADING)
|
2011-05-02 20:20:02 -07:00
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
o->preload = EVAS_IMAGE_PRELOAD_NONE;
|
|
|
|
ENFN->image_data_preload_cancel(ENC, o->engine_data, eo_obj, EINA_FALSE);
|
2011-05-02 20:20:02 -07:00
|
|
|
}
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_free(ENC, o->engine_data);
|
2010-12-24 08:04:27 -08:00
|
|
|
}
|
2005-05-21 19:49:50 -07:00
|
|
|
o->engine_data = NULL;
|
2019-03-04 10:36:57 -08:00
|
|
|
o->load_error = EFL_GFX_IMAGE_LOAD_ERROR_NONE;
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->has_alpha = EINA_TRUE;
|
|
|
|
state_write->cspace = EVAS_COLORSPACE_ARGB8888;
|
|
|
|
if ((state_write->image.w != 0) || (state_write->image.h != 0)) resize_call = EINA_TRUE;
|
|
|
|
state_write->image.w = 0;
|
|
|
|
state_write->image.h = 0;
|
|
|
|
state_write->image.stride = 0;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2012-10-08 18:58:41 -07:00
|
|
|
if (resize_call) evas_object_inform_call_image_resize(eo_obj);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2016-03-15 00:19:12 -07:00
|
|
|
void
|
|
|
|
_evas_image_load(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj, Evas_Image_Data *o)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2006-08-18 07:45:26 -07:00
|
|
|
Evas_Image_Load_Opts lo;
|
2019-03-04 10:36:57 -08:00
|
|
|
int load_error = 0;
|
2005-05-21 19:49:50 -07:00
|
|
|
|
2004-09-22 18:58:50 -07:00
|
|
|
if (o->engine_data) return;
|
2005-05-21 19:49:50 -07:00
|
|
|
|
2017-01-01 05:15:24 -08:00
|
|
|
lo.emile.scale_down_by = o->load_opts->scale_down_by;
|
|
|
|
lo.emile.dpi = o->load_opts->dpi;
|
|
|
|
lo.emile.w = o->load_opts->w;
|
|
|
|
lo.emile.h = o->load_opts->h;
|
|
|
|
lo.emile.region.x = o->load_opts->region.x;
|
|
|
|
lo.emile.region.y = o->load_opts->region.y;
|
|
|
|
lo.emile.region.w = o->load_opts->region.w;
|
|
|
|
lo.emile.region.h = o->load_opts->region.h;
|
|
|
|
lo.emile.scale_load.src_x = o->load_opts->scale_load.src_x;
|
|
|
|
lo.emile.scale_load.src_y = o->load_opts->scale_load.src_y;
|
|
|
|
lo.emile.scale_load.src_w = o->load_opts->scale_load.src_w;
|
|
|
|
lo.emile.scale_load.src_h = o->load_opts->scale_load.src_h;
|
|
|
|
lo.emile.scale_load.dst_w = o->load_opts->scale_load.dst_w;
|
|
|
|
lo.emile.scale_load.dst_h = o->load_opts->scale_load.dst_h;
|
|
|
|
lo.emile.scale_load.smooth = o->load_opts->scale_load.smooth;
|
|
|
|
lo.emile.scale_load.scale_hint = o->load_opts->scale_load.scale_hint;
|
|
|
|
lo.emile.orientation = o->load_opts->orientation;
|
|
|
|
lo.emile.degree = 0;
|
|
|
|
lo.skip_head = o->skip_head;
|
2019-03-04 10:36:57 -08:00
|
|
|
o->engine_data = ENFN->image_mmap(ENC, o->cur->f, o->cur->key, &load_error, &lo);
|
|
|
|
o->load_error = _evas_load_error_to_efl_gfx_image_load_error(load_error);
|
2013-07-11 00:03:01 -07:00
|
|
|
|
2017-01-01 05:15:24 -08:00
|
|
|
if (o->engine_data)
|
|
|
|
{
|
|
|
|
int w, h;
|
|
|
|
int stride = 0;
|
|
|
|
Eina_Bool resize_call = EINA_FALSE;
|
|
|
|
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_size_get(ENC, o->engine_data, &w, &h);
|
2017-01-01 05:15:24 -08:00
|
|
|
if (ENFN->image_stride_get)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_stride_get(ENC, o->engine_data, &stride);
|
2017-01-01 05:15:24 -08:00
|
|
|
else
|
|
|
|
stride = w * 4;
|
|
|
|
|
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
state_write->has_alpha = ENFN->image_alpha_get(ENC, o->engine_data);
|
|
|
|
state_write->cspace = ENFN->image_colorspace_get(ENC, o->engine_data);
|
2017-08-07 07:34:33 -07:00
|
|
|
if ((state_write->image.w != w) || (state_write->image.h != h))
|
|
|
|
resize_call = EINA_TRUE;
|
|
|
|
state_write->image.w = w;
|
|
|
|
state_write->image.h = h;
|
|
|
|
state_write->image.stride = stride;
|
|
|
|
}
|
2017-01-01 05:15:24 -08:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
|
|
|
if (resize_call) evas_object_inform_call_image_resize(eo_obj);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2019-03-04 10:36:57 -08:00
|
|
|
o->load_error = EFL_GFX_IMAGE_LOAD_ERROR_GENERIC;
|
2017-01-01 05:15:24 -08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
_evas_image_load_post_update(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj)
|
|
|
|
{
|
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
if (o->engine_data)
|
|
|
|
{
|
2012-09-04 01:42:38 -07:00
|
|
|
int w, h;
|
|
|
|
int stride = 0;
|
2012-09-04 21:20:42 -07:00
|
|
|
Eina_Bool resize_call = EINA_FALSE;
|
2005-05-21 19:49:50 -07:00
|
|
|
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_size_get(ENC, o->engine_data, &w, &h);
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_stride_get)
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_stride_get(ENC, o->engine_data, &stride);
|
2012-09-04 01:42:38 -07:00
|
|
|
else
|
|
|
|
stride = w * 4;
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
state_write->has_alpha = ENFN->image_alpha_get(ENC, o->engine_data);
|
|
|
|
state_write->cspace = ENFN->image_colorspace_get(ENC, o->engine_data);
|
2017-08-07 07:34:33 -07:00
|
|
|
if ((state_write->image.w != w) || (state_write->image.h != h))
|
|
|
|
resize_call = EINA_TRUE;
|
|
|
|
state_write->image.w = w;
|
|
|
|
state_write->image.h = h;
|
|
|
|
state_write->image.stride = stride;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
evas image: fix screen flickering issue at partial + image preloading
Summary:
Prerequisite: Partial rendering ON + Image Prealoding + Triple surface buffer of GL.
Previously, evas trys to draw of an image which didn't prepare of image data yet (in case of preloading)
This time, it will draw a solid color onto the dest sufrace 1,
But luckily, preloading is finished just after, it draws proper image data onto next surface 2 and 3.
Now, triple buffer is filled with the image data but only first frame is still empty. That's a problem.
This patch skips to draw image if it doesn't prepare data yet, but once the preloading is finished,
it starts to draw images.
@fix
Reviewers: #committers
Subscribers: kimcinoo, cedric, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6739
2018-08-08 00:01:11 -07:00
|
|
|
o->changed = EINA_TRUE;
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
o->preload = EVAS_IMAGE_PRELOADED;
|
2012-10-08 18:58:41 -07:00
|
|
|
if (resize_call) evas_object_inform_call_image_resize(eo_obj);
|
evas image: fix screen flickering issue at partial + image preloading
Summary:
Prerequisite: Partial rendering ON + Image Prealoding + Triple surface buffer of GL.
Previously, evas trys to draw of an image which didn't prepare of image data yet (in case of preloading)
This time, it will draw a solid color onto the dest sufrace 1,
But luckily, preloading is finished just after, it draws proper image data onto next surface 2 and 3.
Now, triple buffer is filled with the image data but only first frame is still empty. That's a problem.
This patch skips to draw image if it doesn't prepare data yet, but once the preloading is finished,
it starts to draw images.
@fix
Reviewers: #committers
Subscribers: kimcinoo, cedric, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6739
2018-08-08 00:01:11 -07:00
|
|
|
evas_object_change(eo_obj, obj);
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
|
|
|
|
//preloading error check
|
|
|
|
if (ENFN->image_load_error_get)
|
2019-03-04 10:36:57 -08:00
|
|
|
o->load_error = _evas_load_error_to_efl_gfx_image_load_error(ENFN->image_load_error_get(ENC, o->engine_data));
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
o->preload = EVAS_IMAGE_PRELOAD_NONE;
|
2019-03-04 10:36:57 -08:00
|
|
|
o->load_error = EFL_GFX_IMAGE_LOAD_ERROR_GENERIC;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2008-11-04 01:19:35 -08:00
|
|
|
static Evas_Coord
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_image_figure_x_fill(Evas_Object *eo_obj EINA_UNUSED, Evas_Object_Protected_Data *obj, Evas_Coord start, Evas_Coord size, Evas_Coord *size_ret)
|
2008-11-04 01:19:35 -08:00
|
|
|
{
|
|
|
|
Evas_Coord w;
|
|
|
|
|
|
|
|
w = ((size * obj->layer->evas->output.w) /
|
2012-09-04 01:42:38 -07:00
|
|
|
(Evas_Coord)obj->layer->evas->viewport.w);
|
2008-11-04 01:19:35 -08:00
|
|
|
if (size <= 0) size = 1;
|
|
|
|
if (start > 0)
|
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
while (start - size > 0)
|
|
|
|
start -= size;
|
2008-11-04 01:19:35 -08:00
|
|
|
}
|
|
|
|
else if (start < 0)
|
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
while (start < 0)
|
|
|
|
start += size;
|
2008-11-04 01:19:35 -08:00
|
|
|
}
|
|
|
|
start = ((start * obj->layer->evas->output.w) /
|
2012-09-04 01:42:38 -07:00
|
|
|
(Evas_Coord)obj->layer->evas->viewport.w);
|
2008-11-04 01:19:35 -08:00
|
|
|
*size_ret = w;
|
|
|
|
return start;
|
|
|
|
}
|
|
|
|
|
|
|
|
static Evas_Coord
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_image_figure_y_fill(Evas_Object *eo_obj EINA_UNUSED, Evas_Object_Protected_Data *obj, Evas_Coord start, Evas_Coord size, Evas_Coord *size_ret)
|
2008-11-04 01:19:35 -08:00
|
|
|
{
|
|
|
|
Evas_Coord h;
|
|
|
|
|
|
|
|
h = ((size * obj->layer->evas->output.h) /
|
2012-09-04 01:42:38 -07:00
|
|
|
(Evas_Coord)obj->layer->evas->viewport.h);
|
2008-11-04 01:19:35 -08:00
|
|
|
if (size <= 0) size = 1;
|
|
|
|
if (start > 0)
|
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
while (start - size > 0)
|
|
|
|
start -= size;
|
2008-11-04 01:19:35 -08:00
|
|
|
}
|
|
|
|
else if (start < 0)
|
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
while (start < 0)
|
|
|
|
start += size;
|
2008-11-04 01:19:35 -08:00
|
|
|
}
|
|
|
|
start = ((start * obj->layer->evas->output.h) /
|
2012-09-04 01:42:38 -07:00
|
|
|
(Evas_Coord)obj->layer->evas->viewport.h);
|
2008-11-04 01:19:35 -08:00
|
|
|
*size_ret = h;
|
|
|
|
return start;
|
|
|
|
}
|
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
static void
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_image_init(Evas_Object *eo_obj)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2002-11-08 00:02:15 -08:00
|
|
|
/* set up methods (compulsory) */
|
|
|
|
obj->func = &object_func;
|
2016-08-15 06:44:41 -07:00
|
|
|
obj->private_data = efl_data_ref(eo_obj, MY_CLASS);
|
2002-11-08 00:02:15 -08:00
|
|
|
obj->type = o_type;
|
2017-05-11 00:59:54 -07:00
|
|
|
obj->is_image_object = EINA_TRUE;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2014-03-12 07:28:40 -07:00
|
|
|
EOLIAN static void
|
2016-08-10 07:23:04 -07:00
|
|
|
_efl_canvas_image_internal_efl_object_destructor(Eo *eo_obj, Evas_Image_Data *o EINA_UNUSED)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2013-01-23 17:50:57 -08:00
|
|
|
|
2017-07-06 00:29:20 -07:00
|
|
|
if (obj->legacy.ctor)
|
2016-03-16 03:37:04 -07:00
|
|
|
evas_object_image_video_surface_set(eo_obj, NULL);
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_image_free(eo_obj, obj);
|
2016-08-15 06:44:41 -07:00
|
|
|
efl_destructor(efl_super(eo_obj, MY_CLASS));
|
2013-01-27 16:28:53 -08:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
_evas_object_image_free(Evas_Object *obj)
|
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o;
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2016-08-15 06:44:41 -07:00
|
|
|
EINA_SAFETY_ON_FALSE_RETURN(efl_isa(obj, MY_CLASS));
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2016-08-15 06:44:41 -07:00
|
|
|
o = efl_data_scope_get(obj, MY_CLASS);
|
2013-01-27 16:28:53 -08:00
|
|
|
|
2013-11-03 19:47:48 -08:00
|
|
|
// eina_cow_free reset the pointer to the default read only state
|
2017-08-07 07:34:33 -07:00
|
|
|
eina_cow_free(evas_object_image_load_opts_cow, (const Eina_Cow_Data **)&o->load_opts);
|
|
|
|
eina_cow_free(evas_object_image_pixels_cow, (const Eina_Cow_Data **)&o->pixels);
|
|
|
|
eina_cow_free(evas_object_image_state_cow, (const Eina_Cow_Data **)&o->cur);
|
|
|
|
eina_cow_free(evas_object_image_state_cow, (const Eina_Cow_Data **)&o->prev);
|
2012-10-08 18:58:41 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
|
|
|
evas_object_image_free(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj)
|
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
2009-06-23 06:57:27 -07:00
|
|
|
Eina_Rectangle *r;
|
2002-11-08 00:02:15 -08:00
|
|
|
|
|
|
|
/* free obj */
|
2017-10-04 21:01:35 -07:00
|
|
|
eina_file_close(o->cur->f);
|
2013-01-27 16:28:53 -08:00
|
|
|
if (o->cur->key) eina_stringshare_del(o->cur->key);
|
2016-03-07 21:11:07 -08:00
|
|
|
if (o->cur->source) _evas_image_proxy_unset(eo_obj, obj, o);
|
|
|
|
if (o->cur->scene) _evas_image_3d_unset(eo_obj, obj, o);
|
2013-02-19 02:37:57 -08:00
|
|
|
if (obj->layer && obj->layer->evas)
|
2009-09-27 20:51:21 -07:00
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
if (o->engine_data && ENC)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
if (o->preload & EVAS_IMAGE_PRELOADING)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
o->preload = EVAS_IMAGE_PRELOAD_NONE;
|
|
|
|
ENFN->image_data_preload_cancel(ENC, o->engine_data, eo_obj, EINA_FALSE);
|
2017-08-07 07:34:33 -07:00
|
|
|
}
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_free(ENC, o->engine_data);
|
2017-08-07 07:34:33 -07:00
|
|
|
}
|
2017-08-25 10:51:10 -07:00
|
|
|
if (o->engine_data_prep && ENC)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_free(ENC, o->engine_data_prep);
|
2017-08-07 07:34:33 -07:00
|
|
|
}
|
|
|
|
if (o->video_surface)
|
|
|
|
{
|
|
|
|
o->video_surface = EINA_FALSE;
|
|
|
|
obj->layer->evas->video_objects = eina_list_remove(obj->layer->evas->video_objects, eo_obj);
|
|
|
|
}
|
2011-10-02 20:28:52 -07:00
|
|
|
}
|
2005-10-03 06:14:07 -07:00
|
|
|
o->engine_data = NULL;
|
2016-11-16 19:28:52 -08:00
|
|
|
o->engine_data_prep = NULL;
|
2017-07-18 19:43:35 -07:00
|
|
|
if (o->pixels->images_to_free)
|
|
|
|
{
|
|
|
|
eina_hash_free(o->pixels->images_to_free);
|
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
pixi_write->images_to_free = NULL;
|
2017-07-18 19:43:35 -07:00
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
|
|
|
}
|
2013-01-25 07:19:32 -08:00
|
|
|
if (o->pixels->pixel_updates)
|
2013-01-25 04:15:38 -08:00
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
|
|
|
{
|
|
|
|
EINA_LIST_FREE(pixi_write->pixel_updates, r)
|
|
|
|
eina_rectangle_free(r);
|
|
|
|
}
|
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
2013-01-25 04:15:38 -08:00
|
|
|
}
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2013-01-11 11:54:12 -08:00
|
|
|
static void
|
|
|
|
_draw_image(Evas_Object_Protected_Data *obj,
|
2017-05-12 15:03:05 -07:00
|
|
|
void *engine, void *data, void *context, void *surface, void *image,
|
2013-01-11 11:54:12 -08:00
|
|
|
int src_x, int src_y, int src_w, int src_h, int dst_x,
|
|
|
|
int dst_y, int dst_w, int dst_h, int smooth,
|
|
|
|
Eina_Bool do_async)
|
|
|
|
{
|
|
|
|
Eina_Bool async_unref;
|
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
async_unref = ENFN->image_draw(engine, data, context, surface,
|
2014-10-22 02:34:51 -07:00
|
|
|
image, src_x, src_y,
|
|
|
|
src_w, src_h, dst_x,
|
|
|
|
dst_y, dst_w, dst_h,
|
|
|
|
smooth, do_async);
|
2013-01-11 11:54:12 -08:00
|
|
|
if (do_async && async_unref)
|
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
evas_cache_image_ref((Image_Entry *)image);
|
2013-01-11 11:54:12 -08:00
|
|
|
|
|
|
|
evas_unref_queue_image_put(obj->layer->evas, image);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2013-01-11 11:56:17 -08:00
|
|
|
void
|
|
|
|
evas_draw_image_map_async_check(Evas_Object_Protected_Data *obj,
|
2017-05-12 15:03:05 -07:00
|
|
|
void *engine, void *data, void *context, void *surface,
|
2013-01-11 11:56:17 -08:00
|
|
|
void *image, RGBA_Map *m, int smooth, int level,
|
|
|
|
Eina_Bool do_async)
|
|
|
|
{
|
|
|
|
Eina_Bool async_unref;
|
2017-05-12 15:03:05 -07:00
|
|
|
obj->layer->evas->engine.func->context_anti_alias_set(engine, context,
|
2014-11-25 19:22:55 -08:00
|
|
|
obj->cur->anti_alias);
|
2017-05-12 15:03:05 -07:00
|
|
|
async_unref = ENFN->image_map_draw(engine, data, context,
|
2014-10-22 02:34:51 -07:00
|
|
|
surface, image, m,
|
|
|
|
smooth, level,
|
|
|
|
do_async);
|
2013-01-11 11:56:17 -08:00
|
|
|
if (do_async && async_unref)
|
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
evas_cache_image_ref((Image_Entry *)image);
|
2013-01-11 11:56:17 -08:00
|
|
|
|
|
|
|
evas_unref_queue_image_put(obj->layer->evas, image);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2018-10-26 04:14:17 -07:00
|
|
|
void
|
|
|
|
evas_object_pixels_get_force(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj)
|
|
|
|
{
|
|
|
|
Evas_Image_Data *o = obj->private_data;
|
|
|
|
|
|
|
|
o->pixels->func.get_pixels(o->pixels->func.get_pixels_data, eo_obj);
|
|
|
|
}
|
|
|
|
|
2013-07-15 03:11:06 -07:00
|
|
|
static void *
|
2014-03-12 07:28:40 -07:00
|
|
|
evas_process_dirty_pixels(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj, Evas_Image_Data *o,
|
2017-05-12 15:03:05 -07:00
|
|
|
void *engine, void *output, void *surface, void *pixels)
|
2013-07-15 03:11:06 -07:00
|
|
|
{
|
2015-02-24 02:05:39 -08:00
|
|
|
Eina_Bool direct_override = EINA_FALSE, direct_force_off = EINA_FALSE;
|
2013-07-15 03:11:06 -07:00
|
|
|
|
|
|
|
if (o->dirty_pixels)
|
|
|
|
{
|
|
|
|
if (o->pixels->func.get_pixels)
|
|
|
|
{
|
2013-08-07 02:40:42 -07:00
|
|
|
Evas_Coord x, y, w, h;
|
|
|
|
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->image_native_get)
|
2013-07-15 03:11:06 -07:00
|
|
|
{
|
|
|
|
Evas_Native_Surface *ns;
|
2015-03-02 23:38:52 -08:00
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
ns = ENFN->image_native_get(engine, o->engine_data);
|
2015-03-02 23:38:52 -08:00
|
|
|
if (ns)
|
2013-07-15 03:11:06 -07:00
|
|
|
{
|
2014-12-09 04:36:45 -08:00
|
|
|
Eina_Bool direct_renderable = EINA_FALSE;
|
|
|
|
|
2013-07-15 03:11:06 -07:00
|
|
|
// Check if we can do direct rendering...
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->gl_direct_override_get)
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->gl_direct_override_get(engine, &direct_override, &direct_force_off);
|
2014-12-09 04:36:45 -08:00
|
|
|
if (ENFN->gl_surface_direct_renderable_get)
|
2017-08-25 10:51:47 -07:00
|
|
|
direct_renderable = ENFN->gl_surface_direct_renderable_get(engine, output, ns, &direct_override, surface);
|
2014-12-09 04:36:45 -08:00
|
|
|
|
2017-08-07 07:34:33 -07:00
|
|
|
if (((direct_override) ||
|
|
|
|
((direct_renderable) &&
|
|
|
|
(obj->cur->geometry.w == o->cur->image.w) &&
|
|
|
|
(obj->cur->geometry.h == o->cur->image.h) &&
|
|
|
|
(obj->cur->color.r == 255) &&
|
|
|
|
(obj->cur->color.g == 255) &&
|
|
|
|
(obj->cur->color.b == 255) &&
|
|
|
|
(obj->cur->color.a == 255) &&
|
|
|
|
(obj->cur->cache.clip.r == 255) &&
|
|
|
|
(obj->cur->cache.clip.g == 255) &&
|
|
|
|
(obj->cur->cache.clip.b == 255) &&
|
|
|
|
(obj->cur->cache.clip.a == 255) &&
|
|
|
|
(!obj->map->cur.map))
|
|
|
|
) && (!direct_force_off))
|
2013-07-15 03:11:06 -07:00
|
|
|
{
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->gl_get_pixels_set)
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->gl_get_pixels_set(engine, o->pixels->func.get_pixels, o->pixels->func.get_pixels_data, eo_obj);
|
2015-03-02 23:38:52 -08:00
|
|
|
if (ENFN->gl_image_direct_set)
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->gl_image_direct_set(engine, o->engine_data, EINA_TRUE);
|
2013-07-15 03:11:06 -07:00
|
|
|
o->direct_render = EINA_TRUE;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
o->direct_render = EINA_FALSE;
|
|
|
|
}
|
|
|
|
|
2017-08-07 07:34:33 -07:00
|
|
|
if ((ns) &&
|
|
|
|
(ns->type == EVAS_NATIVE_SURFACE_X11))
|
2013-07-15 03:11:06 -07:00
|
|
|
{
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->context_flush)
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_flush(engine);
|
2013-07-15 03:11:06 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2013-08-07 02:40:42 -07:00
|
|
|
x = obj->cur->geometry.x;
|
|
|
|
y = obj->cur->geometry.y;
|
|
|
|
w = obj->cur->geometry.w;
|
2014-04-14 03:03:47 -07:00
|
|
|
h = obj->cur->geometry.h;
|
2013-08-07 02:40:42 -07:00
|
|
|
|
2013-07-15 03:11:06 -07:00
|
|
|
if (!o->direct_render)
|
2015-03-03 03:08:16 -08:00
|
|
|
{
|
|
|
|
if (ENFN->gl_get_pixels_pre)
|
2017-08-25 10:54:19 -07:00
|
|
|
ENFN->gl_get_pixels_pre(engine, output);
|
2015-03-03 03:08:16 -08:00
|
|
|
o->pixels->func.get_pixels(o->pixels->func.get_pixels_data, eo_obj);
|
|
|
|
if (ENFN->gl_get_pixels_post)
|
2017-08-25 10:54:19 -07:00
|
|
|
ENFN->gl_get_pixels_post(engine, output);
|
2015-03-03 03:08:16 -08:00
|
|
|
}
|
2013-07-15 03:11:06 -07:00
|
|
|
|
2013-08-07 02:40:42 -07:00
|
|
|
if (!(obj->cur->geometry.x == x &&
|
|
|
|
obj->cur->geometry.y == y &&
|
|
|
|
obj->cur->geometry.w == w &&
|
|
|
|
obj->cur->geometry.h == h))
|
2014-03-12 07:28:40 -07:00
|
|
|
CRI("Evas_Image_Data geometry did change during pixels get callback !");
|
2013-08-07 02:40:42 -07:00
|
|
|
|
2014-10-22 02:34:51 -07:00
|
|
|
o->engine_data = ENFN->image_dirty_region
|
2017-08-07 07:34:33 -07:00
|
|
|
(engine, o->engine_data,
|
|
|
|
0, 0, o->cur->image.w, o->cur->image.h);
|
2017-05-12 15:03:05 -07:00
|
|
|
if (o->engine_data != pixels)
|
|
|
|
pixels = o->engine_data;
|
2013-07-15 03:11:06 -07:00
|
|
|
}
|
|
|
|
o->dirty_pixels = EINA_FALSE;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
// Check if the it's not dirty but it has direct rendering
|
2015-03-02 23:38:52 -08:00
|
|
|
if (o->direct_render && ENFN->image_native_get)
|
2013-07-15 03:11:06 -07:00
|
|
|
{
|
2015-03-02 23:38:52 -08:00
|
|
|
Evas_Native_Surface *ns;
|
2017-05-12 15:03:05 -07:00
|
|
|
ns = ENFN->image_native_get(engine, o->engine_data);
|
2017-08-25 10:54:19 -07:00
|
|
|
|
2015-03-02 23:38:52 -08:00
|
|
|
if (ENFN->gl_direct_override_get)
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->gl_direct_override_get(engine, &direct_override, &direct_force_off);
|
2015-03-02 23:38:52 -08:00
|
|
|
if (ENFN->gl_surface_direct_renderable_get)
|
2017-08-25 10:51:47 -07:00
|
|
|
ENFN->gl_surface_direct_renderable_get(engine, output, ns, &direct_override, surface);
|
2015-03-02 23:38:52 -08:00
|
|
|
|
|
|
|
if (direct_override && !direct_force_off)
|
|
|
|
{
|
|
|
|
// always use direct rendering
|
2015-07-19 23:24:04 -07:00
|
|
|
if (ENFN->gl_get_pixels_set)
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->gl_get_pixels_set(engine, o->pixels->func.get_pixels, o->pixels->func.get_pixels_data, eo_obj);
|
2015-07-19 23:24:04 -07:00
|
|
|
if (ENFN->gl_image_direct_set)
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->gl_image_direct_set(engine, o->engine_data, EINA_TRUE);
|
2015-03-02 23:38:52 -08:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
// Auto-fallback to FBO rendering (for perf & power consumption)
|
2015-03-03 03:08:16 -08:00
|
|
|
if (ENFN->gl_get_pixels_pre)
|
2017-08-25 10:54:19 -07:00
|
|
|
ENFN->gl_get_pixels_pre(engine, output);
|
2015-03-02 23:38:52 -08:00
|
|
|
o->pixels->func.get_pixels(o->pixels->func.get_pixels_data, obj->object);
|
2015-03-03 03:08:16 -08:00
|
|
|
if (ENFN->gl_get_pixels_post)
|
2017-08-25 10:54:19 -07:00
|
|
|
ENFN->gl_get_pixels_post(engine, output);
|
2015-03-02 23:38:52 -08:00
|
|
|
o->direct_render = EINA_FALSE;
|
|
|
|
}
|
2013-07-15 03:11:06 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return pixels;
|
|
|
|
}
|
|
|
|
|
2016-01-12 22:19:07 -08:00
|
|
|
EOLIAN static void
|
2016-06-09 23:55:28 -07:00
|
|
|
_efl_canvas_image_internal_efl_canvas_filter_internal_filter_dirty(Eo *eo_obj, Evas_Image_Data *o)
|
2015-06-18 05:45:21 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2016-03-01 21:41:32 -08:00
|
|
|
|
2015-06-18 05:45:21 -07:00
|
|
|
o->changed = 1;
|
2016-03-01 21:41:32 -08:00
|
|
|
evas_object_change(eo_obj, obj);
|
2015-06-18 05:45:21 -07:00
|
|
|
}
|
|
|
|
|
2016-01-12 22:19:07 -08:00
|
|
|
EOLIAN static Eina_Bool
|
2016-12-22 02:41:04 -08:00
|
|
|
_efl_canvas_image_internal_efl_canvas_filter_internal_filter_input_alpha(
|
2017-08-07 07:34:33 -07:00
|
|
|
Eo *eo_obj EINA_UNUSED, Evas_Image_Data *o EINA_UNUSED)
|
2014-03-21 01:03:33 -07:00
|
|
|
{
|
2015-06-18 05:45:21 -07:00
|
|
|
return EINA_FALSE;
|
|
|
|
}
|
|
|
|
|
2016-03-01 23:38:57 -08:00
|
|
|
EOLIAN static void
|
2016-06-09 01:30:05 -07:00
|
|
|
_efl_canvas_image_internal_efl_gfx_filter_filter_program_set(Eo *obj, Evas_Image_Data *pd,
|
|
|
|
const char *code, const char *name)
|
2016-03-01 23:38:57 -08:00
|
|
|
{
|
|
|
|
pd->has_filter = (code != NULL);
|
2016-08-15 06:44:41 -07:00
|
|
|
efl_gfx_filter_program_set(efl_super(obj, MY_CLASS), code, name);
|
2016-03-01 23:38:57 -08:00
|
|
|
}
|
|
|
|
|
2016-12-22 02:41:04 -08:00
|
|
|
EOLIAN static void
|
|
|
|
_efl_canvas_image_internal_efl_canvas_filter_internal_filter_state_prepare(
|
2017-08-07 07:34:33 -07:00
|
|
|
Eo *eo_obj, Evas_Image_Data *o EINA_UNUSED, Efl_Canvas_Filter_State *state, void *data EINA_UNUSED)
|
2016-12-22 02:41:04 -08:00
|
|
|
{
|
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
|
|
|
|
|
|
|
memset(&state->text, 0, sizeof(state->text));
|
|
|
|
#define STATE_COLOR(dst, src) dst.r = src.r; dst.g = src.g; dst.b = src.b; dst.a = src.a
|
|
|
|
STATE_COLOR(state->color, obj->cur->color);
|
|
|
|
#undef STATE_COLOR
|
|
|
|
|
|
|
|
state->w = obj->cur->geometry.w;
|
|
|
|
state->h = obj->cur->geometry.h;
|
|
|
|
state->scale = obj->cur->scale;
|
|
|
|
}
|
|
|
|
|
2017-04-02 23:34:10 -07:00
|
|
|
static inline Eina_Bool
|
|
|
|
_image_has_border(Evas_Object_Protected_Data *obj EINA_UNUSED, Evas_Image_Data *o)
|
|
|
|
{
|
|
|
|
return o->cur->border.l || o->cur->border.r || o->cur->border.t ||
|
2017-08-07 07:34:33 -07:00
|
|
|
o->cur->border.b || (o->cur->border.fill == 0);
|
2017-04-02 23:34:10 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
static inline Eina_Bool
|
|
|
|
_image_is_filled(Evas_Object_Protected_Data *obj, Evas_Image_Data *o)
|
|
|
|
{
|
|
|
|
if (o->filled) return EINA_TRUE;
|
|
|
|
return !o->cur->fill.x && !o->cur->fill.y &&
|
2017-08-07 07:34:33 -07:00
|
|
|
(o->cur->fill.w == obj->cur->geometry.w) &&
|
|
|
|
(o->cur->fill.h == obj->cur->geometry.h);
|
2017-04-02 23:34:10 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
static inline Eina_Bool
|
|
|
|
_image_is_scaled(Evas_Object_Protected_Data *obj, Evas_Image_Data *o)
|
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
return (obj->cur->geometry.w != o->cur->image.w) ||
|
|
|
|
(obj->cur->geometry.h != o->cur->image.h);
|
2017-04-02 23:34:10 -07:00
|
|
|
}
|
|
|
|
|
2016-01-12 22:19:07 -08:00
|
|
|
EOLIAN static Eina_Bool
|
2016-12-22 02:41:04 -08:00
|
|
|
_efl_canvas_image_internal_efl_canvas_filter_internal_filter_input_render(
|
2017-08-07 07:34:33 -07:00
|
|
|
Eo *eo_obj, Evas_Image_Data *o,
|
|
|
|
void *_filter, void *engine, void *output, void *context, void *data EINA_UNUSED,
|
|
|
|
int l, int r EINA_UNUSED, int t, int b EINA_UNUSED,
|
|
|
|
int x, int y, Eina_Bool do_async)
|
2015-06-18 05:45:21 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
2015-06-18 05:45:21 -07:00
|
|
|
Evas_Filter_Context *filter = _filter;
|
2017-05-12 15:03:05 -07:00
|
|
|
void *surface, *ctx;
|
2017-04-02 23:34:10 -07:00
|
|
|
Eina_Bool ok;
|
2015-06-18 05:45:21 -07:00
|
|
|
int W, H;
|
|
|
|
|
|
|
|
W = obj->cur->geometry.w;
|
|
|
|
H = obj->cur->geometry.h;
|
2014-03-21 01:03:33 -07:00
|
|
|
|
2017-04-02 23:34:10 -07:00
|
|
|
// FIXME: In GL we could use the image even if scaled
|
2017-04-03 22:28:29 -07:00
|
|
|
if (!_image_has_border(obj, o) && _image_is_filled(obj, o) && !_image_is_scaled(obj, o))
|
2017-04-02 23:34:10 -07:00
|
|
|
{
|
|
|
|
int imagew, imageh, uvw, uvh;
|
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
surface = _evas_image_pixels_get(eo_obj, obj, engine, output, context, NULL, x, y,
|
2017-04-02 23:34:10 -07:00
|
|
|
&imagew, &imageh, &uvw, &uvh, EINA_FALSE, EINA_FALSE);
|
|
|
|
|
|
|
|
ok = evas_filter_buffer_backing_set(filter, EVAS_FILTER_BUFFER_INPUT_ID, surface);
|
|
|
|
if (ok) return EINA_TRUE;
|
|
|
|
}
|
|
|
|
|
2017-03-22 00:16:22 -07:00
|
|
|
surface = evas_filter_buffer_backing_get(filter, EVAS_FILTER_BUFFER_INPUT_ID, EINA_TRUE);
|
|
|
|
EINA_SAFETY_ON_NULL_RETURN_VAL(surface, EINA_FALSE);
|
|
|
|
|
2015-06-18 05:45:21 -07:00
|
|
|
if (!o->filled)
|
|
|
|
{
|
|
|
|
l = 0;
|
|
|
|
t = 0;
|
2015-10-01 03:59:22 -07:00
|
|
|
r = 0;
|
|
|
|
b = 0;
|
2015-06-18 05:45:21 -07:00
|
|
|
}
|
2014-03-21 01:03:33 -07:00
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
ctx = ENFN->context_new(engine);
|
2017-03-22 00:16:22 -07:00
|
|
|
|
|
|
|
if (o->cur->has_alpha && !obj->cur->snapshot)
|
2014-03-21 01:03:33 -07:00
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_color_set(engine, ctx, 0, 0, 0, 0);
|
|
|
|
ENFN->context_render_op_set(engine, ctx, EVAS_RENDER_COPY);
|
|
|
|
ENFN->rectangle_draw(engine, output, ctx, surface, 0, 0, W, H, do_async);
|
|
|
|
ENFN->context_color_set(engine, ctx, 255, 255, 255, 255);
|
|
|
|
ENFN->context_render_op_set(engine, ctx, EVAS_RENDER_BLEND);
|
2015-06-18 05:45:21 -07:00
|
|
|
}
|
2014-03-21 01:03:33 -07:00
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
_evas_image_render(eo_obj, obj,
|
|
|
|
engine, output, ctx, surface,
|
2017-01-10 03:07:51 -08:00
|
|
|
x + l - obj->cur->geometry.x,
|
|
|
|
y + t - obj->cur->geometry.y,
|
2017-04-03 22:28:29 -07:00
|
|
|
l, t, r, b, EINA_TRUE, do_async);
|
2015-06-18 05:45:21 -07:00
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_free(engine, ctx);
|
|
|
|
ENFN->image_free(engine, surface);
|
2015-06-18 05:45:21 -07:00
|
|
|
|
|
|
|
return EINA_TRUE;
|
2014-03-21 01:03:33 -07:00
|
|
|
}
|
|
|
|
|
2017-06-22 10:39:24 -07:00
|
|
|
void
|
2017-08-25 10:51:20 -07:00
|
|
|
_evas_object_image_plane_release(Evas_Object *eo_obj EINA_UNUSED,
|
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
Efl_Canvas_Output *output)
|
2017-06-22 10:39:24 -07:00
|
|
|
{
|
|
|
|
Evas_Image_Data *o;
|
|
|
|
|
|
|
|
if (!obj) return;
|
|
|
|
|
|
|
|
o = obj->private_data;
|
|
|
|
|
|
|
|
if (!o->engine_data) return;
|
|
|
|
|
|
|
|
if (!o->plane) return;
|
|
|
|
|
2017-08-25 10:51:20 -07:00
|
|
|
ENFN->image_plane_release(output->output, o->engine_data, o->plane);
|
|
|
|
output->planes = eina_list_remove(output->planes, obj);
|
2017-06-22 10:39:24 -07:00
|
|
|
o->plane = NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
Eina_Bool
|
2017-08-25 10:51:20 -07:00
|
|
|
_evas_object_image_can_use_plane(Evas_Object_Protected_Data *obj,
|
|
|
|
Efl_Canvas_Output *output)
|
2017-06-22 10:39:24 -07:00
|
|
|
{
|
|
|
|
Evas_Native_Surface *ns;
|
|
|
|
Evas_Image_Data *o = obj->private_data;
|
|
|
|
|
|
|
|
/* Let the video surface code handle this one... */
|
|
|
|
if (o->video_surface)
|
|
|
|
return EINA_TRUE;
|
|
|
|
|
|
|
|
if (!o->can_scanout)
|
|
|
|
return EINA_FALSE;
|
|
|
|
|
|
|
|
if (!o->engine_data)
|
|
|
|
return EINA_FALSE;
|
|
|
|
|
|
|
|
if (!ENFN->image_plane_assign)
|
|
|
|
return EINA_FALSE;
|
|
|
|
|
|
|
|
if (!ENFN->image_native_get)
|
|
|
|
return EINA_FALSE;
|
|
|
|
|
2017-08-25 10:51:10 -07:00
|
|
|
ns = ENFN->image_native_get(ENC, o->engine_data);
|
2017-06-22 10:39:24 -07:00
|
|
|
if (!ns) return EINA_FALSE;
|
|
|
|
|
2017-08-25 10:51:20 -07:00
|
|
|
// FIXME: adjust position with output offset.
|
|
|
|
o->plane = ENFN->image_plane_assign(output->output, o->engine_data,
|
2017-06-22 10:39:24 -07:00
|
|
|
obj->cur->geometry.x,
|
|
|
|
obj->cur->geometry.y);
|
|
|
|
|
|
|
|
if (!o->plane)
|
|
|
|
return EINA_FALSE;
|
|
|
|
|
2017-08-25 10:51:20 -07:00
|
|
|
output->planes = eina_list_append(output->planes, obj);
|
2017-06-22 10:39:24 -07:00
|
|
|
return EINA_TRUE;
|
|
|
|
}
|
|
|
|
|
2018-10-22 08:20:28 -07:00
|
|
|
static int
|
|
|
|
evas_object_image_is_on_plane(Evas_Object *obj EINA_UNUSED, Evas_Object_Protected_Data *pd EINA_UNUSED, void *type_private_data)
|
|
|
|
{
|
|
|
|
Evas_Image_Data *o = type_private_data;
|
|
|
|
|
|
|
|
if (o->plane) return 1;
|
|
|
|
return 0;
|
|
|
|
}
|
2018-10-22 08:22:26 -07:00
|
|
|
|
|
|
|
static int
|
|
|
|
evas_object_image_plane_changed(Evas_Object *obj EINA_UNUSED, Evas_Object_Protected_Data *pd EINA_UNUSED, void *type_private_data)
|
|
|
|
{
|
|
|
|
Evas_Image_Data *o = type_private_data;
|
|
|
|
|
|
|
|
if (!!o->plane != o->plane_status)
|
|
|
|
{
|
|
|
|
o->plane_status = !!o->plane;
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
static void
|
2013-07-08 17:46:15 -07:00
|
|
|
evas_object_image_render(Evas_Object *eo_obj, Evas_Object_Protected_Data *obj, void *type_private_data,
|
2017-05-12 15:03:05 -07:00
|
|
|
void *engine, void *output, void *context, void *surface, int x, int y, Eina_Bool do_async)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o = type_private_data;
|
2002-11-08 00:02:15 -08:00
|
|
|
|
2018-08-07 21:51:40 -07:00
|
|
|
/* image is not ready yet, skip rendering. Leave it to next frame */
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
if (o->preload == EVAS_IMAGE_PRELOADING) return;
|
2018-08-07 21:51:40 -07:00
|
|
|
|
2013-01-27 16:28:53 -08:00
|
|
|
if ((o->cur->fill.w < 1) || (o->cur->fill.h < 1))
|
2017-08-07 07:34:33 -07:00
|
|
|
return; /* no error message, already printed in pre_render */
|
2008-12-09 14:46:57 -08:00
|
|
|
|
2011-02-06 20:18:37 -08:00
|
|
|
/* Proxy sanity */
|
|
|
|
if (o->proxyrendering)
|
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
_evas_image_proxy_error(eo_obj, engine, output, context, surface, x, y, EINA_FALSE);
|
2011-02-06 20:18:37 -08:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2015-02-02 22:38:50 -08:00
|
|
|
/* Mask sanity */
|
|
|
|
if (obj->mask->is_mask && (surface != obj->mask->surface))
|
|
|
|
{
|
|
|
|
ERR("Drawing a mask to another surface? Something's wrong...");
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2016-11-16 19:28:52 -08:00
|
|
|
if (o->engine_data_prep)
|
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_multiplier_unset(engine, context);
|
|
|
|
ENFN->context_render_op_set(engine, context, obj->cur->render_op);
|
|
|
|
ENFN->image_draw(engine, output, context, surface, o->engine_data_prep,
|
2016-11-16 19:28:52 -08:00
|
|
|
0, 0, obj->cur->geometry.w, obj->cur->geometry.h,
|
|
|
|
obj->cur->geometry.x + x, obj->cur->geometry.y + y,
|
|
|
|
obj->cur->geometry.w, obj->cur->geometry.h,
|
|
|
|
0, do_async);
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2017-06-22 10:39:24 -07:00
|
|
|
if (o->plane)
|
|
|
|
{
|
|
|
|
/* We must call pixels get because enlightenment uses it for internal
|
|
|
|
* bookkeeping and won't send frame callbacks to wayland clients if we
|
|
|
|
* don't
|
|
|
|
*/
|
2018-10-26 04:14:17 -07:00
|
|
|
evas_object_pixels_get_force(eo_obj, obj);
|
2017-06-22 10:39:24 -07:00
|
|
|
#if 0
|
|
|
|
Evas_Native_Surface *ns;
|
|
|
|
|
|
|
|
/* Draw a bright red rectangle where the object replaced by
|
|
|
|
* a hardware plane would have been.
|
|
|
|
*/
|
2017-08-25 10:51:10 -07:00
|
|
|
ns = ENFN->image_native_get(ENC, o->engine_data);
|
2017-06-22 10:39:24 -07:00
|
|
|
if (ns && ns->type == EVAS_NATIVE_SURFACE_WL_DMABUF)
|
|
|
|
{
|
|
|
|
ENFN->context_color_set(output, context, 255, 0, 0, 255);
|
|
|
|
ENFN->context_multiplier_unset(output, context);
|
|
|
|
ENFN->context_render_op_set(output, context, EVAS_RENDER_COPY);
|
|
|
|
ENFN->rectangle_draw(engine, output, context, surface,
|
|
|
|
obj->cur->geometry.x + x,
|
|
|
|
obj->cur->geometry.y + y,
|
|
|
|
obj->cur->geometry.w,
|
|
|
|
obj->cur->geometry.h,
|
|
|
|
do_async);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
return;
|
|
|
|
}
|
2011-10-02 20:28:52 -07:00
|
|
|
/* We are displaying the overlay */
|
|
|
|
if (o->video_visible)
|
|
|
|
{
|
|
|
|
/* Create a transparent rectangle */
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_color_set(engine, context, 0, 0, 0, 0);
|
|
|
|
ENFN->context_multiplier_unset(engine, context);
|
|
|
|
ENFN->context_render_op_set(engine, context, EVAS_RENDER_COPY);
|
|
|
|
ENFN->rectangle_draw(engine, output, context, surface,
|
2014-10-22 02:34:51 -07:00
|
|
|
obj->cur->geometry.x + x, obj->cur->geometry.y + y,
|
|
|
|
obj->cur->geometry.w, obj->cur->geometry.h,
|
|
|
|
do_async);
|
2011-10-02 20:28:52 -07:00
|
|
|
|
2012-12-18 08:28:55 -08:00
|
|
|
return;
|
2011-10-02 20:28:52 -07:00
|
|
|
}
|
2011-02-06 20:18:37 -08:00
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_color_set(engine, context, 255, 255, 255, 255);
|
2005-05-21 19:49:50 -07:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
if ((obj->cur->cache.clip.r == 255) &&
|
|
|
|
(obj->cur->cache.clip.g == 255) &&
|
|
|
|
(obj->cur->cache.clip.b == 255) &&
|
|
|
|
(obj->cur->cache.clip.a == 255))
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_multiplier_unset(engine, context);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
else
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_multiplier_set(engine, context,
|
2014-10-22 02:34:51 -07:00
|
|
|
obj->cur->cache.clip.r,
|
|
|
|
obj->cur->cache.clip.g,
|
|
|
|
obj->cur->cache.clip.b,
|
|
|
|
obj->cur->cache.clip.a);
|
2006-05-02 00:28:49 -07:00
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_render_op_set(engine, context, obj->cur->render_op);
|
2011-02-06 20:18:37 -08:00
|
|
|
|
2013-07-15 03:11:06 -07:00
|
|
|
// Clear out the pixel get stuff..
|
2014-10-22 02:34:51 -07:00
|
|
|
if (ENFN->gl_get_pixels_set)
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->gl_get_pixels_set(engine, NULL, NULL, NULL);
|
2015-03-02 23:38:52 -08:00
|
|
|
if (ENFN->gl_image_direct_set)
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->gl_image_direct_set(engine, o->engine_data, EINA_FALSE);
|
2013-07-15 03:11:06 -07:00
|
|
|
|
2015-06-18 05:45:21 -07:00
|
|
|
/* Render filter */
|
|
|
|
if (o->has_filter)
|
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
if (evas_filter_object_render(eo_obj, obj, engine, output, context, surface, x, y, do_async, EINA_FALSE))
|
2015-06-18 05:45:21 -07:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
_evas_image_render(eo_obj, obj, engine, output, context, surface, x, y, 0, 0, 0, 0, EINA_FALSE, do_async);
|
2015-06-18 05:45:21 -07:00
|
|
|
}
|
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
void *
|
|
|
|
_evas_image_pixels_get(Eo *eo_obj, Evas_Object_Protected_Data *obj,
|
2017-05-12 15:03:05 -07:00
|
|
|
void *engine, void *output, void *context, void *surface,
|
|
|
|
int x, int y,
|
2017-03-28 00:09:34 -07:00
|
|
|
int *imagew, int *imageh, int *uvw, int *uvh,
|
|
|
|
Eina_Bool filtered, Eina_Bool needs_post_render)
|
2015-06-18 05:45:21 -07:00
|
|
|
{
|
2015-10-07 19:19:50 -07:00
|
|
|
Evas_Image_Data *o = obj->private_data, *oi = NULL;
|
2017-03-27 22:40:29 -07:00
|
|
|
Evas_Object_Protected_Data *source = NULL;
|
2017-03-28 00:09:34 -07:00
|
|
|
void *pixels = NULL;
|
2015-06-18 05:45:21 -07:00
|
|
|
|
2017-03-28 00:09:34 -07:00
|
|
|
EVAS_OBJECT_DATA_ALIVE_CHECK(obj, NULL);
|
|
|
|
|
|
|
|
if (filtered && o->has_filter)
|
|
|
|
pixels = evas_filter_output_buffer_get(eo_obj);
|
|
|
|
|
|
|
|
if (!pixels && o->cur->source)
|
2017-03-27 22:40:29 -07:00
|
|
|
{
|
|
|
|
source = efl_data_scope_get(o->cur->source, EFL_CANVAS_OBJECT_CLASS);
|
|
|
|
if (source && (source->type == o_type))
|
|
|
|
oi = efl_data_scope_get(o->cur->source, MY_CLASS);
|
|
|
|
}
|
2013-12-26 23:56:30 -08:00
|
|
|
|
2017-03-28 00:09:34 -07:00
|
|
|
if (pixels)
|
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->image_size_get(engine, pixels, imagew, imageh);
|
2017-03-28 00:09:34 -07:00
|
|
|
*uvw = *imagew;
|
|
|
|
*uvh = *imageh;
|
|
|
|
}
|
|
|
|
else if (o->cur->scene)
|
2013-12-26 23:56:30 -08:00
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
_evas_image_3d_render(obj->layer->evas->evas, eo_obj, obj, o, o->cur->scene, engine, output);
|
2013-12-26 23:56:30 -08:00
|
|
|
pixels = obj->data_3d->surface;
|
2017-03-27 22:40:29 -07:00
|
|
|
*imagew = obj->data_3d->w;
|
|
|
|
*imageh = obj->data_3d->h;
|
|
|
|
*uvw = *imagew;
|
|
|
|
*uvh = *imageh;
|
2013-12-26 23:56:30 -08:00
|
|
|
}
|
2015-05-09 11:02:13 -07:00
|
|
|
else if (obj->cur->snapshot)
|
|
|
|
{
|
|
|
|
pixels = o->engine_data;
|
2017-03-27 22:40:29 -07:00
|
|
|
*imagew = o->cur->image.w;
|
|
|
|
*imageh = o->cur->image.h;
|
|
|
|
*uvw = *imagew;
|
|
|
|
*uvh = *imageh;
|
2015-05-09 11:02:13 -07:00
|
|
|
}
|
2015-10-13 19:19:48 -07:00
|
|
|
else if (!o->cur->source || !source)
|
2011-02-06 20:18:37 -08:00
|
|
|
{
|
2017-03-28 00:09:34 -07:00
|
|
|
// normal image (from file or user pixel set)
|
|
|
|
needs_post_render = EINA_FALSE;
|
2017-03-27 22:40:29 -07:00
|
|
|
if (output && surface)
|
2017-05-12 15:03:05 -07:00
|
|
|
pixels = evas_process_dirty_pixels(eo_obj, obj, o, engine, output, surface, o->engine_data);
|
2017-03-27 22:40:29 -07:00
|
|
|
else
|
|
|
|
pixels = o->engine_data;
|
|
|
|
*imagew = o->cur->image.w;
|
|
|
|
*imageh = o->cur->image.h;
|
|
|
|
*uvw = *imagew;
|
|
|
|
*uvh = *imageh;
|
2011-02-06 20:18:37 -08:00
|
|
|
}
|
2013-01-16 23:21:06 -08:00
|
|
|
else if (source->proxy->surface && !source->proxy->redraw)
|
2011-02-06 20:18:37 -08:00
|
|
|
{
|
2013-01-16 23:21:06 -08:00
|
|
|
pixels = source->proxy->surface;
|
2017-03-27 22:40:29 -07:00
|
|
|
*imagew = source->proxy->w;
|
|
|
|
*imageh = source->proxy->h;
|
|
|
|
*uvw = *imagew;
|
|
|
|
*uvh = *imageh;
|
2011-02-06 20:18:37 -08:00
|
|
|
}
|
2015-10-07 19:19:50 -07:00
|
|
|
else if (oi && oi->engine_data)
|
2011-02-06 20:18:37 -08:00
|
|
|
{
|
2015-10-07 19:19:50 -07:00
|
|
|
if (oi->has_filter)
|
2017-03-28 00:09:34 -07:00
|
|
|
pixels = evas_filter_output_buffer_get(source->object);
|
|
|
|
if (!pixels)
|
|
|
|
pixels = oi->engine_data;
|
2017-03-27 22:40:29 -07:00
|
|
|
*imagew = oi->cur->image.w;
|
|
|
|
*imageh = oi->cur->image.h;
|
|
|
|
*uvw = source->cur->geometry.w;
|
|
|
|
*uvh = source->cur->geometry.h;
|
2015-10-13 06:13:48 -07:00
|
|
|
/* check source_clip since we skip proxy_subrender here */
|
2017-03-27 22:40:29 -07:00
|
|
|
if (context && o->proxy_src_clip && source->cur->clipper)
|
2015-10-13 06:13:48 -07:00
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_clip_clip(engine, context,
|
2016-06-27 04:36:24 -07:00
|
|
|
source->cur->clipper->cur->cache.clip.x + x,
|
|
|
|
source->cur->clipper->cur->cache.clip.y + y,
|
|
|
|
source->cur->clipper->cur->cache.clip.w,
|
|
|
|
source->cur->clipper->cur->cache.clip.h);
|
2015-10-13 06:13:48 -07:00
|
|
|
}
|
2011-02-06 20:18:37 -08:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2012-09-04 01:56:46 -07:00
|
|
|
o->proxyrendering = EINA_TRUE;
|
2017-08-25 10:52:29 -07:00
|
|
|
evas_render_proxy_subrender(obj->layer->evas->evas, output, o->cur->source,
|
2016-12-19 22:47:54 -08:00
|
|
|
eo_obj, obj, o->proxy_src_clip, EINA_FALSE);
|
2013-01-16 23:21:06 -08:00
|
|
|
pixels = source->proxy->surface;
|
2017-03-27 22:40:29 -07:00
|
|
|
*imagew = source->proxy->w;
|
|
|
|
*imageh = source->proxy->h;
|
|
|
|
*uvw = *imagew;
|
|
|
|
*uvh = *imageh;
|
2012-09-04 01:56:46 -07:00
|
|
|
o->proxyrendering = EINA_FALSE;
|
2011-02-06 20:18:37 -08:00
|
|
|
}
|
|
|
|
|
2017-03-28 00:09:34 -07:00
|
|
|
if (needs_post_render && !obj->layer->evas->inside_post_render)
|
|
|
|
{
|
|
|
|
ERR("Can not save or map this image now! Proxies, snapshots and "
|
|
|
|
"filtered images support those operations only from inside a "
|
|
|
|
"post-render event.");
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
return pixels;
|
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
|
|
|
_evas_image_render(Eo *eo_obj, Evas_Object_Protected_Data *obj,
|
2017-05-12 15:03:05 -07:00
|
|
|
void *engine, void *output, void *context, void *surface, int x, int y,
|
2017-04-03 22:28:29 -07:00
|
|
|
int l, int t, int r, int b, Eina_Bool skip_map, Eina_Bool do_async)
|
2017-03-27 22:40:29 -07:00
|
|
|
{
|
|
|
|
Evas_Image_Data *o = obj->private_data;
|
|
|
|
int imagew, imageh, uvw, uvh, cw, ch;
|
|
|
|
int ix, iy, iw, ih, offx, offy;
|
|
|
|
int idw, idh, idx, idy;
|
|
|
|
void *pixels;
|
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
pixels = _evas_image_pixels_get(eo_obj, obj, engine, output, context, surface, x, y,
|
2017-03-28 00:09:34 -07:00
|
|
|
&imagew, &imageh, &uvw, &uvh, EINA_FALSE, EINA_FALSE);
|
2017-03-27 22:40:29 -07:00
|
|
|
|
|
|
|
if (!pixels) return;
|
2017-05-12 15:03:05 -07:00
|
|
|
if (ENFN->context_clip_get(engine, context, NULL, NULL, &cw, &ch) && (!cw || !ch))
|
2015-10-23 00:29:40 -07:00
|
|
|
return;
|
2015-10-13 06:13:48 -07:00
|
|
|
|
2017-04-03 22:28:29 -07:00
|
|
|
if (!skip_map && (obj->map->cur.map) && (obj->map->cur.map->count > 3)
|
|
|
|
&& (obj->map->cur.usemap))
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
evas_object_map_update(eo_obj, x, y, imagew, imageh, uvw, uvh);
|
2011-02-06 15:52:17 -08:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
evas_draw_image_map_async_check(
|
2017-08-07 07:34:33 -07:00
|
|
|
obj, engine, output, context, surface, pixels, obj->map->spans,
|
|
|
|
o->cur->smooth_scale | obj->map->cur.map->smooth, 0, do_async);
|
2017-03-27 22:40:29 -07:00
|
|
|
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->image_scale_hint_set(engine, pixels, o->scale_hint);
|
2017-03-27 22:40:29 -07:00
|
|
|
idx = evas_object_image_figure_x_fill(eo_obj, obj, o->cur->fill.x, o->cur->fill.w, &idw);
|
|
|
|
idy = evas_object_image_figure_y_fill(eo_obj, obj, o->cur->fill.y, o->cur->fill.h, &idh);
|
|
|
|
if (idw < 1) idw = 1;
|
|
|
|
if (idh < 1) idh = 1;
|
|
|
|
if (idx > 0) idx -= idw;
|
|
|
|
if (idy > 0) idy -= idh;
|
|
|
|
|
|
|
|
offx = obj->cur->geometry.x + x;
|
|
|
|
offy = obj->cur->geometry.y + y;
|
|
|
|
|
|
|
|
while (idx < obj->cur->geometry.w)
|
|
|
|
{
|
|
|
|
int ydy, dobreak_w = 0;
|
|
|
|
|
|
|
|
ydy = idy;
|
|
|
|
ix = idx;
|
|
|
|
if ((o->cur->fill.w == obj->cur->geometry.w) &&
|
|
|
|
(o->cur->fill.x == 0))
|
|
|
|
{
|
|
|
|
dobreak_w = 1;
|
|
|
|
iw = obj->cur->geometry.w;
|
2009-10-20 09:03:57 -07:00
|
|
|
}
|
|
|
|
else
|
2017-03-27 22:40:29 -07:00
|
|
|
iw = idx + idw - ix;
|
|
|
|
|
|
|
|
// Filter stuff
|
|
|
|
if (o->filled)
|
2009-10-20 09:03:57 -07:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
iw -= l + r;
|
|
|
|
if (iw <= 0) break;
|
|
|
|
}
|
2015-06-18 05:45:21 -07:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
while (idy < obj->cur->geometry.h)
|
|
|
|
{
|
|
|
|
int dobreak_h = 0;
|
2014-03-17 00:10:03 -07:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
iy = idy;
|
|
|
|
if ((o->cur->fill.h == obj->cur->geometry.h) &&
|
|
|
|
(o->cur->fill.y == 0))
|
|
|
|
{
|
|
|
|
ih = obj->cur->geometry.h;
|
|
|
|
dobreak_h = 1;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
ih = idy + idh - iy;
|
2014-03-17 00:10:03 -07:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
// Filter stuff
|
|
|
|
if (o->filled)
|
2009-10-20 09:03:57 -07:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
ih -= t + b;
|
|
|
|
if (ih <= 0) break;
|
|
|
|
}
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
if ((o->cur->border.l == 0) && (o->cur->border.r == 0) &&
|
|
|
|
(o->cur->border.t == 0) && (o->cur->border.b == 0) &&
|
|
|
|
(o->cur->border.fill != 0))
|
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels,
|
2017-03-27 22:40:29 -07:00
|
|
|
0, 0, imagew, imageh,
|
|
|
|
offx + ix, offy + iy, iw, ih,
|
|
|
|
o->cur->smooth_scale, do_async);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
int inx, iny, inw, inh, outx, outy, outw, outh;
|
|
|
|
int bl, br, bt, bb, bsl, bsr, bst, bsb;
|
|
|
|
int imw, imh, ox, oy;
|
|
|
|
|
|
|
|
ox = offx + ix;
|
|
|
|
oy = offy + iy;
|
|
|
|
imw = imagew;
|
|
|
|
imh = imageh;
|
|
|
|
bl = o->cur->border.l;
|
|
|
|
br = o->cur->border.r;
|
|
|
|
bt = o->cur->border.t;
|
|
|
|
bb = o->cur->border.b;
|
|
|
|
// fix impossible border settings if img pixels not enough
|
|
|
|
if ((bl + br) > 0)
|
2009-10-20 09:03:57 -07:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
if ((bl + br) > imw)
|
|
|
|
{
|
|
|
|
bl = (bl * imw) / (bl + br);
|
|
|
|
br = imw - bl;
|
|
|
|
}
|
|
|
|
if ((bl + br) == imw)
|
|
|
|
{
|
|
|
|
if (bl < br) br--;
|
|
|
|
else bl--;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if ((bt + bb) > 0)
|
|
|
|
{
|
|
|
|
if ((bt + bb) > imh)
|
|
|
|
{
|
|
|
|
bt = (bt * imh) / (bt + bb);
|
|
|
|
bb = imh - bt;
|
|
|
|
}
|
|
|
|
if ((bt + bb) == imh)
|
|
|
|
{
|
|
|
|
if (bt < bb) bb--;
|
|
|
|
else bt--;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (!EINA_DBL_EQ(o->cur->border.scale, 1.0))
|
|
|
|
{
|
|
|
|
bsl = ((double)bl * o->cur->border.scale);
|
|
|
|
bsr = ((double)br * o->cur->border.scale);
|
|
|
|
bst = ((double)bt * o->cur->border.scale);
|
|
|
|
bsb = ((double)bb * o->cur->border.scale);
|
2009-10-20 09:03:57 -07:00
|
|
|
}
|
|
|
|
else
|
2014-03-20 02:24:38 -07:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
bsl = bl; bsr = br; bst = bt; bsb = bb;
|
2014-03-20 02:24:38 -07:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
// adjust output border rendering if it doesnt fit
|
|
|
|
if ((bsl + bsr) > iw)
|
2009-10-20 09:03:57 -07:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
int b0 = bsl, b1 = bsr;
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
if ((bsl + bsr) > 0)
|
2009-10-20 09:03:57 -07:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
bsl = (bsl * iw) / (bsl + bsr);
|
|
|
|
bsr = iw - bsl;
|
2014-03-20 02:24:38 -07:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
if (b0 > 0) bl = (bl * bsl) / b0;
|
|
|
|
else bl = 0;
|
|
|
|
if (b1 > 0) br = (br * bsr) / b1;
|
|
|
|
else br = 0;
|
|
|
|
}
|
|
|
|
if ((bst + bsb) > ih)
|
|
|
|
{
|
|
|
|
int b0 = bst, b1 = bsb;
|
2014-03-19 19:10:43 -07:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
if ((bst + bsb) > 0)
|
2012-11-27 10:23:25 -08:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
bst = (bst * ih) / (bst + bsb);
|
|
|
|
bsb = ih - bst;
|
2012-11-27 10:23:25 -08:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
if (b0 > 0) bt = (bt * bst) / b0;
|
|
|
|
else bt = 0;
|
|
|
|
if (b1 > 0) bb = (bb * bsb) / b1;
|
|
|
|
else bb = 0;
|
|
|
|
}
|
|
|
|
// #--.
|
|
|
|
// | |
|
|
|
|
// '--'
|
|
|
|
inx = 0; iny = 0;
|
|
|
|
inw = bl; inh = bt;
|
|
|
|
outx = ox; outy = oy;
|
|
|
|
outw = bsl; outh = bst;
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
2017-03-27 22:40:29 -07:00
|
|
|
// .##.
|
|
|
|
// | |
|
|
|
|
// '--'
|
|
|
|
inx = bl; iny = 0;
|
|
|
|
inw = imw - bl - br; inh = bt;
|
|
|
|
outx = ox + bsl; outy = oy;
|
|
|
|
outw = iw - bsl - bsr; outh = bst;
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
2017-03-27 22:40:29 -07:00
|
|
|
// .--#
|
|
|
|
// | |
|
|
|
|
// '--'
|
|
|
|
inx = imw - br; iny = 0;
|
|
|
|
inw = br; inh = bt;
|
|
|
|
outx = ox + iw - bsr; outy = oy;
|
|
|
|
outw = bsr; outh = bst;
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
2017-03-27 22:40:29 -07:00
|
|
|
// .--.
|
|
|
|
// # |
|
|
|
|
// '--'
|
|
|
|
inx = 0; iny = bt;
|
|
|
|
inw = bl; inh = imh - bt - bb;
|
|
|
|
outx = ox; outy = oy + bst;
|
|
|
|
outw = bsl; outh = ih - bst - bsb;
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
2017-03-27 22:40:29 -07:00
|
|
|
// .--.
|
|
|
|
// |##|
|
|
|
|
// '--'
|
|
|
|
if (o->cur->border.fill > EVAS_BORDER_FILL_NONE)
|
|
|
|
{
|
|
|
|
inx = bl; iny = bt;
|
|
|
|
inw = imw - bl - br; inh = imh - bt - bb;
|
|
|
|
outx = ox + bsl; outy = oy + bst;
|
|
|
|
outw = iw - bsl - bsr; outh = ih - bst - bsb;
|
|
|
|
if ((o->cur->border.fill == EVAS_BORDER_FILL_SOLID) &&
|
|
|
|
(obj->cur->cache.clip.a == 255) &&
|
|
|
|
(!obj->clip.mask) &&
|
|
|
|
(obj->cur->render_op == EVAS_RENDER_BLEND))
|
2009-10-20 09:03:57 -07:00
|
|
|
{
|
2017-05-12 15:03:05 -07:00
|
|
|
ENFN->context_render_op_set(engine, context, EVAS_RENDER_COPY);
|
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
|
|
|
ENFN->context_render_op_set(engine, context, obj->cur->render_op);
|
2009-10-20 09:03:57 -07:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
else
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
2009-10-20 09:03:57 -07:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
// .--.
|
|
|
|
// | #
|
|
|
|
// '--'
|
|
|
|
inx = imw - br; iny = bt;
|
|
|
|
inw = br; inh = imh - bt - bb;
|
|
|
|
outx = ox + iw - bsr; outy = oy + bst;
|
|
|
|
outw = bsr; outh = ih - bst - bsb;
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
2017-03-27 22:40:29 -07:00
|
|
|
// .--.
|
|
|
|
// | |
|
|
|
|
// #--'
|
|
|
|
inx = 0; iny = imh - bb;
|
|
|
|
inw = bl; inh = bb;
|
|
|
|
outx = ox; outy = oy + ih - bsb;
|
|
|
|
outw = bsl; outh = bsb;
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
2017-03-27 22:40:29 -07:00
|
|
|
// .--.
|
|
|
|
// | |
|
|
|
|
// '##'
|
|
|
|
inx = bl; iny = imh - bb;
|
|
|
|
inw = imw - bl - br; inh = bb;
|
|
|
|
outx = ox + bsl; outy = oy + ih - bsb;
|
|
|
|
outw = iw - bsl - bsr; outh = bsb;
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
2017-03-27 22:40:29 -07:00
|
|
|
// .--.
|
|
|
|
// | |
|
|
|
|
// '--#
|
|
|
|
inx = imw - br; iny = imh - bb;
|
|
|
|
inw = br; inh = bb;
|
|
|
|
outx = ox + iw - bsr; outy = oy + ih - bsb;
|
|
|
|
outw = bsr; outh = bsb;
|
2017-05-12 15:03:05 -07:00
|
|
|
_draw_image(obj, engine, output, context, surface, pixels, inx, iny, inw, inh, outx, outy, outw, outh, o->cur->smooth_scale, do_async);
|
2009-10-20 09:03:57 -07:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
idy += idh;
|
|
|
|
if (dobreak_h) break;
|
2012-01-20 04:29:14 -08:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
idx += idw;
|
|
|
|
idy = ydy;
|
|
|
|
if (dobreak_w) break;
|
2013-06-17 02:22:15 -07:00
|
|
|
}
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
2013-07-08 17:46:15 -07:00
|
|
|
evas_object_image_render_pre(Evas_Object *eo_obj,
|
2017-08-07 07:34:33 -07:00
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o = type_private_data;
|
2011-05-21 15:28:13 -07:00
|
|
|
int is_v = 0, was_v = 0;
|
2016-11-16 19:28:52 -08:00
|
|
|
Eina_Bool changed_prep = EINA_TRUE;
|
2002-11-08 00:02:15 -08:00
|
|
|
|
evas image: fix screen flickering issue at partial + image preloading
Summary:
Prerequisite: Partial rendering ON + Image Prealoding + Triple surface buffer of GL.
Previously, evas trys to draw of an image which didn't prepare of image data yet (in case of preloading)
This time, it will draw a solid color onto the dest sufrace 1,
But luckily, preloading is finished just after, it draws proper image data onto next surface 2 and 3.
Now, triple buffer is filled with the image data but only first frame is still empty. That's a problem.
This patch skips to draw image if it doesn't prepare data yet, but once the preloading is finished,
it starts to draw images.
@fix
Reviewers: #committers
Subscribers: kimcinoo, cedric, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6739
2018-08-08 00:01:11 -07:00
|
|
|
/* image is not ready yet, skip rendering. Leave it to next frame */
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
if (o->preload & EVAS_IMAGE_PRELOADING) return;
|
2002-11-08 00:02:15 -08:00
|
|
|
/* dont pre-render the obj twice! */
|
|
|
|
if (obj->pre_render_done) return;
|
2013-01-02 21:38:03 -08:00
|
|
|
obj->pre_render_done = EINA_TRUE;
|
2002-11-08 00:02:15 -08:00
|
|
|
/* pre-render phase. this does anything an object needs to do just before */
|
|
|
|
/* rendering. this could mean loading the image data, retrieving it from */
|
|
|
|
/* elsewhere, decoding video etc. */
|
|
|
|
/* then when this is done the object needs to figure if it changed and */
|
2004-02-16 11:22:48 -08:00
|
|
|
/* if so what and where and add the appropriate redraw rectangles */
|
2012-10-08 18:58:41 -07:00
|
|
|
Evas_Public_Data *e = obj->layer->evas;
|
2008-12-09 14:46:57 -08:00
|
|
|
|
2015-02-11 19:10:04 -08:00
|
|
|
if ((o->cur->fill.w < 1) || (o->cur->fill.h < 1)) return;
|
2008-12-09 14:46:57 -08:00
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
/* if someone is clipping this obj - go calculate the clipper */
|
2013-03-12 05:58:19 -07:00
|
|
|
if (obj->cur->clipper)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2017-08-07 07:34:33 -07:00
|
|
|
if (obj->cur->cache.clip.dirty)
|
|
|
|
evas_object_clip_recalc(obj->cur->clipper);
|
|
|
|
obj->cur->clipper->func->render_pre(obj->cur->clipper->object,
|
|
|
|
obj->cur->clipper,
|
|
|
|
obj->cur->clipper->private_data);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
2011-02-06 20:18:37 -08:00
|
|
|
/* Proxy: Do it early */
|
2013-01-27 16:28:53 -08:00
|
|
|
if (o->cur->source)
|
2011-02-06 20:18:37 -08:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *source = efl_data_scope_get(o->cur->source, EFL_CANVAS_OBJECT_CLASS);
|
2013-01-16 23:21:06 -08:00
|
|
|
if (source->proxy->redraw || source->changed)
|
2012-10-08 18:58:41 -07:00
|
|
|
{
|
|
|
|
/* XXX: Do I need to sort out the map here? */
|
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
|
|
|
goto done;
|
|
|
|
}
|
2011-02-06 20:18:37 -08:00
|
|
|
}
|
2013-12-26 23:56:30 -08:00
|
|
|
else if (o->cur->scene)
|
|
|
|
{
|
2015-06-17 07:31:14 -07:00
|
|
|
Evas_Canvas3D_Scene *scene = o->cur->scene;
|
2014-04-25 10:28:38 -07:00
|
|
|
Eina_Bool dirty;
|
|
|
|
|
2016-03-01 10:06:28 -08:00
|
|
|
dirty = evas_canvas3d_object_dirty_get(scene, EVAS_CANVAS3D_STATE_ANY);
|
2014-04-25 10:28:38 -07:00
|
|
|
if (dirty)
|
2013-12-26 23:56:30 -08:00
|
|
|
{
|
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
|
|
|
goto done;
|
|
|
|
}
|
|
|
|
}
|
2011-02-06 20:18:37 -08:00
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
/* now figure what changed and add draw rects */
|
|
|
|
/* if it just became visible or invisible */
|
2019-05-29 12:36:53 -07:00
|
|
|
is_v = evas_object_is_visible(obj);
|
2019-05-29 12:36:46 -07:00
|
|
|
was_v = evas_object_was_visible(obj);
|
2002-11-08 00:02:15 -08:00
|
|
|
if (is_v != was_v)
|
|
|
|
{
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_visible_change(&e->clip_changes, eo_obj, is_v, was_v);
|
2016-08-11 07:18:15 -07:00
|
|
|
goto done;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
2012-10-25 08:24:27 -07:00
|
|
|
if (obj->changed_map || obj->changed_src_visible)
|
2009-11-03 07:41:36 -08:00
|
|
|
{
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
2009-11-03 07:41:36 -08:00
|
|
|
goto done;
|
|
|
|
}
|
2004-02-16 11:22:48 -08:00
|
|
|
/* it's not visible - we accounted for it appearing or not so just abort */
|
2002-11-08 00:02:15 -08:00
|
|
|
if (!is_v) goto done;
|
|
|
|
/* clipper changed this is in addition to anything else for obj */
|
2013-04-13 13:36:28 -07:00
|
|
|
if (was_v)
|
2013-04-13 13:18:31 -07:00
|
|
|
evas_object_render_pre_clipper_change(&e->clip_changes, eo_obj);
|
2004-02-16 11:22:48 -08:00
|
|
|
/* if we restacked (layer or just within a layer) and don't clip anyone */
|
2002-11-08 00:02:15 -08:00
|
|
|
if (obj->restack)
|
|
|
|
{
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
2016-08-11 07:18:15 -07:00
|
|
|
goto done;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
/* if it changed color */
|
2013-03-12 05:58:19 -07:00
|
|
|
if ((obj->cur->color.r != obj->prev->color.r) ||
|
|
|
|
(obj->cur->color.g != obj->prev->color.g) ||
|
|
|
|
(obj->cur->color.b != obj->prev->color.b) ||
|
2016-08-11 07:18:15 -07:00
|
|
|
(obj->cur->color.a != obj->prev->color.a) ||
|
|
|
|
(obj->cur->cache.clip.r != obj->prev->cache.clip.r) ||
|
|
|
|
(obj->cur->cache.clip.g != obj->prev->cache.clip.g) ||
|
|
|
|
(obj->cur->cache.clip.b != obj->prev->cache.clip.b) ||
|
|
|
|
(obj->cur->cache.clip.a != obj->prev->cache.clip.a))
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
2016-08-11 07:18:15 -07:00
|
|
|
goto done;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
2018-08-06 04:23:48 -07:00
|
|
|
if ((obj->cur->render_op != obj->prev->render_op) || /* if it changed render op */
|
|
|
|
(obj->cur->anti_alias != obj->prev->anti_alias)) /* if it changed anti_alias */
|
2006-09-30 03:18:37 -07:00
|
|
|
{
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
2016-08-11 07:18:15 -07:00
|
|
|
goto done;
|
2006-09-30 03:18:37 -07:00
|
|
|
}
|
2002-11-08 00:02:15 -08:00
|
|
|
if (o->changed)
|
|
|
|
{
|
2017-10-04 21:01:35 -07:00
|
|
|
if (((o->cur->f) && (!o->prev->f)) ||
|
|
|
|
((!o->cur->f) && (o->prev->f)) ||
|
2013-01-27 16:28:53 -08:00
|
|
|
((o->cur->key) && (!o->prev->key)) ||
|
|
|
|
((!o->cur->key) && (o->prev->key))
|
2017-08-07 07:34:33 -07:00
|
|
|
)
|
2012-09-04 01:42:38 -07:00
|
|
|
{
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
2016-08-11 07:18:15 -07:00
|
|
|
goto done;
|
2012-09-04 01:42:38 -07:00
|
|
|
}
|
2013-01-27 16:28:53 -08:00
|
|
|
if ((o->cur->image.w != o->prev->image.w) ||
|
|
|
|
(o->cur->image.h != o->prev->image.h) ||
|
|
|
|
(o->cur->has_alpha != o->prev->has_alpha) ||
|
|
|
|
(o->cur->cspace != o->prev->cspace) ||
|
|
|
|
(o->cur->smooth_scale != o->prev->smooth_scale))
|
2012-09-04 01:42:38 -07:00
|
|
|
{
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
2016-08-11 07:18:15 -07:00
|
|
|
goto done;
|
2012-09-04 01:42:38 -07:00
|
|
|
}
|
2013-01-27 16:28:53 -08:00
|
|
|
if ((o->cur->border.l != o->prev->border.l) ||
|
|
|
|
(o->cur->border.r != o->prev->border.r) ||
|
|
|
|
(o->cur->border.t != o->prev->border.t) ||
|
|
|
|
(o->cur->border.b != o->prev->border.b) ||
|
|
|
|
(o->cur->border.fill != o->prev->border.fill) ||
|
2017-01-06 09:57:46 -08:00
|
|
|
(!EINA_DBL_EQ(o->cur->border.scale, o->prev->border.scale)))
|
2012-09-04 01:42:38 -07:00
|
|
|
{
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
2016-08-11 07:18:15 -07:00
|
|
|
goto done;
|
2012-09-04 01:42:38 -07:00
|
|
|
}
|
2018-08-06 04:23:48 -07:00
|
|
|
if ((o->cur->frame != o->prev->frame) ||
|
|
|
|
(o->cur->orient != o->prev->orient) ||
|
2016-11-20 23:58:29 -08:00
|
|
|
/* Legacy compatibility (invalid behaviour): dirty_set() used to
|
|
|
|
* trigger full image redraw, even though this was not correct. */
|
2018-08-06 04:23:48 -07:00
|
|
|
(o->dirty_pixels && !o->pixels->pixel_updates))
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
{
|
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
2016-08-11 07:18:15 -07:00
|
|
|
goto done;
|
evas: add image orient set/get API in software backend for now.
Summary:
Added API's to rotate(0, 90, 180, 270), flip(horizontal, vertical, transpose, transverse)
evas image object. Also added example to demonstrate this.
Signed-off-by: kabeer khan <kabeer.khan@samsung.com>
Reviewers: raster, stephenmhouston, cedric
Subscribers: stephenmhouston, cedric
Differential Revision: https://phab.enlightenment.org/D1950
Signed-off-by: Cedric BAIL <cedric@osg.samsung.com>
2015-02-11 08:30:49 -08:00
|
|
|
}
|
evas image: fix screen flickering issue at partial + image preloading
Summary:
Prerequisite: Partial rendering ON + Image Prealoding + Triple surface buffer of GL.
Previously, evas trys to draw of an image which didn't prepare of image data yet (in case of preloading)
This time, it will draw a solid color onto the dest sufrace 1,
But luckily, preloading is finished just after, it draws proper image data onto next surface 2 and 3.
Now, triple buffer is filled with the image data but only first frame is still empty. That's a problem.
This patch skips to draw image if it doesn't prepare data yet, but once the preloading is finished,
it starts to draw images.
@fix
Reviewers: #committers
Subscribers: kimcinoo, cedric, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6739
2018-08-08 00:01:11 -07:00
|
|
|
//pre-loading is finished
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
if (o->preload == EVAS_IMAGE_PRELOADED)
|
evas image: fix screen flickering issue at partial + image preloading
Summary:
Prerequisite: Partial rendering ON + Image Prealoding + Triple surface buffer of GL.
Previously, evas trys to draw of an image which didn't prepare of image data yet (in case of preloading)
This time, it will draw a solid color onto the dest sufrace 1,
But luckily, preloading is finished just after, it draws proper image data onto next surface 2 and 3.
Now, triple buffer is filled with the image data but only first frame is still empty. That's a problem.
This patch skips to draw image if it doesn't prepare data yet, but once the preloading is finished,
it starts to draw images.
@fix
Reviewers: #committers
Subscribers: kimcinoo, cedric, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6739
2018-08-08 00:01:11 -07:00
|
|
|
{
|
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
o->preload = EVAS_IMAGE_PRELOAD_NONE;
|
evas image: fix screen flickering issue at partial + image preloading
Summary:
Prerequisite: Partial rendering ON + Image Prealoding + Triple surface buffer of GL.
Previously, evas trys to draw of an image which didn't prepare of image data yet (in case of preloading)
This time, it will draw a solid color onto the dest sufrace 1,
But luckily, preloading is finished just after, it draws proper image data onto next surface 2 and 3.
Now, triple buffer is filled with the image data but only first frame is still empty. That's a problem.
This patch skips to draw image if it doesn't prepare data yet, but once the preloading is finished,
it starts to draw images.
@fix
Reviewers: #committers
Subscribers: kimcinoo, cedric, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6739
2018-08-08 00:01:11 -07:00
|
|
|
goto done;
|
|
|
|
}
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
if (((obj->cur->geometry.x != obj->prev->geometry.x) ||
|
|
|
|
(obj->cur->geometry.y != obj->prev->geometry.y) ||
|
|
|
|
(obj->cur->geometry.w != obj->prev->geometry.w) ||
|
|
|
|
(obj->cur->geometry.h != obj->prev->geometry.h))
|
2017-08-07 07:34:33 -07:00
|
|
|
)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2016-11-16 19:28:52 -08:00
|
|
|
if ((obj->cur->geometry.w == obj->prev->geometry.w) &&
|
|
|
|
(obj->cur->geometry.h == obj->prev->geometry.h))
|
|
|
|
{
|
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
|
|
|
goto done;
|
|
|
|
}
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
if (o->changed)
|
|
|
|
{
|
2013-01-27 16:28:53 -08:00
|
|
|
if ((o->cur->fill.x != o->prev->fill.x) ||
|
|
|
|
(o->cur->fill.y != o->prev->fill.y) ||
|
|
|
|
(o->cur->fill.w != o->prev->fill.w) ||
|
|
|
|
(o->cur->fill.h != o->prev->fill.h))
|
2012-09-04 01:42:38 -07:00
|
|
|
{
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj, obj);
|
2016-08-11 07:18:15 -07:00
|
|
|
goto done;
|
2012-09-04 01:42:38 -07:00
|
|
|
}
|
2013-01-25 04:15:38 -08:00
|
|
|
if (o->pixels->pixel_updates)
|
2011-04-14 03:47:40 -07:00
|
|
|
{
|
2013-01-27 16:28:53 -08:00
|
|
|
if ((o->cur->border.l == 0) &&
|
|
|
|
(o->cur->border.r == 0) &&
|
|
|
|
(o->cur->border.t == 0) &&
|
|
|
|
(o->cur->border.b == 0) &&
|
|
|
|
(o->cur->image.w > 0) &&
|
|
|
|
(o->cur->image.h > 0) &&
|
2013-01-21 19:56:00 -08:00
|
|
|
(!((obj->map->cur.map) && (obj->map->cur.usemap))))
|
2011-04-14 03:47:40 -07:00
|
|
|
{
|
|
|
|
Eina_Rectangle *rr;
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2016-08-11 07:18:15 -07:00
|
|
|
if ((!o->cur->has_alpha) &&
|
2019-05-29 12:37:07 -07:00
|
|
|
(evas_object_is_opaque(obj)) &&
|
2016-08-11 07:18:15 -07:00
|
|
|
(obj->cur->color.a == 255))
|
2016-07-21 17:50:58 -07:00
|
|
|
{
|
|
|
|
Evas_Coord x, y, w, h;
|
|
|
|
|
|
|
|
x = obj->cur->cache.clip.x;
|
|
|
|
y = obj->cur->cache.clip.y;
|
|
|
|
w = obj->cur->cache.clip.w;
|
|
|
|
h = obj->cur->cache.clip.h;
|
|
|
|
if (obj->cur->clipper)
|
|
|
|
{
|
2016-08-11 07:18:15 -07:00
|
|
|
if (obj->cur->clipper->cur->cache.clip.a != 255)
|
|
|
|
w = 0;
|
|
|
|
else
|
|
|
|
{
|
|
|
|
RECTS_CLIP_TO_RECT(x, y, w, h,
|
|
|
|
obj->cur->clipper->cur->cache.clip.x,
|
|
|
|
obj->cur->clipper->cur->cache.clip.y,
|
|
|
|
obj->cur->clipper->cur->cache.clip.w,
|
|
|
|
obj->cur->clipper->cur->cache.clip.h);
|
|
|
|
}
|
2016-07-21 17:50:58 -07:00
|
|
|
}
|
2016-08-11 07:18:15 -07:00
|
|
|
if ((w > 0) && (h > 0))
|
2016-11-25 17:47:34 -08:00
|
|
|
evas_render_update_del(e,
|
|
|
|
x + e->framespace.x,
|
|
|
|
y + e->framespace.y,
|
|
|
|
w, h);
|
2016-07-21 17:50:58 -07:00
|
|
|
}
|
2013-01-25 04:15:38 -08:00
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
EINA_LIST_FREE(pixi_write->pixel_updates, rr)
|
|
|
|
{
|
|
|
|
Evas_Coord idw, idh, idx, idy;
|
|
|
|
int x, y, w, h;
|
2017-08-25 10:51:10 -07:00
|
|
|
e->engine.func->image_dirty_region(ENC, o->engine_data, rr->x, rr->y, rr->w, rr->h);
|
2017-08-07 07:34:33 -07:00
|
|
|
|
|
|
|
idx = evas_object_image_figure_x_fill(eo_obj, obj, o->cur->fill.x, o->cur->fill.w, &idw);
|
|
|
|
idy = evas_object_image_figure_y_fill(eo_obj, obj, o->cur->fill.y, o->cur->fill.h, &idh);
|
|
|
|
|
|
|
|
if (idw < 1) idw = 1;
|
|
|
|
if (idh < 1) idh = 1;
|
|
|
|
if (idx > 0) idx -= idw;
|
|
|
|
if (idy > 0) idy -= idh;
|
|
|
|
while (idx < obj->cur->geometry.w)
|
|
|
|
{
|
|
|
|
Evas_Coord ydy;
|
|
|
|
|
|
|
|
ydy = idy;
|
|
|
|
x = idx;
|
|
|
|
w = ((int)(idx + idw)) - x;
|
|
|
|
while (idy < obj->cur->geometry.h)
|
|
|
|
{
|
|
|
|
Eina_Rectangle r;
|
|
|
|
|
|
|
|
y = idy;
|
|
|
|
h = ((int)(idy + idh)) - y;
|
|
|
|
|
|
|
|
r.x = (rr->x * w) / o->cur->image.w;
|
|
|
|
r.y = (rr->y * h) / o->cur->image.h;
|
|
|
|
r.w = ((rr->w * w) + (o->cur->image.w * 2) - 1) / o->cur->image.w;
|
|
|
|
r.h = ((rr->h * h) + (o->cur->image.h * 2) - 1) / o->cur->image.h;
|
|
|
|
r.x += obj->cur->geometry.x + x;
|
|
|
|
r.y += obj->cur->geometry.y + y;
|
|
|
|
RECTS_CLIP_TO_RECT(r.x, r.y, r.w, r.h,
|
|
|
|
obj->cur->cache.clip.x, obj->cur->cache.clip.y,
|
|
|
|
obj->cur->cache.clip.w, obj->cur->cache.clip.h);
|
|
|
|
evas_add_rect(&e->clip_changes, r.x, r.y, r.w, r.h);
|
|
|
|
idy += h;
|
|
|
|
}
|
|
|
|
idx += idw;
|
|
|
|
idy = ydy;
|
|
|
|
}
|
|
|
|
eina_rectangle_free(rr);
|
|
|
|
}
|
|
|
|
}
|
2013-01-25 04:15:38 -08:00
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
2011-04-14 03:47:40 -07:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2016-07-19 21:13:41 -07:00
|
|
|
if ((o->cur->image.w > 0) &&
|
|
|
|
(o->cur->image.h > 0) &&
|
|
|
|
(o->cur->image.w == obj->cur->geometry.w) &&
|
|
|
|
(o->cur->image.h == obj->cur->geometry.h) &&
|
|
|
|
(o->cur->fill.x == 0) &&
|
|
|
|
(o->cur->fill.y == 0) &&
|
|
|
|
(o->cur->fill.w == o->cur->image.w) &&
|
|
|
|
(o->cur->fill.h == o->cur->image.h) &&
|
|
|
|
(!((obj->map->cur.map) && (obj->map->cur.usemap))))
|
2014-03-26 23:47:00 -07:00
|
|
|
{
|
2016-07-19 21:13:41 -07:00
|
|
|
Eina_Rectangle *rr;
|
|
|
|
|
2016-08-11 07:18:15 -07:00
|
|
|
if ((!o->cur->has_alpha) &&
|
2019-05-29 12:37:07 -07:00
|
|
|
(evas_object_is_opaque(obj)) &&
|
2016-08-11 07:18:15 -07:00
|
|
|
(obj->cur->color.a == 255))
|
2016-07-21 17:50:58 -07:00
|
|
|
{
|
|
|
|
Evas_Coord x, y, w, h;
|
|
|
|
|
|
|
|
x = obj->cur->cache.clip.x;
|
|
|
|
y = obj->cur->cache.clip.y;
|
|
|
|
w = obj->cur->cache.clip.w;
|
|
|
|
h = obj->cur->cache.clip.h;
|
|
|
|
if (obj->cur->clipper)
|
|
|
|
{
|
2016-08-11 07:18:15 -07:00
|
|
|
if (obj->cur->clipper->cur->cache.clip.a != 255)
|
|
|
|
w = 0;
|
|
|
|
else
|
|
|
|
{
|
|
|
|
RECTS_CLIP_TO_RECT(x, y, w, h,
|
|
|
|
obj->cur->clipper->cur->cache.clip.x,
|
|
|
|
obj->cur->clipper->cur->cache.clip.y,
|
|
|
|
obj->cur->clipper->cur->cache.clip.w,
|
|
|
|
obj->cur->clipper->cur->cache.clip.h);
|
|
|
|
}
|
2016-07-21 17:50:58 -07:00
|
|
|
}
|
2016-08-11 07:18:15 -07:00
|
|
|
if ((w > 0) && (h > 0))
|
2016-11-25 17:47:34 -08:00
|
|
|
evas_render_update_del(e,
|
|
|
|
x + e->framespace.x,
|
|
|
|
y + e->framespace.y,
|
|
|
|
w, h);
|
2016-07-21 17:50:58 -07:00
|
|
|
}
|
2016-08-11 07:18:15 -07:00
|
|
|
else if ((o->cur->border.fill == EVAS_BORDER_FILL_SOLID) &&
|
|
|
|
(obj->cur->color.a == 255))
|
2016-07-21 17:50:58 -07:00
|
|
|
{
|
|
|
|
Evas_Coord x, y, w, h;
|
|
|
|
|
|
|
|
x = obj->cur->geometry.x + o->cur->border.l;
|
|
|
|
y = obj->cur->geometry.y + o->cur->border.t;
|
|
|
|
w = obj->cur->geometry.w - o->cur->border.l - o->cur->border.r;
|
|
|
|
h = obj->cur->geometry.h - o->cur->border.t - o->cur->border.b;
|
|
|
|
if (obj->cur->clipper)
|
|
|
|
{
|
2016-08-11 07:18:15 -07:00
|
|
|
if (obj->cur->clipper->cur->cache.clip.a != 255)
|
|
|
|
w = 0;
|
|
|
|
else
|
|
|
|
{
|
|
|
|
RECTS_CLIP_TO_RECT(x, y, w, h,
|
|
|
|
obj->cur->clipper->cur->cache.clip.x,
|
|
|
|
obj->cur->clipper->cur->cache.clip.y,
|
|
|
|
obj->cur->clipper->cur->cache.clip.w,
|
|
|
|
obj->cur->clipper->cur->cache.clip.h);
|
|
|
|
}
|
2016-07-21 17:50:58 -07:00
|
|
|
}
|
2016-08-11 07:18:15 -07:00
|
|
|
if ((w > 0) && (h > 0))
|
2016-11-25 17:47:34 -08:00
|
|
|
evas_render_update_del(e,
|
|
|
|
x + e->framespace.x,
|
|
|
|
y + e->framespace.y,
|
|
|
|
w, h);
|
2016-07-21 17:50:58 -07:00
|
|
|
}
|
2016-07-19 21:13:41 -07:00
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
EINA_LIST_FREE(pixi_write->pixel_updates, rr)
|
|
|
|
{
|
|
|
|
Eina_Rectangle r;
|
|
|
|
|
2017-08-25 10:51:10 -07:00
|
|
|
e->engine.func->image_dirty_region(ENC, o->engine_data, rr->x, rr->y, rr->w, rr->h);
|
2017-08-07 07:34:33 -07:00
|
|
|
r.x = rr->x;
|
|
|
|
r.y = rr->y;
|
|
|
|
r.w = rr->w;
|
|
|
|
r.h = rr->h;
|
|
|
|
r.x += obj->cur->geometry.x;
|
|
|
|
r.y += obj->cur->geometry.y;
|
|
|
|
RECTS_CLIP_TO_RECT(r.x, r.y, r.w, r.h,
|
|
|
|
obj->cur->cache.clip.x, obj->cur->cache.clip.y,
|
|
|
|
obj->cur->cache.clip.w, obj->cur->cache.clip.h);
|
|
|
|
evas_add_rect(&e->clip_changes, r.x, r.y, r.w, r.h);
|
|
|
|
eina_rectangle_free(rr);
|
|
|
|
}
|
|
|
|
}
|
2016-07-19 21:13:41 -07:00
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
2014-03-26 23:47:00 -07:00
|
|
|
}
|
2016-07-19 21:13:41 -07:00
|
|
|
else
|
|
|
|
{
|
|
|
|
Eina_Rectangle *r;
|
2014-03-26 23:47:00 -07:00
|
|
|
|
2016-07-19 21:13:41 -07:00
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
EINA_LIST_FREE(pixi_write->pixel_updates, r)
|
|
|
|
eina_rectangle_free(r);
|
|
|
|
}
|
2016-07-19 21:13:41 -07:00
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
2017-08-25 10:51:10 -07:00
|
|
|
e->engine.func->image_dirty_region(ENC, o->engine_data, 0, 0, o->cur->image.w, o->cur->image.h);
|
2016-07-19 21:13:41 -07:00
|
|
|
|
|
|
|
evas_object_render_pre_prev_cur_add(&e->clip_changes, eo_obj,
|
|
|
|
obj);
|
|
|
|
}
|
2014-02-17 06:05:36 -08:00
|
|
|
}
|
2016-07-21 17:50:58 -07:00
|
|
|
goto done;
|
2014-02-17 06:05:36 -08:00
|
|
|
}
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
/* it obviously didn't change - add a NO obscure - this "unupdates" this */
|
|
|
|
/* area so if there were updates for it they get wiped. don't do it if we */
|
2004-02-16 11:22:48 -08:00
|
|
|
/* aren't fully opaque and we are visible */
|
2019-05-29 12:37:07 -07:00
|
|
|
if (evas_object_is_opaque(obj))
|
2009-11-06 21:01:43 -08:00
|
|
|
{
|
2011-11-10 21:56:40 -08:00
|
|
|
Evas_Coord x, y, w, h;
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
x = obj->cur->cache.clip.x;
|
|
|
|
y = obj->cur->cache.clip.y;
|
|
|
|
w = obj->cur->cache.clip.w;
|
|
|
|
h = obj->cur->cache.clip.h;
|
|
|
|
if (obj->cur->clipper)
|
2011-11-10 21:56:40 -08:00
|
|
|
{
|
|
|
|
RECTS_CLIP_TO_RECT(x, y, w, h,
|
2013-03-12 05:58:19 -07:00
|
|
|
obj->cur->clipper->cur->cache.clip.x,
|
|
|
|
obj->cur->clipper->cur->cache.clip.y,
|
|
|
|
obj->cur->clipper->cur->cache.clip.w,
|
|
|
|
obj->cur->clipper->cur->cache.clip.h);
|
2011-11-10 21:56:40 -08:00
|
|
|
}
|
2016-11-25 17:47:34 -08:00
|
|
|
evas_render_update_del(e,
|
|
|
|
x + e->framespace.x,
|
|
|
|
y + e->framespace.y,
|
|
|
|
w, h);
|
2016-11-16 19:28:52 -08:00
|
|
|
changed_prep = EINA_FALSE;
|
2009-11-06 21:01:43 -08:00
|
|
|
}
|
2016-11-21 03:49:56 -08:00
|
|
|
else
|
|
|
|
changed_prep = EINA_FALSE;
|
2017-08-07 07:34:33 -07:00
|
|
|
done:
|
2012-10-08 18:58:41 -07:00
|
|
|
evas_object_render_pre_effect_updates(&e->clip_changes, eo_obj, is_v, was_v);
|
2016-08-11 07:18:15 -07:00
|
|
|
if (o->pixels->pixel_updates)
|
|
|
|
{
|
|
|
|
Eina_Rectangle *rr;
|
|
|
|
|
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
EINA_LIST_FREE(pixi_write->pixel_updates, rr)
|
|
|
|
{
|
|
|
|
eina_rectangle_free(rr);
|
|
|
|
}
|
|
|
|
}
|
2016-08-11 07:18:15 -07:00
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
|
|
|
}
|
2016-11-16 19:28:52 -08:00
|
|
|
if (changed_prep)
|
|
|
|
{
|
|
|
|
if (o->engine_data_prep)
|
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_free(ENC, o->engine_data_prep);
|
2016-11-16 19:28:52 -08:00
|
|
|
o->engine_data_prep = NULL;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
o->changed = EINA_FALSE;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
2017-02-03 18:31:55 -08:00
|
|
|
evas_object_image_render_post(Evas_Object *eo_obj EINA_UNUSED,
|
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o = type_private_data;
|
2009-06-23 06:57:27 -07:00
|
|
|
Eina_Rectangle *r;
|
2002-11-08 00:02:15 -08:00
|
|
|
|
2019-02-20 22:57:17 -08:00
|
|
|
/* image is not ready yet, skip rendering. Leave it to next frame */
|
|
|
|
if (o->preload & EVAS_IMAGE_PRELOADING) return;
|
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
/* this moves the current data to the previous state parts of the object */
|
|
|
|
/* in whatever way is safest for the object. also if we don't need object */
|
|
|
|
/* data anymore we can free it if the object deems this is a good idea */
|
|
|
|
/* remove those pesky changes */
|
2017-02-03 18:31:55 -08:00
|
|
|
evas_object_clip_changes_clean(obj);
|
2013-01-25 04:15:38 -08:00
|
|
|
|
2013-01-25 14:21:37 -08:00
|
|
|
if (o->pixels->pixel_updates)
|
2013-01-25 04:15:38 -08:00
|
|
|
{
|
2013-01-25 14:21:37 -08:00
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
EINA_LIST_FREE(pixi_write->pixel_updates, r)
|
|
|
|
eina_rectangle_free(r);
|
|
|
|
}
|
2013-01-25 14:21:37 -08:00
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
2013-01-25 04:15:38 -08:00
|
|
|
}
|
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
/* move cur to prev safely for object data */
|
2017-02-03 18:31:55 -08:00
|
|
|
evas_object_cur_prev(obj);
|
2017-08-07 07:34:33 -07:00
|
|
|
eina_cow_memcpy(evas_object_image_state_cow, (const Eina_Cow_Data **)&o->prev, o->cur);
|
2002-11-08 00:02:15 -08:00
|
|
|
/* FIXME: copy strings across */
|
evas image: fix non-rendered preload image.
Summary:
This is one more corner-case issue that I found,
When second image doesn't use preload (but still share the resource)
canvas engine triggers cancellation for first image preload function.
Unluckly, preload thread is cancelled on the intermediate rendering,
First image is not going to rendered, even image turn it changed states.
Because end of that frame, canvas reset/flushed all active objects.
Here changes to retain the changes status to redraw it in the next frame.
Test Plan:
img1 = image_add;
image_file_set(img1, "test.jpg");
image_preload(img1, true);
show(img);
img2 = image_add;
image_file_set(img2, "test.jpg"); //same resource
image_preload(img2, false);
show(img2);
img1 is invisible.
Reviewers: #committers
Subscribers: cedric, #reviewers, #committers
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D7157
2018-10-22 22:49:46 -07:00
|
|
|
|
|
|
|
//Somehow(preloading cancelled) image has been changed, need to redraw.
|
|
|
|
if (o->changed) evas_object_change(eo_obj, obj);
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
2017-08-07 07:34:33 -07:00
|
|
|
static void *
|
|
|
|
evas_object_image_engine_data_get(Evas_Object *eo_obj)
|
2008-08-25 22:45:04 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
2008-08-25 22:45:04 -07:00
|
|
|
if (!o) return NULL;
|
|
|
|
return o->engine_data;
|
|
|
|
}
|
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
static int
|
2013-07-08 17:46:15 -07:00
|
|
|
evas_object_image_is_opaque(Evas_Object *eo_obj EINA_UNUSED,
|
2017-08-07 07:34:33 -07:00
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
|
|
|
/* this returns 1 if the internal object data implies that the object is */
|
2004-02-16 11:22:48 -08:00
|
|
|
/* currently fully opaque over the entire rectangle it occupies */
|
2011-10-21 10:14:03 -07:00
|
|
|
/* disable caching due tyo maps screwing with this
|
2012-10-09 00:49:07 -07:00
|
|
|
o->cur.opaque_valid = 0;*/
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o = type_private_data;
|
2013-03-12 05:58:19 -07:00
|
|
|
|
2018-11-21 03:55:32 -08:00
|
|
|
if (o->preload == EVAS_IMAGE_PRELOADING) return 0;
|
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
if (o->cur->opaque_valid)
|
2010-08-09 19:35:07 -07:00
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
if (!o->cur->opaque) return 0;
|
2010-08-09 19:35:07 -07:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque = 0;
|
|
|
|
state_write->opaque_valid = 1;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2012-10-09 00:49:07 -07:00
|
|
|
|
2013-01-27 16:28:53 -08:00
|
|
|
if ((o->cur->fill.w < 1) || (o->cur->fill.h < 1))
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->cur->opaque;
|
2013-01-27 16:28:53 -08:00
|
|
|
if (((o->cur->border.l != 0) ||
|
|
|
|
(o->cur->border.r != 0) ||
|
|
|
|
(o->cur->border.t != 0) ||
|
|
|
|
(o->cur->border.b != 0)) &&
|
|
|
|
(!o->cur->border.fill))
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->cur->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
if (!o->engine_data)
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->cur->opaque;
|
2016-07-17 21:37:15 -07:00
|
|
|
if (o->has_filter)
|
|
|
|
return o->cur->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
|
|
|
|
// FIXME: use proxy
|
2013-01-27 16:28:53 -08:00
|
|
|
if (o->cur->source)
|
2012-10-09 00:49:07 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *cur_source = efl_data_scope_get(o->cur->source, EFL_CANVAS_OBJECT_CLASS);
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
2019-05-29 12:37:07 -07:00
|
|
|
state_write->opaque = evas_object_is_opaque(cur_source);
|
2017-08-07 07:34:33 -07:00
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
|
|
|
return o->cur->opaque; /* FIXME: Should go poke at the object */
|
2012-10-09 00:49:07 -07:00
|
|
|
}
|
2013-01-27 16:28:53 -08:00
|
|
|
if (o->cur->has_alpha)
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->cur->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque = 1;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
2011-10-21 10:14:03 -07:00
|
|
|
}
|
2012-10-09 00:49:07 -07:00
|
|
|
|
2013-01-21 19:56:00 -08:00
|
|
|
if ((obj->map->cur.map) && (obj->map->cur.usemap))
|
2011-10-21 10:14:03 -07:00
|
|
|
{
|
2013-01-21 19:56:00 -08:00
|
|
|
Evas_Map *m = obj->map->cur.map;
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2011-10-21 10:14:03 -07:00
|
|
|
if ((m->points[0].a == 255) &&
|
|
|
|
(m->points[1].a == 255) &&
|
|
|
|
(m->points[2].a == 255) &&
|
|
|
|
(m->points[3].a == 255))
|
|
|
|
{
|
2017-01-06 09:57:46 -08:00
|
|
|
if (((EINA_DBL_EQ(m->points[0].x, m->points[3].x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[1].x, m->points[2].x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[0].y, m->points[1].y)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[2].y, m->points[3].y))) ||
|
|
|
|
((EINA_DBL_EQ(m->points[0].x, m->points[1].x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[2].x, m->points[3].x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[0].y, m->points[3].y)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[1].y, m->points[2].y))))
|
2011-10-26 06:33:25 -07:00
|
|
|
{
|
2017-01-06 09:57:46 -08:00
|
|
|
if ((EINA_DBL_EQ(m->points[0].x, obj->cur->geometry.x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[0].y, obj->cur->geometry.y)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[2].x,
|
2017-08-07 07:34:33 -07:00
|
|
|
obj->cur->geometry.x + obj->cur->geometry.w)) &&
|
2017-01-06 09:57:46 -08:00
|
|
|
(EINA_DBL_EQ(m->points[2].y,
|
2017-08-07 07:34:33 -07:00
|
|
|
obj->cur->geometry.y + obj->cur->geometry.h)))
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->cur->opaque;
|
2011-10-26 06:33:25 -07:00
|
|
|
}
|
2011-10-21 10:14:03 -07:00
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
|
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque = 0;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
|
|
|
|
|
|
|
return o->cur->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
if (obj->cur->render_op == EVAS_RENDER_COPY)
|
2012-10-09 00:49:07 -07:00
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(o, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque = 1;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(o, state_write);
|
|
|
|
|
|
|
|
return o->cur->opaque;
|
2011-10-21 10:14:03 -07:00
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->cur->opaque;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
|
|
|
|
|
|
|
static int
|
2013-07-08 17:46:15 -07:00
|
|
|
evas_object_image_was_opaque(Evas_Object *eo_obj EINA_UNUSED,
|
2017-08-07 07:34:33 -07:00
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data)
|
2002-11-08 00:02:15 -08:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o = type_private_data;
|
2013-03-12 05:58:19 -07:00
|
|
|
|
2002-11-08 00:02:15 -08:00
|
|
|
/* this returns 1 if the internal object data implies that the object was */
|
2004-02-16 11:22:48 -08:00
|
|
|
/* previously fully opaque over the entire rectangle it occupies */
|
2013-03-12 05:58:19 -07:00
|
|
|
if (o->prev->opaque_valid)
|
2010-08-09 19:35:07 -07:00
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
if (!o->prev->opaque) return 0;
|
2010-08-09 19:35:07 -07:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_BEGIN(evas_object_image_state_cow, o->prev, Evas_Object_Image_State, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque = 0;
|
|
|
|
state_write->opaque_valid = 1;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_END(evas_object_image_state_cow, o->prev, state_write);
|
2012-10-09 00:49:07 -07:00
|
|
|
|
2013-01-27 16:28:53 -08:00
|
|
|
if ((o->prev->fill.w < 1) || (o->prev->fill.h < 1))
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->prev->opaque;
|
2013-01-27 16:28:53 -08:00
|
|
|
if (((o->prev->border.l != 0) ||
|
|
|
|
(o->prev->border.r != 0) ||
|
|
|
|
(o->prev->border.t != 0) ||
|
|
|
|
(o->prev->border.b != 0)) &&
|
|
|
|
(!o->prev->border.fill))
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->prev->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
if (!o->engine_data)
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->prev->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
|
|
|
|
// FIXME: use proxy
|
2013-01-27 16:28:53 -08:00
|
|
|
if (o->prev->source)
|
2017-08-07 07:34:33 -07:00
|
|
|
return o->prev->opaque; /* FIXME: Should go poke at the object */
|
2013-01-27 16:28:53 -08:00
|
|
|
if (o->prev->has_alpha)
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->prev->opaque;
|
2016-07-17 21:53:33 -07:00
|
|
|
if (o->has_filter)
|
|
|
|
return o->cur->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_BEGIN(evas_object_image_state_cow, o->prev, Evas_Object_Image_State, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque = 1;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_END(evas_object_image_state_cow, o->prev, state_write);
|
2012-10-09 00:49:07 -07:00
|
|
|
}
|
2013-01-21 19:56:00 -08:00
|
|
|
if (obj->map->prev.usemap)
|
2012-10-09 00:49:07 -07:00
|
|
|
{
|
2013-01-21 19:56:00 -08:00
|
|
|
Evas_Map *m = obj->map->prev.map;
|
2012-10-09 00:49:07 -07:00
|
|
|
|
|
|
|
if ((m->points[0].a == 255) &&
|
|
|
|
(m->points[1].a == 255) &&
|
|
|
|
(m->points[2].a == 255) &&
|
|
|
|
(m->points[3].a == 255))
|
|
|
|
{
|
2017-01-06 09:57:46 -08:00
|
|
|
if (((EINA_DBL_EQ(m->points[0].x, m->points[3].x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[1].x, m->points[2].x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[0].y, m->points[1].y)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[2].y, m->points[3].y))) ||
|
|
|
|
((EINA_DBL_EQ(m->points[0].x, m->points[1].x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[2].x, m->points[3].x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[0].y, m->points[3].y)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[1].y, m->points[2].y))))
|
2012-10-09 00:49:07 -07:00
|
|
|
{
|
2017-01-06 09:57:46 -08:00
|
|
|
if ((EINA_DBL_EQ(m->points[0].x, obj->prev->geometry.x)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[0].y, obj->prev->geometry.y)) &&
|
|
|
|
(EINA_DBL_EQ(m->points[2].x,
|
2017-08-07 07:34:33 -07:00
|
|
|
obj->prev->geometry.x + obj->prev->geometry.w)) &&
|
2017-01-06 09:57:46 -08:00
|
|
|
(EINA_DBL_EQ(m->points[2].y,
|
2017-08-07 07:34:33 -07:00
|
|
|
obj->prev->geometry.y + obj->prev->geometry.h)))
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->prev->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_BEGIN(evas_object_image_state_cow, o->prev, Evas_Object_Image_State, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque = 0;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_END(evas_object_image_state_cow, o->prev, state_write);
|
|
|
|
|
|
|
|
return o->prev->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
if (obj->prev->render_op == EVAS_RENDER_COPY)
|
2012-10-09 00:49:07 -07:00
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_BEGIN(evas_object_image_state_cow, o->prev, Evas_Object_Image_State, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque = 1;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_END(evas_object_image_state_cow, o->prev, state_write);
|
|
|
|
|
|
|
|
return o->prev->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
if (obj->prev->render_op != EVAS_RENDER_BLEND)
|
2012-10-09 00:49:07 -07:00
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_BEGIN(evas_object_image_state_cow, o->prev, Evas_Object_Image_State, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
state_write->opaque = 0;
|
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
EINA_COW_WRITE_END(evas_object_image_state_cow, o->prev, state_write);
|
|
|
|
|
|
|
|
return o->prev->opaque;
|
2012-10-09 00:49:07 -07:00
|
|
|
}
|
2013-03-12 05:58:19 -07:00
|
|
|
return o->prev->opaque;
|
2002-11-08 00:02:15 -08:00
|
|
|
}
|
2007-07-23 07:22:57 -07:00
|
|
|
|
|
|
|
static int
|
2013-07-08 17:46:15 -07:00
|
|
|
evas_object_image_is_inside(Evas_Object *eo_obj,
|
2017-08-07 07:34:33 -07:00
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data,
|
|
|
|
Evas_Coord px, Evas_Coord py)
|
2007-07-23 07:22:57 -07:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o = type_private_data;
|
2017-03-27 22:40:29 -07:00
|
|
|
int imagew, imageh, uvw, uvh, ix, iy, iw, ih, idw, idh, idx, idy;
|
2012-12-19 14:41:12 -08:00
|
|
|
int is_inside = 0;
|
2017-03-27 22:40:29 -07:00
|
|
|
void *pixels;
|
2017-08-25 10:51:40 -07:00
|
|
|
void *output;
|
2017-03-27 22:40:29 -07:00
|
|
|
|
|
|
|
// FIXME: The below loop is incredibly dubious and probably should be simplified.
|
|
|
|
// We're looking for one single pixel, not a random series of positions.
|
|
|
|
// Original comment:
|
2012-12-19 14:41:12 -08:00
|
|
|
/* the following code is similar to evas_object_image_render(), but doesn't
|
|
|
|
* draw, just get the pixels so we can check the transparency.
|
|
|
|
*/
|
2017-08-25 10:51:40 -07:00
|
|
|
output = _evas_object_image_output_find(obj);
|
|
|
|
pixels = _evas_image_pixels_get(eo_obj, obj, ENC, output, NULL, NULL, 0, 0,
|
2017-03-28 00:09:34 -07:00
|
|
|
&imagew, &imageh, &uvw, &uvh, EINA_TRUE, EINA_FALSE);
|
2017-03-27 22:40:29 -07:00
|
|
|
if (!pixels) return is_inside;
|
|
|
|
|
|
|
|
if (o->dirty_pixels)
|
2012-12-19 14:41:12 -08:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
if (o->pixels->func.get_pixels)
|
|
|
|
{
|
2018-04-04 22:38:24 -07:00
|
|
|
if (ENFN->gl_get_pixels_pre)
|
|
|
|
ENFN->gl_get_pixels_pre(ENC, output);
|
|
|
|
o->pixels->func.get_pixels(o->pixels->func.get_pixels_data, eo_obj);
|
|
|
|
if (ENFN->gl_get_pixels_post)
|
|
|
|
ENFN->gl_get_pixels_post(ENC, output);
|
2017-03-27 22:40:29 -07:00
|
|
|
}
|
2009-06-03 07:16:55 -07:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
|
|
|
|
/* TODO: not handling map, need to apply map to point */
|
|
|
|
if ((obj->map->cur.map) && (obj->map->cur.map->count > 3) && (obj->map->cur.usemap))
|
2009-06-03 07:16:55 -07:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
evas_object_map_update(eo_obj, 0, 0, imagew, imageh, uvw, uvh);
|
|
|
|
|
|
|
|
ERR("map not supported");
|
|
|
|
return is_inside;
|
2012-12-19 14:41:12 -08:00
|
|
|
}
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
idx = evas_object_image_figure_x_fill(eo_obj, obj, o->cur->fill.x, o->cur->fill.w, &idw);
|
|
|
|
idy = evas_object_image_figure_y_fill(eo_obj, obj, o->cur->fill.y, o->cur->fill.h, &idh);
|
|
|
|
if (idw < 1) idw = 1;
|
|
|
|
if (idh < 1) idh = 1;
|
|
|
|
if (idx > 0) idx -= idw;
|
|
|
|
if (idy > 0) idy -= idh;
|
|
|
|
|
|
|
|
while (idx < obj->cur->geometry.w)
|
2012-12-19 14:41:12 -08:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
int ydy, dobreak_w = 0;
|
2012-12-19 14:41:12 -08:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
ydy = idy;
|
|
|
|
ix = idx;
|
|
|
|
if ((o->cur->fill.w == obj->cur->geometry.w) &&
|
|
|
|
(o->cur->fill.x == 0))
|
2010-02-20 22:21:15 -08:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
dobreak_w = 1;
|
|
|
|
iw = obj->cur->geometry.w;
|
2010-02-20 22:21:15 -08:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
else
|
|
|
|
iw = idx + idw - ix;
|
2012-12-19 14:41:12 -08:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
while (idy < obj->cur->geometry.h)
|
2010-02-20 22:21:15 -08:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
int dobreak_h = 0;
|
|
|
|
DATA8 alpha = 0;
|
2012-12-19 14:41:12 -08:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
iy = idy;
|
|
|
|
if ((o->cur->fill.h == obj->cur->geometry.h) &&
|
|
|
|
(o->cur->fill.y == 0))
|
|
|
|
{
|
|
|
|
ih = obj->cur->geometry.h;
|
|
|
|
dobreak_h = 1;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
ih = idy + idh - iy;
|
|
|
|
|
|
|
|
if ((o->cur->border.l == 0) && (o->cur->border.r == 0) &&
|
|
|
|
(o->cur->border.t == 0) && (o->cur->border.b == 0) &&
|
|
|
|
(o->cur->border.fill != 0))
|
2012-12-19 14:41:12 -08:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
0, 0, imagew, imageh,
|
|
|
|
obj->cur->geometry.x + ix,
|
|
|
|
obj->cur->geometry.y + iy,
|
|
|
|
iw, ih))
|
2012-12-19 14:41:12 -08:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
is_inside = alpha > 0;
|
|
|
|
dobreak_h = 1;
|
2012-12-19 14:41:12 -08:00
|
|
|
dobreak_w = 1;
|
2017-03-27 22:40:29 -07:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
int inx, iny, inw, inh, outx, outy, outw, outh;
|
|
|
|
int bl, br, bt, bb, bsl, bsr, bst, bsb;
|
|
|
|
int imw, imh, ox, oy;
|
|
|
|
|
|
|
|
ox = obj->cur->geometry.x + ix;
|
|
|
|
oy = obj->cur->geometry.y + iy;
|
|
|
|
imw = imagew;
|
|
|
|
imh = imageh;
|
|
|
|
bl = o->cur->border.l;
|
|
|
|
br = o->cur->border.r;
|
|
|
|
bt = o->cur->border.t;
|
|
|
|
bb = o->cur->border.b;
|
|
|
|
if ((bl + br) > iw)
|
|
|
|
{
|
|
|
|
bl = iw / 2;
|
|
|
|
br = iw - bl;
|
|
|
|
}
|
|
|
|
if ((bl + br) > imw)
|
|
|
|
{
|
|
|
|
bl = imw / 2;
|
|
|
|
br = imw - bl;
|
|
|
|
}
|
|
|
|
if ((bt + bb) > ih)
|
|
|
|
{
|
|
|
|
bt = ih / 2;
|
|
|
|
bb = ih - bt;
|
|
|
|
}
|
|
|
|
if ((bt + bb) > imh)
|
|
|
|
{
|
|
|
|
bt = imh / 2;
|
|
|
|
bb = imh - bt;
|
|
|
|
}
|
|
|
|
if (!EINA_DBL_EQ(o->cur->border.scale, 1.0))
|
|
|
|
{
|
|
|
|
bsl = ((double)bl * o->cur->border.scale);
|
|
|
|
bsr = ((double)br * o->cur->border.scale);
|
|
|
|
bst = ((double)bt * o->cur->border.scale);
|
|
|
|
bsb = ((double)bb * o->cur->border.scale);
|
2012-12-19 14:41:12 -08:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
bsl = bl; bsr = br; bst = bt; bsb = bb;
|
|
|
|
}
|
|
|
|
// #--
|
|
|
|
// |
|
|
|
|
inx = 0; iny = 0;
|
|
|
|
inw = bl; inh = bt;
|
|
|
|
outx = ox; outy = oy;
|
|
|
|
outw = bsl; outh = bst;
|
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
inx, iny, inw, inh,
|
|
|
|
outx, outy, outw, outh))
|
|
|
|
{
|
|
|
|
is_inside = alpha > 0;
|
|
|
|
dobreak_h = 1;
|
|
|
|
dobreak_w = 1;
|
|
|
|
break;
|
|
|
|
}
|
2012-09-04 01:42:38 -07:00
|
|
|
|
2017-03-27 22:40:29 -07:00
|
|
|
// .##
|
|
|
|
// |
|
|
|
|
inx = bl; iny = 0;
|
|
|
|
inw = imw - bl - br; inh = bt;
|
|
|
|
outx = ox + bsl; outy = oy;
|
|
|
|
outw = iw - bsl - bsr; outh = bst;
|
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
inx, iny, inw, inh,
|
|
|
|
outx, outy, outw, outh))
|
|
|
|
{
|
|
|
|
is_inside = alpha > 0;
|
|
|
|
dobreak_h = 1;
|
|
|
|
dobreak_w = 1;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
// --#
|
|
|
|
// |
|
|
|
|
inx = imw - br; iny = 0;
|
|
|
|
inw = br; inh = bt;
|
|
|
|
outx = ox + iw - bsr; outy = oy;
|
|
|
|
outw = bsr; outh = bst;
|
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
inx, iny, inw, inh,
|
|
|
|
outx, outy, outw, outh))
|
|
|
|
{
|
|
|
|
is_inside = alpha > 0;
|
|
|
|
dobreak_h = 1;
|
|
|
|
dobreak_w = 1;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
// .--
|
|
|
|
// #
|
|
|
|
inx = 0; iny = bt;
|
|
|
|
inw = bl; inh = imh - bt - bb;
|
|
|
|
outx = ox; outy = oy + bst;
|
|
|
|
outw = bsl; outh = ih - bst - bsb;
|
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
inx, iny, inw, inh,
|
|
|
|
outx, outy, outw, outh))
|
|
|
|
{
|
|
|
|
is_inside = alpha > 0;
|
|
|
|
dobreak_h = 1;
|
|
|
|
dobreak_w = 1;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
// .--.
|
|
|
|
// |##|
|
|
|
|
if (o->cur->border.fill > EVAS_BORDER_FILL_NONE)
|
|
|
|
{
|
|
|
|
inx = bl; iny = bt;
|
|
|
|
inw = imw - bl - br; inh = imh - bt - bb;
|
|
|
|
outx = ox + bsl; outy = oy + bst;
|
|
|
|
outw = iw - bsl - bsr; outh = ih - bst - bsb;
|
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
inx, iny, inw, inh,
|
|
|
|
outx, outy, outw, outh))
|
2012-12-19 14:41:12 -08:00
|
|
|
{
|
2017-03-27 22:40:29 -07:00
|
|
|
is_inside = alpha > 0;
|
2012-12-19 14:41:12 -08:00
|
|
|
dobreak_h = 1;
|
2017-03-27 22:40:29 -07:00
|
|
|
dobreak_w = 1;
|
|
|
|
break;
|
2012-12-19 14:41:12 -08:00
|
|
|
}
|
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
// --.
|
|
|
|
// #
|
|
|
|
inx = imw - br; iny = bt;
|
|
|
|
inw = br; inh = imh - bt - bb;
|
|
|
|
outx = ox + iw - bsr; outy = oy + bst;
|
|
|
|
outw = bsr; outh = ih - bst - bsb;
|
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
inx, iny, inw, inh,
|
|
|
|
outx, outy, outw, outh))
|
|
|
|
{
|
|
|
|
is_inside = alpha > 0;
|
|
|
|
dobreak_h = 1;
|
|
|
|
dobreak_w = 1;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
// |
|
|
|
|
// #--
|
|
|
|
inx = 0; iny = imh - bb;
|
|
|
|
inw = bl; inh = bb;
|
|
|
|
outx = ox; outy = oy + ih - bsb;
|
|
|
|
outw = bsl; outh = bsb;
|
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
inx, iny, inw, inh,
|
|
|
|
outx, outy, outw, outh))
|
|
|
|
{
|
|
|
|
is_inside = alpha > 0;
|
|
|
|
dobreak_h = 1;
|
|
|
|
dobreak_w = 1;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
// |
|
|
|
|
// .##
|
|
|
|
inx = bl; iny = imh - bb;
|
|
|
|
inw = imw - bl - br; inh = bb;
|
|
|
|
outx = ox + bsl; outy = oy + ih - bsb;
|
|
|
|
outw = iw - bsl - bsr; outh = bsb;
|
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
inx, iny, inw, inh,
|
|
|
|
outx, outy, outw, outh))
|
|
|
|
{
|
|
|
|
is_inside = alpha > 0;
|
|
|
|
dobreak_h = 1;
|
|
|
|
dobreak_w = 1;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
// |
|
|
|
|
// --#
|
|
|
|
inx = imw - br; iny = imh - bb;
|
|
|
|
inw = br; inh = bb;
|
|
|
|
outx = ox + iw - bsr; outy = oy + ih - bsb;
|
|
|
|
outw = bsr; outh = bsb;
|
|
|
|
if (ENFN->pixel_alpha_get(pixels, px, py, &alpha,
|
|
|
|
inx, iny, inw, inh,
|
|
|
|
outx, outy, outw, outh))
|
|
|
|
{
|
|
|
|
is_inside = alpha > 0;
|
|
|
|
dobreak_h = 1;
|
|
|
|
dobreak_w = 1;
|
|
|
|
break;
|
|
|
|
}
|
2012-12-19 14:41:12 -08:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
idy += idh;
|
|
|
|
if (dobreak_h) break;
|
2012-12-19 14:41:12 -08:00
|
|
|
}
|
2017-03-27 22:40:29 -07:00
|
|
|
idx += idw;
|
|
|
|
idy = ydy;
|
|
|
|
if (dobreak_w) break;
|
2007-07-23 07:22:57 -07:00
|
|
|
}
|
|
|
|
|
2012-12-19 14:41:12 -08:00
|
|
|
return is_inside;
|
2007-07-23 07:22:57 -07:00
|
|
|
}
|
2008-05-18 20:13:16 -07:00
|
|
|
|
2009-02-16 20:53:03 -08:00
|
|
|
static int
|
2013-07-08 17:46:15 -07:00
|
|
|
evas_object_image_has_opaque_rect(Evas_Object *eo_obj EINA_UNUSED,
|
2017-08-07 07:34:33 -07:00
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data)
|
2009-02-16 20:53:03 -08:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o = type_private_data;
|
2009-09-03 22:13:19 -07:00
|
|
|
|
2013-01-21 19:56:00 -08:00
|
|
|
if ((obj->map->cur.map) && (obj->map->cur.usemap)) return 0;
|
2013-01-27 16:28:53 -08:00
|
|
|
if (((o->cur->border.l | o->cur->border.r | o->cur->border.t | o->cur->border.b) != 0) &&
|
|
|
|
(o->cur->border.fill == EVAS_BORDER_FILL_SOLID) &&
|
2013-03-12 05:58:19 -07:00
|
|
|
(obj->cur->render_op == EVAS_RENDER_BLEND) &&
|
|
|
|
(obj->cur->cache.clip.a == 255) &&
|
2013-01-27 16:28:53 -08:00
|
|
|
(o->cur->fill.x == 0) &&
|
|
|
|
(o->cur->fill.y == 0) &&
|
2013-03-12 05:58:19 -07:00
|
|
|
(o->cur->fill.w == obj->cur->geometry.w) &&
|
|
|
|
(o->cur->fill.h == obj->cur->geometry.h)
|
2009-02-16 20:53:03 -08:00
|
|
|
) return 1;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
static int
|
2013-07-08 17:46:15 -07:00
|
|
|
evas_object_image_get_opaque_rect(Evas_Object *eo_obj EINA_UNUSED,
|
2017-08-07 07:34:33 -07:00
|
|
|
Evas_Object_Protected_Data *obj,
|
|
|
|
void *type_private_data,
|
|
|
|
Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h)
|
2009-02-16 20:53:03 -08:00
|
|
|
{
|
2014-03-12 07:28:40 -07:00
|
|
|
Evas_Image_Data *o = type_private_data;
|
2009-09-03 22:13:19 -07:00
|
|
|
|
2016-07-15 02:41:12 -07:00
|
|
|
if (!o->cur->has_alpha)
|
2010-02-20 22:21:15 -08:00
|
|
|
{
|
2016-07-15 02:41:12 -07:00
|
|
|
*x = obj->cur->geometry.x;
|
|
|
|
*y = obj->cur->geometry.y;
|
|
|
|
*w = obj->cur->geometry.w;
|
|
|
|
*h = obj->cur->geometry.h;
|
|
|
|
}
|
2016-07-19 19:34:01 -07:00
|
|
|
else if (o->cur->border.fill == EVAS_BORDER_FILL_SOLID)
|
2010-02-20 22:21:15 -08:00
|
|
|
{
|
2013-03-12 05:58:19 -07:00
|
|
|
*x = obj->cur->geometry.x + (o->cur->border.l * o->cur->border.scale);
|
|
|
|
*y = obj->cur->geometry.y + (o->cur->border.t * o->cur->border.scale);
|
2016-07-15 02:41:12 -07:00
|
|
|
*w = obj->cur->geometry.w - ((o->cur->border.l * o->cur->border.scale)
|
|
|
|
+ (o->cur->border.r * o->cur->border.scale));
|
2010-02-20 22:21:15 -08:00
|
|
|
if (*w < 0) *w = 0;
|
2016-07-15 02:41:12 -07:00
|
|
|
*h = obj->cur->geometry.h - ((o->cur->border.t * o->cur->border.scale)
|
|
|
|
+ (o->cur->border.b * o->cur->border.scale));
|
2010-02-20 22:21:15 -08:00
|
|
|
if (*h < 0) *h = 0;
|
|
|
|
}
|
2016-07-19 19:34:01 -07:00
|
|
|
else
|
|
|
|
{
|
|
|
|
*w = 0;
|
|
|
|
*h = 0;
|
|
|
|
}
|
2009-02-17 09:36:29 -08:00
|
|
|
return 1;
|
2009-02-16 20:53:03 -08:00
|
|
|
}
|
|
|
|
|
2009-10-28 01:59:01 -07:00
|
|
|
static int
|
2012-11-04 03:51:42 -08:00
|
|
|
evas_object_image_can_map(Evas_Object *obj EINA_UNUSED)
|
2009-10-28 01:59:01 -07:00
|
|
|
{
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
2016-03-15 00:19:12 -07:00
|
|
|
void *
|
|
|
|
_evas_image_data_convert_internal(Evas_Image_Data *o, void *data, Evas_Colorspace to_cspace)
|
2008-05-18 20:13:16 -07:00
|
|
|
{
|
|
|
|
void *out = NULL;
|
|
|
|
|
|
|
|
if (!data)
|
|
|
|
return NULL;
|
|
|
|
|
2013-01-27 16:28:53 -08:00
|
|
|
switch (o->cur->cspace)
|
2008-05-18 20:13:16 -07:00
|
|
|
{
|
2012-09-04 01:42:38 -07:00
|
|
|
case EVAS_COLORSPACE_ARGB8888:
|
2017-08-07 07:34:33 -07:00
|
|
|
out = evas_common_convert_argb8888_to(data,
|
|
|
|
o->cur->image.w,
|
|
|
|
o->cur->image.h,
|
|
|
|
o->cur->image.stride >> 2,
|
|
|
|
o->cur->has_alpha,
|
|
|
|
to_cspace);
|
|
|
|
break;
|
|
|
|
|
2012-09-04 01:42:38 -07:00
|
|
|
case EVAS_COLORSPACE_RGB565_A5P:
|
2017-08-07 07:34:33 -07:00
|
|
|
out = evas_common_convert_rgb565_a5p_to(data,
|
|
|
|
o->cur->image.w,
|
|
|
|
o->cur->image.h,
|
|
|
|
o->cur->image.stride >> 1,
|
|
|
|
o->cur->has_alpha,
|
|
|
|
to_cspace);
|
|
|
|
break;
|
|
|
|
|
|
|
|
case EVAS_COLORSPACE_YCBCR422601_PL:
|
|
|
|
out = evas_common_convert_yuv_422_601_to(data,
|
2013-01-27 16:28:53 -08:00
|
|
|
o->cur->image.w,
|
|
|
|
o->cur->image.h,
|
2012-09-04 01:42:38 -07:00
|
|
|
to_cspace);
|
2017-08-07 07:34:33 -07:00
|
|
|
break;
|
|
|
|
|
|
|
|
case EVAS_COLORSPACE_YCBCR422P601_PL:
|
|
|
|
out = evas_common_convert_yuv_422P_601_to(data,
|
|
|
|
o->cur->image.w,
|
|
|
|
o->cur->image.h,
|
|
|
|
to_cspace);
|
|
|
|
break;
|
|
|
|
|
|
|
|
case EVAS_COLORSPACE_YCBCR420NV12601_PL:
|
|
|
|
out = evas_common_convert_yuv_420_601_to(data,
|
|
|
|
o->cur->image.w,
|
|
|
|
o->cur->image.h,
|
|
|
|
to_cspace);
|
|
|
|
break;
|
|
|
|
|
|
|
|
case EVAS_COLORSPACE_YCBCR420TM12601_PL:
|
|
|
|
out = evas_common_convert_yuv_420T_601_to(data,
|
2013-01-27 16:28:53 -08:00
|
|
|
o->cur->image.w,
|
2017-08-07 07:34:33 -07:00
|
|
|
o->cur->image.h,
|
|
|
|
to_cspace);
|
|
|
|
break;
|
|
|
|
|
2015-12-29 05:01:16 -08:00
|
|
|
case EVAS_COLORSPACE_AGRY88:
|
2017-08-07 07:34:33 -07:00
|
|
|
out = evas_common_convert_agry88_to(data,
|
2015-12-29 05:01:16 -08:00
|
|
|
o->cur->image.w,
|
|
|
|
o->cur->image.h,
|
|
|
|
o->cur->image.stride,
|
|
|
|
o->cur->has_alpha,
|
|
|
|
to_cspace);
|
2017-08-07 07:34:33 -07:00
|
|
|
break;
|
|
|
|
|
|
|
|
case EVAS_COLORSPACE_GRY8:
|
|
|
|
out = evas_common_convert_gry8_to(data,
|
|
|
|
o->cur->image.w,
|
|
|
|
o->cur->image.h,
|
|
|
|
o->cur->image.stride,
|
|
|
|
o->cur->has_alpha,
|
|
|
|
to_cspace);
|
|
|
|
break;
|
|
|
|
|
|
|
|
default:
|
2017-12-13 09:53:33 -08:00
|
|
|
WRN("unknown colorspace: %i\n", o->cur->cspace);
|
2017-08-07 07:34:33 -07:00
|
|
|
break;
|
2008-05-18 20:13:16 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
return out;
|
|
|
|
}
|
2008-12-12 14:36:47 -08:00
|
|
|
|
|
|
|
static void
|
2012-11-04 03:51:42 -08:00
|
|
|
evas_object_image_filled_resize_listener(void *data EINA_UNUSED, Evas *e EINA_UNUSED, Evas_Object *obj, void *einfo EINA_UNUSED)
|
2008-12-12 14:36:47 -08:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Image_Data *o = efl_data_scope_get(obj, EFL_CANVAS_IMAGE_INTERNAL_CLASS);
|
2017-09-15 02:37:25 -07:00
|
|
|
Eina_Size2D sz;
|
2009-02-24 00:31:31 -08:00
|
|
|
|
2018-04-05 01:47:26 -07:00
|
|
|
sz = efl_gfx_entity_size_get(obj);
|
2017-09-15 02:37:25 -07:00
|
|
|
if (sz.w < 1) sz.w = 1;
|
|
|
|
if (sz.h < 1) sz.h = 1;
|
|
|
|
_evas_image_fill_set(obj, o, 0, 0, sz.w, sz.h);
|
2008-12-12 14:36:47 -08:00
|
|
|
}
|
2011-02-06 15:52:17 -08:00
|
|
|
|
2011-05-02 20:20:02 -07:00
|
|
|
Eina_Bool
|
2012-10-08 18:58:41 -07:00
|
|
|
_evas_object_image_preloading_get(const Evas_Object *eo_obj)
|
2011-05-02 20:20:02 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
evas image: fix a bug in image preloading.
Summary:
Current preloading is too buggy since it's on thread-based.
This is a fundamental improvement to fix a bug.
The critical issue here is,
When preloading img object suddenly cancel its preloading,
the object possibly cannot render image next then because
renderer doesn't have any idea when async cancelling is
finished. Renderer just tries to render regardless of
image loading status, and this could occur no-texture(in gl case)
image object.
So, here improvement is, adding a notification for async cancelled
so that putting img objects to redraw images properly after their preloading is
cancelled.
The best scenario to reproduce this bug is this one.
Evas_Object *img2 = evas_object_image_filled_add(evas);
evas_object_image_file_set(img2, "test.jpg", NULL);
evas_object_image_preload(img2, EINA_FALSE);
evas_object_resize(img2, 200, 200);
evas_object_show(img2);
Evas_Object *img = evas_object_image_filled_add(evas);
evas_object_image_file_set(img, "test.jpg", NULL);
evas_object_image_preload(img, EINA_FALSE);
evas_object_move(img, 200, 200);
evas_object_resize(img, 200, 200);
evas_object_show(img);
evas_object_image_preload(img2, EINA_TRUE);
If you run this on gl backend, occasionally happens rendering fail.
Yet there other bugs on preloading feature....
@fix
Reviewers: #committers, raster
Subscribers: cedric, #reviewers, #committers, zmike
Tags: #efl
Differential Revision: https://phab.enlightenment.org/D6919
2018-09-02 23:19:02 -07:00
|
|
|
return o->preload;
|
2011-05-19 04:19:22 -07:00
|
|
|
}
|
|
|
|
|
2011-10-02 20:28:52 -07:00
|
|
|
Evas_Object *
|
2017-04-17 15:06:28 -07:00
|
|
|
_evas_object_image_video_parent_get(Evas_Object *eo_obj)
|
2011-10-02 20:28:52 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
2013-01-25 04:15:38 -08:00
|
|
|
return o->video_surface ? o->pixels->video.parent : NULL;
|
2011-10-02 20:28:52 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2012-10-08 18:58:41 -07:00
|
|
|
_evas_object_image_video_overlay_show(Evas_Object *eo_obj)
|
2011-10-02 20:28:52 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
2011-10-02 20:28:52 -07:00
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
if (obj->cur->cache.clip.x != obj->prev->cache.clip.x ||
|
|
|
|
obj->cur->cache.clip.y != obj->prev->cache.clip.y ||
|
2011-10-04 02:34:01 -07:00
|
|
|
o->created || !o->video_visible)
|
2013-10-01 11:35:09 -07:00
|
|
|
o->delayed.video_move = EINA_TRUE;
|
|
|
|
|
2013-03-12 05:58:19 -07:00
|
|
|
if (obj->cur->cache.clip.w != obj->prev->cache.clip.w ||
|
|
|
|
obj->cur->cache.clip.h != obj->prev->cache.clip.h ||
|
2011-10-04 02:34:01 -07:00
|
|
|
o->created || !o->video_visible)
|
2013-10-01 11:35:09 -07:00
|
|
|
o->delayed.video_resize = EINA_TRUE;
|
|
|
|
|
2011-10-04 02:34:01 -07:00
|
|
|
if (!o->video_visible || o->created)
|
2011-10-13 02:23:42 -07:00
|
|
|
{
|
2013-10-01 11:35:09 -07:00
|
|
|
o->delayed.video_show = EINA_TRUE;
|
|
|
|
o->delayed.video_hide = EINA_FALSE;
|
2011-10-13 02:23:42 -07:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
/* Cancel dirty on the image */
|
|
|
|
Eina_Rectangle *r;
|
|
|
|
|
2012-09-04 01:56:46 -07:00
|
|
|
o->dirty_pixels = EINA_FALSE;
|
2013-01-25 04:15:38 -08:00
|
|
|
|
|
|
|
EINA_COW_PIXEL_WRITE_BEGIN(o, pixi_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
|
|
|
EINA_LIST_FREE(pixi_write->pixel_updates, r)
|
|
|
|
eina_rectangle_free(r);
|
|
|
|
}
|
2013-01-25 04:15:38 -08:00
|
|
|
EINA_COW_PIXEL_WRITE_END(o, pixi_write);
|
2011-10-13 02:23:42 -07:00
|
|
|
}
|
2011-10-02 20:28:52 -07:00
|
|
|
o->video_visible = EINA_TRUE;
|
|
|
|
o->created = EINA_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2012-10-08 18:58:41 -07:00
|
|
|
_evas_object_image_video_overlay_hide(Evas_Object *eo_obj)
|
2011-10-02 20:28:52 -07:00
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
2011-10-02 20:28:52 -07:00
|
|
|
|
|
|
|
if (o->video_visible || o->created)
|
2013-10-01 11:35:09 -07:00
|
|
|
{
|
|
|
|
o->delayed.video_hide = EINA_TRUE;
|
|
|
|
o->delayed.video_show = EINA_FALSE;
|
|
|
|
}
|
2019-05-29 12:36:53 -07:00
|
|
|
if (evas_object_is_visible(obj))
|
2013-01-25 04:15:38 -08:00
|
|
|
o->pixels->video.update_pixels(o->pixels->video.data, eo_obj, &o->pixels->video);
|
2011-10-02 20:28:52 -07:00
|
|
|
o->video_visible = EINA_FALSE;
|
|
|
|
o->created = EINA_FALSE;
|
|
|
|
}
|
|
|
|
|
2013-10-01 11:35:09 -07:00
|
|
|
void
|
|
|
|
_evas_object_image_video_overlay_do(Evas_Object *eo_obj)
|
|
|
|
{
|
2016-08-15 06:44:41 -07:00
|
|
|
Evas_Object_Protected_Data *obj = efl_data_scope_get(eo_obj, EFL_CANVAS_OBJECT_CLASS);
|
|
|
|
Evas_Image_Data *o = efl_data_scope_get(eo_obj, MY_CLASS);
|
2013-10-01 11:35:09 -07:00
|
|
|
Evas_Public_Data *e = obj->layer->evas;
|
|
|
|
|
|
|
|
if (o->delayed.video_move)
|
|
|
|
o->pixels->video.move(o->pixels->video.data, eo_obj, &o->pixels->video,
|
|
|
|
obj->cur->cache.clip.x + e->framespace.x,
|
|
|
|
obj->cur->cache.clip.y + e->framespace.y);
|
|
|
|
|
|
|
|
if (o->delayed.video_resize)
|
|
|
|
o->pixels->video.resize(o->pixels->video.data, eo_obj,
|
|
|
|
&o->pixels->video,
|
|
|
|
obj->cur->cache.clip.w,
|
|
|
|
obj->cur->cache.clip.h);
|
|
|
|
|
|
|
|
if (o->delayed.video_show)
|
|
|
|
o->pixels->video.show(o->pixels->video.data, eo_obj, &o->pixels->video);
|
|
|
|
else if (o->delayed.video_hide)
|
|
|
|
o->pixels->video.hide(o->pixels->video.data, eo_obj, &o->pixels->video);
|
|
|
|
|
|
|
|
o->delayed.video_move = EINA_FALSE;
|
|
|
|
o->delayed.video_resize = EINA_FALSE;
|
|
|
|
o->delayed.video_show = EINA_FALSE;
|
|
|
|
o->delayed.video_hide = EINA_FALSE;
|
|
|
|
}
|
|
|
|
|
2015-05-09 11:02:13 -07:00
|
|
|
void *
|
2017-02-09 23:08:58 -08:00
|
|
|
_evas_object_image_surface_get(Evas_Object_Protected_Data *obj, Eina_Bool create)
|
2015-05-09 11:02:13 -07:00
|
|
|
{
|
2017-02-09 23:08:58 -08:00
|
|
|
Evas_Image_Data *pd = obj->private_data;
|
2015-05-09 11:02:13 -07:00
|
|
|
|
|
|
|
if (pd->engine_data &&
|
2015-10-07 04:03:37 -07:00
|
|
|
(pd->cur->image.w == obj->cur->geometry.w) &&
|
|
|
|
(pd->cur->image.h == obj->cur->geometry.h))
|
2015-05-09 11:02:13 -07:00
|
|
|
return pd->engine_data;
|
|
|
|
|
|
|
|
if (pd->engine_data)
|
2017-02-09 23:08:58 -08:00
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
ENFN->image_free(ENC, pd->engine_data);
|
2017-02-09 23:08:58 -08:00
|
|
|
pd->engine_data = NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (!create) return pd->engine_data;
|
2015-05-09 11:02:13 -07:00
|
|
|
|
|
|
|
// FIXME: alpha forced to 1 for now, need to figure out Evas alpha here
|
2015-10-07 04:03:37 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_BEGIN(pd, state_write)
|
2017-08-07 07:34:33 -07:00
|
|
|
{
|
2017-08-25 10:51:10 -07:00
|
|
|
pd->engine_data = ENFN->image_map_surface_new(ENC,
|
2017-08-07 07:34:33 -07:00
|
|
|
obj->cur->geometry.w,
|
|
|
|
obj->cur->geometry.h,
|
|
|
|
1);
|
|
|
|
state_write->image.w = obj->cur->geometry.w;
|
|
|
|
state_write->image.h = obj->cur->geometry.h;
|
|
|
|
}
|
2015-10-07 04:03:37 -07:00
|
|
|
EINA_COW_IMAGE_STATE_WRITE_END(pd, state_write);
|
2015-05-09 11:02:13 -07:00
|
|
|
|
|
|
|
return pd->engine_data;
|
|
|
|
}
|
|
|
|
|
2017-10-12 18:54:54 -07:00
|
|
|
EOLIAN static void
|
2017-07-24 22:42:54 -07:00
|
|
|
_efl_canvas_image_internal_efl_object_debug_name_override(Eo *eo_obj, Evas_Image_Data *o, Eina_Strbuf *sb)
|
|
|
|
{
|
2017-10-12 18:54:54 -07:00
|
|
|
efl_debug_name_override(efl_super(eo_obj, MY_CLASS), sb);
|
2017-10-04 21:01:35 -07:00
|
|
|
if (o->cur->f)
|
2017-07-24 22:42:54 -07:00
|
|
|
{
|
2017-10-04 21:01:35 -07:00
|
|
|
const char *fname = eina_file_filename_get(o->cur->f);
|
2017-07-24 22:42:54 -07:00
|
|
|
eina_strbuf_append_printf(sb, ":file='%s',key='%s'", fname, o->cur->key);
|
|
|
|
}
|
|
|
|
else if (o->pixels && o->pixels->func.get_pixels)
|
|
|
|
{
|
|
|
|
eina_strbuf_append_printf(sb, ":get_pixels=%p:dirty=%d",
|
|
|
|
o->pixels->func.get_pixels, o->dirty_pixels);
|
|
|
|
}
|
|
|
|
else if (o->cur->source)
|
|
|
|
{
|
|
|
|
eina_strbuf_append_printf(sb, ":proxy_source=%p", o->cur->source);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
eina_strbuf_append_printf(sb, ":unknown_image");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-04-21 08:58:38 -07:00
|
|
|
#define EFL_CANVAS_IMAGE_INTERNAL_EXTRA_OPS \
|
2017-08-07 07:34:33 -07:00
|
|
|
EFL_OBJECT_OP_FUNC(efl_dbg_info_get, _efl_canvas_image_internal_efl_object_dbg_info_get)
|
2017-04-21 08:58:38 -07:00
|
|
|
|
2016-06-09 01:30:05 -07:00
|
|
|
#include "canvas/efl_canvas_image_internal.eo.c"
|
2015-04-14 06:21:52 -07:00
|
|
|
|
|
|
|
/* vim:set ts=8 sw=3 sts=3 expandtab cino=>5n-2f0^-2{2(0W1st0 :*/
|