forked from enlightenment/efl
Evas gl: Add support for ETC1+Alpha textures
Compile-in the required shaders, add support for the new EVAS_COLORSPACE_ETC1_ALPHA, and upload textures as RGB+A pairs. @feature
This commit is contained in:
parent
0bba7422cb
commit
48bcf182b4
|
@ -134,6 +134,7 @@ _evas_common_rgba_image_surface_size(unsigned int w, unsigned int h,
|
|||
case EVAS_COLORSPACE_RGBA_S3TC_DXT3:
|
||||
case EVAS_COLORSPACE_RGBA_S3TC_DXT4:
|
||||
case EVAS_COLORSPACE_RGBA_S3TC_DXT5:
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
block_size = 16;
|
||||
// fallthrough
|
||||
case EVAS_COLORSPACE_ETC1:
|
||||
|
|
|
@ -332,6 +332,9 @@ typedef enum {
|
|||
SHADER_YUY2_NOMUL,
|
||||
SHADER_NV12,
|
||||
SHADER_NV12_NOMUL,
|
||||
|
||||
SHADER_RGB_A_PAIR,
|
||||
SHADER_RGB_A_PAIR_NOMUL,
|
||||
/*
|
||||
SHADER_FILTER_INVERT,
|
||||
SHADER_FILTER_INVERT_NOMUL,
|
||||
|
@ -413,6 +416,8 @@ struct _Evas_GL_Shared
|
|||
#define MAX_ATLAS_H 512
|
||||
#define DEF_ATLAS_H 512
|
||||
|
||||
#define ATLAS_FORMATS_COUNT 11
|
||||
|
||||
Eina_List *cspaces; // depend on the values of etc1, etc2 and st3c
|
||||
|
||||
struct {
|
||||
|
@ -433,7 +438,7 @@ struct _Evas_GL_Shared
|
|||
|
||||
struct {
|
||||
Eina_List *whole;
|
||||
Eina_List *atlas[10];
|
||||
Eina_List *atlas[ATLAS_FORMATS_COUNT];
|
||||
} tex;
|
||||
|
||||
Eina_Hash *native_pm_hash;
|
||||
|
@ -595,7 +600,11 @@ struct _Evas_GL_Texture
|
|||
{
|
||||
Evas_Engine_GL_Context *gc;
|
||||
Evas_GL_Image *im;
|
||||
Evas_GL_Texture_Pool *pt, *ptu, *ptv, *ptuv, *ptt;
|
||||
Evas_GL_Texture_Pool *pt, *ptu, *ptv, *ptt;
|
||||
union {
|
||||
Evas_GL_Texture_Pool *ptuv;
|
||||
Evas_GL_Texture_Pool *pta;
|
||||
};
|
||||
RGBA_Font_Glyph *fglyph;
|
||||
int x, y, w, h;
|
||||
int tx, ty;
|
||||
|
@ -777,6 +786,12 @@ void evas_gl_common_context_nv12_push(Evas_Engine_GL_Context *gc,
|
|||
int x, int y, int w, int h,
|
||||
int r, int g, int b, int a,
|
||||
Eina_Bool smooth);
|
||||
void evas_gl_common_context_rgb_a_pair_push(Evas_Engine_GL_Context *gc,
|
||||
Evas_GL_Texture *tex,
|
||||
double sx, double sy, double sw, double sh,
|
||||
int x, int y, int w, int h,
|
||||
int r, int g, int b, int a,
|
||||
Eina_Bool smooth);
|
||||
void evas_gl_common_context_image_map_push(Evas_Engine_GL_Context *gc,
|
||||
Evas_GL_Texture *tex,
|
||||
int npoints,
|
||||
|
@ -821,6 +836,8 @@ Evas_GL_Texture *evas_gl_common_texture_nv12_new(Evas_Engine_GL_Context *gc, DA
|
|||
void evas_gl_common_texture_nv12_update(Evas_GL_Texture *tex, DATA8 **row, unsigned int w, unsigned int h);
|
||||
Evas_GL_Texture *evas_gl_common_texture_nv12tiled_new(Evas_Engine_GL_Context *gc, DATA8 **rows, unsigned int w, unsigned int h);
|
||||
void evas_gl_common_texture_nv12tiled_update(Evas_GL_Texture *tex, DATA8 **row, unsigned int w, unsigned int h);
|
||||
Evas_GL_Texture *evas_gl_common_texture_rgb_a_pair_new(Evas_Engine_GL_Context *gc, RGBA_Image *im);
|
||||
void evas_gl_common_texture_rgb_a_pair_update(Evas_GL_Texture *tex, RGBA_Image *im);
|
||||
|
||||
void evas_gl_common_image_alloc_ensure(Evas_GL_Image *im);
|
||||
void evas_gl_common_image_all_unload(Evas_Engine_GL_Context *gc);
|
||||
|
@ -900,6 +917,7 @@ void pt_unref(Evas_GL_Texture_Pool *pt);
|
|||
#else
|
||||
# define GLERR(fn, fl, ln, op)
|
||||
#endif
|
||||
#define GLERRLOG() GLERR(__FUNCTION__, __FILE__, __LINE__, "")
|
||||
|
||||
Eina_Bool evas_gl_common_module_open(void);
|
||||
void evas_gl_common_module_close(void);
|
||||
|
@ -913,6 +931,15 @@ _tex_sub_2d(Evas_Engine_GL_Context *gc, int x, int y, int w, int h, int fmt, int
|
|||
GLERR(__FUNCTION__, __FILE__, __LINE__, "");
|
||||
}
|
||||
|
||||
static inline void
|
||||
_comp_tex_sub_2d(Evas_Engine_GL_Context *gc, int x, int y, int w, int h, int fmt, int imgsize, const void *pix)
|
||||
{
|
||||
if ((w > gc->shared->info.max_texture_size) ||
|
||||
(h > gc->shared->info.max_texture_size)) return;
|
||||
glCompressedTexSubImage2D(GL_TEXTURE_2D, 0, x, y, w, h, fmt, imgsize, pix);
|
||||
GLERR(__FUNCTION__, __FILE__, __LINE__, "glCompressedTexSubImage2D");
|
||||
}
|
||||
|
||||
#include "evas_gl_3d_common.h"
|
||||
|
||||
#endif
|
||||
|
|
|
@ -861,6 +861,11 @@ evas_gl_common_context_new(void)
|
|||
SHADER_TEXTURE_ADD(shared, NV12_NOMUL, tex);
|
||||
SHADER_TEXTURE_ADD(shared, NV12_NOMUL, texuv);
|
||||
|
||||
SHADER_TEXTURE_ADD(shared, RGB_A_PAIR, tex);
|
||||
SHADER_TEXTURE_ADD(shared, RGB_A_PAIR, texm);
|
||||
SHADER_TEXTURE_ADD(shared, RGB_A_PAIR_NOMUL, tex);
|
||||
SHADER_TEXTURE_ADD(shared, RGB_A_PAIR_NOMUL, texm);
|
||||
|
||||
if (gc->state.current.cur_prog == PRG_INVALID)
|
||||
glUseProgram(shared->shader[0].prog);
|
||||
else glUseProgram(gc->state.current.cur_prog);
|
||||
|
@ -2293,6 +2298,108 @@ evas_gl_common_context_nv12_push(Evas_Engine_GL_Context *gc,
|
|||
}
|
||||
}
|
||||
|
||||
void
|
||||
evas_gl_common_context_rgb_a_pair_push(Evas_Engine_GL_Context *gc,
|
||||
Evas_GL_Texture *tex,
|
||||
double sx, double sy,
|
||||
double sw, double sh,
|
||||
int x, int y, int w, int h,
|
||||
int r, int g, int b, int a,
|
||||
Eina_Bool smooth)
|
||||
|
||||
{
|
||||
/* This RGB+Alpha mode is used for ETC1+Alpha textures, where the shader
|
||||
* will multiply RGB by alpha. Two textures are created: tex->{pt,pta}.
|
||||
* Since the exact encoding doesn't matter here (decoding is transparent
|
||||
* from the shader point of view), this method could be used for other
|
||||
* colorspaces as well (eg. RGB565+Alpha4, ...).
|
||||
*/
|
||||
|
||||
int pnum, nv, nc, nu, nm, i;
|
||||
GLfloat tx1, tx2, ty1, ty2, t2x1, t2x2, t2y1, t2y2;
|
||||
GLuint prog;
|
||||
int pn;
|
||||
|
||||
prog = gc->shared->shader[evas_gl_common_shader_choice
|
||||
(0, NULL, r, g, b, a, SHADER_RGB_A_PAIR_NOMUL, SHADER_RGB_A_PAIR)].prog;
|
||||
|
||||
pn = _evas_gl_common_context_push(RTYPE_IMAGE,
|
||||
gc, tex, NULL,
|
||||
prog,
|
||||
x, y, w, h,
|
||||
EINA_TRUE,
|
||||
smooth,
|
||||
EINA_FALSE, 0, 0, 0, 0);
|
||||
|
||||
gc->pipe[pn].region.type = RTYPE_IMAGE;
|
||||
gc->pipe[pn].shader.cur_tex = tex->pt->texture;
|
||||
gc->pipe[pn].shader.cur_texm = tex->pta->texture;
|
||||
gc->pipe[pn].shader.cur_prog = prog;
|
||||
gc->pipe[pn].shader.smooth = smooth;
|
||||
gc->pipe[pn].shader.blend = EINA_TRUE;
|
||||
gc->pipe[pn].shader.render_op = gc->dc->render_op;
|
||||
gc->pipe[pn].shader.clip = 0;
|
||||
gc->pipe[pn].shader.cx = 0;
|
||||
gc->pipe[pn].shader.cy = 0;
|
||||
gc->pipe[pn].shader.cw = 0;
|
||||
gc->pipe[pn].shader.ch = 0;
|
||||
gc->pipe[pn].array.line = 0;
|
||||
gc->pipe[pn].array.use_vertex = EINA_TRUE;
|
||||
// if nomul... dont need this
|
||||
gc->pipe[pn].array.use_color = EINA_TRUE;
|
||||
gc->pipe[pn].array.use_texuv = EINA_TRUE;
|
||||
gc->pipe[pn].array.use_texuv2 = 0;
|
||||
gc->pipe[pn].array.use_texuv3 = 0;
|
||||
gc->pipe[pn].array.use_texm = EINA_TRUE;
|
||||
gc->pipe[pn].array.use_texsam = 0;
|
||||
|
||||
pipe_region_expand(gc, pn, x, y, w, h);
|
||||
|
||||
pnum = gc->pipe[pn].array.num;
|
||||
nv = pnum * 3; nc = pnum * 4; nu = pnum * 2; nm = pnum * 2;
|
||||
gc->pipe[pn].array.num += 6;
|
||||
array_alloc(gc, pn);
|
||||
|
||||
tx1 = (sx) / (double)tex->pt->w;
|
||||
ty1 = (sy) / (double)tex->pt->h;
|
||||
tx2 = (sx + sw) / (double)tex->pt->w;
|
||||
ty2 = (sy + sh) / (double)tex->pt->h;
|
||||
|
||||
t2x1 = sx / (double)tex->pta->w;
|
||||
t2y1 = sy / (double)tex->pta->h;
|
||||
t2x2 = (sx + sw) / (double)tex->pta->w;
|
||||
t2y2 = (sy + sh) / (double)tex->pta->h;
|
||||
|
||||
PUSH_VERTEX(pn, x , y , 0);
|
||||
PUSH_VERTEX(pn, x + w, y , 0);
|
||||
PUSH_VERTEX(pn, x , y + h, 0);
|
||||
|
||||
PUSH_TEXUV(pn, tx1, ty1);
|
||||
PUSH_TEXUV(pn, tx2, ty1);
|
||||
PUSH_TEXUV(pn, tx1, ty2);
|
||||
|
||||
PUSH_TEXM(pn, t2x1, t2y1);
|
||||
PUSH_TEXM(pn, t2x2, t2y1);
|
||||
PUSH_TEXM(pn, t2x1, t2y2);
|
||||
|
||||
PUSH_VERTEX(pn, x + w, y , 0);
|
||||
PUSH_VERTEX(pn, x + w, y + h, 0);
|
||||
PUSH_VERTEX(pn, x , y + h, 0);
|
||||
|
||||
PUSH_TEXUV(pn, tx2, ty1);
|
||||
PUSH_TEXUV(pn, tx2, ty2);
|
||||
PUSH_TEXUV(pn, tx1, ty2);
|
||||
|
||||
PUSH_TEXM(pn, t2x2, t2y1);
|
||||
PUSH_TEXM(pn, t2x2, t2y2);
|
||||
PUSH_TEXM(pn, t2x1, t2y2);
|
||||
|
||||
for (i = 0; i < 6; i++)
|
||||
{
|
||||
PUSH_COLOR(pn, r, g, b, a);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
evas_gl_common_context_image_map_push(Evas_Engine_GL_Context *gc,
|
||||
Evas_GL_Texture *tex,
|
||||
|
|
|
@ -132,9 +132,13 @@ _evas_gl_cspace_list_fill(Evas_Engine_GL_Context *gc)
|
|||
CS_APPEND(EVAS_COLORSPACE_RGBA8_ETC2_EAC);
|
||||
CS_APPEND(EVAS_COLORSPACE_RGB8_ETC2);
|
||||
CS_APPEND(EVAS_COLORSPACE_ETC1);
|
||||
CS_APPEND(EVAS_COLORSPACE_ETC1_ALPHA);
|
||||
}
|
||||
else if (gc->shared->info.etc1)
|
||||
CS_APPEND(EVAS_COLORSPACE_ETC1);
|
||||
{
|
||||
CS_APPEND(EVAS_COLORSPACE_ETC1);
|
||||
CS_APPEND(EVAS_COLORSPACE_ETC1_ALPHA);
|
||||
}
|
||||
if (gc->shared->info.s3tc)
|
||||
{
|
||||
CS_APPEND(EVAS_COLORSPACE_RGB_S3TC_DXT1);
|
||||
|
@ -347,6 +351,7 @@ evas_gl_common_image_new_from_data(Evas_Engine_GL_Context *gc, unsigned int w, u
|
|||
case EVAS_COLORSPACE_AGRY88:
|
||||
break;
|
||||
case EVAS_COLORSPACE_ETC1:
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
if (gc->shared->info.etc1 && !gc->shared->info.etc2) break;
|
||||
ERR("We don't know what to do with ETC1 on this hardware. You need to add a software converter here.");
|
||||
break;
|
||||
|
@ -400,6 +405,7 @@ evas_gl_common_image_new_from_copied_data(Evas_Engine_GL_Context *gc, unsigned i
|
|||
case EVAS_COLORSPACE_AGRY88:
|
||||
break;
|
||||
case EVAS_COLORSPACE_ETC1:
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
if (gc->shared->info.etc1 && !gc->shared->info.etc2) break;
|
||||
ERR("We don't know what to do with ETC1 on this hardware. You need to add a software converter here.");
|
||||
break;
|
||||
|
@ -460,6 +466,7 @@ evas_gl_common_image_new(Evas_Engine_GL_Context *gc, unsigned int w, unsigned in
|
|||
case EVAS_COLORSPACE_AGRY88:
|
||||
break;
|
||||
case EVAS_COLORSPACE_ETC1:
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
if (gc->shared->info.etc1 && !gc->shared->info.etc2) break;
|
||||
ERR("We don't know what to do with ETC1 on this hardware. You need to add a software converter here.");
|
||||
break;
|
||||
|
@ -601,12 +608,19 @@ evas_gl_common_image_content_hint_set(Evas_GL_Image *im, int hint)
|
|||
if (!im->gc->shared->info.sec_image_map) return;
|
||||
if (!im->gc->shared->info.bgra) return;
|
||||
// does not handle yuv yet.
|
||||
if (im->cs.space != EVAS_COLORSPACE_ARGB8888 &&
|
||||
im->cs.space != EVAS_COLORSPACE_GRY8 &&
|
||||
im->cs.space != EVAS_COLORSPACE_AGRY88 &&
|
||||
im->cs.space != EVAS_COLORSPACE_ETC1 &&
|
||||
im->cs.space != EVAS_COLORSPACE_RGB8_ETC2 &&
|
||||
im->cs.space != EVAS_COLORSPACE_RGBA8_ETC2_EAC) return;
|
||||
// TODO: Check this list of cspaces
|
||||
switch (im->cs.space)
|
||||
{
|
||||
case EVAS_COLORSPACE_YCBCR422P601_PL:
|
||||
case EVAS_COLORSPACE_YCBCR422P709_PL:
|
||||
case EVAS_COLORSPACE_RGB565_A5P:
|
||||
case EVAS_COLORSPACE_YCBCR422601_PL:
|
||||
case EVAS_COLORSPACE_YCBCR420NV12601_PL:
|
||||
case EVAS_COLORSPACE_YCBCR420TM12601_PL:
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
return;
|
||||
default: break;
|
||||
}
|
||||
if (im->content_hint == EVAS_IMAGE_CONTENT_HINT_DYNAMIC)
|
||||
{
|
||||
if (im->cs.data)
|
||||
|
@ -831,6 +845,22 @@ evas_gl_common_image_update(Evas_Engine_GL_Context *gc, Evas_GL_Image *im)
|
|||
im->dirty = 0;
|
||||
if (!im->tex) return;
|
||||
break;
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
if ((im->tex) && (im->dirty))
|
||||
{
|
||||
evas_cache_image_load_data(&im->im->cache_entry);
|
||||
evas_gl_common_texture_rgb_a_pair_update(im->tex, im->im);
|
||||
evas_cache_image_unload_data(&im->im->cache_entry);
|
||||
}
|
||||
else if ((!im->tex))
|
||||
{
|
||||
evas_cache_image_load_data(&im->im->cache_entry);
|
||||
im->tex = evas_gl_common_texture_rgb_a_pair_new(gc, im->im);
|
||||
evas_cache_image_unload_data(&im->im->cache_entry);
|
||||
}
|
||||
im->dirty = 0;
|
||||
if (!im->tex) return;
|
||||
break;
|
||||
case EVAS_COLORSPACE_YCBCR422P601_PL:
|
||||
case EVAS_COLORSPACE_YCBCR422P709_PL:
|
||||
if ((im->tex) && (im->dirty))
|
||||
|
@ -942,13 +972,14 @@ evas_gl_common_image_map_draw(Evas_Engine_GL_Context *gc, Evas_GL_Image *im,
|
|||
im->cs.space);
|
||||
}
|
||||
|
||||
void
|
||||
evas_gl_common_image_push(Evas_Engine_GL_Context *gc, Evas_GL_Image *im,
|
||||
int dx, int dy, int dw, int dh,
|
||||
int sx, int sy, int sw, int sh,
|
||||
int cx, int cy, int cw, int ch,
|
||||
int r, int g, int b, int a, int smooth,
|
||||
int yuv, int yuy2, int nv12)
|
||||
static void
|
||||
_evas_gl_common_image_push(Evas_Engine_GL_Context *gc, Evas_GL_Image *im,
|
||||
int dx, int dy, int dw, int dh,
|
||||
int sx, int sy, int sw, int sh,
|
||||
int cx, int cy, int cw, int ch,
|
||||
int r, int g, int b, int a, Eina_Bool smooth,
|
||||
Eina_Bool yuv, Eina_Bool yuy2, Eina_Bool nv12,
|
||||
Eina_Bool rgb_a_pair)
|
||||
{
|
||||
double ssx, ssy, ssw, ssh;
|
||||
int nx, ny, nw, nh;
|
||||
|
@ -981,6 +1012,13 @@ evas_gl_common_image_push(Evas_Engine_GL_Context *gc, Evas_GL_Image *im,
|
|||
dx, dy, dw, dh,
|
||||
r, g, b, a,
|
||||
smooth);
|
||||
else if (rgb_a_pair)
|
||||
evas_gl_common_context_rgb_a_pair_push(gc,
|
||||
im->tex,
|
||||
sx, sy, sw, sh,
|
||||
dx, dy, dw, dh,
|
||||
r, g, b, a,
|
||||
smooth);
|
||||
else
|
||||
evas_gl_common_context_image_push(gc,
|
||||
im->tex,
|
||||
|
@ -1017,6 +1055,13 @@ evas_gl_common_image_push(Evas_Engine_GL_Context *gc, Evas_GL_Image *im,
|
|||
nx, ny, nw, nh,
|
||||
r, g, b, a,
|
||||
smooth);
|
||||
else if (rgb_a_pair)
|
||||
evas_gl_common_context_rgb_a_pair_push(gc,
|
||||
im->tex,
|
||||
ssx, ssy, ssw, ssh,
|
||||
nx, ny, nw, nh,
|
||||
r, g, b, a,
|
||||
smooth);
|
||||
else
|
||||
evas_gl_common_context_image_push(gc,
|
||||
im->tex,
|
||||
|
@ -1035,9 +1080,10 @@ evas_gl_common_image_draw(Evas_Engine_GL_Context *gc, Evas_GL_Image *im, int sx,
|
|||
Cutout_Rect *rct;
|
||||
int c, cx, cy, cw, ch;
|
||||
int i;
|
||||
int yuv = 0;
|
||||
int yuy2 = 0;
|
||||
int nv12 = 0;
|
||||
Eina_Bool yuv = EINA_FALSE;
|
||||
Eina_Bool yuy2 = EINA_FALSE;
|
||||
Eina_Bool nv12 = EINA_FALSE;
|
||||
Eina_Bool rgb_a_pair = EINA_FALSE;
|
||||
|
||||
if (sw < 1) sw = 1;
|
||||
if (sh < 1) sh = 1;
|
||||
|
@ -1061,14 +1107,24 @@ evas_gl_common_image_draw(Evas_Engine_GL_Context *gc, Evas_GL_Image *im, int sx,
|
|||
return;
|
||||
}
|
||||
|
||||
if ((im->cs.space == EVAS_COLORSPACE_YCBCR422P601_PL) ||
|
||||
(im->cs.space == EVAS_COLORSPACE_YCBCR422P709_PL))
|
||||
yuv = 1;
|
||||
if (im->cs.space == EVAS_COLORSPACE_YCBCR422601_PL)
|
||||
yuy2 = 1;
|
||||
if ((im->cs.space == EVAS_COLORSPACE_YCBCR420NV12601_PL) ||
|
||||
(im->cs.space == EVAS_COLORSPACE_YCBCR420TM12601_PL))
|
||||
nv12 = 1;
|
||||
switch (im->cs.space)
|
||||
{
|
||||
case EVAS_COLORSPACE_YCBCR422P601_PL:
|
||||
case EVAS_COLORSPACE_YCBCR422P709_PL:
|
||||
yuv = EINA_TRUE;
|
||||
break;
|
||||
case EVAS_COLORSPACE_YCBCR422601_PL:
|
||||
yuy2 = EINA_TRUE;
|
||||
break;
|
||||
case EVAS_COLORSPACE_YCBCR420NV12601_PL:
|
||||
case EVAS_COLORSPACE_YCBCR420TM12601_PL:
|
||||
nv12 = EINA_TRUE;
|
||||
break;
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
rgb_a_pair = EINA_TRUE;
|
||||
break;
|
||||
default: break;
|
||||
}
|
||||
|
||||
if ((sw == dw) && (sh == dh)) smooth = 0;
|
||||
|
||||
|
@ -1079,22 +1135,22 @@ evas_gl_common_image_draw(Evas_Engine_GL_Context *gc, Evas_GL_Image *im, int sx,
|
|||
{
|
||||
if (gc->dc->clip.use)
|
||||
{
|
||||
evas_gl_common_image_push(gc, im,
|
||||
dx, dy, dw, dh,
|
||||
sx, sy, sw, sh,
|
||||
gc->dc->clip.x, gc->dc->clip.y,
|
||||
gc->dc->clip.w, gc->dc->clip.h,
|
||||
r, g, b, a, smooth,
|
||||
yuv, yuy2, nv12);
|
||||
_evas_gl_common_image_push(gc, im,
|
||||
dx, dy, dw, dh,
|
||||
sx, sy, sw, sh,
|
||||
gc->dc->clip.x, gc->dc->clip.y,
|
||||
gc->dc->clip.w, gc->dc->clip.h,
|
||||
r, g, b, a, smooth,
|
||||
yuv, yuy2, nv12, rgb_a_pair);
|
||||
}
|
||||
else
|
||||
{
|
||||
evas_gl_common_image_push(gc, im,
|
||||
dx, dy, dw, dh,
|
||||
sx, sy, sw, sh,
|
||||
dx, dy, dw, dh,
|
||||
r, g, b, a, smooth,
|
||||
yuv, yuy2, nv12);
|
||||
_evas_gl_common_image_push(gc, im,
|
||||
dx, dy, dw, dh,
|
||||
sx, sy, sw, sh,
|
||||
dx, dy, dw, dh,
|
||||
r, g, b, a, smooth,
|
||||
yuv, yuy2, nv12, rgb_a_pair);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
@ -1114,12 +1170,12 @@ evas_gl_common_image_draw(Evas_Engine_GL_Context *gc, Evas_GL_Image *im, int sx,
|
|||
{
|
||||
rct = rects->rects + i;
|
||||
|
||||
evas_gl_common_image_push(gc, im,
|
||||
dx, dy, dw, dh,
|
||||
sx, sy, sw, sh,
|
||||
rct->x, rct->y, rct->w, rct->h,
|
||||
r, g, b, a, smooth,
|
||||
yuv, yuy2, nv12);
|
||||
_evas_gl_common_image_push(gc, im,
|
||||
dx, dy, dw, dh,
|
||||
sx, sy, sw, sh,
|
||||
rct->x, rct->y, rct->w, rct->h,
|
||||
r, g, b, a, smooth,
|
||||
yuv, yuy2, nv12, rgb_a_pair);
|
||||
}
|
||||
/* restore clip info */
|
||||
gc->dc->clip.use = c; gc->dc->clip.x = cx; gc->dc->clip.y = cy; gc->dc->clip.w = cw; gc->dc->clip.h = ch;
|
||||
|
|
|
@ -771,6 +771,43 @@ Evas_GL_Program_Source shader_yuv_nomul_vert_src =
|
|||
NULL, 0
|
||||
};
|
||||
|
||||
/////////////////////////////////////////////
|
||||
const char rgb_a_pair_frag_glsl[] =
|
||||
#include "shader/rgb_a_pair_frag.h"
|
||||
;
|
||||
Evas_GL_Program_Source shader_rgb_a_pair_frag_src =
|
||||
{
|
||||
rgb_a_pair_frag_glsl,
|
||||
NULL, 0
|
||||
};
|
||||
|
||||
const char rgb_a_pair_vert_glsl[] =
|
||||
#include "shader/rgb_a_pair_vert.h"
|
||||
;
|
||||
Evas_GL_Program_Source shader_rgb_a_pair_vert_src =
|
||||
{
|
||||
rgb_a_pair_vert_glsl,
|
||||
NULL, 0
|
||||
};
|
||||
|
||||
const char rgb_a_pair_nomul_frag_glsl[] =
|
||||
#include "shader/rgb_a_pair_nomul_frag.h"
|
||||
;
|
||||
Evas_GL_Program_Source shader_rgb_a_pair_nomul_frag_src =
|
||||
{
|
||||
rgb_a_pair_nomul_frag_glsl,
|
||||
NULL, 0
|
||||
};
|
||||
|
||||
const char rgb_a_pair_nomul_vert_glsl[] =
|
||||
#include "shader/rgb_a_pair_nomul_vert.h"
|
||||
;
|
||||
Evas_GL_Program_Source shader_rgb_a_pair_nomul_vert_src =
|
||||
{
|
||||
rgb_a_pair_nomul_vert_glsl,
|
||||
NULL, 0
|
||||
};
|
||||
|
||||
|
||||
/////////////////////////////////////////////
|
||||
static void
|
||||
|
@ -1048,6 +1085,9 @@ static const struct {
|
|||
SHADER_SOURCE_LINE(YUY2_NOMUL, yuy2_nomul),
|
||||
SHADER_SOURCE_LINE(NV12, nv12),
|
||||
SHADER_SOURCE_LINE(NV12_NOMUL, nv12_nomul),
|
||||
|
||||
SHADER_SOURCE_LINE(RGB_A_PAIR, rgb_a_pair),
|
||||
SHADER_SOURCE_LINE(RGB_A_PAIR_NOMUL, rgb_a_pair_nomul),
|
||||
};
|
||||
|
||||
static int
|
||||
|
|
|
@ -71,6 +71,7 @@ static const struct {
|
|||
{ EINA_FALSE, EINA_TRUE, EVAS_COLORSPACE_GRY8, &lum_fmt, &lum_ifmt },
|
||||
{ EINA_TRUE, EINA_FALSE, EVAS_COLORSPACE_AGRY88, &lum_alpha_fmt, &lum_alpha_ifmt },
|
||||
{ EINA_TRUE, EINA_TRUE, EVAS_COLORSPACE_AGRY88, &lum_alpha_fmt, &lum_alpha_ifmt },
|
||||
// ETC1/2 support
|
||||
{ EINA_FALSE, EINA_FALSE, EVAS_COLORSPACE_ETC1, &etc1_fmt, &etc1_fmt },
|
||||
{ EINA_FALSE, EINA_TRUE, EVAS_COLORSPACE_ETC1, &etc1_fmt, &etc1_fmt },
|
||||
{ EINA_FALSE, EINA_FALSE, EVAS_COLORSPACE_RGB8_ETC2, &etc2_rgb_fmt, &etc2_rgb_fmt },
|
||||
|
@ -80,6 +81,8 @@ static const struct {
|
|||
// images marked as no alpha but format supports it (RGBA8_ETC2_EAC):
|
||||
{ EINA_FALSE, EINA_FALSE, EVAS_COLORSPACE_RGBA8_ETC2_EAC, &etc2_rgba_fmt, &etc2_rgba_fmt },
|
||||
{ EINA_FALSE, EINA_TRUE, EVAS_COLORSPACE_RGBA8_ETC2_EAC, &etc2_rgba_fmt, &etc2_rgba_fmt },
|
||||
{ EINA_TRUE, EINA_FALSE, EVAS_COLORSPACE_ETC1_ALPHA, &etc1_fmt, &etc1_fmt },
|
||||
{ EINA_TRUE, EINA_TRUE, EVAS_COLORSPACE_ETC1_ALPHA, &etc1_fmt, &etc1_fmt },
|
||||
// S3TC support
|
||||
{ EINA_FALSE, EINA_FALSE, EVAS_COLORSPACE_RGB_S3TC_DXT1, &s3tc_rgb_dxt1_fmt, &s3tc_rgb_dxt1_fmt },
|
||||
{ EINA_FALSE, EINA_TRUE, EVAS_COLORSPACE_RGB_S3TC_DXT1, &s3tc_rgb_dxt1_fmt, &s3tc_rgb_dxt1_fmt },
|
||||
|
@ -516,6 +519,7 @@ evas_gl_common_texture_new(Evas_Engine_GL_Context *gc, RGBA_Image *im)
|
|||
case EVAS_COLORSPACE_ETC1:
|
||||
case EVAS_COLORSPACE_RGB8_ETC2:
|
||||
case EVAS_COLORSPACE_RGBA8_ETC2_EAC:
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
case EVAS_COLORSPACE_RGB_S3TC_DXT1:
|
||||
case EVAS_COLORSPACE_RGBA_S3TC_DXT1:
|
||||
case EVAS_COLORSPACE_RGBA_S3TC_DXT2:
|
||||
|
@ -1183,6 +1187,7 @@ evas_gl_common_texture_update(Evas_GL_Texture *tex, RGBA_Image *im)
|
|||
case EVAS_COLORSPACE_RGB_S3TC_DXT1:
|
||||
case EVAS_COLORSPACE_RGBA_S3TC_DXT1:
|
||||
case EVAS_COLORSPACE_ETC1:
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
case EVAS_COLORSPACE_RGB8_ETC2:
|
||||
{
|
||||
/*
|
||||
|
@ -1205,7 +1210,8 @@ evas_gl_common_texture_update(Evas_GL_Texture *tex, RGBA_Image *im)
|
|||
GLERR(__FUNCTION__, __FILE__, __LINE__, "");
|
||||
|
||||
if ((tex->gc->shared->info.etc1_subimage ||
|
||||
(im->cache_entry.space != EVAS_COLORSPACE_ETC1))
|
||||
((im->cache_entry.space != EVAS_COLORSPACE_ETC1) &&
|
||||
(im->cache_entry.space != EVAS_COLORSPACE_ETC1_ALPHA)))
|
||||
&& (tex->pt->w != width || tex->pt->h != height))
|
||||
{
|
||||
int err;
|
||||
|
@ -1225,7 +1231,8 @@ evas_gl_common_texture_update(Evas_GL_Texture *tex, RGBA_Image *im)
|
|||
// FIXME: Changing settings on the fly.
|
||||
// The first texture will be black.
|
||||
// How to fallback? We need a whole texture now.
|
||||
if (im->cache_entry.space == EVAS_COLORSPACE_ETC1)
|
||||
if ((im->cache_entry.space == EVAS_COLORSPACE_ETC1) ||
|
||||
(im->cache_entry.space == EVAS_COLORSPACE_ETC1_ALPHA))
|
||||
tex->gc->shared->info.etc1_subimage = EINA_FALSE;
|
||||
}
|
||||
}
|
||||
|
@ -1461,6 +1468,171 @@ evas_gl_common_texture_alpha_update(Evas_GL_Texture *tex, DATA8 *pixels,
|
|||
}
|
||||
}
|
||||
|
||||
Evas_GL_Texture *
|
||||
evas_gl_common_texture_rgb_a_pair_new(Evas_Engine_GL_Context *gc,
|
||||
RGBA_Image *im)
|
||||
{
|
||||
Evas_GL_Texture *tex;
|
||||
int lformat, w, h;
|
||||
|
||||
// FIXME/TODO: We don't support texture atlasses here (a bit tricky)
|
||||
|
||||
// Some debugging. We could return.
|
||||
if (im->cache_entry.space != EVAS_COLORSPACE_ETC1_ALPHA)
|
||||
WRN("Using RGB+A texture pair with format %d", im->cache_entry.space);
|
||||
|
||||
w = im->cache_entry.w;
|
||||
h = im->cache_entry.h;
|
||||
|
||||
lformat = _evas_gl_texture_search_format(EINA_FALSE, gc->shared->info.bgra,
|
||||
im->cache_entry.space);
|
||||
if (lformat < 0) return NULL;
|
||||
|
||||
tex = evas_gl_common_texture_alloc(gc, w, h, EINA_TRUE);
|
||||
if (!tex) return NULL;
|
||||
|
||||
// Allocate RGB texture normally - as a 'whole'
|
||||
tex->pt = _pool_tex_new(gc, w, h,
|
||||
*matching_format[lformat].intformat,
|
||||
*matching_format[lformat].format);
|
||||
if (!tex->pt)
|
||||
{
|
||||
evas_gl_common_texture_light_free(tex);
|
||||
return NULL;
|
||||
}
|
||||
pt_link(gc, tex->pt);
|
||||
tex->pt->slot = -1;
|
||||
|
||||
// And now Alpha texture -- FIXME could intformat be different? (eg. ALPHA4)
|
||||
tex->pta = _pool_tex_new(gc, w, h,
|
||||
*matching_format[lformat].intformat,
|
||||
*matching_format[lformat].format);
|
||||
if (!tex->pta)
|
||||
{
|
||||
pt_unref(tex->pt);
|
||||
evas_gl_common_texture_light_free(tex);
|
||||
return NULL;
|
||||
}
|
||||
pt_link(gc, tex->pta);
|
||||
tex->pta->slot = -1;
|
||||
|
||||
evas_gl_common_texture_rgb_a_pair_update(tex, im);
|
||||
return tex;
|
||||
}
|
||||
|
||||
void
|
||||
evas_gl_common_texture_rgb_a_pair_update(Evas_GL_Texture *tex,
|
||||
RGBA_Image *im)
|
||||
{
|
||||
DATA8 *data1, *data2;
|
||||
Eina_Bool comp, upload;
|
||||
int w, h, sz, rowlen, ystep = 1;
|
||||
|
||||
if (!tex->pt) return;
|
||||
|
||||
// Handle compressed formats with 4x4 blocks format
|
||||
if (((int) im->cache_entry.space >= (int) EVAS_COLORSPACE_ETC1) &&
|
||||
((int) im->cache_entry.space <= (int) EVAS_COLORSPACE_RGBA_S3TC_DXT5))
|
||||
ystep = 4;
|
||||
|
||||
w = im->cache_entry.w + im->cache_entry.borders.l + im->cache_entry.borders.r;
|
||||
h = im->cache_entry.h + im->cache_entry.borders.t + im->cache_entry.borders.b;
|
||||
rowlen = _evas_gl_texture_size_get(w, ystep, tex->pt->intformat, NULL);
|
||||
sz = _evas_gl_texture_size_get(w, h, tex->pt->intformat, &comp);
|
||||
data1 = im->image.data8;
|
||||
data2 = data1 + sz;
|
||||
upload = !!data1;
|
||||
|
||||
if (tex->gc->shared->info.unpack_row_length)
|
||||
{
|
||||
glPixelStorei(GL_UNPACK_ROW_LENGTH, w); GLERRLOG();
|
||||
glPixelStorei(GL_UNPACK_ALIGNMENT, 1); GLERRLOG();
|
||||
glBindTexture(GL_TEXTURE_2D, tex->pt->texture); GLERRLOG();
|
||||
if (!_tex_2d(tex->gc, tex->pt->intformat, w, h, tex->pt->format, tex->pt->dataformat))
|
||||
goto on_error;
|
||||
if (upload)
|
||||
{
|
||||
if (comp)
|
||||
_comp_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, sz, data1);
|
||||
else
|
||||
_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, tex->pt->dataformat, data1);
|
||||
}
|
||||
glBindTexture(GL_TEXTURE_2D, tex->pta->texture); GLERRLOG();
|
||||
if (!_tex_2d(tex->gc, tex->pta->intformat, w, h, tex->pta->format, tex->pta->dataformat))
|
||||
goto on_error;
|
||||
if (upload)
|
||||
{
|
||||
if (comp)
|
||||
_comp_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, sz, data2);
|
||||
else
|
||||
_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, tex->pt->dataformat, data2);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
int y;
|
||||
|
||||
glPixelStorei(GL_UNPACK_ALIGNMENT, 1); GLERRLOG();
|
||||
glBindTexture(GL_TEXTURE_2D, tex->pt->texture); GLERRLOG();
|
||||
if (!_tex_2d(tex->gc, tex->pt->intformat, w, h, tex->pt->format,
|
||||
tex->pt->dataformat))
|
||||
goto on_error;
|
||||
if (upload)
|
||||
{
|
||||
if (w == tex->w)
|
||||
{
|
||||
if (comp)
|
||||
_comp_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, sz, data1);
|
||||
else
|
||||
_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, tex->pt->dataformat, data1);
|
||||
}
|
||||
else
|
||||
{
|
||||
for (y = 0; y < h; y += ystep)
|
||||
{
|
||||
if (comp)
|
||||
_comp_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, sz, data1);
|
||||
else
|
||||
_tex_sub_2d(tex->gc, 0, y, w, ystep, tex->pt->format,
|
||||
tex->pt->dataformat, data1 + rowlen * y / ystep);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
glBindTexture(GL_TEXTURE_2D, tex->pta->texture); GLERRLOG();
|
||||
if (!_tex_2d(tex->gc, tex->pta->intformat, w, h, tex->pta->format,
|
||||
tex->pta->dataformat))
|
||||
goto on_error;
|
||||
if (upload)
|
||||
{
|
||||
if (w == tex->w)
|
||||
{
|
||||
if (comp)
|
||||
_comp_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, sz, data2);
|
||||
else
|
||||
_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, tex->pt->dataformat, data2);
|
||||
}
|
||||
else
|
||||
{
|
||||
for (y = 0; y < h; y += ystep)
|
||||
{
|
||||
if (comp)
|
||||
_comp_tex_sub_2d(tex->gc, 0, 0, w, h, tex->pt->format, sz, data2);
|
||||
else
|
||||
_tex_sub_2d(tex->gc, 0, y, w, ystep, tex->pt->format,
|
||||
tex->pt->dataformat, data2 + rowlen * y / ystep);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
on_error:
|
||||
if (tex->pt->texture != tex->gc->pipe[0].shader.cur_tex)
|
||||
{
|
||||
glBindTexture(GL_TEXTURE_2D, tex->gc->pipe[0].shader.cur_tex);
|
||||
GLERRLOG();
|
||||
}
|
||||
}
|
||||
|
||||
Evas_GL_Texture *
|
||||
evas_gl_common_texture_yuv_new(Evas_Engine_GL_Context *gc, DATA8 **rows, unsigned int w, unsigned int h)
|
||||
{
|
||||
|
|
|
@ -2304,6 +2304,7 @@ eng_image_data_get(void *data, void *image, int to_write, DATA32 **image_data, i
|
|||
case EVAS_COLORSPACE_ETC1:
|
||||
case EVAS_COLORSPACE_RGB8_ETC2:
|
||||
case EVAS_COLORSPACE_RGBA8_ETC2_EAC:
|
||||
case EVAS_COLORSPACE_ETC1_ALPHA:
|
||||
ERR("This image is encoded in ETC1 or ETC2, not returning any data");
|
||||
error = EVAS_LOAD_ERROR_UNKNOWN_FORMAT;
|
||||
*image_data = NULL;
|
||||
|
|
Loading…
Reference in New Issue