summaryrefslogtreecommitdiff
path: root/drivers/gles2
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gles2')
-rw-r--r--drivers/gles2/rasterizer_canvas_gles2.cpp8
-rw-r--r--drivers/gles2/rasterizer_scene_gles2.cpp3
-rw-r--r--drivers/gles2/rasterizer_storage_gles2.cpp48
-rw-r--r--drivers/gles2/shader_compiler_gles2.cpp23
-rw-r--r--drivers/gles2/shaders/stdlib.glsl75
5 files changed, 139 insertions, 18 deletions
diff --git a/drivers/gles2/rasterizer_canvas_gles2.cpp b/drivers/gles2/rasterizer_canvas_gles2.cpp
index 8a177e32b0..6be48a4c58 100644
--- a/drivers/gles2/rasterizer_canvas_gles2.cpp
+++ b/drivers/gles2/rasterizer_canvas_gles2.cpp
@@ -1265,14 +1265,11 @@ void RasterizerCanvasGLES2::_canvas_item_render_commands(Item *p_item, Item *cur
void RasterizerCanvasGLES2::_copy_screen(const Rect2 &p_rect) {
if (storage->frame.current_rt->flags[RasterizerStorage::RENDER_TARGET_DIRECT_TO_SCREEN]) {
- ERR_PRINT_ONCE("Cannot use screen texture copying in render target set to render direct to screen");
+ ERR_PRINT_ONCE("Cannot use screen texture copying in render target set to render direct to screen.");
return;
}
- if (storage->frame.current_rt->copy_screen_effect.color == 0) {
- ERR_EXPLAIN("Can't use screen texture copying in a render target configured without copy buffers");
- ERR_FAIL();
- }
+ ERR_FAIL_COND_MSG(storage->frame.current_rt->copy_screen_effect.color == 0, "Can't use screen texture copying in a render target configured without copy buffers.");
glDisable(GL_BLEND);
@@ -1650,6 +1647,7 @@ void RasterizerCanvasGLES2::canvas_render_items(Item *p_item_list, int p_z, cons
//always re-set uniforms, since light parameters changed
_set_uniforms();
+ state.canvas_shader.use_material((void *)material_ptr);
glActiveTexture(GL_TEXTURE0 + storage->config.max_texture_image_units - 4);
RasterizerStorageGLES2::Texture *t = storage->texture_owner.getornull(light->texture);
diff --git a/drivers/gles2/rasterizer_scene_gles2.cpp b/drivers/gles2/rasterizer_scene_gles2.cpp
index 453abeb853..cc414c26af 100644
--- a/drivers/gles2/rasterizer_scene_gles2.cpp
+++ b/drivers/gles2/rasterizer_scene_gles2.cpp
@@ -882,8 +882,7 @@ RID RasterizerSceneGLES2::light_instance_create(RID p_light) {
if (!light_instance->light_ptr) {
memdelete(light_instance);
- ERR_EXPLAIN("Condition ' !light_instance->light_ptr ' is true.");
- ERR_FAIL_V(RID());
+ ERR_FAIL_V_MSG(RID(), "Condition ' !light_instance->light_ptr ' is true.");
}
light_instance->self = light_instance_owner.make_rid(light_instance);
diff --git a/drivers/gles2/rasterizer_storage_gles2.cpp b/drivers/gles2/rasterizer_storage_gles2.cpp
index a0188da4f6..5c02d8096d 100644
--- a/drivers/gles2/rasterizer_storage_gles2.cpp
+++ b/drivers/gles2/rasterizer_storage_gles2.cpp
@@ -1570,7 +1570,7 @@ void RasterizerStorageGLES2::shader_get_param_list(RID p_shader, List<PropertyIn
if (u.hint == ShaderLanguage::ShaderNode::Uniform::HINT_RANGE) {
pi.hint = PROPERTY_HINT_RANGE;
- pi.hint_string = rtos(u.hint_range[0]) + "," + rtos(u.hint_range[1]);
+ pi.hint_string = rtos(u.hint_range[0]) + "," + rtos(u.hint_range[1]) + "," + rtos(u.hint_range[2]);
}
} break;
@@ -2171,8 +2171,7 @@ void RasterizerStorageGLES2::mesh_add_surface(RID p_mesh, uint32_t p_format, VS:
//must have index and bones, both.
{
uint32_t bones_weight = VS::ARRAY_FORMAT_BONES | VS::ARRAY_FORMAT_WEIGHTS;
- ERR_EXPLAIN("Array must have both bones and weights in format or none.");
- ERR_FAIL_COND((p_format & bones_weight) && (p_format & bones_weight) != bones_weight);
+ ERR_FAIL_COND_MSG((p_format & bones_weight) && (p_format & bones_weight) != bones_weight, "Array must have both bones and weights in format or none.");
}
//bool has_morph = p_blend_shapes.size();
@@ -3497,6 +3496,8 @@ RID RasterizerStorageGLES2::skeleton_create() {
Skeleton *skeleton = memnew(Skeleton);
+ glGenTextures(1, &skeleton->tex_id);
+
return skeleton_owner.make_rid(skeleton);
}
@@ -3514,7 +3515,6 @@ void RasterizerStorageGLES2::skeleton_allocate(RID p_skeleton, int p_bones, bool
skeleton->use_2d = p_2d_skeleton;
if (config.float_texture_supported) {
- glGenTextures(1, &skeleton->tex_id);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, skeleton->tex_id);
@@ -5691,21 +5691,49 @@ void RasterizerStorageGLES2::initialize() {
GLenum status = glCheckFramebufferStatus(GL_FRAMEBUFFER);
+ glBindFramebuffer(GL_FRAMEBUFFER, system_fbo);
+ glDeleteFramebuffers(1, &fbo);
+ glBindTexture(GL_TEXTURE_2D, 0);
+ glDeleteTextures(1, &depth);
+
if (status == GL_FRAMEBUFFER_COMPLETE) {
config.depth_internalformat = GL_DEPTH_COMPONENT;
config.depth_type = GL_UNSIGNED_INT;
} else {
+ // If it fails, test to see if it supports a framebuffer texture using UNSIGNED_SHORT
+ // This is needed because many OSX devices don't support either UNSIGNED_INT or UNSIGNED_SHORT
+
config.depth_internalformat = GL_DEPTH_COMPONENT16;
config.depth_type = GL_UNSIGNED_SHORT;
- }
- glBindFramebuffer(GL_FRAMEBUFFER, system_fbo);
- glDeleteFramebuffers(1, &fbo);
- glBindTexture(GL_TEXTURE_2D, 0);
- glDeleteTextures(1, &depth);
+ glGenFramebuffers(1, &fbo);
+ glBindFramebuffer(GL_FRAMEBUFFER, fbo);
+
+ glGenTextures(1, &depth);
+ glBindTexture(GL_TEXTURE_2D, depth);
+ glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT16, 32, 32, 0, GL_DEPTH_COMPONENT16, GL_UNSIGNED_SHORT, NULL);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
+
+ glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, depth, 0);
+
+ status = glCheckFramebufferStatus(GL_FRAMEBUFFER);
+ if (status != GL_FRAMEBUFFER_COMPLETE) {
+ //if it fails again depth textures aren't supported, use rgba shadows and renderbuffer for depth
+ config.support_depth_texture = false;
+ config.use_rgba_3d_shadows = true;
+ }
+
+ glBindFramebuffer(GL_FRAMEBUFFER, system_fbo);
+ glDeleteFramebuffers(1, &fbo);
+ glBindTexture(GL_TEXTURE_2D, 0);
+ glDeleteTextures(1, &depth);
+ }
} else {
- // Will use renderbuffer for depth
+ // Will use renderbuffer for depth, on mobile check for 24 bit depth support
if (config.extensions.has("GL_OES_depth24")) {
config.depth_internalformat = _DEPTH_COMPONENT24_OES;
config.depth_type = GL_UNSIGNED_INT;
diff --git a/drivers/gles2/shader_compiler_gles2.cpp b/drivers/gles2/shader_compiler_gles2.cpp
index 935cb32fda..640d45ae65 100644
--- a/drivers/gles2/shader_compiler_gles2.cpp
+++ b/drivers/gles2/shader_compiler_gles2.cpp
@@ -758,11 +758,13 @@ String ShaderCompilerGLES2::_dump_node_code(SL::Node *p_node, int p_level, Gener
} break;
case SL::OP_SELECT_IF: {
+ code += "(";
code += _dump_node_code(op_node->arguments[0], p_level, r_gen_code, p_actions, p_default_actions, p_assigning);
code += " ? ";
code += _dump_node_code(op_node->arguments[1], p_level, r_gen_code, p_actions, p_default_actions, p_assigning);
code += " : ";
code += _dump_node_code(op_node->arguments[2], p_level, r_gen_code, p_actions, p_default_actions, p_assigning);
+ code += ")";
} break;
case SL::OP_MOD: {
@@ -802,6 +804,23 @@ String ShaderCompilerGLES2::_dump_node_code(SL::Node *p_node, int p_level, Gener
code += "else\n";
code += _dump_node_code(cf_node->blocks[1], p_level + 1, r_gen_code, p_actions, p_default_actions, p_assigning);
}
+ } else if (cf_node->flow_op == SL::FLOW_OP_SWITCH) {
+ code += _mktab(p_level) + "switch (" + _dump_node_code(cf_node->expressions[0], p_level, r_gen_code, p_actions, p_default_actions, p_assigning) + ")\n";
+ code += _dump_node_code(cf_node->blocks[0], p_level + 1, r_gen_code, p_actions, p_default_actions, p_assigning);
+ } else if (cf_node->flow_op == SL::FLOW_OP_CASE) {
+ code += _mktab(p_level) + "case " + _dump_node_code(cf_node->expressions[0], p_level, r_gen_code, p_actions, p_default_actions, p_assigning) + ":\n";
+ code += _dump_node_code(cf_node->blocks[0], p_level + 1, r_gen_code, p_actions, p_default_actions, p_assigning);
+ } else if (cf_node->flow_op == SL::FLOW_OP_DEFAULT) {
+ code += _mktab(p_level) + "default:\n";
+ code += _dump_node_code(cf_node->blocks[0], p_level + 1, r_gen_code, p_actions, p_default_actions, p_assigning);
+ } else if (cf_node->flow_op == SL::FLOW_OP_DO) {
+ code += _mktab(p_level);
+ code += "do";
+ code += _dump_node_code(cf_node->blocks[0], p_level + 1, r_gen_code, p_actions, p_default_actions, p_assigning);
+ code += _mktab(p_level);
+ code += "while (";
+ code += _dump_node_code(cf_node->expressions[0], p_level, r_gen_code, p_actions, p_default_actions, p_assigning);
+ code += ");";
} else if (cf_node->flow_op == SL::FLOW_OP_WHILE) {
code += _mktab(p_level);
code += "while (";
@@ -900,7 +919,7 @@ ShaderCompilerGLES2::ShaderCompilerGLES2() {
actions[VS::SHADER_CANVAS_ITEM].renames["WORLD_MATRIX"] = "modelview_matrix";
actions[VS::SHADER_CANVAS_ITEM].renames["PROJECTION_MATRIX"] = "projection_matrix";
- actions[VS::SHADER_CANVAS_ITEM].renames["EXTRA_MATRIX"] = "extra_matrix";
+ actions[VS::SHADER_CANVAS_ITEM].renames["EXTRA_MATRIX"] = "extra_matrix_instance";
actions[VS::SHADER_CANVAS_ITEM].renames["TIME"] = "time";
actions[VS::SHADER_CANVAS_ITEM].renames["AT_LIGHT_PASS"] = "at_light_pass";
actions[VS::SHADER_CANVAS_ITEM].renames["INSTANCE_CUSTOM"] = "instance_custom";
@@ -947,6 +966,7 @@ ShaderCompilerGLES2::ShaderCompilerGLES2() {
actions[VS::SHADER_CANVAS_ITEM].usage_defines["outerProduct"] = "#define OUTER_PRODUCT_USED\n";
actions[VS::SHADER_CANVAS_ITEM].usage_defines["round"] = "#define ROUND_USED\n";
actions[VS::SHADER_CANVAS_ITEM].usage_defines["roundEven"] = "#define ROUND_EVEN_USED\n";
+ actions[VS::SHADER_CANVAS_ITEM].usage_defines["inverse"] = "#define INVERSE_USED\n";
actions[VS::SHADER_CANVAS_ITEM].usage_defines["isinf"] = "#define IS_INF_USED\n";
actions[VS::SHADER_CANVAS_ITEM].usage_defines["isnan"] = "#define IS_NAN_USED\n";
actions[VS::SHADER_CANVAS_ITEM].usage_defines["trunc"] = "#define TRUNC_USED\n";
@@ -1056,6 +1076,7 @@ ShaderCompilerGLES2::ShaderCompilerGLES2() {
actions[VS::SHADER_SPATIAL].usage_defines["outerProduct"] = "#define OUTER_PRODUCT_USED\n";
actions[VS::SHADER_SPATIAL].usage_defines["round"] = "#define ROUND_USED\n";
actions[VS::SHADER_SPATIAL].usage_defines["roundEven"] = "#define ROUND_EVEN_USED\n";
+ actions[VS::SHADER_SPATIAL].usage_defines["inverse"] = "#define INVERSE_USED\n";
actions[VS::SHADER_SPATIAL].usage_defines["isinf"] = "#define IS_INF_USED\n";
actions[VS::SHADER_SPATIAL].usage_defines["isnan"] = "#define IS_NAN_USED\n";
actions[VS::SHADER_SPATIAL].usage_defines["trunc"] = "#define TRUNC_USED\n";
diff --git a/drivers/gles2/shaders/stdlib.glsl b/drivers/gles2/shaders/stdlib.glsl
index 96421fcb4a..9c74418743 100644
--- a/drivers/gles2/shaders/stdlib.glsl
+++ b/drivers/gles2/shaders/stdlib.glsl
@@ -299,6 +299,81 @@ highp float determinant(highp mat4 m) {
#endif
+#if defined(INVERSE_USED)
+
+highp mat2 inverse(highp mat2 m) {
+ highp float d = 1.0 / (m[0].x * m[1].y - m[1].x * m[0].y);
+ return mat2(
+ vec2(m[1].y * d, -m[0].y * d),
+ vec2(-m[1].x * d, m[0].x * d));
+}
+
+highp mat3 inverse(highp mat3 m) {
+ highp float d = 1.0 / (m[0].x * (m[1].y * m[2].z - m[2].y * m[1].z) - m[1].x * (m[0].y * m[2].z - m[2].y * m[0].z) + m[2].x * (m[0].y * m[1].z - m[1].y * m[0].z));
+ return mat3(
+ vec3((m[1].y * m[2].z - m[2].y * m[1].z), -(m[1].x * m[2].z - m[2].x * m[1].z), (m[1].x * m[2].y - m[2].x * m[1].y)) * d,
+ vec3(-(m[0].y * m[2].z - m[2].y * m[0].z), (m[0].x * m[2].z - m[2].x * m[0].z), -(m[0].x * m[2].y - m[2].x * m[0].y)) * d,
+ vec3((m[0].y * m[1].z - m[1].y * m[0].z), -(m[0].x * m[1].z - m[1].x * m[0].z), (m[0].x * m[1].y - m[1].x * m[0].y)) * d);
+}
+
+highp mat4 inverse(highp mat4 m) {
+ highp float c00 = m[2].z * m[3].w - m[3].z * m[2].w;
+ highp float c02 = m[1].z * m[3].w - m[3].z * m[1].w;
+ highp float c03 = m[1].z * m[2].w - m[2].z * m[1].w;
+
+ highp float c04 = m[2].y * m[3].w - m[3].y * m[2].w;
+ highp float c06 = m[1].y * m[3].w - m[3].y * m[1].w;
+ highp float c07 = m[1].y * m[2].w - m[2].y * m[1].w;
+
+ highp float c08 = m[2].y * m[3].z - m[3].y * m[2].z;
+ highp float c10 = m[1].y * m[3].z - m[3].y * m[1].z;
+ highp float c11 = m[1].y * m[2].z - m[2].y * m[1].z;
+
+ highp float c12 = m[2].x * m[3].w - m[3].x * m[2].w;
+ highp float c14 = m[1].x * m[3].w - m[3].x * m[1].w;
+ highp float c15 = m[1].x * m[2].w - m[2].x * m[1].w;
+
+ highp float c16 = m[2].x * m[3].z - m[3].x * m[2].z;
+ highp float c18 = m[1].x * m[3].z - m[3].x * m[1].z;
+ highp float c19 = m[1].x * m[2].z - m[2].x * m[1].z;
+
+ highp float c20 = m[2].x * m[3].y - m[3].x * m[2].y;
+ highp float c22 = m[1].x * m[3].y - m[3].x * m[1].y;
+ highp float c23 = m[1].x * m[2].y - m[2].x * m[1].y;
+
+ vec4 f0 = vec4(c00, c00, c02, c03);
+ vec4 f1 = vec4(c04, c04, c06, c07);
+ vec4 f2 = vec4(c08, c08, c10, c11);
+ vec4 f3 = vec4(c12, c12, c14, c15);
+ vec4 f4 = vec4(c16, c16, c18, c19);
+ vec4 f5 = vec4(c20, c20, c22, c23);
+
+ vec4 v0 = vec4(m[1].x, m[0].x, m[0].x, m[0].x);
+ vec4 v1 = vec4(m[1].y, m[0].y, m[0].y, m[0].y);
+ vec4 v2 = vec4(m[1].z, m[0].z, m[0].z, m[0].z);
+ vec4 v3 = vec4(m[1].w, m[0].w, m[0].w, m[0].w);
+
+ vec4 inv0 = vec4(v1 * f0 - v2 * f1 + v3 * f2);
+ vec4 inv1 = vec4(v0 * f0 - v2 * f3 + v3 * f4);
+ vec4 inv2 = vec4(v0 * f1 - v1 * f3 + v3 * f5);
+ vec4 inv3 = vec4(v0 * f2 - v1 * f4 + v2 * f5);
+
+ vec4 sa = vec4(+1, -1, +1, -1);
+ vec4 sb = vec4(-1, +1, -1, +1);
+
+ mat4 inv = mat4(inv0 * sa, inv1 * sb, inv2 * sa, inv3 * sb);
+
+ vec4 r0 = vec4(inv[0].x, inv[1].x, inv[2].x, inv[3].x);
+ vec4 d0 = vec4(m[0] * r0);
+
+ highp float d1 = (d0.x + d0.y) + (d0.z + d0.w);
+ highp float d = 1.0 / d1;
+
+ return inv * d;
+}
+
+#endif
+
#ifndef USE_GLES_OVER_GL
#if defined(TRANSPOSE_USED)