diff options
Diffstat (limited to 'drivers/gles2/rasterizer_storage_gles2.cpp')
-rw-r--r-- | drivers/gles2/rasterizer_storage_gles2.cpp | 529 |
1 files changed, 347 insertions, 182 deletions
diff --git a/drivers/gles2/rasterizer_storage_gles2.cpp b/drivers/gles2/rasterizer_storage_gles2.cpp index 82cb1ef90b..55b1c7e560 100644 --- a/drivers/gles2/rasterizer_storage_gles2.cpp +++ b/drivers/gles2/rasterizer_storage_gles2.cpp @@ -5,8 +5,8 @@ /* GODOT ENGINE */ /* https://godotengine.org */ /*************************************************************************/ -/* Copyright (c) 2007-2019 Juan Linietsky, Ariel Manzur. */ -/* Copyright (c) 2014-2019 Godot Engine contributors (cf. AUTHORS.md) */ +/* Copyright (c) 2007-2020 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2020 Godot Engine contributors (cf. AUTHORS.md). */ /* */ /* Permission is hereby granted, free of charge, to any person obtaining */ /* a copy of this software and associated documentation files (the */ @@ -85,7 +85,9 @@ GLuint RasterizerStorageGLES2::system_fbo = 0; #define glClearDepth glClearDepthf // enable extensions manually for android and ios +#ifndef UWP_ENABLED #include <dlfcn.h> // needed to load extensions +#endif #ifdef IPHONE_ENABLED @@ -93,18 +95,36 @@ GLuint RasterizerStorageGLES2::system_fbo = 0; //void *glRenderbufferStorageMultisampleAPPLE; //void *glResolveMultisampleFramebufferAPPLE; #define glRenderbufferStorageMultisample glRenderbufferStorageMultisampleAPPLE -#elif ANDROID_ENABLED +#elif defined(ANDROID_ENABLED) #include <GLES2/gl2ext.h> PFNGLRENDERBUFFERSTORAGEMULTISAMPLEEXTPROC glRenderbufferStorageMultisampleEXT; PFNGLFRAMEBUFFERTEXTURE2DMULTISAMPLEEXTPROC glFramebufferTexture2DMultisampleEXT; #define glRenderbufferStorageMultisample glRenderbufferStorageMultisampleEXT #define glFramebufferTexture2DMultisample glFramebufferTexture2DMultisampleEXT + +PFNGLTEXIMAGE3DOESPROC glTexImage3DOES; +PFNGLTEXSUBIMAGE3DOESPROC glTexSubImage3DOES; +PFNGLCOMPRESSEDTEXSUBIMAGE3DOESPROC glCompressedTexSubImage3DOES; +#define glTexImage3D glTexImage3DOES +#define glTexSubImage3D glTexSubImage3DOES +#define glCompressedTexSubImage3D glCompressedTexSubImage3DOES + +#elif defined(UWP_ENABLED) +#include <GLES2/gl2ext.h> +#define glRenderbufferStorageMultisample glRenderbufferStorageMultisampleANGLE +#define glFramebufferTexture2DMultisample glFramebufferTexture2DMultisampleANGLE #endif +#define GL_TEXTURE_3D 0x806F #define GL_MAX_SAMPLES 0x8D57 #endif //!GLES_OVER_GL +#if !defined(GLES_OVER_GL) +#define GL_TEXTURE_2D_ARRAY 0x8C1A +#define GL_TEXTURE_3D 0x806F +#endif + void RasterizerStorageGLES2::bind_quad_array() const { glBindBuffer(GL_ARRAY_BUFFER, resources.quadie); glVertexAttribPointer(VS::ARRAY_VERTEX, 2, GL_FLOAT, GL_FALSE, sizeof(float) * 4, 0); @@ -174,7 +194,7 @@ Ref<Image> RasterizerStorageGLES2::_get_gl_image_and_format(const Ref<Image> &p_ r_gl_type = GL_UNSIGNED_SHORT_4_4_4_4; } break; - case Image::FORMAT_RGBA5551: { + case Image::FORMAT_RGB565: { r_gl_internal_format = GL_RGB5_A1; r_gl_format = GL_RGBA; @@ -559,10 +579,22 @@ void RasterizerStorageGLES2::texture_allocate(RID p_texture, int p_width, int p_ texture->images.resize(6); } break; case VS::TEXTURE_TYPE_2D_ARRAY: { - texture->images.resize(p_depth_3d); + if (config.texture_array_supported) { + texture->target = GL_TEXTURE_2D_ARRAY; + texture->images.resize(p_depth_3d); + } else { + WARN_PRINT_ONCE("Texture Arrays not supported on this hardware."); + return; + } } break; case VS::TEXTURE_TYPE_3D: { - texture->images.resize(p_depth_3d); + if (config.texture_3d_supported) { + texture->target = GL_TEXTURE_3D; + texture->images.resize(p_depth_3d); + } else { + WARN_PRINT_ONCE("3D textures not supported on this hardware."); + return; + } } break; default: { ERR_PRINT("Unknown texture type!"); @@ -583,7 +615,7 @@ void RasterizerStorageGLES2::texture_allocate(RID p_texture, int p_width, int p_ if (p_flags & VS::TEXTURE_FLAG_USED_FOR_STREAMING) { //not supported - ERR_PRINTS("Streaming texture for non power of 2 or has mipmaps on this hardware: " + texture->path + "'. Mipmaps and repeat disabled."); + ERR_PRINT("Streaming texture for non power of 2 or has mipmaps on this hardware: " + texture->path + "'. Mipmaps and repeat disabled."); texture->flags &= ~(VS::TEXTURE_FLAG_REPEAT | VS::TEXTURE_FLAG_MIPMAPS); } else { texture->alloc_height = po2_height; @@ -607,7 +639,42 @@ void RasterizerStorageGLES2::texture_allocate(RID p_texture, int p_width, int p_ glActiveTexture(GL_TEXTURE0); glBindTexture(texture->target, texture->tex_id); - if (p_flags & VS::TEXTURE_FLAG_USED_FOR_STREAMING) { +#if defined(GLES_OVER_GL) || defined(ANDROID_ENABLED) + if ((p_type == VS::TEXTURE_TYPE_3D && config.texture_3d_supported) || (p_type == VS::TEXTURE_TYPE_2D_ARRAY && config.texture_array_supported)) { + + int width = p_width; + int height = p_height; + int depth = p_depth_3d; + + int mipmaps = 0; + + while (width > 0 || height > 0 || (p_type == VS::TEXTURE_TYPE_3D && depth > 0)) { + width = MAX(1, width); + height = MAX(1, height); + depth = MAX(1, depth); + + glTexImage3D(texture->target, mipmaps, internal_format, width, height, depth, 0, format, type, NULL); + + width /= 2; + height /= 2; + + if (p_type == VS::TEXTURE_TYPE_3D) { + depth /= 2; + } + + mipmaps++; + + if (!(p_flags & VS::TEXTURE_FLAG_MIPMAPS)) + break; + } +#ifdef GLES_OVER_GL + glTexParameteri(texture->target, GL_TEXTURE_BASE_LEVEL, 0); + glTexParameteri(texture->target, GL_TEXTURE_MAX_LEVEL, mipmaps - 1); +#endif + + } else +#endif + if (p_flags & VS::TEXTURE_FLAG_USED_FOR_STREAMING) { //prealloc if video glTexImage2D(texture->target, 0, internal_format, texture->alloc_width, texture->alloc_height, 0, format, type, NULL); } @@ -619,6 +686,9 @@ void RasterizerStorageGLES2::texture_set_data(RID p_texture, const Ref<Image> &p Texture *texture = texture_owner.getornull(p_texture); ERR_FAIL_COND(!texture); + if ((texture->type == VS::TEXTURE_TYPE_2D_ARRAY && !config.texture_array_supported) || (texture->type == VS::TEXTURE_TYPE_3D && !config.texture_3d_supported)) { + return; + } ERR_FAIL_COND(!texture->active); ERR_FAIL_COND(texture->render_target); ERR_FAIL_COND(texture->format != p_image->get_format()); @@ -638,7 +708,7 @@ void RasterizerStorageGLES2::texture_set_data(RID p_texture, const Ref<Image> &p if (texture->resize_to_po2) { if (p_image->is_compressed()) { - ERR_PRINTS("Texture '" + texture->path + "' is required to be a power of 2 because it uses either mipmaps or repeat, so it was decompressed. This will hurt performance and memory usage."); + ERR_PRINT("Texture '" + texture->path + "' is required to be a power of 2 because it uses either mipmaps or repeat, so it was decompressed. This will hurt performance and memory usage."); } if (img == p_image) { @@ -661,10 +731,26 @@ void RasterizerStorageGLES2::texture_set_data(RID p_texture, const Ref<Image> &p } } - GLenum blit_target = (texture->target == GL_TEXTURE_CUBE_MAP) ? _cube_side_enum[p_layer] : GL_TEXTURE_2D; + GLenum blit_target = GL_TEXTURE_2D; + + switch (texture->type) { + case VS::TEXTURE_TYPE_2D: { + blit_target = GL_TEXTURE_2D; + } break; + case VS::TEXTURE_TYPE_CUBEMAP: { + ERR_FAIL_INDEX(p_layer, 6); + blit_target = _cube_side_enum[p_layer]; + } break; + case VS::TEXTURE_TYPE_2D_ARRAY: { + blit_target = GL_TEXTURE_2D_ARRAY; + } break; + case VS::TEXTURE_TYPE_3D: { + blit_target = GL_TEXTURE_3D; + } break; + } texture->data_size = img->get_data().size(); - PoolVector<uint8_t>::Read read = img->get_data().read(); + const uint8_t *read = img->get_data().ptr(); ERR_FAIL_COND(!read.ptr()); glActiveTexture(GL_TEXTURE0); @@ -718,23 +804,41 @@ void RasterizerStorageGLES2::texture_set_data(RID p_texture, const Ref<Image> &p int size, ofs; img->get_mipmap_offset_and_size(i, ofs, size); + if (texture->type == VS::TEXTURE_TYPE_2D || texture->type == VS::TEXTURE_TYPE_CUBEMAP) { - if (compressed) { - glPixelStorei(GL_UNPACK_ALIGNMENT, 4); + if (compressed) { + glPixelStorei(GL_UNPACK_ALIGNMENT, 4); - int bw = w; - int bh = h; + int bw = w; + int bh = h; - glCompressedTexImage2D(blit_target, i, internal_format, bw, bh, 0, size, &read[ofs]); - } else { + glCompressedTexImage2D(blit_target, i, internal_format, bw, bh, 0, size, &read[ofs]); + } else { - glPixelStorei(GL_UNPACK_ALIGNMENT, 1); - if (texture->flags & VS::TEXTURE_FLAG_USED_FOR_STREAMING) { - glTexSubImage2D(blit_target, i, 0, 0, w, h, format, type, &read[ofs]); + glPixelStorei(GL_UNPACK_ALIGNMENT, 1); + if (texture->flags & VS::TEXTURE_FLAG_USED_FOR_STREAMING) { + glTexSubImage2D(blit_target, i, 0, 0, w, h, format, type, &read[ofs]); + } else { + glTexImage2D(blit_target, i, internal_format, w, h, 0, format, type, &read[ofs]); + } + } + } +#if defined(GLES_OVER_GL) || defined(ANDROID_ENABLED) + else { + if (texture->compressed) { + glPixelStorei(GL_UNPACK_ALIGNMENT, 4); + + int bw = w; + int bh = h; + + glCompressedTexSubImage3D(blit_target, i, 0, 0, p_layer, bw, bh, 1, internal_format, size, &read[ofs]); } else { - glTexImage2D(blit_target, i, internal_format, w, h, 0, format, type, &read[ofs]); + glPixelStorei(GL_UNPACK_ALIGNMENT, 1); + + glTexSubImage3D(blit_target, i, 0, 0, p_layer, w, h, 1, format, type, &read[ofs]); } } +#endif tsize += size; @@ -784,12 +888,12 @@ Ref<Image> RasterizerStorageGLES2::texture_get_data(RID p_texture, int p_layer) bool compressed; _get_gl_image_and_format(Ref<Image>(), texture->format, texture->flags, real_format, gl_format, gl_internal_format, gl_type, compressed, false); - PoolVector<uint8_t> data; + Vector<uint8_t> data; int data_size = Image::get_image_data_size(texture->alloc_width, texture->alloc_height, real_format, texture->mipmaps > 1); data.resize(data_size * 2); //add some memory at the end, just in case for buggy drivers - PoolVector<uint8_t>::Write wb = data.write(); + uint8_t *wb = data.ptrw(); glActiveTexture(GL_TEXTURE0); @@ -826,12 +930,12 @@ Ref<Image> RasterizerStorageGLES2::texture_get_data(RID p_texture, int p_layer) bool compressed; _get_gl_image_and_format(Ref<Image>(), texture->format, texture->flags, real_format, gl_format, gl_internal_format, gl_type, compressed, texture->resize_to_po2); - PoolVector<uint8_t> data; + Vector<uint8_t> data; int data_size = Image::get_image_data_size(texture->alloc_width, texture->alloc_height, Image::FORMAT_RGBA8, false); data.resize(data_size * 2); //add some memory at the end, just in case for buggy drivers - PoolVector<uint8_t>::Write wb = data.write(); + uint8_t *wb = data.ptrw(); GLuint temp_framebuffer; glGenFramebuffers(1, &temp_framebuffer); @@ -1080,7 +1184,7 @@ void RasterizerStorageGLES2::texture_set_proxy(RID p_texture, RID p_proxy) { } if (p_proxy.is_valid()) { - Texture *proxy = texture_owner.get(p_proxy); + Texture *proxy = texture_owner.getornull(p_proxy); ERR_FAIL_COND(!proxy); ERR_FAIL_COND(proxy == texture); proxy->proxy_owners.insert(texture); @@ -1097,7 +1201,7 @@ void RasterizerStorageGLES2::texture_set_force_redraw_if_visible(RID p_texture, } void RasterizerStorageGLES2::texture_set_detect_3d_callback(RID p_texture, VisualServer::TextureDetectCallback p_callback, void *p_userdata) { - Texture *texture = texture_owner.get(p_texture); + Texture *texture = texture_owner.getornull(p_texture); ERR_FAIL_COND(!texture); texture->detect_3d = p_callback; @@ -1105,7 +1209,7 @@ void RasterizerStorageGLES2::texture_set_detect_3d_callback(RID p_texture, Visua } void RasterizerStorageGLES2::texture_set_detect_srgb_callback(RID p_texture, VisualServer::TextureDetectCallback p_callback, void *p_userdata) { - Texture *texture = texture_owner.get(p_texture); + Texture *texture = texture_owner.getornull(p_texture); ERR_FAIL_COND(!texture); texture->detect_srgb = p_callback; @@ -1113,7 +1217,7 @@ void RasterizerStorageGLES2::texture_set_detect_srgb_callback(RID p_texture, Vis } void RasterizerStorageGLES2::texture_set_detect_normal_callback(RID p_texture, VisualServer::TextureDetectCallback p_callback, void *p_userdata) { - Texture *texture = texture_owner.get(p_texture); + Texture *texture = texture_owner.getornull(p_texture); ERR_FAIL_COND(!texture); texture->detect_normal = p_callback; @@ -1194,32 +1298,21 @@ void RasterizerStorageGLES2::sky_set_texture(RID p_sky, RID p_panorama, int p_ra GLenum type = GL_UNSIGNED_BYTE; // Set the initial (empty) mipmaps -#if 1 - //Mobile hardware (PowerVR specially) prefers this approach, the other one kills the game + // Mobile hardware (PowerVR specially) prefers this approach, + // the previous approach with manual lod levels kills the game. for (int i = 0; i < 6; i++) { glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, internal_format, size, size, 0, format, type, NULL); } glGenerateMipmap(GL_TEXTURE_CUBE_MAP); - //no filters for now + + // No filters for now glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); -#else - while (size >= 1) { - - for (int i = 0; i < 6; i++) { - glTexImage2D(_cube_side_enum[i], lod, internal_format, size, size, 0, format, type, NULL); - } - - lod++; - - size >>= 1; - } -#endif - //framebuffer + // Framebuffer glBindFramebuffer(GL_FRAMEBUFFER, resources.mipmap_blur_fbo); @@ -1363,7 +1456,7 @@ void RasterizerStorageGLES2::shader_set_code(RID p_shader, const String &p_code) String RasterizerStorageGLES2::shader_get_code(RID p_shader) const { - const Shader *shader = shader_owner.get(p_shader); + const Shader *shader = shader_owner.getornull(p_shader); ERR_FAIL_COND_V(!shader, ""); return shader->code; @@ -1491,6 +1584,7 @@ void RasterizerStorageGLES2::_update_shader(Shader *p_shader) const { p_shader->texture_count = gen_code.texture_uniforms.size(); p_shader->texture_hints = gen_code.texture_hints; + p_shader->texture_types = gen_code.texture_types; p_shader->uses_vertex_time = gen_code.uses_vertex_time; p_shader->uses_fragment_time = gen_code.uses_fragment_time; @@ -1516,7 +1610,7 @@ void RasterizerStorageGLES2::update_dirty_shaders() { void RasterizerStorageGLES2::shader_get_param_list(RID p_shader, List<PropertyInfo> *p_param_list) const { - Shader *shader = shader_owner.get(p_shader); + Shader *shader = shader_owner.getornull(p_shader); ERR_FAIL_COND(!shader); if (shader->dirty_list.in_list()) { @@ -1542,6 +1636,9 @@ void RasterizerStorageGLES2::shader_get_param_list(RID p_shader, List<PropertyIn pi.name = E->get(); switch (u.type) { + case ShaderLanguage::TYPE_STRUCT: { + pi.type = Variant::ARRAY; + } break; case ShaderLanguage::TYPE_VOID: { pi.type = Variant::NIL; } break; @@ -1584,11 +1681,11 @@ void RasterizerStorageGLES2::shader_get_param_list(RID p_shader, List<PropertyIn case ShaderLanguage::TYPE_UVEC3: case ShaderLanguage::TYPE_IVEC4: case ShaderLanguage::TYPE_UVEC4: { - pi.type = Variant::POOL_INT_ARRAY; + pi.type = Variant::PACKED_INT32_ARRAY; } break; case ShaderLanguage::TYPE_FLOAT: { - pi.type = Variant::REAL; + pi.type = Variant::FLOAT; 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]) + "," + rtos(u.hint_range[2]); @@ -1627,7 +1724,7 @@ void RasterizerStorageGLES2::shader_get_param_list(RID p_shader, List<PropertyIn case ShaderLanguage::TYPE_USAMPLER2D: { pi.type = Variant::OBJECT; pi.hint = PROPERTY_HINT_RESOURCE_TYPE; - pi.hint_string = "Texture"; + pi.hint_string = "Texture2D"; } break; case ShaderLanguage::TYPE_SAMPLERCUBE: { @@ -1638,11 +1735,19 @@ void RasterizerStorageGLES2::shader_get_param_list(RID p_shader, List<PropertyIn case ShaderLanguage::TYPE_SAMPLER2DARRAY: case ShaderLanguage::TYPE_ISAMPLER2DARRAY: - case ShaderLanguage::TYPE_USAMPLER2DARRAY: + case ShaderLanguage::TYPE_USAMPLER2DARRAY: { + + pi.type = Variant::OBJECT; + pi.hint = PROPERTY_HINT_RESOURCE_TYPE; + pi.hint_string = "TextureArray"; + } break; + case ShaderLanguage::TYPE_SAMPLER3D: case ShaderLanguage::TYPE_ISAMPLER3D: case ShaderLanguage::TYPE_USAMPLER3D: { - // Not implemented in GLES2 + pi.type = Variant::OBJECT; + pi.hint = PROPERTY_HINT_RESOURCE_TYPE; + pi.hint_string = "Texture3D"; } break; } @@ -1652,7 +1757,7 @@ void RasterizerStorageGLES2::shader_get_param_list(RID p_shader, List<PropertyIn void RasterizerStorageGLES2::shader_set_default_texture_param(RID p_shader, const StringName &p_name, RID p_texture) { - Shader *shader = shader_owner.get(p_shader); + Shader *shader = shader_owner.getornull(p_shader); ERR_FAIL_COND(!shader); ERR_FAIL_COND(p_texture.is_valid() && !texture_owner.owns(p_texture)); @@ -1667,7 +1772,7 @@ void RasterizerStorageGLES2::shader_set_default_texture_param(RID p_shader, cons RID RasterizerStorageGLES2::shader_get_default_texture_param(RID p_shader, const StringName &p_name) const { - const Shader *shader = shader_owner.get(p_shader); + const Shader *shader = shader_owner.getornull(p_shader); ERR_FAIL_COND_V(!shader, RID()); const Map<StringName, RID>::Element *E = shader->default_textures.find(p_name); @@ -1698,7 +1803,7 @@ RID RasterizerStorageGLES2::material_create() { void RasterizerStorageGLES2::material_set_shader(RID p_material, RID p_shader) { - Material *material = material_owner.get(p_material); + Material *material = material_owner.getornull(p_material); ERR_FAIL_COND(!material); Shader *shader = shader_owner.getornull(p_shader); @@ -1719,7 +1824,7 @@ void RasterizerStorageGLES2::material_set_shader(RID p_material, RID p_shader) { RID RasterizerStorageGLES2::material_get_shader(RID p_material) const { - const Material *material = material_owner.get(p_material); + const Material *material = material_owner.getornull(p_material); ERR_FAIL_COND_V(!material, RID()); if (material->shader) { @@ -1731,7 +1836,7 @@ RID RasterizerStorageGLES2::material_get_shader(RID p_material) const { void RasterizerStorageGLES2::material_set_param(RID p_material, const StringName &p_param, const Variant &p_value) { - Material *material = material_owner.get(p_material); + Material *material = material_owner.getornull(p_material); ERR_FAIL_COND(!material); if (p_value.get_type() == Variant::NIL) { @@ -1745,7 +1850,7 @@ void RasterizerStorageGLES2::material_set_param(RID p_material, const StringName Variant RasterizerStorageGLES2::material_get_param(RID p_material, const StringName &p_param) const { - const Material *material = material_owner.get(p_material); + const Material *material = material_owner.getornull(p_material); ERR_FAIL_COND_V(!material, RID()); if (material->params.has(p_param)) { @@ -1756,7 +1861,7 @@ Variant RasterizerStorageGLES2::material_get_param(RID p_material, const StringN } Variant RasterizerStorageGLES2::material_get_param_default(RID p_material, const StringName &p_param) const { - const Material *material = material_owner.get(p_material); + const Material *material = material_owner.getornull(p_material); ERR_FAIL_COND_V(!material, Variant()); if (material->shader) { @@ -1777,14 +1882,14 @@ void RasterizerStorageGLES2::material_set_line_width(RID p_material, float p_wid } void RasterizerStorageGLES2::material_set_next_pass(RID p_material, RID p_next_material) { - Material *material = material_owner.get(p_material); + Material *material = material_owner.getornull(p_material); ERR_FAIL_COND(!material); material->next_pass = p_next_material; } bool RasterizerStorageGLES2::material_is_animated(RID p_material) { - Material *material = material_owner.get(p_material); + Material *material = material_owner.getornull(p_material); ERR_FAIL_COND_V(!material, false); if (material->dirty_list.in_list()) { _update_material(material); @@ -1798,7 +1903,7 @@ bool RasterizerStorageGLES2::material_is_animated(RID p_material) { } bool RasterizerStorageGLES2::material_casts_shadows(RID p_material) { - Material *material = material_owner.get(p_material); + Material *material = material_owner.getornull(p_material); ERR_FAIL_COND_V(!material, false); if (material->dirty_list.in_list()) { _update_material(material); @@ -1845,7 +1950,7 @@ void RasterizerStorageGLES2::material_set_render_priority(RID p_material, int pr ERR_FAIL_COND(priority < VS::MATERIAL_RENDER_PRIORITY_MIN); ERR_FAIL_COND(priority > VS::MATERIAL_RENDER_PRIORITY_MAX); - Material *material = material_owner.get(p_material); + Material *material = material_owner.getornull(p_material); ERR_FAIL_COND(!material); material->render_priority = priority; @@ -1976,7 +2081,7 @@ RID RasterizerStorageGLES2::mesh_create() { return mesh_owner.make_rid(mesh); } -static PoolVector<uint8_t> _unpack_half_floats(const PoolVector<uint8_t> &array, uint32_t &format, int p_vertices) { +static Vector<uint8_t> _unpack_half_floats(const Vector<uint8_t> &array, uint32_t &format, int p_vertices) { uint32_t p_format = format; @@ -2118,11 +2223,11 @@ static PoolVector<uint8_t> _unpack_half_floats(const PoolVector<uint8_t> &array, dst_stride += dst_size[i]; } - PoolVector<uint8_t> ret; + Vector<uint8_t> ret; ret.resize(p_vertices * dst_stride); - PoolVector<uint8_t>::Read r = array.read(); - PoolVector<uint8_t>::Write w = ret.write(); + const uint8_t *r = array.ptr(); + uint8_t *w = ret.ptrw(); int src_offset = 0; int dst_offset = 0; @@ -2165,7 +2270,7 @@ static PoolVector<uint8_t> _unpack_half_floats(const PoolVector<uint8_t> &array, return ret; } -void RasterizerStorageGLES2::mesh_add_surface(RID p_mesh, uint32_t p_format, VS::PrimitiveType p_primitive, const PoolVector<uint8_t> &p_array, int p_vertex_count, const PoolVector<uint8_t> &p_index_array, int p_index_count, const AABB &p_aabb, const Vector<PoolVector<uint8_t> > &p_blend_shapes, const Vector<AABB> &p_bone_aabbs) { +void RasterizerStorageGLES2::mesh_add_surface(RID p_mesh, uint32_t p_format, VS::PrimitiveType p_primitive, const Vector<uint8_t> &p_array, int p_vertex_count, const Vector<uint8_t> &p_index_array, int p_index_count, const AABB &p_aabb, const Vector<Vector<uint8_t> > &p_blend_shapes, const Vector<AABB> &p_bone_aabbs) { Mesh *mesh = mesh_owner.getornull(p_mesh); ERR_FAIL_COND(!mesh); @@ -2352,18 +2457,18 @@ void RasterizerStorageGLES2::mesh_add_surface(RID p_mesh, uint32_t p_format, VS: } //validate sizes - PoolVector<uint8_t> array = p_array; + Vector<uint8_t> array = p_array; int array_size = stride * p_vertex_count; int index_array_size = 0; if (array.size() != array_size && array.size() + p_vertex_count * 2 == array_size) { //old format, convert - array = PoolVector<uint8_t>(); + array = Vector<uint8_t>(); array.resize(p_array.size() + p_vertex_count * 2); - PoolVector<uint8_t>::Write w = array.write(); - PoolVector<uint8_t>::Read r = p_array.read(); + uint8_t *w = array.ptrw(); + const uint8_t *r = p_array.ptr(); uint16_t *w16 = (uint16_t *)w.ptr(); const uint16_t *r16 = (uint16_t *)r.ptr(); @@ -2387,7 +2492,7 @@ void RasterizerStorageGLES2::mesh_add_surface(RID p_mesh, uint32_t p_format, VS: if (!config.support_half_float_vertices && uses_half_float) { uint32_t new_format = p_format; - PoolVector<uint8_t> unpacked_array = _unpack_half_floats(array, new_format, p_vertex_count); + Vector<uint8_t> unpacked_array = _unpack_half_floats(array, new_format, p_vertex_count); mesh_add_surface(p_mesh, new_format, p_primitive, unpacked_array, p_vertex_count, p_index_array, p_index_count, p_aabb, p_blend_shapes, p_bone_aabbs); return; //do not go any further, above function used unpacked stuff will be used instead. @@ -2428,22 +2533,10 @@ void RasterizerStorageGLES2::mesh_add_surface(RID p_mesh, uint32_t p_format, VS: if (surface->blend_shape_data.size()) { ERR_PRINT_ONCE("Blend shapes are not supported in OpenGL ES 2.0"); } - surface->data = array; - surface->index_data = p_index_array; -#else - // Even on non-tools builds, a copy of the surface->data is needed in certain circumstances. - // Rigged meshes using the USE_SKELETON_SOFTWARE path need to read bone data - // from surface->data. - - // if USE_SKELETON_SOFTWARE is active - if (config.use_skeleton_software) { - // if this geometry is used specifically for skinning - if (p_format & (VS::ARRAY_FORMAT_BONES | VS::ARRAY_FORMAT_WEIGHTS)) - surface->data = array; - } - // An alternative is to always make a copy of surface->data. #endif + surface->data = array; + surface->index_data = p_index_array; surface->total_data_size += surface->array_byte_size + surface->index_array_byte_size; for (int i = 0; i < surface->skeleton_bone_used.size(); i++) { @@ -2456,7 +2549,7 @@ void RasterizerStorageGLES2::mesh_add_surface(RID p_mesh, uint32_t p_format, VS: // Okay, now the OpenGL stuff, wheeeeey \o/ { - PoolVector<uint8_t>::Read vr = array.read(); + const uint8_t *vr = array.ptr(); glGenBuffers(1, &surface->vertex_id); glBindBuffer(GL_ARRAY_BUFFER, surface->vertex_id); @@ -2465,7 +2558,7 @@ void RasterizerStorageGLES2::mesh_add_surface(RID p_mesh, uint32_t p_format, VS: glBindBuffer(GL_ARRAY_BUFFER, 0); if (p_format & VS::ARRAY_FORMAT_INDEX) { - PoolVector<uint8_t>::Read ir = p_index_array.read(); + const uint8_t *ir = p_index_array.ptr(); glGenBuffers(1, &surface->index_id); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, surface->index_id); @@ -2485,7 +2578,7 @@ void RasterizerStorageGLES2::mesh_add_surface(RID p_mesh, uint32_t p_format, VS: Surface::BlendShape mt; - PoolVector<uint8_t>::Read vr = p_blend_shapes[i].read(); + const uint8_t *vr = p_blend_shapes[i].ptr(); surface->total_data_size += array_size; @@ -2535,7 +2628,7 @@ VS::BlendShapeMode RasterizerStorageGLES2::mesh_get_blend_shape_mode(RID p_mesh) return mesh->blend_shape_mode; } -void RasterizerStorageGLES2::mesh_surface_update_region(RID p_mesh, int p_surface, int p_offset, const PoolVector<uint8_t> &p_data) { +void RasterizerStorageGLES2::mesh_surface_update_region(RID p_mesh, int p_surface, int p_offset, const Vector<uint8_t> &p_data) { Mesh *mesh = mesh_owner.getornull(p_mesh); ERR_FAIL_COND(!mesh); @@ -2544,7 +2637,7 @@ void RasterizerStorageGLES2::mesh_surface_update_region(RID p_mesh, int p_surfac int total_size = p_data.size(); ERR_FAIL_COND(p_offset + total_size > mesh->surfaces[p_surface]->array_byte_size); - PoolVector<uint8_t>::Read r = p_data.read(); + const uint8_t *r = p_data.ptr(); glBindBuffer(GL_ARRAY_BUFFER, mesh->surfaces[p_surface]->vertex_id); glBufferSubData(GL_ARRAY_BUFFER, p_offset, total_size, r.ptr()); @@ -2596,11 +2689,11 @@ int RasterizerStorageGLES2::mesh_surface_get_array_index_len(RID p_mesh, int p_s return mesh->surfaces[p_surface]->index_array_len; } -PoolVector<uint8_t> RasterizerStorageGLES2::mesh_surface_get_array(RID p_mesh, int p_surface) const { +Vector<uint8_t> RasterizerStorageGLES2::mesh_surface_get_array(RID p_mesh, int p_surface) const { const Mesh *mesh = mesh_owner.getornull(p_mesh); - ERR_FAIL_COND_V(!mesh, PoolVector<uint8_t>()); - ERR_FAIL_INDEX_V(p_surface, mesh->surfaces.size(), PoolVector<uint8_t>()); + ERR_FAIL_COND_V(!mesh, Vector<uint8_t>()); + ERR_FAIL_INDEX_V(p_surface, mesh->surfaces.size(), Vector<uint8_t>()); Surface *surface = mesh->surfaces[p_surface]; #ifndef TOOLS_ENABLED @@ -2609,10 +2702,10 @@ PoolVector<uint8_t> RasterizerStorageGLES2::mesh_surface_get_array(RID p_mesh, i return surface->data; } -PoolVector<uint8_t> RasterizerStorageGLES2::mesh_surface_get_index_array(RID p_mesh, int p_surface) const { +Vector<uint8_t> RasterizerStorageGLES2::mesh_surface_get_index_array(RID p_mesh, int p_surface) const { const Mesh *mesh = mesh_owner.getornull(p_mesh); - ERR_FAIL_COND_V(!mesh, PoolVector<uint8_t>()); - ERR_FAIL_INDEX_V(p_surface, mesh->surfaces.size(), PoolVector<uint8_t>()); + ERR_FAIL_COND_V(!mesh, Vector<uint8_t>()); + ERR_FAIL_INDEX_V(p_surface, mesh->surfaces.size(), Vector<uint8_t>()); Surface *surface = mesh->surfaces[p_surface]; @@ -2644,10 +2737,10 @@ AABB RasterizerStorageGLES2::mesh_surface_get_aabb(RID p_mesh, int p_surface) co return mesh->surfaces[p_surface]->aabb; } -Vector<PoolVector<uint8_t> > RasterizerStorageGLES2::mesh_surface_get_blend_shapes(RID p_mesh, int p_surface) const { +Vector<Vector<uint8_t> > RasterizerStorageGLES2::mesh_surface_get_blend_shapes(RID p_mesh, int p_surface) const { const Mesh *mesh = mesh_owner.getornull(p_mesh); - ERR_FAIL_COND_V(!mesh, Vector<PoolVector<uint8_t> >()); - ERR_FAIL_INDEX_V(p_surface, mesh->surfaces.size(), Vector<PoolVector<uint8_t> >()); + ERR_FAIL_COND_V(!mesh, Vector<Vector<uint8_t> >()); + ERR_FAIL_INDEX_V(p_surface, mesh->surfaces.size(), Vector<Vector<uint8_t> >()); #ifndef TOOLS_ENABLED ERR_PRINT("OpenGL ES 2.0 does not allow retrieving mesh array data"); #endif @@ -2703,6 +2796,7 @@ void RasterizerStorageGLES2::mesh_set_custom_aabb(RID p_mesh, const AABB &p_aabb ERR_FAIL_COND(!mesh); mesh->custom_aabb = p_aabb; + mesh->instance_change_notify(true, false); } AABB RasterizerStorageGLES2::mesh_get_custom_aabb(RID p_mesh) const { @@ -2713,7 +2807,7 @@ AABB RasterizerStorageGLES2::mesh_get_custom_aabb(RID p_mesh) const { } AABB RasterizerStorageGLES2::mesh_get_aabb(RID p_mesh, RID p_skeleton) const { - Mesh *mesh = mesh_owner.get(p_mesh); + Mesh *mesh = mesh_owner.getornull(p_mesh); ERR_FAIL_COND_V(!mesh, AABB()); if (mesh->custom_aabb != AABB()) @@ -2721,7 +2815,7 @@ AABB RasterizerStorageGLES2::mesh_get_aabb(RID p_mesh, RID p_skeleton) const { Skeleton *sk = NULL; if (p_skeleton.is_valid()) { - sk = skeleton_owner.get(p_skeleton); + sk = skeleton_owner.getornull(p_skeleton); } AABB aabb; @@ -2867,20 +2961,20 @@ void RasterizerStorageGLES2::multimesh_allocate(RID p_multimesh, int p_instances multimesh->xform_floats = 12; } - if (multimesh->color_format == VS::MULTIMESH_COLOR_NONE) { - multimesh->color_floats = 0; - } else if (multimesh->color_format == VS::MULTIMESH_COLOR_8BIT) { + if (multimesh->color_format == VS::MULTIMESH_COLOR_8BIT) { multimesh->color_floats = 1; } else if (multimesh->color_format == VS::MULTIMESH_COLOR_FLOAT) { multimesh->color_floats = 4; + } else { + multimesh->color_floats = 0; } - if (multimesh->custom_data_format == VS::MULTIMESH_CUSTOM_DATA_NONE) { - multimesh->custom_data_floats = 0; - } else if (multimesh->custom_data_format == VS::MULTIMESH_CUSTOM_DATA_8BIT) { + if (multimesh->custom_data_format == VS::MULTIMESH_CUSTOM_DATA_8BIT) { multimesh->custom_data_floats = 1; } else if (multimesh->custom_data_format == VS::MULTIMESH_CUSTOM_DATA_FLOAT) { multimesh->custom_data_floats = 4; + } else { + multimesh->custom_data_floats = 0; } int format_floats = multimesh->color_floats + multimesh->xform_floats + multimesh->custom_data_floats; @@ -3056,6 +3150,7 @@ void RasterizerStorageGLES2::multimesh_instance_set_color(RID p_multimesh, int p ERR_FAIL_COND(!multimesh); ERR_FAIL_INDEX(p_index, multimesh->size); ERR_FAIL_COND(multimesh->color_format == VS::MULTIMESH_COLOR_NONE); + ERR_FAIL_INDEX(multimesh->color_format, VS::MULTIMESH_COLOR_MAX); int stride = multimesh->color_floats + multimesh->xform_floats + multimesh->custom_data_floats; float *dataptr = &multimesh->data.write[stride * p_index + multimesh->xform_floats]; @@ -3088,6 +3183,7 @@ void RasterizerStorageGLES2::multimesh_instance_set_custom_data(RID p_multimesh, ERR_FAIL_COND(!multimesh); ERR_FAIL_INDEX(p_index, multimesh->size); ERR_FAIL_COND(multimesh->custom_data_format == VS::MULTIMESH_CUSTOM_DATA_NONE); + ERR_FAIL_INDEX(multimesh->custom_data_format, VS::MULTIMESH_CUSTOM_DATA_MAX); int stride = multimesh->color_floats + multimesh->xform_floats + multimesh->custom_data_floats; float *dataptr = &multimesh->data.write[stride * p_index + multimesh->xform_floats + multimesh->color_floats]; @@ -3175,6 +3271,7 @@ Color RasterizerStorageGLES2::multimesh_instance_get_color(RID p_multimesh, int ERR_FAIL_COND_V(!multimesh, Color()); ERR_FAIL_INDEX_V(p_index, multimesh->size, Color()); ERR_FAIL_COND_V(multimesh->color_format == VS::MULTIMESH_COLOR_NONE, Color()); + ERR_FAIL_INDEX_V(multimesh->color_format, VS::MULTIMESH_COLOR_MAX, Color()); int stride = multimesh->color_floats + multimesh->xform_floats + multimesh->custom_data_floats; float *dataptr = &multimesh->data.write[stride * p_index + multimesh->xform_floats]; @@ -3207,6 +3304,7 @@ Color RasterizerStorageGLES2::multimesh_instance_get_custom_data(RID p_multimesh ERR_FAIL_COND_V(!multimesh, Color()); ERR_FAIL_INDEX_V(p_index, multimesh->size, Color()); ERR_FAIL_COND_V(multimesh->custom_data_format == VS::MULTIMESH_CUSTOM_DATA_NONE, Color()); + ERR_FAIL_INDEX_V(multimesh->custom_data_format, VS::MULTIMESH_CUSTOM_DATA_MAX, Color()); int stride = multimesh->color_floats + multimesh->xform_floats + multimesh->custom_data_floats; float *dataptr = &multimesh->data.write[stride * p_index + multimesh->xform_floats + multimesh->color_floats]; @@ -3234,7 +3332,7 @@ Color RasterizerStorageGLES2::multimesh_instance_get_custom_data(RID p_multimesh return Color(); } -void RasterizerStorageGLES2::multimesh_set_as_bulk_array(RID p_multimesh, const PoolVector<float> &p_array) { +void RasterizerStorageGLES2::multimesh_set_as_bulk_array(RID p_multimesh, const Vector<float> &p_array) { MultiMesh *multimesh = multimesh_owner.getornull(p_multimesh); ERR_FAIL_COND(!multimesh); ERR_FAIL_COND(!multimesh->data.ptr()); @@ -3243,7 +3341,7 @@ void RasterizerStorageGLES2::multimesh_set_as_bulk_array(RID p_multimesh, const ERR_FAIL_COND(dsize != p_array.size()); - PoolVector<float>::Read r = p_array.read(); + const float *r = p_array.ptr(); ERR_FAIL_COND(!r.ptr()); copymem(multimesh->data.ptrw(), r.ptr(), dsize * sizeof(float)); @@ -3373,7 +3471,7 @@ RID RasterizerStorageGLES2::immediate_create() { } void RasterizerStorageGLES2::immediate_begin(RID p_immediate, VS::PrimitiveType p_primitive, RID p_texture) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); ERR_FAIL_COND(im->building); @@ -3386,7 +3484,7 @@ void RasterizerStorageGLES2::immediate_begin(RID p_immediate, VS::PrimitiveType } void RasterizerStorageGLES2::immediate_vertex(RID p_immediate, const Vector3 &p_vertex) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); ERR_FAIL_COND(!im->building); @@ -3414,7 +3512,7 @@ void RasterizerStorageGLES2::immediate_vertex(RID p_immediate, const Vector3 &p_ } void RasterizerStorageGLES2::immediate_normal(RID p_immediate, const Vector3 &p_normal) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); ERR_FAIL_COND(!im->building); @@ -3423,7 +3521,7 @@ void RasterizerStorageGLES2::immediate_normal(RID p_immediate, const Vector3 &p_ } void RasterizerStorageGLES2::immediate_tangent(RID p_immediate, const Plane &p_tangent) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); ERR_FAIL_COND(!im->building); @@ -3432,7 +3530,7 @@ void RasterizerStorageGLES2::immediate_tangent(RID p_immediate, const Plane &p_t } void RasterizerStorageGLES2::immediate_color(RID p_immediate, const Color &p_color) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); ERR_FAIL_COND(!im->building); @@ -3441,7 +3539,7 @@ void RasterizerStorageGLES2::immediate_color(RID p_immediate, const Color &p_col } void RasterizerStorageGLES2::immediate_uv(RID p_immediate, const Vector2 &tex_uv) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); ERR_FAIL_COND(!im->building); @@ -3450,7 +3548,7 @@ void RasterizerStorageGLES2::immediate_uv(RID p_immediate, const Vector2 &tex_uv } void RasterizerStorageGLES2::immediate_uv2(RID p_immediate, const Vector2 &tex_uv) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); ERR_FAIL_COND(!im->building); @@ -3459,7 +3557,7 @@ void RasterizerStorageGLES2::immediate_uv2(RID p_immediate, const Vector2 &tex_u } void RasterizerStorageGLES2::immediate_end(RID p_immediate) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); ERR_FAIL_COND(!im->building); @@ -3468,7 +3566,7 @@ void RasterizerStorageGLES2::immediate_end(RID p_immediate) { } void RasterizerStorageGLES2::immediate_clear(RID p_immediate) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); ERR_FAIL_COND(im->building); @@ -3477,13 +3575,13 @@ void RasterizerStorageGLES2::immediate_clear(RID p_immediate) { } AABB RasterizerStorageGLES2::immediate_get_aabb(RID p_immediate) const { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND_V(!im, AABB()); return im->aabb; } void RasterizerStorageGLES2::immediate_set_material(RID p_immediate, RID p_material) { - Immediate *im = immediate_owner.get(p_immediate); + Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND(!im); im->material = p_material; @@ -3491,7 +3589,7 @@ void RasterizerStorageGLES2::immediate_set_material(RID p_immediate, RID p_mater } RID RasterizerStorageGLES2::immediate_get_material(RID p_immediate) const { - const Immediate *im = immediate_owner.get(p_immediate); + const Immediate *im = immediate_owner.getornull(p_immediate); ERR_FAIL_COND_V(!im, RID()); return im->material; } @@ -3669,7 +3767,7 @@ void RasterizerStorageGLES2::skeleton_set_base_transform_2d(RID p_skeleton, cons skeleton->base_transform_2d = p_base_transform; } -void RasterizerStorageGLES2::_update_skeleton_transform_buffer(const PoolVector<float> &p_data, size_t p_size) { +void RasterizerStorageGLES2::_update_skeleton_transform_buffer(const Vector<float> &p_data, size_t p_size) { glBindBuffer(GL_ARRAY_BUFFER, resources.skeleton_transform_buffer); @@ -3678,9 +3776,9 @@ void RasterizerStorageGLES2::_update_skeleton_transform_buffer(const PoolVector< resources.skeleton_transform_buffer_size = p_size; - glBufferData(GL_ARRAY_BUFFER, p_size * sizeof(float), p_data.read().ptr(), GL_DYNAMIC_DRAW); + glBufferData(GL_ARRAY_BUFFER, p_size * sizeof(float), p_data.ptr(), GL_DYNAMIC_DRAW); } else { - glBufferSubData(GL_ARRAY_BUFFER, 0, p_size * sizeof(float), p_data.read().ptr()); + glBufferSubData(GL_ARRAY_BUFFER, 0, p_size * sizeof(float), p_data.ptr()); } glBindBuffer(GL_ARRAY_BUFFER, 0); @@ -4200,11 +4298,11 @@ Transform RasterizerStorageGLES2::gi_probe_get_to_cell_xform(RID p_probe) const return Transform(); } -void RasterizerStorageGLES2::gi_probe_set_dynamic_data(RID p_probe, const PoolVector<int> &p_data) { +void RasterizerStorageGLES2::gi_probe_set_dynamic_data(RID p_probe, const Vector<int> &p_data) { } -PoolVector<int> RasterizerStorageGLES2::gi_probe_get_dynamic_data(RID p_probe) const { - return PoolVector<int>(); +Vector<int> RasterizerStorageGLES2::gi_probe_get_dynamic_data(RID p_probe) const { + return Vector<int>(); } void RasterizerStorageGLES2::gi_probe_set_dynamic_range(RID p_probe, int p_range) { @@ -4291,7 +4389,7 @@ AABB RasterizerStorageGLES2::lightmap_capture_get_bounds(RID p_capture) const { ERR_FAIL_COND_V(!capture, AABB()); return capture->bounds; } -void RasterizerStorageGLES2::lightmap_capture_set_octree(RID p_capture, const PoolVector<uint8_t> &p_octree) { +void RasterizerStorageGLES2::lightmap_capture_set_octree(RID p_capture, const Vector<uint8_t> &p_octree) { LightmapCapture *capture = lightmap_capture_data_owner.getornull(p_capture); ERR_FAIL_COND(!capture); @@ -4300,25 +4398,25 @@ void RasterizerStorageGLES2::lightmap_capture_set_octree(RID p_capture, const Po capture->octree.resize(p_octree.size() / sizeof(LightmapCaptureOctree)); if (p_octree.size()) { - PoolVector<LightmapCaptureOctree>::Write w = capture->octree.write(); - PoolVector<uint8_t>::Read r = p_octree.read(); + LightmapCaptureOctree *w = capture->octree.ptrw(); + const uint8_t *r = p_octree.ptr(); copymem(w.ptr(), r.ptr(), p_octree.size()); } capture->instance_change_notify(true, false); } -PoolVector<uint8_t> RasterizerStorageGLES2::lightmap_capture_get_octree(RID p_capture) const { +Vector<uint8_t> RasterizerStorageGLES2::lightmap_capture_get_octree(RID p_capture) const { const LightmapCapture *capture = lightmap_capture_data_owner.getornull(p_capture); - ERR_FAIL_COND_V(!capture, PoolVector<uint8_t>()); + ERR_FAIL_COND_V(!capture, Vector<uint8_t>()); if (capture->octree.size() == 0) - return PoolVector<uint8_t>(); + return Vector<uint8_t>(); - PoolVector<uint8_t> ret; + Vector<uint8_t> ret; ret.resize(capture->octree.size() * sizeof(LightmapCaptureOctree)); { - PoolVector<LightmapCaptureOctree>::Read r = capture->octree.read(); - PoolVector<uint8_t>::Write w = ret.write(); + const LightmapCaptureOctree *r = capture->octree.ptr(); + uint8_t *w = ret.ptrw(); copymem(w.ptr(), r.ptr(), ret.size()); } @@ -4363,7 +4461,7 @@ float RasterizerStorageGLES2::lightmap_capture_get_energy(RID p_capture) const { return capture->energy; } -const PoolVector<RasterizerStorage::LightmapCaptureOctree> *RasterizerStorageGLES2::lightmap_capture_get_octree_ptr(RID p_capture) const { +const Vector<RasterizerStorage::LightmapCaptureOctree> *RasterizerStorageGLES2::lightmap_capture_get_octree_ptr(RID p_capture) const { const LightmapCapture *capture = lightmap_capture_data_owner.getornull(p_capture); ERR_FAIL_COND_V(!capture, NULL); return &capture->octree; @@ -4583,13 +4681,24 @@ void RasterizerStorageGLES2::_render_target_allocate(RenderTarget *rt) { GLuint color_internal_format; GLuint color_format; GLuint color_type = GL_UNSIGNED_BYTE; + Image::Format image_format; if (rt->flags[RasterizerStorage::RENDER_TARGET_TRANSPARENT]) { +#ifdef GLES_OVER_GL + color_internal_format = GL_RGBA8; +#else color_internal_format = GL_RGBA; +#endif color_format = GL_RGBA; + image_format = Image::FORMAT_RGBA8; } else { +#ifdef GLES_OVER_GL + color_internal_format = GL_RGB8; +#else color_internal_format = GL_RGB; +#endif color_format = GL_RGB; + image_format = Image::FORMAT_RGB8; } rt->used_dof_blur_near = false; @@ -4646,7 +4755,7 @@ void RasterizerStorageGLES2::_render_target_allocate(RenderTarget *rt) { glGenRenderbuffers(1, &rt->depth); glBindRenderbuffer(GL_RENDERBUFFER, rt->depth); - glRenderbufferStorage(GL_RENDERBUFFER, config.depth_internalformat, rt->width, rt->height); + glRenderbufferStorage(GL_RENDERBUFFER, config.depth_buffer_internalformat, rt->width, rt->height); glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rt->depth); } @@ -4676,10 +4785,10 @@ void RasterizerStorageGLES2::_render_target_allocate(RenderTarget *rt) { return; } - texture->format = Image::FORMAT_RGBA8; - texture->gl_format_cache = GL_RGBA; + texture->format = image_format; + texture->gl_format_cache = color_format; texture->gl_type_cache = GL_UNSIGNED_BYTE; - texture->gl_internal_format_cache = GL_RGBA; + texture->gl_internal_format_cache = color_internal_format; texture->tex_id = rt->color; texture->width = rt->width; texture->alloc_width = rt->width; @@ -4704,7 +4813,7 @@ void RasterizerStorageGLES2::_render_target_allocate(RenderTarget *rt) { int max_samples = 0; glGetIntegerv(GL_MAX_SAMPLES, &max_samples); if (msaa > max_samples) { - WARN_PRINTS("MSAA must be <= GL_MAX_SAMPLES, falling-back to GL_MAX_SAMPLES = " + itos(max_samples)); + WARN_PRINT("MSAA must be <= GL_MAX_SAMPLES, falling-back to GL_MAX_SAMPLES = " + itos(max_samples)); msaa = max_samples; } @@ -4714,7 +4823,7 @@ void RasterizerStorageGLES2::_render_target_allocate(RenderTarget *rt) { glGenRenderbuffers(1, &rt->multisample_depth); glBindRenderbuffer(GL_RENDERBUFFER, rt->multisample_depth); - glRenderbufferStorageMultisample(GL_RENDERBUFFER, msaa, config.depth_internalformat, rt->width, rt->height); + glRenderbufferStorageMultisample(GL_RENDERBUFFER, msaa, config.depth_buffer_internalformat, rt->width, rt->height); glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rt->multisample_depth); @@ -4896,7 +5005,11 @@ void RasterizerStorageGLES2::_render_target_allocate(RenderTarget *rt) { bool used_depth = false; if (j == 0 && i == 0) { //use always - glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, rt->depth, 0); + if (config.support_depth_texture) { + glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, rt->depth, 0); + } else { + glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rt->depth); + } used_depth = true; } @@ -4947,7 +5060,7 @@ void RasterizerStorageGLES2::_render_target_clear(RenderTarget *rt) { glDeleteFramebuffers(1, &rt->external.fbo); // clean up our texture - Texture *t = texture_owner.get(rt->external.texture); + Texture *t = texture_owner.getornull(rt->external.texture); t->alloc_height = 0; t->alloc_width = 0; t->width = 0; @@ -4969,7 +5082,7 @@ void RasterizerStorageGLES2::_render_target_clear(RenderTarget *rt) { rt->depth = 0; } - Texture *tex = texture_owner.get(rt->texture); + Texture *tex = texture_owner.getornull(rt->texture); tex->alloc_height = 0; tex->alloc_width = 0; tex->width = 0; @@ -5096,7 +5209,7 @@ void RasterizerStorageGLES2::render_target_set_external_texture(RID p_render_tar } // clean up our texture - Texture *t = texture_owner.get(rt->external.texture); + Texture *t = texture_owner.getornull(rt->external.texture); t->alloc_height = 0; t->alloc_width = 0; t->width = 0; @@ -5148,7 +5261,7 @@ void RasterizerStorageGLES2::render_target_set_external_texture(RID p_render_tar glBindFramebuffer(GL_FRAMEBUFFER, rt->external.fbo); // find our texture - t = texture_owner.get(rt->external.texture); + t = texture_owner.getornull(rt->external.texture); } // set our texture @@ -5178,7 +5291,7 @@ void RasterizerStorageGLES2::render_target_set_external_texture(RID p_render_tar // create a multisample depth buffer, we're not reusing Godots because Godot's didn't get created.. glGenRenderbuffers(1, &rt->external.depth); glBindRenderbuffer(GL_RENDERBUFFER, rt->external.depth); - glRenderbufferStorageMultisample(GL_RENDERBUFFER, msaa, config.depth_internalformat, rt->width, rt->height); + glRenderbufferStorageMultisample(GL_RENDERBUFFER, msaa, config.depth_buffer_internalformat, rt->width, rt->height); glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rt->external.depth); } @@ -5248,7 +5361,7 @@ bool RasterizerStorageGLES2::render_target_was_used(RID p_render_target) { return rt->used_in_frame; } -void RasterizerStorageGLES2::render_target_clear_used(RID p_render_target) { +void RasterizerStorageGLES2::render_target_set_as_unused(RID p_render_target) { RenderTarget *rt = render_target_owner.getornull(p_render_target); ERR_FAIL_COND(!rt); @@ -5291,7 +5404,7 @@ RID RasterizerStorageGLES2::canvas_light_shadow_buffer_create(int p_width) { glGenRenderbuffers(1, &cls->depth); glBindRenderbuffer(GL_RENDERBUFFER, cls->depth); - glRenderbufferStorage(GL_RENDERBUFFER, config.depth_internalformat, cls->size, cls->height); + glRenderbufferStorage(GL_RENDERBUFFER, config.depth_buffer_internalformat, cls->size, cls->height); glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, cls->depth); glGenTextures(1, &cls->distance); @@ -5336,9 +5449,9 @@ RID RasterizerStorageGLES2::canvas_light_occluder_create() { return canvas_occluder_owner.make_rid(co); } -void RasterizerStorageGLES2::canvas_light_occluder_set_polylines(RID p_occluder, const PoolVector<Vector2> &p_lines) { +void RasterizerStorageGLES2::canvas_light_occluder_set_polylines(RID p_occluder, const Vector<Vector2> &p_lines) { - CanvasOccluder *co = canvas_occluder_owner.get(p_occluder); + CanvasOccluder *co = canvas_occluder_owner.getornull(p_occluder); ERR_FAIL_COND(!co); co->lines = p_lines; @@ -5357,17 +5470,17 @@ void RasterizerStorageGLES2::canvas_light_occluder_set_polylines(RID p_occluder, if (p_lines.size()) { - PoolVector<float> geometry; - PoolVector<uint16_t> indices; + Vector<float> geometry; + Vector<uint16_t> indices; int lc = p_lines.size(); geometry.resize(lc * 6); indices.resize(lc * 3); - PoolVector<float>::Write vw = geometry.write(); - PoolVector<uint16_t>::Write iw = indices.write(); + float *vw = geometry.ptrw(); + uint16_t *iw = indices.ptrw(); - PoolVector<Vector2>::Read lr = p_lines.read(); + const Vector2 *lr = p_lines.ptr(); const int POLY_HEIGHT = 16384; @@ -5455,7 +5568,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { RenderTarget *rt = render_target_owner.getornull(p_rid); _render_target_clear(rt); - Texture *t = texture_owner.get(rt->texture); + Texture *t = texture_owner.getornull(rt->texture); texture_owner.free(rt->texture); memdelete(t); render_target_owner.free(p_rid); @@ -5464,7 +5577,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { return true; } else if (texture_owner.owns(p_rid)) { - Texture *t = texture_owner.get(p_rid); + Texture *t = texture_owner.getornull(p_rid); // can't free a render target texture ERR_FAIL_COND_V(t->render_target, true); @@ -5475,7 +5588,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { return true; } else if (sky_owner.owns(p_rid)) { - Sky *sky = sky_owner.get(p_rid); + Sky *sky = sky_owner.getornull(p_rid); sky_set_texture(p_rid, RID(), 256); sky_owner.free(p_rid); memdelete(sky); @@ -5483,7 +5596,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { return true; } else if (shader_owner.owns(p_rid)) { - Shader *shader = shader_owner.get(p_rid); + Shader *shader = shader_owner.getornull(p_rid); if (shader->shader && shader->custom_code_id) { shader->shader->free_custom_shader(shader->custom_code_id); @@ -5508,7 +5621,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { return true; } else if (material_owner.owns(p_rid)) { - Material *m = material_owner.get(p_rid); + Material *m = material_owner.getornull(p_rid); if (m->shader) { m->shader->materials.remove(&m->list); @@ -5540,7 +5653,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { return true; } else if (skeleton_owner.owns(p_rid)) { - Skeleton *s = skeleton_owner.get(p_rid); + Skeleton *s = skeleton_owner.getornull(p_rid); if (s->update_list.in_list()) { skeleton_update_list.remove(&s->update_list); @@ -5562,7 +5675,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { return true; } else if (mesh_owner.owns(p_rid)) { - Mesh *mesh = mesh_owner.get(p_rid); + Mesh *mesh = mesh_owner.getornull(p_rid); mesh->instance_remove_deps(); mesh_clear(p_rid); @@ -5585,7 +5698,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { return true; } else if (multimesh_owner.owns(p_rid)) { - MultiMesh *multimesh = multimesh_owner.get(p_rid); + MultiMesh *multimesh = multimesh_owner.getornull(p_rid); multimesh->instance_remove_deps(); if (multimesh->mesh.is_valid()) { @@ -5604,7 +5717,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { return true; } else if (immediate_owner.owns(p_rid)) { - Immediate *im = immediate_owner.get(p_rid); + Immediate *im = immediate_owner.getornull(p_rid); im->instance_remove_deps(); immediate_owner.free(p_rid); @@ -5613,7 +5726,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { return true; } else if (light_owner.owns(p_rid)) { - Light *light = light_owner.get(p_rid); + Light *light = light_owner.getornull(p_rid); light->instance_remove_deps(); light_owner.free(p_rid); @@ -5623,7 +5736,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { } else if (reflection_probe_owner.owns(p_rid)) { // delete the texture - ReflectionProbe *reflection_probe = reflection_probe_owner.get(p_rid); + ReflectionProbe *reflection_probe = reflection_probe_owner.getornull(p_rid); reflection_probe->instance_remove_deps(); reflection_probe_owner.free(p_rid); @@ -5633,7 +5746,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { } else if (lightmap_capture_data_owner.owns(p_rid)) { // delete the texture - LightmapCapture *lightmap_capture = lightmap_capture_data_owner.get(p_rid); + LightmapCapture *lightmap_capture = lightmap_capture_data_owner.getornull(p_rid); lightmap_capture->instance_remove_deps(); lightmap_capture_data_owner.free(p_rid); @@ -5642,7 +5755,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { } else if (canvas_occluder_owner.owns(p_rid)) { - CanvasOccluder *co = canvas_occluder_owner.get(p_rid); + CanvasOccluder *co = canvas_occluder_owner.getornull(p_rid); if (co->index_id) glDeleteBuffers(1, &co->index_id); if (co->vertex_id) @@ -5655,7 +5768,7 @@ bool RasterizerStorageGLES2::free(RID p_rid) { } else if (canvas_light_shadow_owner.owns(p_rid)) { - CanvasLightShadow *cls = canvas_light_shadow_owner.get(p_rid); + CanvasLightShadow *cls = canvas_light_shadow_owner.getornull(p_rid); glDeleteFramebuffers(1, &cls->fbo); glDeleteRenderbuffers(1, &cls->depth); glDeleteTextures(1, &cls->distance); @@ -5756,6 +5869,16 @@ int RasterizerStorageGLES2::get_render_info(VS::RenderInfo p_info) { } } +String RasterizerStorageGLES2::get_video_adapter_name() const { + + return (const char *)glGetString(GL_RENDERER); +} + +String RasterizerStorageGLES2::get_video_adapter_vendor() const { + + return (const char *)glGetString(GL_VENDOR); +} + void RasterizerStorageGLES2::initialize() { RasterizerStorageGLES2::system_fbo = 0; @@ -5772,30 +5895,45 @@ void RasterizerStorageGLES2::initialize() { config.keep_original_textures = false; config.shrink_textures_x2 = false; + config.depth_internalformat = GL_DEPTH_COMPONENT; + config.depth_type = GL_UNSIGNED_INT; #ifdef GLES_OVER_GL + config.texture_3d_supported = true; + config.texture_array_supported = config.extensions.has("GL_EXT_texture_array"); config.float_texture_supported = true; config.s3tc_supported = true; config.pvrtc_supported = false; config.etc1_supported = false; config.support_npot_repeat_mipmap = true; - config.depth_internalformat = GL_DEPTH_COMPONENT; - config.depth_type = GL_UNSIGNED_INT; + config.depth_buffer_internalformat = GL_DEPTH_COMPONENT24; #else + config.texture_3d_supported = config.extensions.has("GL_OES_texture_3D"); + config.texture_array_supported = false; config.float_texture_supported = config.extensions.has("GL_ARB_texture_float") || config.extensions.has("GL_OES_texture_float"); config.s3tc_supported = config.extensions.has("GL_EXT_texture_compression_s3tc") || config.extensions.has("WEBGL_compressed_texture_s3tc"); config.etc1_supported = config.extensions.has("GL_OES_compressed_ETC1_RGB8_texture") || config.extensions.has("WEBGL_compressed_texture_etc1"); config.pvrtc_supported = config.extensions.has("IMG_texture_compression_pvrtc") || config.extensions.has("WEBGL_compressed_texture_pvrtc"); config.support_npot_repeat_mipmap = config.extensions.has("GL_OES_texture_npot"); - // on mobile check for 24 bit depth support + +#ifdef JAVASCRIPT_ENABLED + // RenderBuffer internal format must be 16 bits in WebGL, + // but depth_texture should default to 32 always + // if the implementation doesn't support 32, it should just quietly use 16 instead + // https://www.khronos.org/registry/webgl/extensions/WEBGL_depth_texture/ + config.depth_buffer_internalformat = GL_DEPTH_COMPONENT16; + config.depth_type = GL_UNSIGNED_INT; +#else + // on mobile check for 24 bit depth support for RenderBufferStorage if (config.extensions.has("GL_OES_depth24")) { - config.depth_internalformat = _DEPTH_COMPONENT24_OES; + config.depth_buffer_internalformat = _DEPTH_COMPONENT24_OES; config.depth_type = GL_UNSIGNED_INT; } else { - config.depth_internalformat = GL_DEPTH_COMPONENT16; + config.depth_buffer_internalformat = GL_DEPTH_COMPONENT16; config.depth_type = GL_UNSIGNED_SHORT; } #endif +#endif #ifndef GLES_OVER_GL //Manually load extensions for android and ios @@ -5810,6 +5948,9 @@ void RasterizerStorageGLES2::initialize() { void *gles2_lib = dlopen("libGLESv2.so", RTLD_LAZY); glRenderbufferStorageMultisampleEXT = (PFNGLRENDERBUFFERSTORAGEMULTISAMPLEEXTPROC)dlsym(gles2_lib, "glRenderbufferStorageMultisampleEXT"); glFramebufferTexture2DMultisampleEXT = (PFNGLFRAMEBUFFERTEXTURE2DMULTISAMPLEEXTPROC)dlsym(gles2_lib, "glFramebufferTexture2DMultisampleEXT"); + glTexImage3DOES = (PFNGLTEXIMAGE3DOESPROC)dlsym(gles2_lib, "glTexImage3DOES"); + glTexSubImage3DOES = (PFNGLTEXSUBIMAGE3DOESPROC)dlsym(gles2_lib, "glTexSubImage3DOES"); + glCompressedTexSubImage3DOES = (PFNGLCOMPRESSEDTEXSUBIMAGE3DOESPROC)dlsym(gles2_lib, "glCompressedTexSubImage3DOES"); #endif #endif @@ -5871,7 +6012,7 @@ void RasterizerStorageGLES2::initialize() { GLuint depth; glGenTextures(1, &depth); glBindTexture(GL_TEXTURE_2D, depth); - glTexImage2D(GL_TEXTURE_2D, 0, config.depth_internalformat, 32, 32, 0, config.depth_internalformat, config.depth_type, NULL); + glTexImage2D(GL_TEXTURE_2D, 0, config.depth_internalformat, 32, 32, 0, GL_DEPTH_COMPONENT, config.depth_type, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); @@ -5890,8 +6031,12 @@ void RasterizerStorageGLES2::initialize() { if (status != GL_FRAMEBUFFER_COMPLETE) { // 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 - +#ifdef GLES_OVER_GL config.depth_internalformat = GL_DEPTH_COMPONENT16; +#else + // OES_depth_texture extension only specifies GL_DEPTH_COMPONENT. + config.depth_internalformat = GL_DEPTH_COMPONENT; +#endif config.depth_type = GL_UNSIGNED_SHORT; glGenFramebuffers(1, &fbo); @@ -5899,7 +6044,7 @@ void RasterizerStorageGLES2::initialize() { 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); + glTexImage2D(GL_TEXTURE_2D, 0, config.depth_internalformat, 32, 32, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_SHORT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); @@ -6028,6 +6173,26 @@ void RasterizerStorageGLES2::initialize() { glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, 8, 8, 0, GL_RGB, GL_UNSIGNED_BYTE, anisotexdata); glGenerateMipmap(GL_TEXTURE_2D); glBindTexture(GL_TEXTURE_2D, 0); + +#if defined(GLES_OVER_GL) || defined(ANDROID_ENABLED) + glGenTextures(1, &resources.white_tex_3d); + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_3D, resources.white_tex_3d); + glTexImage3D(GL_TEXTURE_3D, 0, GL_RGB, 2, 2, 2, 0, GL_RGB, GL_UNSIGNED_BYTE, whitetexdata); + +#ifdef GLES_OVER_GL + glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_BASE_LEVEL, 0); + glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MAX_LEVEL, 0); +#endif + + glGenTextures(1, &resources.white_tex_array); + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D_ARRAY, resources.white_tex_array); + glTexImage3D(GL_TEXTURE_2D_ARRAY, 0, GL_RGB, 8, 8, 1, 0, GL_RGB, GL_UNSIGNED_BYTE, NULL); + glTexSubImage3D(GL_TEXTURE_2D_ARRAY, 0, 0, 0, 0, 8, 8, 1, GL_RGB, GL_UNSIGNED_BYTE, whitetexdata); + glGenerateMipmap(GL_TEXTURE_2D_ARRAY); + glBindTexture(GL_TEXTURE_2D, 0); +#endif } // skeleton buffer |