forked from enlightenment/efl
improvement to gl engine wrt. caching.
SVN revision: 56801
This commit is contained in:
parent
e2bd68dc91
commit
7881c0b849
|
@ -57,3 +57,10 @@
|
||||||
clip on the object. This is still buggy.
|
clip on the object. This is still buggy.
|
||||||
* Software support for arbitrary maps. So you can use any size map
|
* Software support for arbitrary maps. So you can use any size map
|
||||||
(not just 4 points) for maps. Once again this is a little buggy.
|
(not just 4 points) for maps. Once again this is a little buggy.
|
||||||
|
|
||||||
|
2011-02-02 Carsten Haitzler (The Rasterman)
|
||||||
|
|
||||||
|
* GL engine gets a speculative texture cache to shadow the
|
||||||
|
normal image cache to avoid excess texture uploads when
|
||||||
|
cycling images often. Should improve performance in some
|
||||||
|
cases.
|
||||||
|
|
|
@ -125,6 +125,8 @@ struct _Evas_GL_Shared
|
||||||
{
|
{
|
||||||
Eina_List *images;
|
Eina_List *images;
|
||||||
|
|
||||||
|
int images_size;
|
||||||
|
|
||||||
struct {
|
struct {
|
||||||
GLint max_texture_units;
|
GLint max_texture_units;
|
||||||
GLint max_texture_size;
|
GLint max_texture_size;
|
||||||
|
@ -471,6 +473,7 @@ void evas_gl_common_image_native_enable(Evas_GL_Image *im);
|
||||||
void evas_gl_common_image_native_disable(Evas_GL_Image *im);
|
void evas_gl_common_image_native_disable(Evas_GL_Image *im);
|
||||||
void evas_gl_common_image_scale_hint_set(Evas_GL_Image *im, int hint);
|
void evas_gl_common_image_scale_hint_set(Evas_GL_Image *im, int hint);
|
||||||
void evas_gl_common_image_content_hint_set(Evas_GL_Image *im, int hint);
|
void evas_gl_common_image_content_hint_set(Evas_GL_Image *im, int hint);
|
||||||
|
void evas_gl_common_image_cache_flush(Evas_GL_Context *gc);
|
||||||
void evas_gl_common_image_free(Evas_GL_Image *im);
|
void evas_gl_common_image_free(Evas_GL_Image *im);
|
||||||
Evas_GL_Image *evas_gl_common_image_surface_new(Evas_GL_Context *gc, unsigned int w, unsigned int h, int alpha);
|
Evas_GL_Image *evas_gl_common_image_surface_new(Evas_GL_Context *gc, unsigned int w, unsigned int h, int alpha);
|
||||||
void evas_gl_common_image_dirty(Evas_GL_Image *im, unsigned int x, unsigned int y, unsigned int w, unsigned int h);
|
void evas_gl_common_image_dirty(Evas_GL_Image *im, unsigned int x, unsigned int y, unsigned int w, unsigned int h);
|
||||||
|
|
|
@ -30,11 +30,14 @@ evas_gl_common_image_load(Evas_GL_Context *gc, const char *file, const char *key
|
||||||
im_im = evas_common_load_image_from_file(file, key, lo, error);
|
im_im = evas_common_load_image_from_file(file, key, lo, error);
|
||||||
if (!im_im) return NULL;
|
if (!im_im) return NULL;
|
||||||
|
|
||||||
|
// FIXME: keep unreffed shared images around
|
||||||
EINA_LIST_FOREACH(gc->shared->images, l, im)
|
EINA_LIST_FOREACH(gc->shared->images, l, im)
|
||||||
{
|
{
|
||||||
if (im->im == im_im)
|
if (im->im == im_im)
|
||||||
{
|
{
|
||||||
evas_cache_image_drop(&im_im->cache_entry);
|
// why did i put this here? i think to free the rgba pixel data once a texture
|
||||||
|
// exists.
|
||||||
|
// evas_cache_image_drop(&im_im->cache_entry);
|
||||||
gc->shared->images = eina_list_remove_list(gc->shared->images, l);
|
gc->shared->images = eina_list_remove_list(gc->shared->images, l);
|
||||||
gc->shared->images = eina_list_prepend(gc->shared->images, im);
|
gc->shared->images = eina_list_prepend(gc->shared->images, im);
|
||||||
im->references++;
|
im->references++;
|
||||||
|
@ -230,6 +233,8 @@ evas_gl_common_image_native_enable(Evas_GL_Image *im)
|
||||||
im->cs.no_free = 0;
|
im->cs.no_free = 0;
|
||||||
if (im->cached)
|
if (im->cached)
|
||||||
{
|
{
|
||||||
|
if (im->references == 0)
|
||||||
|
im->gc->shared->images_size -= (im->w * im->h);
|
||||||
im->gc->shared->images = eina_list_remove(im->gc->shared->images, im);
|
im->gc->shared->images = eina_list_remove(im->gc->shared->images, im);
|
||||||
im->cached = 0;
|
im->cached = 0;
|
||||||
}
|
}
|
||||||
|
@ -302,6 +307,8 @@ evas_gl_common_image_content_hint_set(Evas_GL_Image *im, int hint)
|
||||||
im->cs.no_free = 0;
|
im->cs.no_free = 0;
|
||||||
if (im->cached)
|
if (im->cached)
|
||||||
{
|
{
|
||||||
|
if (im->references == 0)
|
||||||
|
im->gc->shared->images_size -= (im->w * im->h);
|
||||||
im->gc->shared->images = eina_list_remove(im->gc->shared->images, im);
|
im->gc->shared->images = eina_list_remove(im->gc->shared->images, im);
|
||||||
im->cached = 0;
|
im->cached = 0;
|
||||||
}
|
}
|
||||||
|
@ -342,6 +349,59 @@ evas_gl_common_image_content_hint_set(Evas_GL_Image *im, int hint)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
_evas_gl_image_cache_trim(Evas_GL_Context *gc)
|
||||||
|
{
|
||||||
|
int size = evas_common_image_get_cache();
|
||||||
|
|
||||||
|
while (gc->shared->images_size > size)
|
||||||
|
{
|
||||||
|
Evas_GL_Image *im2;
|
||||||
|
Eina_List *l;
|
||||||
|
|
||||||
|
EINA_LIST_REVERSE_FOREACH(gc->shared->images, l, im2)
|
||||||
|
{
|
||||||
|
if (im2->references == 0)
|
||||||
|
{
|
||||||
|
im2->cached = 0;
|
||||||
|
im2->gc->shared->images =
|
||||||
|
eina_list_remove_list(im2->gc->shared->images, l);
|
||||||
|
im2->gc->shared->images_size -= (im2->w * im2->h);
|
||||||
|
evas_gl_common_image_free(im2);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!l)
|
||||||
|
{
|
||||||
|
printf("EEEK images_size > 0 but no 0 ref images in cache\n");
|
||||||
|
break; // something went wrong
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static Eina_Bool
|
||||||
|
_evas_gl_image_cache_add(Evas_GL_Image *im)
|
||||||
|
{
|
||||||
|
if (im->references == 0)
|
||||||
|
{
|
||||||
|
im->gc->shared->images_size += (im->w * im->h);
|
||||||
|
_evas_gl_image_cache_trim(im->gc);
|
||||||
|
return EINA_TRUE;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
im->gc->shared->images = eina_list_remove(im->gc->shared->images, im);
|
||||||
|
im->cached = 0;
|
||||||
|
}
|
||||||
|
return EINA_FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
evas_gl_common_image_cache_flush(Evas_GL_Context *gc)
|
||||||
|
{
|
||||||
|
_evas_gl_image_cache_trim(gc);
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
evas_gl_common_image_free(Evas_GL_Image *im)
|
evas_gl_common_image_free(Evas_GL_Image *im)
|
||||||
{
|
{
|
||||||
|
@ -355,7 +415,10 @@ evas_gl_common_image_free(Evas_GL_Image *im)
|
||||||
{
|
{
|
||||||
if (!im->cs.no_free) free(im->cs.data);
|
if (!im->cs.no_free) free(im->cs.data);
|
||||||
}
|
}
|
||||||
if (im->cached) im->gc->shared->images = eina_list_remove(im->gc->shared->images, im);
|
if (im->cached)
|
||||||
|
{
|
||||||
|
if (_evas_gl_image_cache_add(im)) return;
|
||||||
|
}
|
||||||
if (im->im) evas_cache_image_drop(&im->im->cache_entry);
|
if (im->im) evas_cache_image_drop(&im->im->cache_entry);
|
||||||
if (im->tex) evas_gl_common_texture_free(im->tex);
|
if (im->tex) evas_gl_common_texture_free(im->tex);
|
||||||
free(im);
|
free(im);
|
||||||
|
|
|
@ -847,6 +847,7 @@ evas_gl_common_texture_update(Evas_GL_Texture *tex, RGBA_Image *im)
|
||||||
glPixelStorei(GL_UNPACK_ALIGNMENT, 4);
|
glPixelStorei(GL_UNPACK_ALIGNMENT, 4);
|
||||||
GLERR(__FUNCTION__, __FILE__, __LINE__, "");
|
GLERR(__FUNCTION__, __FILE__, __LINE__, "");
|
||||||
|
|
||||||
|
// printf("tex upload %ix%i\n", im->cache_entry.w, im->cache_entry.h);
|
||||||
// +-+
|
// +-+
|
||||||
// +-+
|
// +-+
|
||||||
//
|
//
|
||||||
|
|
|
@ -1814,6 +1814,42 @@ eng_image_content_hint_get(void *data __UNUSED__, void *image)
|
||||||
return gim->content_hint;
|
return gim->content_hint;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
eng_image_cache_flush(void *data __UNUSED__)
|
||||||
|
{
|
||||||
|
Render_Engine *re;
|
||||||
|
int tmp_size;
|
||||||
|
|
||||||
|
re = (Render_Engine *)data;
|
||||||
|
|
||||||
|
tmp_size = evas_common_image_get_cache();
|
||||||
|
evas_common_image_set_cache(0);
|
||||||
|
evas_common_rgba_image_scalecache_flush();
|
||||||
|
evas_gl_common_image_cache_flush(re->win->gl_context);
|
||||||
|
evas_common_image_set_cache(tmp_size);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
eng_image_cache_set(void *data __UNUSED__, int bytes)
|
||||||
|
{
|
||||||
|
Render_Engine *re;
|
||||||
|
|
||||||
|
re = (Render_Engine *)data;
|
||||||
|
evas_common_image_set_cache(bytes);
|
||||||
|
evas_common_rgba_image_scalecache_size_set(bytes);
|
||||||
|
evas_gl_common_image_cache_flush(re->win->gl_context);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
eng_image_cache_get(void *data __UNUSED__)
|
||||||
|
{
|
||||||
|
Render_Engine *re;
|
||||||
|
|
||||||
|
re = (Render_Engine *)data;
|
||||||
|
return evas_common_image_get_cache();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
eng_image_stride_get(void *data __UNUSED__, void *image, int *stride)
|
eng_image_stride_get(void *data __UNUSED__, void *image, int *stride)
|
||||||
{
|
{
|
||||||
|
@ -1949,6 +1985,10 @@ module_open(Evas_Module *em)
|
||||||
ORD(image_content_hint_set);
|
ORD(image_content_hint_set);
|
||||||
ORD(image_content_hint_get);
|
ORD(image_content_hint_get);
|
||||||
|
|
||||||
|
ORD(image_cache_flush);
|
||||||
|
ORD(image_cache_set);
|
||||||
|
ORD(image_cache_get);
|
||||||
|
|
||||||
/* now advertise out own api */
|
/* now advertise out own api */
|
||||||
em->functions = (void *)(&func);
|
em->functions = (void *)(&func);
|
||||||
return 1;
|
return 1;
|
||||||
|
|
Loading…
Reference in New Issue