feat(gltf): use alternate blending mode for glTF views (#9115)

This commit is contained in:
Matt
2025-10-30 17:33:24 -04:00
committed by GitHub
parent d82de1ef38
commit e6bd7fcd9b
5 changed files with 47 additions and 24 deletions
+8 -3
View File
@@ -626,7 +626,12 @@ static unsigned int create_texture(int32_t w, int32_t h, const void * data)
#if 0
GL_CALL(glGenerateMipmap(GL_TEXTURE_2D));
GL_CALL(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 20));
GL_CALL(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST_MIPMAP_NEAREST));
GL_CALL(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR));
/* GL_CALL(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST_MIPMAP_NEAREST));
* Alternatively, the above form can be used in some cases for slightly faster performance, but
* visual quality when using image scales that are not exactly 1:1 (or 2:1 or some other increment)
* will be not as good.
*/
#endif
GL_CALL(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST));
@@ -658,8 +663,8 @@ static void lv_draw_opengles_3d(lv_draw_task_t * t, const lv_draw_3d_dsc_t * dsc
lv_area_t clip_area = t->clip_area;
lv_area_move(&clip_area, -dest_layer->buf_area.x1, -dest_layer->buf_area.y1);
lv_opengles_render_texture(dsc->tex_id, coords, dsc->opa, targ_tex_w, targ_tex_h, &clip_area, dsc->h_flip,
!dsc->v_flip);
lv_opengles_render(dsc->tex_id, coords, dsc->opa, targ_tex_w, targ_tex_h, &clip_area, dsc->h_flip, !dsc->v_flip,
lv_color_black(), true);
if(target_texture) {
GL_CALL(glBindFramebuffer(GL_FRAMEBUFFER, 0));
@@ -100,7 +100,7 @@ static const char *src_fragment_shader_v100 = R"(
}
if (abs(u_ColorDepth - 8.0) < 0.1) {
float gray = texColor.r;
gl_FragColor = vec4(gray, gray, gray, u_Opa);
gl_FragColor = vec4(vec3(gray * u_Opa), u_Opa);
} else {
float combinedAlpha = texColor.a * u_Opa;
gl_FragColor = vec4(texColor.rgb * combinedAlpha, combinedAlpha);
@@ -203,12 +203,16 @@ static const char *src_fragment_shader_v300es = R"(
if (u_IsFill) {
texColor = vec4(u_FillColor, 1.0);
} else {
//texColor = texture(u_Texture, v_TexCoord);
texColor = textureLod(u_Texture, v_TexCoord, 0.0); // If the vertices have been transformed, and mipmaps have not been generated, some rotation angles (notably 90 and 270) require using textureLod() to mitigate derivative calculation errors from increments flipping direction
texColor = texture(u_Texture, v_TexCoord);
/* If the vertices have been transformed, and mipmaps have not been generated,
* some rotation angles (notably 90 and 270) require using textureLod() to mitigate
* derivative calculation errors from interpolator increments flipping direction.
* texColor = textureLod(u_Texture, v_TexCoord, u_LodLevel);
*/
}
if (abs(u_ColorDepth - 8.0) < 0.1) {
float gray = texColor.r;
color = vec4(gray, gray, gray, u_Opa);
color = vec4(vec3(gray * u_Opa), u_Opa);
} else {
float combinedAlpha = texColor.a * u_Opa;
color = vec4(texColor.rgb * combinedAlpha, combinedAlpha);
+23 -16
View File
@@ -33,10 +33,9 @@
/**********************
* STATIC PROTOTYPES
**********************/
static void lv_opengles_render_internal(unsigned int texture, const lv_area_t * texture_area, lv_opa_t opa,
int32_t disp_w, int32_t disp_h, const lv_area_t * texture_clip_area,
bool h_flip, bool v_flip, lv_color_t fill_color);
static void lv_opengles_enable_blending(void);
static void lv_opengles_enable_blending(bool blend_opt);
static void lv_opengles_disable_blending(void);
static void lv_opengles_vertex_buffer_init(const void * data, unsigned int size);
static void lv_opengles_vertex_buffer_deinit(void);
static void lv_opengles_vertex_buffer_bind(void);
@@ -102,7 +101,7 @@ void lv_opengles_init(void)
{
if(is_init) return;
lv_opengles_enable_blending();
lv_opengles_enable_blending(false);
unsigned int indices[] = {
0, 1, 2,
@@ -146,15 +145,15 @@ void lv_opengles_render_texture(unsigned int texture, const lv_area_t * texture_
int32_t disp_h, const lv_area_t * texture_clip_area, bool h_flip, bool v_flip)
{
LV_PROFILER_DRAW_BEGIN;
lv_opengles_render_internal(texture, texture_area, opa, disp_w, disp_h, texture_clip_area, h_flip, v_flip,
lv_color_black());
lv_opengles_render(texture, texture_area, opa, disp_w, disp_h, texture_clip_area, h_flip, v_flip,
lv_color_black(), false);
LV_PROFILER_DRAW_END;
}
void lv_opengles_render_fill(lv_color_t color, const lv_area_t * area, lv_opa_t opa, int32_t disp_w, int32_t disp_h)
{
LV_PROFILER_DRAW_BEGIN;
lv_opengles_render_internal(0, area, opa, disp_w, disp_h, area, false, false, color);
lv_opengles_render(0, area, opa, disp_w, disp_h, area, false, false, color, false);
LV_PROFILER_DRAW_END;
}
@@ -210,12 +209,9 @@ void lv_opengles_viewport(int32_t x, int32_t y, int32_t w, int32_t h)
LV_PROFILER_DRAW_END;
}
/**********************
* STATIC FUNCTIONS
**********************/
static void lv_opengles_render_internal(unsigned int texture, const lv_area_t * texture_area, lv_opa_t opa,
int32_t disp_w, int32_t disp_h, const lv_area_t * texture_clip_area, bool h_flip, bool v_flip, lv_color_t fill_color)
void lv_opengles_render(unsigned int texture, const lv_area_t * texture_area, lv_opa_t opa,
int32_t disp_w, int32_t disp_h, const lv_area_t * texture_clip_area,
bool h_flip, bool v_flip, lv_color_t fill_color, bool blend_opt)
{
LV_PROFILER_DRAW_BEGIN;
lv_area_t intersection;
@@ -263,6 +259,7 @@ static void lv_opengles_render_internal(unsigned int texture, const lv_area_t *
};
lv_opengles_shader_bind();
lv_opengles_enable_blending(blend_opt);
lv_opengles_shader_set_uniform1f("u_ColorDepth", LV_COLOR_DEPTH);
lv_opengles_shader_set_uniform1i("u_Texture", 0);
lv_opengles_shader_set_uniformmatrix3fv("u_VertexTransform", 1, transposed_matrix);
@@ -271,13 +268,23 @@ static void lv_opengles_render_internal(unsigned int texture, const lv_area_t *
lv_opengles_shader_set_uniform3f("u_FillColor", (float)fill_color.red / 255.0f, (float)fill_color.green / 255.0f,
(float)fill_color.blue / 255.0f);
lv_opengles_render_draw();
lv_opengles_disable_blending();
LV_PROFILER_DRAW_END;
}
static void lv_opengles_enable_blending(void)
/**********************
* STATIC FUNCTIONS
**********************/
static void lv_opengles_enable_blending(bool blend_opt)
{
GL_CALL(glEnable(GL_BLEND));
GL_CALL(glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA));
GL_CALL(glBlendFunc(blend_opt ? GL_SRC_ALPHA : GL_ONE, GL_ONE_MINUS_SRC_ALPHA));
}
static void lv_opengles_disable_blending(void)
{
GL_CALL(glDisable(GL_BLEND));
}
static void lv_opengles_vertex_buffer_init(const void * data, unsigned int size)
+1 -1
View File
@@ -45,7 +45,7 @@ void lv_opengles_init(void);
void lv_opengles_deinit(void);
/**
* Render a texture
* Render a texture using alternate blending mode for smoother translucent materials and correct anti-aliasing of glTF elements when using transparent background
* @param texture OpenGL texture ID
* @param texture_area the area in the window to render the texture in
* @param opa opacity to blend the texture with existing contents
@@ -17,6 +17,9 @@ extern "C" {
#include "../../lv_conf_internal.h"
#if LV_USE_OPENGLES
#include "../../misc/lv_area.h"
#include "../../misc/lv_color.h"
#if LV_USE_EGL
#include "glad/include/glad/gles2.h"
#include "glad/include/glad/egl.h"
@@ -100,6 +103,10 @@ extern "C" {
* GLOBAL PROTOTYPES
**********************/
void lv_opengles_render(unsigned int texture, const lv_area_t * texture_area, lv_opa_t opa,
int32_t disp_w, int32_t disp_h, const lv_area_t * texture_clip_area,
bool h_flip, bool v_flip, lv_color_t fill_color, bool blend_opt);
/**********************
* MACROS
**********************/