diff --git a/src/celengine/glsupport.cpp b/src/celengine/glsupport.cpp index 989fcdbb2..1c85a7b39 100644 --- a/src/celengine/glsupport.cpp +++ b/src/celengine/glsupport.cpp @@ -8,6 +8,7 @@ namespace gl #ifdef GL_ES bool OES_vertex_array_object = false; +bool OES_texture_border_clamp = false; #else bool ARB_vertex_array_object = false; bool EXT_framebuffer_object = false; @@ -36,6 +37,7 @@ bool init(util::array_view ignore) noexcept { #ifdef GL_ES OES_vertex_array_object = check_extension(ignore, "GL_OES_vertex_array_object"); + OES_texture_border_clamp = check_extension(ignore, "GL_OES_texture_border_clamp") || check_extension(ignore, "GL_EXT_texture_border_clamp") ; #else ARB_vertex_array_object = check_extension(ignore, "GL_ARB_vertex_array_object"); EXT_framebuffer_object = check_extension(ignore, "GL_EXT_framebuffer_object"); diff --git a/src/celengine/glsupport.h b/src/celengine/glsupport.h index a94d118f2..1e1ecc63c 100644 --- a/src/celengine/glsupport.h +++ b/src/celengine/glsupport.h @@ -43,6 +43,7 @@ extern bool EXT_texture_filter_anisotropic; extern bool MESA_pack_invert; #ifdef GL_ES extern bool OES_vertex_array_object; +extern bool OES_texture_border_clamp; #else extern bool ARB_vertex_array_object; extern bool EXT_framebuffer_object; diff --git a/src/celengine/rendcontext.cpp b/src/celengine/rendcontext.cpp index c7294a7c8..e700f6c54 100644 --- a/src/celengine/rendcontext.cpp +++ b/src/celengine/rendcontext.cpp @@ -562,15 +562,23 @@ GLSL_RenderContext::makeCurrent(const Material& m) ringsTex->bind(); textures[nTextures++] = ringsTex; - // Tweak the texture--set clamp to border and a border color with - // a zero alpha. - float bc[4] = { 0.0f, 0.0f, 0.0f, 0.0f }; +#ifdef GL_ES + if (celestia::gl::OES_texture_border_clamp) + { +#endif + // Tweak the texture--set clamp to border and a border color with + // a zero alpha. + float bc[4] = { 0.0f, 0.0f, 0.0f, 0.0f }; #ifndef GL_ES - glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, bc); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER); + glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, bc); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER); #else - glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR_OES, bc); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER_OES); + glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR_OES, bc); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER_OES); +#endif + +#ifdef GL_ES + } #endif glActiveTexture(GL_TEXTURE0); diff --git a/src/celengine/renderglsl.cpp b/src/celengine/renderglsl.cpp index b6e5fbaed..ae86aec02 100644 --- a/src/celengine/renderglsl.cpp +++ b/src/celengine/renderglsl.cpp @@ -205,15 +205,23 @@ void renderEllipsoid_GLSL(const RenderInfo& ri, ringsTex->bind(); nTextures++; - // Tweak the texture--set clamp to border and a border color with - // a zero alpha. - float bc[4] = { 0.0f, 0.0f, 0.0f, 0.0f }; +#ifdef GL_ES + if (gl::OES_texture_border_clamp) + { +#endif + // Tweak the texture--set clamp to border and a border color with + // a zero alpha. + float bc[4] = { 0.0f, 0.0f, 0.0f, 0.0f }; #ifndef GL_ES - glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, bc); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER); + glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, bc); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER); #else - glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR_OES, bc); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER_OES); + glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR_OES, bc); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER_OES); +#endif + +#ifdef GL_ES + } #endif glActiveTexture(GL_TEXTURE0); diff --git a/src/celengine/shadermanager.cpp b/src/celengine/shadermanager.cpp index 5ab0ba2b7..be5e43a72 100644 --- a/src/celengine/shadermanager.cpp +++ b/src/celengine/shadermanager.cpp @@ -1289,10 +1289,17 @@ BeginLightSourceShadows(const ShaderProperties& props, unsigned int light) if (props.hasRingShadowForLight(light)) { + source += "float ringShadowTexCoordX;\n"; + source += assign("ringShadowTexCoordX", ringShadowTexCoord(light)); + +#ifdef GL_ES + if (!gl::OES_texture_border_clamp) + source += "if (ringShadowTexCoordX >= 0.0 && ringShadowTexCoordX <= 1.0)\n{\n"; +#endif if (gl::ARB_shader_texture_lod) { source += mulAssign("shadow", - (1.0f - texture2DLod(sampler2D("ringTex"), vec2(ringShadowTexCoord(light), 0.0f), indexedUniform("ringShadowLOD", light))["a"])); + (1.0f - texture2DLod(sampler2D("ringTex"), vec2(sh_float("ringShadowTexCoordX"), 0.0f), indexedUniform("ringShadowLOD", light))["a"])); } else { @@ -1304,8 +1311,12 @@ BeginLightSourceShadows(const ShaderProperties& props, unsigned int light) // derivative is computed from the plane equation of the triangle, which means that there // are discontinuities between triangles. source += mulAssign("shadow", - (1.0f - texture2DLodBias(sampler2D("ringTex"), vec2(ringShadowTexCoord(light), 0.0f), indexedUniform("ringShadowLOD", light))["a"])); + (1.0f - texture2DLodBias(sampler2D("ringTex"), vec2(sh_float("ringShadowTexCoordX"), 0.0f), indexedUniform("ringShadowLOD", light))["a"])); } +#ifdef GL_ES + if (!gl::OES_texture_border_clamp) + source += "}\n"; +#endif } if (props.hasCloudShadowForLight(light))