summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/egl/egl_manager.cpp89
-rw-r--r--drivers/egl/egl_manager.h2
-rw-r--r--drivers/gles3/rasterizer_gles3.cpp6
-rw-r--r--drivers/gles3/rasterizer_gles3.h2
-rw-r--r--drivers/gles3/shaders/scene.glsl3
-rw-r--r--drivers/gles3/storage/config.cpp27
-rw-r--r--drivers/gles3/storage/config.h4
-rw-r--r--drivers/gles3/storage/particles_storage.cpp4
-rw-r--r--editor/animation_track_editor.cpp17
-rw-r--r--editor/animation_track_editor.h1
-rw-r--r--editor/editor_inspector.cpp35
-rw-r--r--editor/gui/editor_object_selector.cpp1
-rw-r--r--editor/icons/Key.svg2
-rw-r--r--editor/plugins/path_2d_editor_plugin.cpp60
-rw-r--r--editor/plugins/path_2d_editor_plugin.h11
-rw-r--r--editor/plugins/sprite_frames_editor_plugin.cpp10
-rw-r--r--editor/plugins/sprite_frames_editor_plugin.h2
-rw-r--r--main/main.cpp2
-rw-r--r--platform/android/export/export_plugin.cpp131
-rw-r--r--platform/android/export/export_plugin.h23
-rw-r--r--platform/android/java/app/build.gradle1
-rw-r--r--platform/android/java/app/config.gradle3
-rw-r--r--platform/android/java/app/res/drawable-nodpi/splash.pngbin14766 -> 0 bytes
-rw-r--r--platform/android/java/app/res/drawable-nodpi/splash_bg_color.pngbin1360 -> 0 bytes
-rw-r--r--platform/android/java/app/res/drawable/splash_drawable.xml12
-rw-r--r--platform/android/java/app/res/values/themes.xml15
-rw-r--r--platform/android/java/app/src/com/godot/game/GodotApp.java4
-rw-r--r--platform/android/java/editor/build.gradle8
-rw-r--r--platform/android/java/editor/src/debug/res/values/strings.xml4
-rw-r--r--platform/android/java/editor/src/dev/res/values/strings.xml4
-rw-r--r--platform/android/java/editor/src/main/AndroidManifest.xml46
-rw-r--r--platform/android/java/editor/src/main/java/org/godotengine/editor/GodotEditor.kt15
-rw-r--r--platform/android/java/editor/src/main/java/org/godotengine/editor/GodotGame.kt3
-rw-r--r--platform/android/java/editor/src/main/res/layout/godot_editor_layout.xml25
-rw-r--r--platform/android/java/editor/src/main/res/values/strings.xml2
-rw-r--r--platform/android/java/editor/src/main/res/values/themes.xml6
-rw-r--r--platform/android/java/lib/src/org/godotengine/godot/GodotActivity.kt6
-rw-r--r--platform/linuxbsd/wayland/detect_prime_egl.cpp28
-rw-r--r--platform/linuxbsd/wayland/detect_prime_egl.h28
-rw-r--r--platform/linuxbsd/wayland/display_server_wayland.cpp6
-rw-r--r--platform/windows/display_server_windows.cpp81
-rw-r--r--platform/windows/display_server_windows.h1
-rw-r--r--scene/gui/button.cpp17
-rw-r--r--scene/resources/2d/tile_set.cpp12
-rw-r--r--tests/core/io/test_image.h4
-rw-r--r--tests/core/io/test_pck_packer.h8
-rw-r--r--tests/core/io/test_resource.h8
-rw-r--r--tests/scene/test_audio_stream_wav.h6
-rw-r--r--tests/scene/test_instance_placeholder.h8
-rw-r--r--tests/scene/test_node.h4
-rw-r--r--tests/test_utils.cpp7
-rw-r--r--tests/test_utils.h1
-rw-r--r--thirdparty/glad/EGL/eglplatform.h6
-rw-r--r--thirdparty/glad/egl.c12
-rw-r--r--thirdparty/glad/glad/egl.h21
55 files changed, 487 insertions, 357 deletions
diff --git a/drivers/egl/egl_manager.cpp b/drivers/egl/egl_manager.cpp
index 6073856747..9c1d08331d 100644
--- a/drivers/egl/egl_manager.cpp
+++ b/drivers/egl/egl_manager.cpp
@@ -33,10 +33,22 @@
#ifdef EGL_ENABLED
#if defined(EGL_STATIC)
-#define KHRONOS_STATIC 1
+
#define GLAD_EGL_VERSION_1_5 true
+
+#ifdef EGL_EXT_platform_base
+#define GLAD_EGL_EXT_platform_base 1
+#endif
+
+#define KHRONOS_STATIC 1
extern "C" EGLAPI void EGLAPIENTRY eglSetBlobCacheFuncsANDROID(EGLDisplay dpy, EGLSetBlobFuncANDROID set, EGLGetBlobFuncANDROID get);
+extern "C" EGLAPI EGLDisplay EGLAPIENTRY eglGetPlatformDisplayEXT(EGLenum platform, void *native_display, const EGLint *attrib_list);
#undef KHRONOS_STATIC
+
+#endif // defined(EGL_STATIC)
+
+#ifndef EGL_EXT_platform_base
+#define GLAD_EGL_EXT_platform_base 0
#endif
// Creates and caches a GLDisplay. Returns -1 on error.
@@ -56,10 +68,23 @@ int EGLManager::_get_gldisplay_id(void *p_display) {
if (GLAD_EGL_VERSION_1_5) {
Vector<EGLAttrib> attribs = _get_platform_display_attributes();
new_gldisplay.egl_display = eglGetPlatformDisplay(_get_platform_extension_enum(), new_gldisplay.display, (attribs.size() > 0) ? attribs.ptr() : nullptr);
+ } else if (GLAD_EGL_EXT_platform_base) {
+#ifdef EGL_EXT_platform_base
+ // eglGetPlatformDisplayEXT wants its attributes as EGLint, so we'll truncate
+ // what we already have. It's a bit naughty but I'm really not sure what else
+ // we could do here.
+ Vector<EGLint> attribs;
+ for (const EGLAttrib &attrib : _get_platform_display_attributes()) {
+ attribs.push_back((EGLint)attrib);
+ }
+
+ new_gldisplay.egl_display = eglGetPlatformDisplayEXT(_get_platform_extension_enum(), new_gldisplay.display, (attribs.size() > 0) ? attribs.ptr() : nullptr);
+#endif // EGL_EXT_platform_base
} else {
NativeDisplayType *native_display_type = (NativeDisplayType *)new_gldisplay.display;
new_gldisplay.egl_display = eglGetDisplay(*native_display_type);
}
+
ERR_FAIL_COND_V(eglGetError() != EGL_SUCCESS, -1);
ERR_FAIL_COND_V_MSG(new_gldisplay.egl_display == EGL_NO_DISPLAY, -1, "Can't create an EGL display.");
@@ -326,30 +351,51 @@ EGLContext EGLManager::get_context(DisplayServer::WindowID p_window_id) {
return display.egl_context;
}
-Error EGLManager::initialize() {
+Error EGLManager::initialize(void *p_native_display) {
#if defined(GLAD_ENABLED) && !defined(EGL_STATIC)
- // Passing a null display loads just the bare minimum to create one. We'll have
- // to create a temporary test display and reload EGL with it to get a good idea
- // of what version is supported on this machine. Currently we're looking for
- // 1.5, the latest at the time of writing, which is actually pretty old.
- if (!gladLoaderLoadEGL(nullptr)) {
+ // Loading EGL with a new display gets us just the bare minimum API. We'll then
+ // have to temporarily get a proper display and reload EGL once again to
+ // initialize everything else.
+ if (!gladLoaderLoadEGL(EGL_NO_DISPLAY)) {
ERR_FAIL_V_MSG(ERR_UNAVAILABLE, "Can't load EGL.");
}
- // NOTE: EGL_DEFAULT_DISPLAY returns whatever the O.S. deems suitable. I have
- // no idea if this may cause problems with multiple display servers and if we
- // should handle different EGL contexts in another way.
- EGLDisplay tmp_display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
- ERR_FAIL_COND_V(tmp_display == EGL_NO_DISPLAY, ERR_UNAVAILABLE);
+ EGLDisplay tmp_display = EGL_NO_DISPLAY;
+
+ if (GLAD_EGL_EXT_platform_base) {
+#ifdef EGL_EXT_platform_base
+ // eglGetPlatformDisplayEXT wants its attributes as EGLint.
+ Vector<EGLint> attribs;
+ for (const EGLAttrib &attrib : _get_platform_display_attributes()) {
+ attribs.push_back((EGLint)attrib);
+ }
+ tmp_display = eglGetPlatformDisplayEXT(_get_platform_extension_enum(), p_native_display, attribs.ptr());
+#endif // EGL_EXT_platform_base
+ } else {
+ WARN_PRINT("EGL: EGL_EXT_platform_base not found during init, using default platform.");
+ EGLNativeDisplayType *native_display_type = (EGLNativeDisplayType *)p_native_display;
+ tmp_display = eglGetDisplay(*native_display_type);
+ }
+
+ if (tmp_display == EGL_NO_DISPLAY) {
+ eglTerminate(tmp_display);
+ ERR_FAIL_V_MSG(ERR_UNAVAILABLE, "Can't get a valid initial EGL display.");
+ }
eglInitialize(tmp_display, nullptr, nullptr);
int version = gladLoaderLoadEGL(tmp_display);
+ if (!version) {
+ eglTerminate(tmp_display);
+ ERR_FAIL_V_MSG(ERR_UNAVAILABLE, "Can't load EGL.");
+ }
+
+ int major = GLAD_VERSION_MAJOR(version);
+ int minor = GLAD_VERSION_MINOR(version);
- ERR_FAIL_COND_V_MSG(!version, ERR_UNAVAILABLE, "Can't load EGL.");
- print_verbose(vformat("Loaded EGL %d.%d", GLAD_VERSION_MAJOR(version), GLAD_VERSION_MINOR(version)));
+ print_verbose(vformat("Loaded EGL %d.%d", major, minor));
- ERR_FAIL_COND_V_MSG(!GLAD_EGL_VERSION_1_4, ERR_UNAVAILABLE, "EGL version is too old!");
+ ERR_FAIL_COND_V_MSG(!GLAD_EGL_VERSION_1_4, ERR_UNAVAILABLE, vformat("EGL version is too old! %d.%d < 1.4", major, minor));
eglTerminate(tmp_display);
#endif
@@ -378,13 +424,14 @@ Error EGLManager::initialize() {
}
#endif
- String extensions_string = eglQueryString(EGL_NO_DISPLAY, EGL_EXTENSIONS);
- // The above method should always work. If it doesn't, something's very wrong.
- ERR_FAIL_COND_V(eglGetError() != EGL_SUCCESS, ERR_BUG);
+ String client_extensions_string = eglQueryString(EGL_NO_DISPLAY, EGL_EXTENSIONS);
- const char *platform = _get_platform_extension_name();
- if (!extensions_string.split(" ").has(platform)) {
- ERR_FAIL_V_MSG(ERR_UNAVAILABLE, vformat("EGL platform extension \"%s\" not found.", platform));
+ // If the above method fails, we don't support client extensions, so there's nothing to check.
+ if (eglGetError() == EGL_SUCCESS) {
+ const char *platform = _get_platform_extension_name();
+ if (!client_extensions_string.split(" ").has(platform)) {
+ ERR_FAIL_V_MSG(ERR_UNAVAILABLE, vformat("EGL platform extension \"%s\" not found.", platform));
+ }
}
return OK;
diff --git a/drivers/egl/egl_manager.h b/drivers/egl/egl_manager.h
index 83779349f0..a4502c0687 100644
--- a/drivers/egl/egl_manager.h
+++ b/drivers/egl/egl_manager.h
@@ -107,7 +107,7 @@ public:
EGLContext get_context(DisplayServer::WindowID p_window_id);
- Error initialize();
+ Error initialize(void *p_native_display = nullptr);
EGLManager();
virtual ~EGLManager();
diff --git a/drivers/gles3/rasterizer_gles3.cpp b/drivers/gles3/rasterizer_gles3.cpp
index 993197e371..071765a03c 100644
--- a/drivers/gles3/rasterizer_gles3.cpp
+++ b/drivers/gles3/rasterizer_gles3.cpp
@@ -195,9 +195,9 @@ void RasterizerGLES3::initialize() {
Engine::get_singleton()->print_header(vformat("OpenGL API %s - Compatibility - Using Device: %s - %s", RS::get_singleton()->get_video_adapter_api_version(), RS::get_singleton()->get_video_adapter_vendor(), RS::get_singleton()->get_video_adapter_name()));
// FLIP XY Bug: Are more devices affected?
- // Confirmed so far: all Adreno 3xx
+ // Confirmed so far: all Adreno 3xx with old driver (until 2018)
// ok on some tested Adreno devices: 4xx, 5xx and 6xx
- flip_xy_bugfix = GLES3::Config::get_singleton()->adreno_3xx_compatibility;
+ flip_xy_workaround = GLES3::Config::get_singleton()->flip_xy_workaround;
}
void RasterizerGLES3::finalize() {
@@ -411,7 +411,7 @@ void RasterizerGLES3::_blit_render_target_to_screen(RID p_render_target, Display
// Adreno (TM) 3xx devices have a bug that create wrong Landscape rotation of 180 degree
// Reversing both the X and Y axis is equivalent to rotating 180 degrees
bool flip_x = false;
- if (flip_xy_bugfix && screen_rect_end.x > screen_rect_end.y) {
+ if (flip_xy_workaround && screen_rect_end.x > screen_rect_end.y) {
flip_y = !flip_y;
flip_x = !flip_x;
}
diff --git a/drivers/gles3/rasterizer_gles3.h b/drivers/gles3/rasterizer_gles3.h
index 09d3c7bd52..0d0c26016d 100644
--- a/drivers/gles3/rasterizer_gles3.h
+++ b/drivers/gles3/rasterizer_gles3.h
@@ -56,7 +56,7 @@ private:
float delta = 0;
double time_total = 0.0;
- bool flip_xy_bugfix = false;
+ bool flip_xy_workaround = false;
static bool gles_over_gl;
diff --git a/drivers/gles3/shaders/scene.glsl b/drivers/gles3/shaders/scene.glsl
index 2b372cb88d..be7a6aba57 100644
--- a/drivers/gles3/shaders/scene.glsl
+++ b/drivers/gles3/shaders/scene.glsl
@@ -1523,6 +1523,9 @@ void main() {
#CODE : FRAGMENT
}
+ // Keep albedo values in positive number range as negative values "wraparound" into positive numbers resulting in wrong colors
+ albedo = max(albedo, vec3(0.0));
+
#ifdef LIGHT_VERTEX_USED
vertex = light_vertex;
#ifdef USE_MULTIVIEW
diff --git a/drivers/gles3/storage/config.cpp b/drivers/gles3/storage/config.cpp
index 6b5e227782..07e6d04cb7 100644
--- a/drivers/gles3/storage/config.cpp
+++ b/drivers/gles3/storage/config.cpp
@@ -169,8 +169,31 @@ Config::Config() {
//Adreno 3xx Compatibility
const String rendering_device_name = String::utf8((const char *)glGetString(GL_RENDERER));
- //TODO: Check the number between 300 and 399(?)
- adreno_3xx_compatibility = (rendering_device_name.left(13) == "Adreno (TM) 3");
+ if (rendering_device_name.left(13) == "Adreno (TM) 3") {
+ flip_xy_workaround = true;
+ disable_particles_workaround = true;
+
+ // ignore driver version 331+
+ const String gl_version = String::utf8((const char *)glGetString(GL_VERSION));
+ // Adreno 3xx examples (https://opengles.gpuinfo.org/listreports.php):
+ // ===========================================================================
+ // OpenGL ES 3.0 V@84.0 AU@ (CL@)
+ // OpenGL ES 3.0 V@127.0 AU@ (GIT@I96aee987eb)
+ // OpenGL ES 3.0 V@140.0 AU@ (GIT@Ifd751822f5)
+ // OpenGL ES 3.0 V@251.0 AU@08.00.00.312.030 (GIT@Ie4790512f3)
+ // OpenGL ES 3.0 V@269.0 AU@ (GIT@I109c45a694)
+ // OpenGL ES 3.0 V@331.0 (GIT@35e467f, Ice9844a736) (Date:04/15/19)
+ // OpenGL ES 3.0 V@415.0 (GIT@d39f783, I79de86aa2c, 1591296226) (Date:06/04/20)
+ // OpenGL ES 3.0 V@0502.0 (GIT@09fef447e8, I1fe547a144, 1661493934) (Date:08/25/22)
+ String driver_version = gl_version.get_slice("V@", 1).get_slice(" ", 0);
+ if (driver_version.is_valid_float() && driver_version.to_float() >= 331.0) {
+ flip_xy_workaround = false;
+
+ //TODO: also 'GPUParticles'?
+ //https://github.com/godotengine/godot/issues/92662#issuecomment-2161199477
+ //disable_particles_workaround = false;
+ }
+ }
}
Config::~Config() {
diff --git a/drivers/gles3/storage/config.h b/drivers/gles3/storage/config.h
index c3ab65f0bc..ee7b1b26ed 100644
--- a/drivers/gles3/storage/config.h
+++ b/drivers/gles3/storage/config.h
@@ -91,7 +91,9 @@ public:
bool rt_msaa_multiview_supported = false;
bool multiview_supported = false;
- bool adreno_3xx_compatibility = false;
+ // Adreno 3XX compatibility
+ bool disable_particles_workaround = false; // set to 'true' to disable 'GPUParticles'
+ bool flip_xy_workaround = false;
#ifdef ANDROID_ENABLED
PFNGLFRAMEBUFFERTEXTUREMULTIVIEWOVRPROC eglFramebufferTextureMultiviewOVR = nullptr;
diff --git a/drivers/gles3/storage/particles_storage.cpp b/drivers/gles3/storage/particles_storage.cpp
index fee90599e0..b600681280 100644
--- a/drivers/gles3/storage/particles_storage.cpp
+++ b/drivers/gles3/storage/particles_storage.cpp
@@ -122,7 +122,7 @@ void ParticlesStorage::particles_set_mode(RID p_particles, RS::ParticlesMode p_m
}
void ParticlesStorage::particles_set_emitting(RID p_particles, bool p_emitting) {
- ERR_FAIL_COND_MSG(GLES3::Config::get_singleton()->adreno_3xx_compatibility, "Due to driver bugs, GPUParticles are not supported on Adreno 3XX devices. Please use CPUParticles instead.");
+ ERR_FAIL_COND_MSG(GLES3::Config::get_singleton()->disable_particles_workaround, "Due to driver bugs, GPUParticles are not supported on Adreno 3XX devices. Please use CPUParticles instead.");
Particles *particles = particles_owner.get_or_null(p_particles);
ERR_FAIL_NULL(particles);
@@ -131,7 +131,7 @@ void ParticlesStorage::particles_set_emitting(RID p_particles, bool p_emitting)
}
bool ParticlesStorage::particles_get_emitting(RID p_particles) {
- if (GLES3::Config::get_singleton()->adreno_3xx_compatibility) {
+ if (GLES3::Config::get_singleton()->disable_particles_workaround) {
return false;
}
diff --git a/editor/animation_track_editor.cpp b/editor/animation_track_editor.cpp
index 58dd659e86..d45f1d7a78 100644
--- a/editor/animation_track_editor.cpp
+++ b/editor/animation_track_editor.cpp
@@ -2934,7 +2934,7 @@ void AnimationTrackEdit::gui_input(const Ref<InputEvent> &p_event) {
}
if (selected || editor->is_selection_active()) {
AnimationPlayer *player = AnimationPlayerEditor::get_singleton()->get_player();
- if (!player->has_animation(SceneStringName(RESET)) || animation != player->get_animation(SceneStringName(RESET))) {
+ if ((!player->has_animation(SceneStringName(RESET)) || animation != player->get_animation(SceneStringName(RESET))) && editor->can_add_reset_key()) {
menu->add_icon_item(get_editor_theme_icon(SNAME("Reload")), TTR("Add RESET Value(s)"), MENU_KEY_ADD_RESET);
}
@@ -4529,6 +4529,16 @@ bool AnimationTrackEditor::is_snap_enabled() const {
return snap->is_pressed() ^ Input::get_singleton()->is_key_pressed(Key::CMD_OR_CTRL);
}
+bool AnimationTrackEditor::can_add_reset_key() const {
+ for (const KeyValue<SelectedKey, KeyInfo> &E : selection) {
+ const Animation::TrackType track_type = animation->track_get_type(E.key.track);
+ if (track_type != Animation::TYPE_ANIMATION && track_type != Animation::TYPE_AUDIO && track_type != Animation::TYPE_METHOD) {
+ return true;
+ }
+ }
+ return false;
+}
+
void AnimationTrackEditor::_update_tracks() {
int selected = _get_track_selected();
@@ -6621,6 +6631,11 @@ void AnimationTrackEditor::_edit_menu_pressed(int p_option) {
for (const KeyValue<SelectedKey, KeyInfo> &E : selection) {
const SelectedKey &sk = E.key;
+ const Animation::TrackType track_type = animation->track_get_type(E.key.track);
+ if (track_type == Animation::TYPE_ANIMATION || track_type == Animation::TYPE_AUDIO || track_type == Animation::TYPE_METHOD) {
+ continue;
+ }
+
// Only add one key per track.
if (tracks_added.has(sk.track)) {
continue;
diff --git a/editor/animation_track_editor.h b/editor/animation_track_editor.h
index 09f751c8dd..1498a948f5 100644
--- a/editor/animation_track_editor.h
+++ b/editor/animation_track_editor.h
@@ -727,6 +727,7 @@ public:
bool is_key_clipboard_active() const;
bool is_moving_selection() const;
bool is_snap_enabled() const;
+ bool can_add_reset_key() const;
float get_moving_selection_offset() const;
float snap_time(float p_value, bool p_relative = false);
bool is_grouping_tracks();
diff --git a/editor/editor_inspector.cpp b/editor/editor_inspector.cpp
index 33f460e23d..7f21bb9ca8 100644
--- a/editor/editor_inspector.cpp
+++ b/editor/editor_inspector.cpp
@@ -88,17 +88,17 @@ Size2 EditorProperty::get_minimum_size() const {
if (keying) {
Ref<Texture2D> key = get_editor_theme_icon(SNAME("Key"));
- ms.width += key->get_width() + get_theme_constant(SNAME("hseparator"), SNAME("Tree"));
+ ms.width += key->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
}
if (deletable) {
Ref<Texture2D> key = get_editor_theme_icon(SNAME("Close"));
- ms.width += key->get_width() + get_theme_constant(SNAME("hseparator"), SNAME("Tree"));
+ ms.width += key->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
}
if (checkable) {
Ref<Texture2D> check = get_theme_icon(SNAME("checked"), SNAME("CheckBox"));
- ms.width += check->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("CheckBox")) + get_theme_constant(SNAME("hseparator"), SNAME("Tree"));
+ ms.width += check->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
}
if (bottom_editor != nullptr && bottom_editor->is_visible()) {
@@ -179,9 +179,9 @@ void EditorProperty::_notification(int p_what) {
key = get_editor_theme_icon(SNAME("Key"));
}
- rect.size.x -= key->get_width() + get_theme_constant(SNAME("hseparator"), SNAME("Tree"));
+ rect.size.x -= key->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
if (is_layout_rtl()) {
- rect.position.x += key->get_width() + get_theme_constant(SNAME("hseparator"), SNAME("Tree"));
+ rect.position.x += key->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
}
if (no_children) {
@@ -194,16 +194,27 @@ void EditorProperty::_notification(int p_what) {
close = get_editor_theme_icon(SNAME("Close"));
- rect.size.x -= close->get_width() + get_theme_constant(SNAME("hseparator"), SNAME("Tree"));
+ rect.size.x -= close->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
if (is_layout_rtl()) {
- rect.position.x += close->get_width() + get_theme_constant(SNAME("hseparator"), SNAME("Tree"));
+ rect.position.x += close->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
}
if (no_children) {
text_size -= close->get_width() + 4 * EDSCALE;
}
}
+
+ // Account for the space needed on the outer side
+ // when any of the icons are visible.
+ if (keying || deletable) {
+ int separation = get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
+ rect.size.x -= separation;
+
+ if (is_layout_rtl()) {
+ rect.position.x += separation;
+ }
+ }
}
//set children
@@ -291,7 +302,7 @@ void EditorProperty::_notification(int p_what) {
} else {
draw_texture(checkbox, check_rect.position, color2);
}
- int check_ofs = get_theme_constant(SNAME("hseparator"), SNAME("Tree")) + checkbox->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("CheckBox"));
+ int check_ofs = checkbox->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
ofs += check_ofs;
text_limit -= check_ofs;
} else {
@@ -300,7 +311,7 @@ void EditorProperty::_notification(int p_what) {
if (can_revert && !is_read_only()) {
Ref<Texture2D> reload_icon = get_editor_theme_icon(SNAME("ReloadSmall"));
- text_limit -= reload_icon->get_width() + get_theme_constant(SNAME("hseparator"), SNAME("Tree")) * 2;
+ text_limit -= reload_icon->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
revert_rect = Rect2(ofs + text_limit, (size.height - reload_icon->get_height()) / 2, reload_icon->get_width(), reload_icon->get_height());
Color color2(1, 1, 1);
@@ -320,7 +331,7 @@ void EditorProperty::_notification(int p_what) {
if (!pin_hidden && pinned) {
Ref<Texture2D> pinned_icon = get_editor_theme_icon(SNAME("Pin"));
- int margin_w = get_theme_constant(SNAME("hseparator"), SNAME("Tree")) * 2;
+ int margin_w = get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
int total_icon_w = margin_w + pinned_icon->get_width();
int text_w = font->get_string_size(label, rtl ? HORIZONTAL_ALIGNMENT_RIGHT : HORIZONTAL_ALIGNMENT_LEFT, text_limit - total_icon_w, font_size).x;
int y = (size.height - pinned_icon->get_height()) / 2;
@@ -350,7 +361,7 @@ void EditorProperty::_notification(int p_what) {
key = get_editor_theme_icon(SNAME("Key"));
}
- ofs -= key->get_width() + get_theme_constant(SNAME("hseparator"), SNAME("Tree"));
+ ofs -= key->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
Color color2(1, 1, 1);
if (keying_hover) {
@@ -374,7 +385,7 @@ void EditorProperty::_notification(int p_what) {
close = get_editor_theme_icon(SNAME("Close"));
- ofs -= close->get_width() + get_theme_constant(SNAME("hseparator"), SNAME("Tree"));
+ ofs -= close->get_width() + get_theme_constant(SNAME("h_separation"), SNAME("Tree"));
Color color2(1, 1, 1);
if (delete_hover) {
diff --git a/editor/gui/editor_object_selector.cpp b/editor/gui/editor_object_selector.cpp
index 0985753430..434aef1419 100644
--- a/editor/gui/editor_object_selector.cpp
+++ b/editor/gui/editor_object_selector.cpp
@@ -239,6 +239,7 @@ EditorObjectSelector::EditorObjectSelector(EditorSelectionHistory *p_history) {
current_object_label = memnew(Label);
current_object_label->set_text_overrun_behavior(TextServer::OVERRUN_TRIM_ELLIPSIS);
current_object_label->set_h_size_flags(SIZE_EXPAND_FILL);
+ current_object_label->set_vertical_alignment(VERTICAL_ALIGNMENT_CENTER);
current_object_label->set_auto_translate_mode(AUTO_TRANSLATE_MODE_DISABLED);
main_hb->add_child(current_object_label);
diff --git a/editor/icons/Key.svg b/editor/icons/Key.svg
index fdf51fd72d..d0838b68cd 100644
--- a/editor/icons/Key.svg
+++ b/editor/icons/Key.svg
@@ -1 +1 @@
-<svg height="16" viewBox="0 0 16 16" width="16" xmlns="http://www.w3.org/2000/svg"><path d="M1 4v2h1v2h3V6h2.133a4 4 0 1 0 0-2zm10-1a2 2 0 0 1 0 4 2 2 0 0 1 0-4z" fill="#e0e0e0"/></svg>
+<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><path fill="#e0e0e0" d="M1 7v2h1v2h3V9h2.133a4 4 0 1 0 0-2zm10-1a2 2 0 0 1 0 4 2 2 0 0 1 0-4z"/></svg> \ No newline at end of file
diff --git a/editor/plugins/path_2d_editor_plugin.cpp b/editor/plugins/path_2d_editor_plugin.cpp
index a5717c3bb3..ccb4e4921b 100644
--- a/editor/plugins/path_2d_editor_plugin.cpp
+++ b/editor/plugins/path_2d_editor_plugin.cpp
@@ -155,15 +155,16 @@ bool Path2DEditor::forward_gui_input(const Ref<InputEvent> &p_event) {
}
}
+ if (action != ACTION_NONE && mb->is_pressed() && mb->get_button_index() == MouseButton::RIGHT) {
+ _cancel_current_action();
+ return true;
+ }
+
// Check for point creation.
if (mb->is_pressed() && mb->get_button_index() == MouseButton::LEFT && ((mb->is_command_or_control_pressed() && mode == MODE_EDIT) || mode == MODE_CREATE)) {
Ref<Curve2D> curve = node->get_curve();
curve->add_point(cpoint);
-
- EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
- undo_redo->create_action(TTR("Add Point to Curve"));
- undo_redo->add_do_method(curve.ptr(), "add_point", cpoint);
- undo_redo->add_undo_method(curve.ptr(), "remove_point", curve->get_point_count() - 1);
+ moving_from = cpoint;
action = ACTION_MOVING_NEW_POINT;
action_point = curve->get_point_count() - 1;
@@ -235,9 +236,12 @@ bool Path2DEditor::forward_gui_input(const Ref<InputEvent> &p_event) {
}
break;
case ACTION_MOVING_NEW_POINT: {
+ undo_redo->create_action(TTR("Add Point to Curve"));
+ undo_redo->add_do_method(curve.ptr(), "add_point", cpoint);
undo_redo->add_do_method(curve.ptr(), "set_point_position", action_point, cpoint);
- undo_redo->add_undo_method(canvas_item_editor, "update_viewport");
undo_redo->add_do_method(canvas_item_editor, "update_viewport");
+ undo_redo->add_undo_method(curve.ptr(), "remove_point", curve->get_point_count() - 1);
+ undo_redo->add_undo_method(canvas_item_editor, "update_viewport");
undo_redo->commit_action(false);
} break;
@@ -447,6 +451,10 @@ void Path2DEditor::edit(Node *p_path2d) {
canvas_item_editor = CanvasItemEditor::get_singleton();
}
+ if (action != ACTION_NONE) {
+ _cancel_current_action();
+ }
+
if (p_path2d) {
node = Object::cast_to<Path2D>(p_path2d);
@@ -551,6 +559,38 @@ void Path2DEditor::_handle_option_pressed(int p_option) {
}
}
+void Path2DEditor::_cancel_current_action() {
+ ERR_FAIL_NULL(node);
+ Ref<Curve2D> curve = node->get_curve();
+ ERR_FAIL_COND(curve.is_null());
+
+ switch (action) {
+ case ACTION_MOVING_POINT: {
+ curve->set_point_position(action_point, moving_from);
+ } break;
+
+ case ACTION_MOVING_NEW_POINT: {
+ curve->remove_point(curve->get_point_count() - 1);
+ } break;
+
+ case ACTION_MOVING_IN: {
+ curve->set_point_in(action_point, moving_from);
+ curve->set_point_out(action_point, mirror_handle_length ? -moving_from : (-moving_from.normalized() * orig_out_length));
+ } break;
+
+ case ACTION_MOVING_OUT: {
+ curve->set_point_out(action_point, moving_from);
+ curve->set_point_in(action_point, mirror_handle_length ? -moving_from : (-moving_from.normalized() * orig_in_length));
+ } break;
+
+ default: {
+ }
+ }
+
+ canvas_item_editor->update_viewport();
+ action = ACTION_NONE;
+}
+
void Path2DEditor::_confirm_clear_points() {
if (!node || node->get_curve().is_null()) {
return;
@@ -598,14 +638,6 @@ void Path2DEditor::_restore_curve_points(Path2D *p_path2d, const PackedVector2Ar
}
Path2DEditor::Path2DEditor() {
- canvas_item_editor = nullptr;
- mirror_handle_angle = true;
- mirror_handle_length = true;
- on_edge = false;
-
- mode = MODE_EDIT;
- action = ACTION_NONE;
-
curve_edit = memnew(Button);
curve_edit->set_theme_type_variation("FlatButton");
curve_edit->set_toggle_mode(true);
diff --git a/editor/plugins/path_2d_editor_plugin.h b/editor/plugins/path_2d_editor_plugin.h
index 7d1a64160b..a2857fddb7 100644
--- a/editor/plugins/path_2d_editor_plugin.h
+++ b/editor/plugins/path_2d_editor_plugin.h
@@ -57,7 +57,7 @@ class Path2DEditor : public HBoxContainer {
MODE_CLEAR_POINTS,
};
- Mode mode;
+ Mode mode = MODE_EDIT;
Button *curve_clear_points = nullptr;
Button *curve_close = nullptr;
Button *curve_create = nullptr;
@@ -68,9 +68,9 @@ class Path2DEditor : public HBoxContainer {
ConfirmationDialog *clear_points_dialog = nullptr;
- bool mirror_handle_angle;
- bool mirror_handle_length;
- bool on_edge;
+ bool mirror_handle_angle = true;
+ bool mirror_handle_length = true;
+ bool on_edge = false;
enum HandleOption {
HANDLE_OPTION_ANGLE,
@@ -85,7 +85,7 @@ class Path2DEditor : public HBoxContainer {
ACTION_MOVING_OUT,
};
- Action action;
+ Action action = ACTION_NONE;
int action_point = 0;
Point2 moving_from;
Point2 moving_screen_from;
@@ -96,6 +96,7 @@ class Path2DEditor : public HBoxContainer {
void _mode_selected(int p_mode);
void _handle_option_pressed(int p_option);
+ void _cancel_current_action();
void _node_visibility_changed();
diff --git a/editor/plugins/sprite_frames_editor_plugin.cpp b/editor/plugins/sprite_frames_editor_plugin.cpp
index ae6ec0f702..d1da61e5fc 100644
--- a/editor/plugins/sprite_frames_editor_plugin.cpp
+++ b/editor/plugins/sprite_frames_editor_plugin.cpp
@@ -1476,8 +1476,8 @@ void SpriteFramesEditor::edit(Ref<SpriteFrames> p_frames) {
_fetch_sprite_node(); // Fetch node after set frames.
}
-bool SpriteFramesEditor::is_editing() const {
- return frames.is_valid();
+Ref<SpriteFrames> SpriteFramesEditor::get_sprite_frames() const {
+ return frames;
}
Variant SpriteFramesEditor::get_drag_data_fw(const Point2 &p_point, Control *p_from) {
@@ -2337,7 +2337,11 @@ bool SpriteFramesEditorPlugin::handles(Object *p_object) const {
if (animated_sprite_3d && *animated_sprite_3d->get_sprite_frames()) {
return true;
}
- return !frames_editor->is_editing() && Object::cast_to<SpriteFrames>(p_object);
+ SpriteFrames *frames = Object::cast_to<SpriteFrames>(p_object);
+ if (frames && (frames_editor->get_sprite_frames().is_null() || frames_editor->get_sprite_frames() == frames)) {
+ return true;
+ }
+ return false;
}
void SpriteFramesEditorPlugin::make_visible(bool p_visible) {
diff --git a/editor/plugins/sprite_frames_editor_plugin.h b/editor/plugins/sprite_frames_editor_plugin.h
index 0e26a793a7..9b6aaf98fe 100644
--- a/editor/plugins/sprite_frames_editor_plugin.h
+++ b/editor/plugins/sprite_frames_editor_plugin.h
@@ -269,7 +269,7 @@ protected:
public:
void edit(Ref<SpriteFrames> p_frames);
- bool is_editing() const;
+ Ref<SpriteFrames> get_sprite_frames() const;
SpriteFramesEditor();
};
diff --git a/main/main.cpp b/main/main.cpp
index 44201522af..1cbd732747 100644
--- a/main/main.cpp
+++ b/main/main.cpp
@@ -2896,7 +2896,7 @@ Error Main::setup2() {
MAIN_PRINT("Main: Setup Logo");
-#if !defined(TOOLS_ENABLED) && (defined(WEB_ENABLED) || defined(ANDROID_ENABLED))
+#if !defined(TOOLS_ENABLED) && defined(WEB_ENABLED)
bool show_logo = false;
#else
bool show_logo = true;
diff --git a/platform/android/export/export_plugin.cpp b/platform/android/export/export_plugin.cpp
index eebef3f969..ad00659257 100644
--- a/platform/android/export/export_plugin.cpp
+++ b/platform/android/export/export_plugin.cpp
@@ -212,11 +212,6 @@ static const char *android_perms[] = {
static const char *MISMATCHED_VERSIONS_MESSAGE = "Android build version mismatch:\n| Template installed: %s\n| Requested version: %s\nPlease reinstall Android build template from 'Project' menu.";
-static const char *SPLASH_IMAGE_EXPORT_PATH = "res/drawable-nodpi/splash.png";
-static const char *LEGACY_BUILD_SPLASH_IMAGE_EXPORT_PATH = "res/drawable-nodpi-v4/splash.png";
-static const char *SPLASH_BG_COLOR_PATH = "res/drawable-nodpi/splash_bg_color.png";
-static const char *LEGACY_BUILD_SPLASH_BG_COLOR_PATH = "res/drawable-nodpi-v4/splash_bg_color.png";
-static const char *SPLASH_CONFIG_PATH = "res/drawable/splash_drawable.xml";
static const char *GDEXTENSION_LIBS_PATH = "libs/gdextensionlibs.json";
static const int icon_densities_count = 6;
@@ -1642,67 +1637,6 @@ void EditorExportPlatformAndroid::_process_launcher_icons(const String &p_file_n
}
}
-String EditorExportPlatformAndroid::load_splash_refs(Ref<Image> &splash_image, Ref<Image> &splash_bg_color_image) {
- bool scale_splash = GLOBAL_GET("application/boot_splash/fullsize");
- bool apply_filter = GLOBAL_GET("application/boot_splash/use_filter");
- bool show_splash_image = GLOBAL_GET("application/boot_splash/show_image");
- String project_splash_path = GLOBAL_GET("application/boot_splash/image");
-
- // Setup the splash bg color.
- bool bg_color_valid = false;
- Color bg_color = ProjectSettings::get_singleton()->get("application/boot_splash/bg_color", &bg_color_valid);
- if (!bg_color_valid) {
- bg_color = boot_splash_bg_color;
- }
-
- if (show_splash_image) {
- if (!project_splash_path.is_empty()) {
- splash_image.instantiate();
- print_verbose("Loading splash image: " + project_splash_path);
- const Error err = ImageLoader::load_image(project_splash_path, splash_image);
- if (err) {
- if (OS::get_singleton()->is_stdout_verbose()) {
- print_error("- unable to load splash image from " + project_splash_path + " (" + itos(err) + ")");
- }
- splash_image.unref();
- }
- }
- } else {
- splash_image.instantiate();
- splash_image->initialize_data(1, 1, false, Image::FORMAT_RGBA8);
- splash_image->set_pixel(0, 0, bg_color);
- }
-
- if (splash_image.is_null()) {
- // Use the default
- print_verbose("Using default splash image.");
- splash_image = Ref<Image>(memnew(Image(boot_splash_png)));
- }
-
- if (scale_splash) {
- Size2 screen_size = Size2(GLOBAL_GET("display/window/size/viewport_width"), GLOBAL_GET("display/window/size/viewport_height"));
- int width, height;
- if (screen_size.width > screen_size.height) {
- // scale horizontally
- height = screen_size.height;
- width = splash_image->get_width() * screen_size.height / splash_image->get_height();
- } else {
- // scale vertically
- width = screen_size.width;
- height = splash_image->get_height() * screen_size.width / splash_image->get_width();
- }
- splash_image->resize(width, height);
- }
-
- print_verbose("Creating splash background color image.");
- splash_bg_color_image.instantiate();
- splash_bg_color_image->initialize_data(splash_image->get_width(), splash_image->get_height(), false, splash_image->get_format());
- splash_bg_color_image->fill(bg_color);
-
- String processed_splash_config_xml = vformat(SPLASH_CONFIG_XML_CONTENT, bool_to_string(apply_filter));
- return processed_splash_config_xml;
-}
-
void EditorExportPlatformAndroid::load_icon_refs(const Ref<EditorExportPreset> &p_preset, Ref<Image> &icon, Ref<Image> &foreground, Ref<Image> &background) {
String project_icon_path = GLOBAL_GET("application/config/icon");
@@ -1739,61 +1673,34 @@ void EditorExportPlatformAndroid::load_icon_refs(const Ref<EditorExportPreset> &
}
void EditorExportPlatformAndroid::_copy_icons_to_gradle_project(const Ref<EditorExportPreset> &p_preset,
- const String &processed_splash_config_xml,
- const Ref<Image> &splash_image,
- const Ref<Image> &splash_bg_color_image,
- const Ref<Image> &main_image,
- const Ref<Image> &foreground,
- const Ref<Image> &background) {
+ const Ref<Image> &p_main_image,
+ const Ref<Image> &p_foreground,
+ const Ref<Image> &p_background) {
String gradle_build_dir = ExportTemplateManager::get_android_build_directory(p_preset);
- // Store the splash configuration
- if (!processed_splash_config_xml.is_empty()) {
- print_verbose("Storing processed splash configuration: " + String("\n") + processed_splash_config_xml);
- store_string_at_path(gradle_build_dir.path_join(SPLASH_CONFIG_PATH), processed_splash_config_xml);
- }
-
- // Store the splash image
- if (splash_image.is_valid() && !splash_image->is_empty()) {
- String splash_export_path = gradle_build_dir.path_join(SPLASH_IMAGE_EXPORT_PATH);
- print_verbose("Storing splash image in " + splash_export_path);
- Vector<uint8_t> data;
- _load_image_data(splash_image, data);
- store_file_at_path(splash_export_path, data);
- }
-
- // Store the splash bg color image
- if (splash_bg_color_image.is_valid() && !splash_bg_color_image->is_empty()) {
- String splash_bg_color_path = gradle_build_dir.path_join(SPLASH_BG_COLOR_PATH);
- print_verbose("Storing splash background image in " + splash_bg_color_path);
- Vector<uint8_t> data;
- _load_image_data(splash_bg_color_image, data);
- store_file_at_path(splash_bg_color_path, data);
- }
-
// Prepare images to be resized for the icons. If some image ends up being uninitialized,
// the default image from the export template will be used.
for (int i = 0; i < icon_densities_count; ++i) {
- if (main_image.is_valid() && !main_image->is_empty()) {
+ if (p_main_image.is_valid() && !p_main_image->is_empty()) {
print_verbose("Processing launcher icon for dimension " + itos(launcher_icons[i].dimensions) + " into " + launcher_icons[i].export_path);
Vector<uint8_t> data;
- _process_launcher_icons(launcher_icons[i].export_path, main_image, launcher_icons[i].dimensions, data);
+ _process_launcher_icons(launcher_icons[i].export_path, p_main_image, launcher_icons[i].dimensions, data);
store_file_at_path(gradle_build_dir.path_join(launcher_icons[i].export_path), data);
}
- if (foreground.is_valid() && !foreground->is_empty()) {
- print_verbose("Processing launcher adaptive icon foreground for dimension " + itos(launcher_adaptive_icon_foregrounds[i].dimensions) + " into " + launcher_adaptive_icon_foregrounds[i].export_path);
+ if (p_foreground.is_valid() && !p_foreground->is_empty()) {
+ print_verbose("Processing launcher adaptive icon p_foreground for dimension " + itos(launcher_adaptive_icon_foregrounds[i].dimensions) + " into " + launcher_adaptive_icon_foregrounds[i].export_path);
Vector<uint8_t> data;
- _process_launcher_icons(launcher_adaptive_icon_foregrounds[i].export_path, foreground,
+ _process_launcher_icons(launcher_adaptive_icon_foregrounds[i].export_path, p_foreground,
launcher_adaptive_icon_foregrounds[i].dimensions, data);
store_file_at_path(gradle_build_dir.path_join(launcher_adaptive_icon_foregrounds[i].export_path), data);
}
- if (background.is_valid() && !background->is_empty()) {
- print_verbose("Processing launcher adaptive icon background for dimension " + itos(launcher_adaptive_icon_backgrounds[i].dimensions) + " into " + launcher_adaptive_icon_backgrounds[i].export_path);
+ if (p_background.is_valid() && !p_background->is_empty()) {
+ print_verbose("Processing launcher adaptive icon p_background for dimension " + itos(launcher_adaptive_icon_backgrounds[i].dimensions) + " into " + launcher_adaptive_icon_backgrounds[i].export_path);
Vector<uint8_t> data;
- _process_launcher_icons(launcher_adaptive_icon_backgrounds[i].export_path, background,
+ _process_launcher_icons(launcher_adaptive_icon_backgrounds[i].export_path, p_background,
launcher_adaptive_icon_backgrounds[i].dimensions, data);
store_file_at_path(gradle_build_dir.path_join(launcher_adaptive_icon_backgrounds[i].export_path), data);
}
@@ -3093,10 +3000,6 @@ Error EditorExportPlatformAndroid::export_project_helper(const Ref<EditorExportP
print_verbose("- include filter: " + p_preset->get_include_filter());
print_verbose("- exclude filter: " + p_preset->get_exclude_filter());
- Ref<Image> splash_image;
- Ref<Image> splash_bg_color_image;
- String processed_splash_config_xml = load_splash_refs(splash_image, splash_bg_color_image);
-
Ref<Image> main_image;
Ref<Image> foreground;
Ref<Image> background;
@@ -3172,7 +3075,7 @@ Error EditorExportPlatformAndroid::export_project_helper(const Ref<EditorExportP
add_message(EXPORT_MESSAGE_ERROR, TTR("Export"), TTR("Unable to overwrite res/*.xml files with project name."));
}
// Copies the project icon files into the appropriate Gradle project directory.
- _copy_icons_to_gradle_project(p_preset, processed_splash_config_xml, splash_image, splash_bg_color_image, main_image, foreground, background);
+ _copy_icons_to_gradle_project(p_preset, main_image, foreground, background);
// Write an AndroidManifest.xml file into the Gradle project directory.
_write_tmp_manifest(p_preset, p_give_internet, p_debug);
@@ -3486,16 +3389,6 @@ Error EditorExportPlatformAndroid::export_project_helper(const Ref<EditorExportP
_fix_resources(p_preset, data);
}
- // Process the splash image
- if ((file == SPLASH_IMAGE_EXPORT_PATH || file == LEGACY_BUILD_SPLASH_IMAGE_EXPORT_PATH) && splash_image.is_valid() && !splash_image->is_empty()) {
- _load_image_data(splash_image, data);
- }
-
- // Process the splash bg color image
- if ((file == SPLASH_BG_COLOR_PATH || file == LEGACY_BUILD_SPLASH_BG_COLOR_PATH) && splash_bg_color_image.is_valid() && !splash_bg_color_image->is_empty()) {
- _load_image_data(splash_bg_color_image, data);
- }
-
if (file.ends_with(".png") && file.contains("mipmap")) {
for (int i = 0; i < icon_densities_count; ++i) {
if (main_image.is_valid() && !main_image->is_empty()) {
diff --git a/platform/android/export/export_plugin.h b/platform/android/export/export_plugin.h
index 679afdc50f..97bbd0c7bc 100644
--- a/platform/android/export/export_plugin.h
+++ b/platform/android/export/export_plugin.h
@@ -39,18 +39,6 @@
#include "core/os/os.h"
#include "editor/export/editor_export_platform.h"
-const String SPLASH_CONFIG_XML_CONTENT = R"SPLASH(<?xml version="1.0" encoding="utf-8"?>
-<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
- <item android:drawable="@drawable/splash_bg_color" />
- <item>
- <bitmap
- android:gravity="center"
- android:filter="%s"
- android:src="@drawable/splash" />
- </item>
-</layer-list>
-)SPLASH";
-
// Optional environment variables for defining confidential information. If any
// of these is set, they will override the values set in the credentials file.
const String ENV_ANDROID_KEYSTORE_DEBUG_PATH = "GODOT_ANDROID_KEYSTORE_DEBUG_PATH";
@@ -179,17 +167,12 @@ class EditorExportPlatformAndroid : public EditorExportPlatform {
void _process_launcher_icons(const String &p_file_name, const Ref<Image> &p_source_image, int dimension, Vector<uint8_t> &p_data);
- String load_splash_refs(Ref<Image> &splash_image, Ref<Image> &splash_bg_color_image);
-
void load_icon_refs(const Ref<EditorExportPreset> &p_preset, Ref<Image> &icon, Ref<Image> &foreground, Ref<Image> &background);
void _copy_icons_to_gradle_project(const Ref<EditorExportPreset> &p_preset,
- const String &processed_splash_config_xml,
- const Ref<Image> &splash_image,
- const Ref<Image> &splash_bg_color_image,
- const Ref<Image> &main_image,
- const Ref<Image> &foreground,
- const Ref<Image> &background);
+ const Ref<Image> &p_main_image,
+ const Ref<Image> &p_foreground,
+ const Ref<Image> &p_background);
static void _create_editor_debug_keystore_if_needed();
diff --git a/platform/android/java/app/build.gradle b/platform/android/java/app/build.gradle
index bde6a93c86..01d5d9ef92 100644
--- a/platform/android/java/app/build.gradle
+++ b/platform/android/java/app/build.gradle
@@ -32,6 +32,7 @@ configurations {
dependencies {
implementation "androidx.fragment:fragment:$versions.fragmentVersion"
+ implementation "androidx.core:core-splashscreen:$versions.splashscreenVersion"
if (rootProject.findProject(":lib")) {
implementation project(":lib")
diff --git a/platform/android/java/app/config.gradle b/platform/android/java/app/config.gradle
index c404af34d8..01759a1b2f 100644
--- a/platform/android/java/app/config.gradle
+++ b/platform/android/java/app/config.gradle
@@ -11,7 +11,8 @@ ext.versions = [
nexusPublishVersion: '1.3.0',
javaVersion : JavaVersion.VERSION_17,
// Also update 'platform/android/detect.py#get_ndk_version()' when this is updated.
- ndkVersion : '23.2.8568313'
+ ndkVersion : '23.2.8568313',
+ splashscreenVersion: '1.0.1'
]
diff --git a/platform/android/java/app/res/drawable-nodpi/splash.png b/platform/android/java/app/res/drawable-nodpi/splash.png
deleted file mode 100644
index 7bddd4325a..0000000000
--- a/platform/android/java/app/res/drawable-nodpi/splash.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/java/app/res/drawable-nodpi/splash_bg_color.png b/platform/android/java/app/res/drawable-nodpi/splash_bg_color.png
deleted file mode 100644
index 004b6fd508..0000000000
--- a/platform/android/java/app/res/drawable-nodpi/splash_bg_color.png
+++ /dev/null
Binary files differ
diff --git a/platform/android/java/app/res/drawable/splash_drawable.xml b/platform/android/java/app/res/drawable/splash_drawable.xml
deleted file mode 100644
index 30627b998c..0000000000
--- a/platform/android/java/app/res/drawable/splash_drawable.xml
+++ /dev/null
@@ -1,12 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
-
- <item android:drawable="@drawable/splash_bg_color" />
-
- <item>
- <bitmap
- android:gravity="center"
- android:filter="false"
- android:src="@drawable/splash" />
- </item>
-</layer-list>
diff --git a/platform/android/java/app/res/values/themes.xml b/platform/android/java/app/res/values/themes.xml
index d64b50ca45..3ab8401928 100644
--- a/platform/android/java/app/res/values/themes.xml
+++ b/platform/android/java/app/res/values/themes.xml
@@ -3,8 +3,17 @@
<style name="GodotAppMainTheme" parent="@android:style/Theme.Black.NoTitleBar"/>
- <style name="GodotAppSplashTheme" parent="@android:style/Theme.Black.NoTitleBar.Fullscreen">
- <item name="android:windowBackground">@drawable/splash_drawable</item>
- <item name="android:windowLayoutInDisplayCutoutMode">shortEdges</item>
+ <style name="GodotAppSplashTheme" parent="Theme.SplashScreen">
+ <!-- Set the splash screen background, animated icon, and animation
+ duration. -->
+ <item name="android:windowSplashScreenBackground">@mipmap/icon_background</item>
+
+ <!-- Use windowSplashScreenAnimatedIcon to add a drawable or an animated
+ drawable. One of these is required. -->
+ <item name="windowSplashScreenAnimatedIcon">@mipmap/icon_foreground</item>
+
+ <!-- Set the theme of the Activity that directly follows your splash
+ screen. This is required. -->
+ <item name="postSplashScreenTheme">@style/GodotAppMainTheme</item>
</style>
</resources>
diff --git a/platform/android/java/app/src/com/godot/game/GodotApp.java b/platform/android/java/app/src/com/godot/game/GodotApp.java
index 9142d767b4..22e617f6e7 100644
--- a/platform/android/java/app/src/com/godot/game/GodotApp.java
+++ b/platform/android/java/app/src/com/godot/game/GodotApp.java
@@ -34,6 +34,8 @@ import org.godotengine.godot.GodotActivity;
import android.os.Bundle;
+import androidx.core.splashscreen.SplashScreen;
+
/**
* Template activity for Godot Android builds.
* Feel free to extend and modify this class for your custom logic.
@@ -41,7 +43,7 @@ import android.os.Bundle;
public class GodotApp extends GodotActivity {
@Override
public void onCreate(Bundle savedInstanceState) {
- setTheme(R.style.GodotAppMainTheme);
+ SplashScreen.installSplashScreen(this);
super.onCreate(savedInstanceState);
}
}
diff --git a/platform/android/java/editor/build.gradle b/platform/android/java/editor/build.gradle
index c5ef086152..55fe2a22fe 100644
--- a/platform/android/java/editor/build.gradle
+++ b/platform/android/java/editor/build.gradle
@@ -10,6 +10,8 @@ dependencies {
implementation project(":lib")
implementation "androidx.window:window:1.2.0"
+ implementation "androidx.core:core-splashscreen:$versions.splashscreenVersion"
+ implementation "androidx.constraintlayout:constraintlayout:2.1.4"
}
ext {
@@ -92,6 +94,10 @@ android {
targetSdkVersion versions.targetSdk
missingDimensionStrategy 'products', 'editor'
+ manifestPlaceholders += [
+ editorAppName: "Godot Editor 4",
+ editorBuildSuffix: ""
+ ]
}
base {
@@ -124,11 +130,13 @@ android {
dev {
initWith debug
applicationIdSuffix ".dev"
+ manifestPlaceholders += [editorBuildSuffix: " (dev)"]
}
debug {
initWith release
applicationIdSuffix ".debug"
+ manifestPlaceholders += [editorBuildSuffix: " (debug)"]
signingConfig signingConfigs.debug
}
diff --git a/platform/android/java/editor/src/debug/res/values/strings.xml b/platform/android/java/editor/src/debug/res/values/strings.xml
deleted file mode 100644
index 09ee2d77e1..0000000000
--- a/platform/android/java/editor/src/debug/res/values/strings.xml
+++ /dev/null
@@ -1,4 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="godot_editor_name_string">Godot Editor 4 (debug)</string>
-</resources>
diff --git a/platform/android/java/editor/src/dev/res/values/strings.xml b/platform/android/java/editor/src/dev/res/values/strings.xml
deleted file mode 100644
index 215f2c7d0a..0000000000
--- a/platform/android/java/editor/src/dev/res/values/strings.xml
+++ /dev/null
@@ -1,4 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<resources>
- <string name="godot_editor_name_string">Godot Editor 4 (dev)</string>
-</resources>
diff --git a/platform/android/java/editor/src/main/AndroidManifest.xml b/platform/android/java/editor/src/main/AndroidManifest.xml
index f646ef3f51..c7d14a3f49 100644
--- a/platform/android/java/editor/src/main/AndroidManifest.xml
+++ b/platform/android/java/editor/src/main/AndroidManifest.xml
@@ -13,12 +13,15 @@
android:glEsVersion="0x00030000"
android:required="true" />
- <uses-permission android:name="android.permission.MANAGE_EXTERNAL_STORAGE"
+ <uses-permission
+ android:name="android.permission.MANAGE_EXTERNAL_STORAGE"
tools:ignore="ScopedStorage" />
- <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"
- android:maxSdkVersion="29"/>
- <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"
- android:maxSdkVersion="29"/>
+ <uses-permission
+ android:name="android.permission.WRITE_EXTERNAL_STORAGE"
+ android:maxSdkVersion="29" />
+ <uses-permission
+ android:name="android.permission.READ_EXTERNAL_STORAGE"
+ android:maxSdkVersion="29" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.RECORD_AUDIO" />
<uses-permission android:name="android.permission.VIBRATE" />
@@ -26,39 +29,44 @@
<application
android:allowBackup="false"
android:icon="@mipmap/icon"
- android:label="@string/godot_editor_name_string"
- tools:ignore="GoogleAppIndexingWarning"
- android:theme="@style/GodotEditorTheme"
- android:requestLegacyExternalStorage="true">
+ android:label="${editorAppName}${editorBuildSuffix}"
+ android:requestLegacyExternalStorage="true"
+ android:theme="@style/GodotEditorSplashScreenTheme"
+ tools:ignore="GoogleAppIndexingWarning">
+ <profileable
+ android:shell="true"
+ android:enabled="true"
+ tools:targetApi="29" />
<activity
android:name=".GodotEditor"
android:configChanges="orientation|keyboardHidden|screenSize|smallestScreenSize|density|keyboard|navigation|screenLayout|uiMode"
+ android:exported="true"
android:launchMode="singleTask"
- android:screenOrientation="userLandscape"
- android:exported="true">
- <layout android:defaultHeight="@dimen/editor_default_window_height"
- android:defaultWidth="@dimen/editor_default_window_width" />
+ android:screenOrientation="userLandscape">
+ <layout
+ android:defaultWidth="@dimen/editor_default_window_width"
+ android:defaultHeight="@dimen/editor_default_window_height" />
<intent-filter>
<action android:name="android.intent.action.MAIN" />
+
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
-
<activity
android:name=".GodotGame"
android:configChanges="orientation|keyboardHidden|screenSize|smallestScreenSize|density|keyboard|navigation|screenLayout|uiMode"
+ android:exported="false"
android:label="@string/godot_project_name_string"
- android:process=":GodotGame"
android:launchMode="singleTask"
- android:exported="false"
+ android:process=":GodotGame"
android:screenOrientation="userLandscape">
- <layout android:defaultHeight="@dimen/editor_default_window_height"
- android:defaultWidth="@dimen/editor_default_window_width" />
+ <layout
+ android:defaultWidth="@dimen/editor_default_window_width"
+ android:defaultHeight="@dimen/editor_default_window_height" />
</activity>
-
</application>
</manifest>
diff --git a/platform/android/java/editor/src/main/java/org/godotengine/editor/GodotEditor.kt b/platform/android/java/editor/src/main/java/org/godotengine/editor/GodotEditor.kt
index 52acd63674..5515347bd6 100644
--- a/platform/android/java/editor/src/main/java/org/godotengine/editor/GodotEditor.kt
+++ b/platform/android/java/editor/src/main/java/org/godotengine/editor/GodotEditor.kt
@@ -38,8 +38,10 @@ import android.content.Intent
import android.content.pm.PackageManager
import android.os.*
import android.util.Log
+import android.view.View
import android.widget.Toast
import androidx.annotation.CallSuper
+import androidx.core.splashscreen.SplashScreen.Companion.installSplashScreen
import androidx.window.layout.WindowMetricsCalculator
import org.godotengine.godot.GodotActivity
import org.godotengine.godot.GodotLib
@@ -88,8 +90,13 @@ open class GodotEditor : GodotActivity() {
}
private val commandLineParams = ArrayList<String>()
+ private val editorLoadingIndicator: View? by lazy { findViewById(R.id.editor_loading_indicator) }
+
+ override fun getGodotAppLayout() = R.layout.godot_editor_layout
override fun onCreate(savedInstanceState: Bundle?) {
+ installSplashScreen()
+
// We exclude certain permissions from the set we request at startup, as they'll be
// requested on demand based on use-cases.
PermissionsUtil.requestManifestPermissions(this, setOf(Manifest.permission.RECORD_AUDIO))
@@ -121,6 +128,14 @@ open class GodotEditor : GodotActivity() {
}
}
+ override fun onGodotMainLoopStarted() {
+ super.onGodotMainLoopStarted()
+ runOnUiThread {
+ // Hide the loading indicator
+ editorLoadingIndicator?.visibility = View.GONE
+ }
+ }
+
/**
* Check for project permissions to enable
*/
diff --git a/platform/android/java/editor/src/main/java/org/godotengine/editor/GodotGame.kt b/platform/android/java/editor/src/main/java/org/godotengine/editor/GodotGame.kt
index aa4d02b5b2..8e4e089211 100644
--- a/platform/android/java/editor/src/main/java/org/godotengine/editor/GodotGame.kt
+++ b/platform/android/java/editor/src/main/java/org/godotengine/editor/GodotGame.kt
@@ -34,6 +34,9 @@ package org.godotengine.editor
* Drives the 'run project' window of the Godot Editor.
*/
class GodotGame : GodotEditor() {
+
+ override fun getGodotAppLayout() = org.godotengine.godot.R.layout.godot_app_layout
+
override fun overrideOrientationRequest() = false
override fun enableLongPressGestures() = false
diff --git a/platform/android/java/editor/src/main/res/layout/godot_editor_layout.xml b/platform/android/java/editor/src/main/res/layout/godot_editor_layout.xml
new file mode 100644
index 0000000000..431a468f29
--- /dev/null
+++ b/platform/android/java/editor/src/main/res/layout/godot_editor_layout.xml
@@ -0,0 +1,25 @@
+<?xml version="1.0" encoding="utf-8"?>
+<androidx.constraintlayout.widget.ConstraintLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ xmlns:app="http://schemas.android.com/apk/res-auto">
+
+ <FrameLayout
+ android:id="@+id/godot_fragment_container"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent" />
+
+ <ProgressBar
+ style="@android:style/Widget.Holo.ProgressBar.Large"
+ android:id="@+id/editor_loading_indicator"
+ android:layout_width="80dp"
+ android:layout_height="80dp"
+ android:indeterminate="true"
+ app:layout_constraintEnd_toEndOf="parent"
+ app:layout_constraintStart_toStartOf="parent"
+ app:layout_constraintTop_toTopOf="parent"
+ app:layout_constraintBottom_toBottomOf="parent"
+ app:layout_constraintVertical_bias="0.80"/>
+
+</androidx.constraintlayout.widget.ConstraintLayout>
diff --git a/platform/android/java/editor/src/main/res/values/strings.xml b/platform/android/java/editor/src/main/res/values/strings.xml
index 216d02d9c7..909711ab18 100644
--- a/platform/android/java/editor/src/main/res/values/strings.xml
+++ b/platform/android/java/editor/src/main/res/values/strings.xml
@@ -1,6 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
- <string name="godot_editor_name_string">Godot Editor 4</string>
-
<string name="denied_storage_permission_error_msg">Missing storage access permission!</string>
</resources>
diff --git a/platform/android/java/editor/src/main/res/values/themes.xml b/platform/android/java/editor/src/main/res/values/themes.xml
index fda04d6dc7..2b352247db 100644
--- a/platform/android/java/editor/src/main/res/values/themes.xml
+++ b/platform/android/java/editor/src/main/res/values/themes.xml
@@ -2,4 +2,10 @@
<resources>
<style name="GodotEditorTheme" parent="@android:style/Theme.Black.NoTitleBar.Fullscreen">
</style>
+
+ <style name="GodotEditorSplashScreenTheme" parent="Theme.SplashScreen.IconBackground">
+ <!-- Set the theme of the Activity that directly follows your splash
+ screen. This is required. -->
+ <item name="postSplashScreenTheme">@style/GodotEditorTheme</item>
+ </style>
</resources>
diff --git a/platform/android/java/lib/src/org/godotengine/godot/GodotActivity.kt b/platform/android/java/lib/src/org/godotengine/godot/GodotActivity.kt
index 7b8fad8952..4c5e857b7a 100644
--- a/platform/android/java/lib/src/org/godotengine/godot/GodotActivity.kt
+++ b/platform/android/java/lib/src/org/godotengine/godot/GodotActivity.kt
@@ -36,6 +36,7 @@ import android.content.pm.PackageManager
import android.os.Bundle
import android.util.Log
import androidx.annotation.CallSuper
+import androidx.annotation.LayoutRes
import androidx.fragment.app.FragmentActivity
import org.godotengine.godot.utils.PermissionsUtil
import org.godotengine.godot.utils.ProcessPhoenix
@@ -65,7 +66,7 @@ abstract class GodotActivity : FragmentActivity(), GodotHost {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
- setContentView(R.layout.godot_app_layout)
+ setContentView(getGodotAppLayout())
handleStartIntent(intent, true)
@@ -80,6 +81,9 @@ abstract class GodotActivity : FragmentActivity(), GodotHost {
}
}
+ @LayoutRes
+ protected open fun getGodotAppLayout() = R.layout.godot_app_layout
+
override fun onDestroy() {
Log.v(TAG, "Destroying Godot app...")
super.onDestroy()
diff --git a/platform/linuxbsd/wayland/detect_prime_egl.cpp b/platform/linuxbsd/wayland/detect_prime_egl.cpp
index 4c97a80039..e24c03c869 100644
--- a/platform/linuxbsd/wayland/detect_prime_egl.cpp
+++ b/platform/linuxbsd/wayland/detect_prime_egl.cpp
@@ -38,15 +38,6 @@
#include <stdlib.h>
-#ifdef GLAD_ENABLED
-#include "thirdparty/glad/glad/egl.h"
-#include "thirdparty/glad/glad/gl.h"
-#else
-#include <EGL/egl.h>
-#include <EGL/eglext.h>
-#include <GL/glcorearb.h>
-#endif // GLAD_ENABLED
-
#include <cstring>
#include <sys/types.h>
@@ -57,7 +48,7 @@
#undef glGetString
// Runs inside a child. Exiting will not quit the engine.
-void DetectPrimeEGL::create_context() {
+void DetectPrimeEGL::create_context(EGLenum p_platform_enum) {
#if defined(GLAD_ENABLED)
if (!gladLoaderLoadEGL(nullptr)) {
print_verbose("Unable to load EGL, GPU detection skipped.");
@@ -65,7 +56,18 @@ void DetectPrimeEGL::create_context() {
}
#endif
- EGLDisplay egl_display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
+ EGLDisplay egl_display = EGL_NO_DISPLAY;
+
+ if (GLAD_EGL_VERSION_1_5) {
+ egl_display = eglGetPlatformDisplay(p_platform_enum, nullptr, nullptr);
+ } else if (GLAD_EGL_EXT_platform_base) {
+#ifdef EGL_EXT_platform_base
+ egl_display = eglGetPlatformDisplayEXT(p_platform_enum, nullptr, nullptr);
+#endif
+ } else {
+ egl_display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
+ }
+
EGLConfig egl_config;
EGLContext egl_context = EGL_NO_CONTEXT;
@@ -110,7 +112,7 @@ void DetectPrimeEGL::create_context() {
eglMakeCurrent(egl_display, EGL_NO_SURFACE, EGL_NO_SURFACE, egl_context);
}
-int DetectPrimeEGL::detect_prime() {
+int DetectPrimeEGL::detect_prime(EGLenum p_platform_enum) {
pid_t p;
int priorities[4] = {};
String vendors[4];
@@ -168,7 +170,7 @@ int DetectPrimeEGL::detect_prime() {
setenv("DRI_PRIME", itos(i).utf8().ptr(), 1);
- create_context();
+ create_context(p_platform_enum);
PFNGLGETSTRINGPROC glGetString = (PFNGLGETSTRINGPROC)eglGetProcAddress("glGetString");
const char *vendor = (const char *)glGetString(GL_VENDOR);
diff --git a/platform/linuxbsd/wayland/detect_prime_egl.h b/platform/linuxbsd/wayland/detect_prime_egl.h
index 26351b0dce..3391e020d8 100644
--- a/platform/linuxbsd/wayland/detect_prime_egl.h
+++ b/platform/linuxbsd/wayland/detect_prime_egl.h
@@ -34,6 +34,30 @@
#ifdef GLES3_ENABLED
#ifdef EGL_ENABLED
+#ifdef GLAD_ENABLED
+#include "thirdparty/glad/glad/egl.h"
+#include "thirdparty/glad/glad/gl.h"
+#else
+#include <EGL/egl.h>
+#include <EGL/eglext.h>
+#include <GL/glcorearb.h>
+
+#define GLAD_EGL_VERSION_1_5 1
+
+#ifdef EGL_EXT_platform_base
+#define GLAD_EGL_EXT_platform_base 1
+#endif
+
+#define KHRONOS_STATIC 1
+extern "C" EGLAPI EGLDisplay EGLAPIENTRY eglGetPlatformDisplayEXT(EGLenum platform, void *native_display, const EGLint *attrib_list);
+#undef KHRONOS_STATIC
+
+#endif // GLAD_ENABLED
+
+#ifndef EGL_EXT_platform_base
+#define GLAD_EGL_EXT_platform_base 0
+#endif
+
class DetectPrimeEGL {
private:
struct Vendor {
@@ -53,10 +77,10 @@ private:
{ nullptr, 0 }
};
- static void create_context();
+ static void create_context(EGLenum p_platform_enum);
public:
- static int detect_prime();
+ static int detect_prime(EGLenum p_platform_enum);
};
#endif // GLES3_ENABLED
diff --git a/platform/linuxbsd/wayland/display_server_wayland.cpp b/platform/linuxbsd/wayland/display_server_wayland.cpp
index aff83ddeee..c231dc0f90 100644
--- a/platform/linuxbsd/wayland/display_server_wayland.cpp
+++ b/platform/linuxbsd/wayland/display_server_wayland.cpp
@@ -1342,7 +1342,7 @@ DisplayServerWayland::DisplayServerWayland(const String &p_rendering_driver, Win
if (prime_idx == -1) {
print_verbose("Detecting GPUs, set DRI_PRIME in the environment to override GPU detection logic.");
- prime_idx = DetectPrimeEGL::detect_prime();
+ prime_idx = DetectPrimeEGL::detect_prime(EGL_PLATFORM_WAYLAND_KHR);
}
if (prime_idx) {
@@ -1355,7 +1355,7 @@ DisplayServerWayland::DisplayServerWayland(const String &p_rendering_driver, Win
if (rendering_driver == "opengl3") {
egl_manager = memnew(EGLManagerWayland);
- if (egl_manager->initialize() != OK || egl_manager->open_display(wayland_thread.get_wl_display()) != OK) {
+ if (egl_manager->initialize(wayland_thread.get_wl_display()) != OK || egl_manager->open_display(wayland_thread.get_wl_display()) != OK) {
memdelete(egl_manager);
egl_manager = nullptr;
@@ -1375,7 +1375,7 @@ DisplayServerWayland::DisplayServerWayland(const String &p_rendering_driver, Win
if (rendering_driver == "opengl3_es") {
egl_manager = memnew(EGLManagerWaylandGLES);
- if (egl_manager->initialize() != OK) {
+ if (egl_manager->initialize(wayland_thread.get_wl_display()) != OK) {
memdelete(egl_manager);
egl_manager = nullptr;
r_error = ERR_CANT_CREATE;
diff --git a/platform/windows/display_server_windows.cpp b/platform/windows/display_server_windows.cpp
index 01a4fbf96e..838beddac2 100644
--- a/platform/windows/display_server_windows.cpp
+++ b/platform/windows/display_server_windows.cpp
@@ -5595,52 +5595,57 @@ DisplayServerWindows::DisplayServerWindows(const String &p_rendering_driver, Win
HMODULE nt_lib = LoadLibraryW(L"ntdll.dll");
if (nt_lib) {
- RtlGetVersionPtr RtlGetVersion = (RtlGetVersionPtr)GetProcAddress(nt_lib, "RtlGetVersion");
- if (RtlGetVersion) {
- RtlGetVersion(&os_ver);
+ WineGetVersionPtr wine_get_version = (WineGetVersionPtr)GetProcAddress(nt_lib, "wine_get_version"); // Do not read Windows build number under Wine, it can be set to arbitrary value.
+ if (!wine_get_version) {
+ RtlGetVersionPtr RtlGetVersion = (RtlGetVersionPtr)GetProcAddress(nt_lib, "RtlGetVersion");
+ if (RtlGetVersion) {
+ RtlGetVersion(&os_ver);
+ }
}
FreeLibrary(nt_lib);
}
- // Load UXTheme.
- HMODULE ux_theme_lib = LoadLibraryW(L"uxtheme.dll");
- if (ux_theme_lib) {
- ShouldAppsUseDarkMode = (ShouldAppsUseDarkModePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(132));
- GetImmersiveColorFromColorSetEx = (GetImmersiveColorFromColorSetExPtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(95));
- GetImmersiveColorTypeFromName = (GetImmersiveColorTypeFromNamePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(96));
- GetImmersiveUserColorSetPreference = (GetImmersiveUserColorSetPreferencePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(98));
- if (os_ver.dwBuildNumber >= 17763) {
- AllowDarkModeForAppPtr AllowDarkModeForApp = nullptr;
- SetPreferredAppModePtr SetPreferredAppMode = nullptr;
- FlushMenuThemesPtr FlushMenuThemes = nullptr;
- if (os_ver.dwBuildNumber < 18362) {
- AllowDarkModeForApp = (AllowDarkModeForAppPtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(135));
- } else {
- SetPreferredAppMode = (SetPreferredAppModePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(135));
- FlushMenuThemes = (FlushMenuThemesPtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(136));
- }
- RefreshImmersiveColorPolicyStatePtr RefreshImmersiveColorPolicyState = (RefreshImmersiveColorPolicyStatePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(104));
- if (ShouldAppsUseDarkMode) {
- bool dark_mode = ShouldAppsUseDarkMode();
- if (SetPreferredAppMode) {
- SetPreferredAppMode(dark_mode ? APPMODE_ALLOWDARK : APPMODE_DEFAULT);
- } else if (AllowDarkModeForApp) {
- AllowDarkModeForApp(dark_mode);
+ // Load UXTheme, available on Windows 10+ only.
+ if (os_ver.dwBuildNumber >= 10240) {
+ HMODULE ux_theme_lib = LoadLibraryW(L"uxtheme.dll");
+ if (ux_theme_lib) {
+ ShouldAppsUseDarkMode = (ShouldAppsUseDarkModePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(132));
+ GetImmersiveColorFromColorSetEx = (GetImmersiveColorFromColorSetExPtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(95));
+ GetImmersiveColorTypeFromName = (GetImmersiveColorTypeFromNamePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(96));
+ GetImmersiveUserColorSetPreference = (GetImmersiveUserColorSetPreferencePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(98));
+ if (os_ver.dwBuildNumber >= 17763) { // Windows 10 Redstone 5 (1809)+ only.
+ AllowDarkModeForAppPtr AllowDarkModeForApp = nullptr;
+ SetPreferredAppModePtr SetPreferredAppMode = nullptr;
+ FlushMenuThemesPtr FlushMenuThemes = nullptr;
+ if (os_ver.dwBuildNumber < 18362) { // Windows 10 Redstone 5 (1809) and 19H1 (1903) only.
+ AllowDarkModeForApp = (AllowDarkModeForAppPtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(135));
+ } else { // Windows 10 19H2 (1909)+ only.
+ SetPreferredAppMode = (SetPreferredAppModePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(135));
+ FlushMenuThemes = (FlushMenuThemesPtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(136));
}
- if (RefreshImmersiveColorPolicyState) {
- RefreshImmersiveColorPolicyState();
- }
- if (FlushMenuThemes) {
- FlushMenuThemes();
+ RefreshImmersiveColorPolicyStatePtr RefreshImmersiveColorPolicyState = (RefreshImmersiveColorPolicyStatePtr)GetProcAddress(ux_theme_lib, MAKEINTRESOURCEA(104));
+ if (ShouldAppsUseDarkMode) {
+ bool dark_mode = ShouldAppsUseDarkMode();
+ if (SetPreferredAppMode) {
+ SetPreferredAppMode(dark_mode ? APPMODE_ALLOWDARK : APPMODE_DEFAULT);
+ } else if (AllowDarkModeForApp) {
+ AllowDarkModeForApp(dark_mode);
+ }
+ if (RefreshImmersiveColorPolicyState) {
+ RefreshImmersiveColorPolicyState();
+ }
+ if (FlushMenuThemes) {
+ FlushMenuThemes();
+ }
}
}
- }
- ux_theme_available = ShouldAppsUseDarkMode && GetImmersiveColorFromColorSetEx && GetImmersiveColorTypeFromName && GetImmersiveUserColorSetPreference;
- if (os_ver.dwBuildNumber >= 18363) {
- dark_title_available = true;
- if (os_ver.dwBuildNumber < 19041) {
- use_legacy_dark_mode_before_20H1 = true;
+ ux_theme_available = ShouldAppsUseDarkMode && GetImmersiveColorFromColorSetEx && GetImmersiveColorTypeFromName && GetImmersiveUserColorSetPreference;
+ if (os_ver.dwBuildNumber >= 18363) {
+ dark_title_available = true;
+ if (os_ver.dwBuildNumber < 19041) {
+ use_legacy_dark_mode_before_20H1 = true;
+ }
}
}
}
diff --git a/platform/windows/display_server_windows.h b/platform/windows/display_server_windows.h
index 0f649b76d7..382f18c239 100644
--- a/platform/windows/display_server_windows.h
+++ b/platform/windows/display_server_windows.h
@@ -162,6 +162,7 @@ enum PreferredAppMode {
APPMODE_MAX = 4
};
+typedef const char *(CDECL *WineGetVersionPtr)(void);
typedef bool(WINAPI *ShouldAppsUseDarkModePtr)();
typedef DWORD(WINAPI *GetImmersiveColorFromColorSetExPtr)(UINT dwImmersiveColorSet, UINT dwImmersiveColorType, bool bIgnoreHighContrast, UINT dwHighContrastCacheMode);
typedef int(WINAPI *GetImmersiveColorTypeFromNamePtr)(const WCHAR *name);
diff --git a/scene/gui/button.cpp b/scene/gui/button.cpp
index 55ca5fc3ee..4e738216de 100644
--- a/scene/gui/button.cpp
+++ b/scene/gui/button.cpp
@@ -487,6 +487,8 @@ Size2 Button::_fit_icon_size(const Size2 &p_size) const {
}
Size2 Button::get_minimum_size_for_text_and_icon(const String &p_text, Ref<Texture2D> p_icon) const {
+ // Do not include `_internal_margin`, it's already added in the `get_minimum_size` overrides.
+
Ref<TextParagraph> paragraph;
if (p_text.is_empty()) {
paragraph = text_buf;
@@ -500,21 +502,6 @@ Size2 Button::get_minimum_size_for_text_and_icon(const String &p_text, Ref<Textu
minsize.width = 0;
}
- float left_internal_margin_with_h_separation = _internal_margin[SIDE_LEFT];
- float right_internal_margin_with_h_separation = _internal_margin[SIDE_RIGHT];
- { // The width reserved for internal element in derived classes (and h_separation if needed).
-
- if (_internal_margin[SIDE_LEFT] > 0.0f) {
- left_internal_margin_with_h_separation += theme_cache.h_separation;
- }
-
- if (_internal_margin[SIDE_RIGHT] > 0.0f) {
- right_internal_margin_with_h_separation += theme_cache.h_separation;
- }
-
- minsize.width += left_internal_margin_with_h_separation + right_internal_margin_with_h_separation; // The size after the internal element is stripped.
- }
-
if (!expand_icon && p_icon.is_valid()) {
Size2 icon_size = _fit_icon_size(p_icon->get_size());
if (vertical_icon_alignment == VERTICAL_ALIGNMENT_CENTER) {
diff --git a/scene/resources/2d/tile_set.cpp b/scene/resources/2d/tile_set.cpp
index 6c3356a205..d124577d25 100644
--- a/scene/resources/2d/tile_set.cpp
+++ b/scene/resources/2d/tile_set.cpp
@@ -6489,18 +6489,16 @@ Ref<NavigationPolygon> TileData::get_navigation_polygon(int p_layer_id, bool p_f
PackedVector2Array new_points = get_transformed_vertices(layer_tile_data.navigation_polygon->get_vertices(), p_flip_h, p_flip_v, p_transpose);
transformed_polygon->set_vertices(new_points);
+ int num_polygons = layer_tile_data.navigation_polygon->get_polygon_count();
+ for (int i = 0; i < num_polygons; ++i) {
+ transformed_polygon->add_polygon(layer_tile_data.navigation_polygon->get_polygon(i));
+ }
+
for (int i = 0; i < layer_tile_data.navigation_polygon->get_outline_count(); i++) {
PackedVector2Array new_outline = get_transformed_vertices(layer_tile_data.navigation_polygon->get_outline(i), p_flip_h, p_flip_v, p_transpose);
transformed_polygon->add_outline(new_outline);
}
- PackedInt32Array indices;
- indices.resize(new_points.size());
- int *w = indices.ptrw();
- for (int i = 0; i < new_points.size(); i++) {
- w[i] = i;
- }
- transformed_polygon->add_polygon(indices);
layer_tile_data.transformed_navigation_polygon[key] = transformed_polygon;
return transformed_polygon;
} else {
diff --git a/tests/core/io/test_image.h b/tests/core/io/test_image.h
index 7a0cbb13f9..1b51286a9f 100644
--- a/tests/core/io/test_image.h
+++ b/tests/core/io/test_image.h
@@ -78,8 +78,8 @@ TEST_CASE("[Image] Instantiation") {
TEST_CASE("[Image] Saving and loading") {
Ref<Image> image = memnew(Image(4, 4, false, Image::FORMAT_RGBA8));
- const String save_path_png = OS::get_singleton()->get_cache_path().path_join("image.png");
- const String save_path_exr = OS::get_singleton()->get_cache_path().path_join("image.exr");
+ const String save_path_png = TestUtils::get_temp_path("image.png");
+ const String save_path_exr = TestUtils::get_temp_path("image.exr");
// Save PNG
Error err;
diff --git a/tests/core/io/test_pck_packer.h b/tests/core/io/test_pck_packer.h
index fc4534a949..7ef9451963 100644
--- a/tests/core/io/test_pck_packer.h
+++ b/tests/core/io/test_pck_packer.h
@@ -42,7 +42,7 @@ namespace TestPCKPacker {
TEST_CASE("[PCKPacker] Pack an empty PCK file") {
PCKPacker pck_packer;
- const String output_pck_path = OS::get_singleton()->get_cache_path().path_join("output_empty.pck");
+ const String output_pck_path = TestUtils::get_temp_path("output_empty.pck");
CHECK_MESSAGE(
pck_packer.pck_start(output_pck_path) == OK,
"Starting a PCK file should return an OK error code.");
@@ -66,7 +66,7 @@ TEST_CASE("[PCKPacker] Pack an empty PCK file") {
TEST_CASE("[PCKPacker] Pack empty with zero alignment invalid") {
PCKPacker pck_packer;
- const String output_pck_path = OS::get_singleton()->get_cache_path().path_join("output_empty.pck");
+ const String output_pck_path = TestUtils::get_temp_path("output_empty.pck");
ERR_PRINT_OFF;
CHECK_MESSAGE(pck_packer.pck_start(output_pck_path, 0) != OK, "PCK with zero alignment should fail.");
ERR_PRINT_ON;
@@ -74,7 +74,7 @@ TEST_CASE("[PCKPacker] Pack empty with zero alignment invalid") {
TEST_CASE("[PCKPacker] Pack empty with invalid key") {
PCKPacker pck_packer;
- const String output_pck_path = OS::get_singleton()->get_cache_path().path_join("output_empty.pck");
+ const String output_pck_path = TestUtils::get_temp_path("output_empty.pck");
ERR_PRINT_OFF;
CHECK_MESSAGE(pck_packer.pck_start(output_pck_path, 32, "") != OK, "PCK with invalid key should fail.");
ERR_PRINT_ON;
@@ -82,7 +82,7 @@ TEST_CASE("[PCKPacker] Pack empty with invalid key") {
TEST_CASE("[PCKPacker] Pack a PCK file with some files and directories") {
PCKPacker pck_packer;
- const String output_pck_path = OS::get_singleton()->get_cache_path().path_join("output_with_files.pck");
+ const String output_pck_path = TestUtils::get_temp_path("output_with_files.pck");
CHECK_MESSAGE(
pck_packer.pck_start(output_pck_path) == OK,
"Starting a PCK file should return an OK error code.");
diff --git a/tests/core/io/test_resource.h b/tests/core/io/test_resource.h
index a83e7f88ba..cb1fa290b3 100644
--- a/tests/core/io/test_resource.h
+++ b/tests/core/io/test_resource.h
@@ -76,8 +76,8 @@ TEST_CASE("[Resource] Saving and loading") {
Ref<Resource> child_resource = memnew(Resource);
child_resource->set_name("I'm a child resource");
resource->set_meta("other_resource", child_resource);
- const String save_path_binary = OS::get_singleton()->get_cache_path().path_join("resource.res");
- const String save_path_text = OS::get_singleton()->get_cache_path().path_join("resource.tres");
+ const String save_path_binary = TestUtils::get_temp_path("resource.res");
+ const String save_path_text = TestUtils::get_temp_path("resource.tres");
ResourceSaver::save(resource, save_path_binary);
ResourceSaver::save(resource, save_path_text);
@@ -123,8 +123,8 @@ TEST_CASE("[Resource] Breaking circular references on save") {
resource_b->set_meta("next", resource_c);
resource_c->set_meta("next", resource_b);
- const String save_path_binary = OS::get_singleton()->get_cache_path().path_join("resource.res");
- const String save_path_text = OS::get_singleton()->get_cache_path().path_join("resource.tres");
+ const String save_path_binary = TestUtils::get_temp_path("resource.res");
+ const String save_path_text = TestUtils::get_temp_path("resource.tres");
ResourceSaver::save(resource_a, save_path_binary);
// Suppress expected errors caused by the resources above being uncached.
ERR_PRINT_OFF;
diff --git a/tests/scene/test_audio_stream_wav.h b/tests/scene/test_audio_stream_wav.h
index ed1697929e..e8f3c9e8f5 100644
--- a/tests/scene/test_audio_stream_wav.h
+++ b/tests/scene/test_audio_stream_wav.h
@@ -115,7 +115,7 @@ Vector<uint8_t> gen_pcm16_test(float wav_rate, int wav_count, bool stereo) {
}
void run_test(String file_name, AudioStreamWAV::Format data_format, bool stereo, float wav_rate, float wav_count) {
- String save_path = OS::get_singleton()->get_cache_path().path_join(file_name);
+ String save_path = TestUtils::get_temp_path(file_name);
Vector<uint8_t> test_data;
if (data_format == AudioStreamWAV::FORMAT_8_BITS) {
@@ -200,7 +200,7 @@ TEST_CASE("[AudioStreamWAV] Alternate mix rate") {
}
TEST_CASE("[AudioStreamWAV] save_to_wav() adds '.wav' file extension automatically") {
- String save_path = OS::get_singleton()->get_cache_path().path_join("test_wav_extension");
+ String save_path = TestUtils::get_temp_path("test_wav_extension");
Vector<uint8_t> test_data = gen_pcm8_test(WAV_RATE, WAV_COUNT, false);
Ref<AudioStreamWAV> stream = memnew(AudioStreamWAV);
stream->set_data(test_data);
@@ -230,7 +230,7 @@ TEST_CASE("[AudioStreamWAV] Save empty file") {
}
TEST_CASE("[AudioStreamWAV] Saving IMA ADPCM is not supported") {
- String save_path = OS::get_singleton()->get_cache_path().path_join("test_adpcm.wav");
+ String save_path = TestUtils::get_temp_path("test_adpcm.wav");
Ref<AudioStreamWAV> stream = memnew(AudioStreamWAV);
stream->set_format(AudioStreamWAV::FORMAT_IMA_ADPCM);
ERR_PRINT_OFF;
diff --git a/tests/scene/test_instance_placeholder.h b/tests/scene/test_instance_placeholder.h
index 8e8cf7c9df..d915c5d961 100644
--- a/tests/scene/test_instance_placeholder.h
+++ b/tests/scene/test_instance_placeholder.h
@@ -350,7 +350,7 @@ TEST_CASE("[SceneTree][InstancePlaceholder] Instance a PackedScene containing an
Error err = internal_scene->pack(internal);
REQUIRE(err == OK);
- const String internal_path = OS::get_singleton()->get_cache_path().path_join("instance_placeholder_test_internal.tscn");
+ const String internal_path = TestUtils::get_temp_path("instance_placeholder_test_internal.tscn");
err = ResourceSaver::save(internal_scene, internal_path);
REQUIRE(err == OK);
@@ -379,7 +379,7 @@ TEST_CASE("[SceneTree][InstancePlaceholder] Instance a PackedScene containing an
err = main_scene->pack(root);
REQUIRE(err == OK);
- const String main_path = OS::get_singleton()->get_cache_path().path_join("instance_placeholder_test_main.tscn");
+ const String main_path = TestUtils::get_temp_path("instance_placeholder_test_main.tscn");
err = ResourceSaver::save(main_scene, main_path);
REQUIRE(err == OK);
@@ -439,7 +439,7 @@ TEST_CASE("[SceneTree][InstancePlaceholder] Instance a PackedScene containing an
Error err = internal_scene->pack(internal);
REQUIRE(err == OK);
- const String internal_path = OS::get_singleton()->get_cache_path().path_join("instance_placeholder_test_internal_override.tscn");
+ const String internal_path = TestUtils::get_temp_path("instance_placeholder_test_internal_override.tscn");
err = ResourceSaver::save(internal_scene, internal_path);
REQUIRE(err == OK);
@@ -480,7 +480,7 @@ TEST_CASE("[SceneTree][InstancePlaceholder] Instance a PackedScene containing an
err = main_scene->pack(root);
REQUIRE(err == OK);
- const String main_path = OS::get_singleton()->get_cache_path().path_join("instance_placeholder_test_main_override.tscn");
+ const String main_path = TestUtils::get_temp_path("instance_placeholder_test_main_override.tscn");
err = ResourceSaver::save(main_scene, main_path);
REQUIRE(err == OK);
diff --git a/tests/scene/test_node.h b/tests/scene/test_node.h
index 2b14be76e2..93ef3fe728 100644
--- a/tests/scene/test_node.h
+++ b/tests/scene/test_node.h
@@ -518,7 +518,7 @@ TEST_CASE("[SceneTree][Node]Exported node checks") {
ps.instantiate();
ps->pack(node);
- String scene_path = OS::get_singleton()->get_cache_path().path_join("test_scene.tscn");
+ String scene_path = TestUtils::get_temp_path("test_scene.tscn");
ps->set_path(scene_path);
Node *root = memnew(Node);
@@ -531,7 +531,7 @@ TEST_CASE("[SceneTree][Node]Exported node checks") {
ps2.instantiate();
ps2->pack(root);
- scene_path = OS::get_singleton()->get_cache_path().path_join("new_test_scene.tscn");
+ scene_path = TestUtils::get_temp_path("new_test_scene.tscn");
ResourceSaver::save(ps2, scene_path);
memdelete(root);
diff --git a/tests/test_utils.cpp b/tests/test_utils.cpp
index cbd6d1ffbb..9d41e74020 100644
--- a/tests/test_utils.cpp
+++ b/tests/test_utils.cpp
@@ -30,6 +30,7 @@
#include "tests/test_utils.h"
+#include "core/io/dir_access.h"
#include "core/os/os.h"
String TestUtils::get_data_path(const String &p_file) {
@@ -40,3 +41,9 @@ String TestUtils::get_data_path(const String &p_file) {
String TestUtils::get_executable_dir() {
return OS::get_singleton()->get_executable_path().get_base_dir();
}
+
+String TestUtils::get_temp_path(const String &p_suffix) {
+ const String temp_base = OS::get_singleton()->get_cache_path().path_join("godot_test");
+ DirAccess::make_dir_absolute(temp_base); // Ensure the directory exists.
+ return temp_base.path_join(p_suffix);
+}
diff --git a/tests/test_utils.h b/tests/test_utils.h
index 48abe75c06..876a59ee7b 100644
--- a/tests/test_utils.h
+++ b/tests/test_utils.h
@@ -37,6 +37,7 @@ namespace TestUtils {
String get_data_path(const String &p_file);
String get_executable_dir();
+String get_temp_path(const String &p_suffix);
} // namespace TestUtils
#endif // TEST_UTILS_H
diff --git a/thirdparty/glad/EGL/eglplatform.h b/thirdparty/glad/EGL/eglplatform.h
index 99362a23de..6786afd90b 100644
--- a/thirdparty/glad/EGL/eglplatform.h
+++ b/thirdparty/glad/EGL/eglplatform.h
@@ -64,6 +64,12 @@ typedef HDC EGLNativeDisplayType;
typedef HBITMAP EGLNativePixmapType;
typedef HWND EGLNativeWindowType;
+#elif defined(__QNX__)
+
+typedef khronos_uintptr_t EGLNativeDisplayType;
+typedef struct _screen_pixmap* EGLNativePixmapType; /* screen_pixmap_t */
+typedef struct _screen_window* EGLNativeWindowType; /* screen_window_t */
+
#elif defined(__EMSCRIPTEN__)
typedef int EGLNativeDisplayType;
diff --git a/thirdparty/glad/egl.c b/thirdparty/glad/egl.c
index e120ea6b2c..c88d6c17cd 100644
--- a/thirdparty/glad/egl.c
+++ b/thirdparty/glad/egl.c
@@ -30,6 +30,7 @@ int GLAD_EGL_VERSION_1_3 = 0;
int GLAD_EGL_VERSION_1_4 = 0;
int GLAD_EGL_VERSION_1_5 = 0;
int GLAD_EGL_ANDROID_blob_cache = 0;
+int GLAD_EGL_EXT_platform_base = 0;
int GLAD_EGL_KHR_platform_wayland = 0;
int GLAD_EGL_KHR_platform_x11 = 0;
@@ -46,7 +47,9 @@ PFNEGLCREATEPBUFFERFROMCLIENTBUFFERPROC glad_eglCreatePbufferFromClientBuffer =
PFNEGLCREATEPBUFFERSURFACEPROC glad_eglCreatePbufferSurface = NULL;
PFNEGLCREATEPIXMAPSURFACEPROC glad_eglCreatePixmapSurface = NULL;
PFNEGLCREATEPLATFORMPIXMAPSURFACEPROC glad_eglCreatePlatformPixmapSurface = NULL;
+PFNEGLCREATEPLATFORMPIXMAPSURFACEEXTPROC glad_eglCreatePlatformPixmapSurfaceEXT = NULL;
PFNEGLCREATEPLATFORMWINDOWSURFACEPROC glad_eglCreatePlatformWindowSurface = NULL;
+PFNEGLCREATEPLATFORMWINDOWSURFACEEXTPROC glad_eglCreatePlatformWindowSurfaceEXT = NULL;
PFNEGLCREATESYNCPROC glad_eglCreateSync = NULL;
PFNEGLCREATEWINDOWSURFACEPROC glad_eglCreateWindowSurface = NULL;
PFNEGLDESTROYCONTEXTPROC glad_eglDestroyContext = NULL;
@@ -61,6 +64,7 @@ PFNEGLGETCURRENTSURFACEPROC glad_eglGetCurrentSurface = NULL;
PFNEGLGETDISPLAYPROC glad_eglGetDisplay = NULL;
PFNEGLGETERRORPROC glad_eglGetError = NULL;
PFNEGLGETPLATFORMDISPLAYPROC glad_eglGetPlatformDisplay = NULL;
+PFNEGLGETPLATFORMDISPLAYEXTPROC glad_eglGetPlatformDisplayEXT = NULL;
PFNEGLGETPROCADDRESSPROC glad_eglGetProcAddress = NULL;
PFNEGLGETSYNCATTRIBPROC glad_eglGetSyncAttrib = NULL;
PFNEGLINITIALIZEPROC glad_eglInitialize = NULL;
@@ -145,6 +149,12 @@ static void glad_egl_load_EGL_ANDROID_blob_cache( GLADuserptrloadfunc load, void
if(!GLAD_EGL_ANDROID_blob_cache) return;
glad_eglSetBlobCacheFuncsANDROID = (PFNEGLSETBLOBCACHEFUNCSANDROIDPROC) load(userptr, "eglSetBlobCacheFuncsANDROID");
}
+static void glad_egl_load_EGL_EXT_platform_base( GLADuserptrloadfunc load, void* userptr) {
+ if(!GLAD_EGL_EXT_platform_base) return;
+ glad_eglCreatePlatformPixmapSurfaceEXT = (PFNEGLCREATEPLATFORMPIXMAPSURFACEEXTPROC) load(userptr, "eglCreatePlatformPixmapSurfaceEXT");
+ glad_eglCreatePlatformWindowSurfaceEXT = (PFNEGLCREATEPLATFORMWINDOWSURFACEEXTPROC) load(userptr, "eglCreatePlatformWindowSurfaceEXT");
+ glad_eglGetPlatformDisplayEXT = (PFNEGLGETPLATFORMDISPLAYEXTPROC) load(userptr, "eglGetPlatformDisplayEXT");
+}
@@ -183,6 +193,7 @@ static int glad_egl_find_extensions_egl(EGLDisplay display) {
if (!glad_egl_get_extensions(display, &extensions)) return 0;
GLAD_EGL_ANDROID_blob_cache = glad_egl_has_extension(extensions, "EGL_ANDROID_blob_cache");
+ GLAD_EGL_EXT_platform_base = glad_egl_has_extension(extensions, "EGL_EXT_platform_base");
GLAD_EGL_KHR_platform_wayland = glad_egl_has_extension(extensions, "EGL_KHR_platform_wayland");
GLAD_EGL_KHR_platform_x11 = glad_egl_has_extension(extensions, "EGL_KHR_platform_x11");
@@ -248,6 +259,7 @@ int gladLoadEGLUserPtr(EGLDisplay display, GLADuserptrloadfunc load, void* userp
if (!glad_egl_find_extensions_egl(display)) return 0;
glad_egl_load_EGL_ANDROID_blob_cache(load, userptr);
+ glad_egl_load_EGL_EXT_platform_base(load, userptr);
return version;
diff --git a/thirdparty/glad/glad/egl.h b/thirdparty/glad/glad/egl.h
index 1bf35c1404..8e03362f23 100644
--- a/thirdparty/glad/glad/egl.h
+++ b/thirdparty/glad/glad/egl.h
@@ -1,11 +1,11 @@
/**
- * Loader generated by glad 2.0.3 on Fri Feb 3 07:06:48 2023
+ * Loader generated by glad 2.0.6 on Sat Jun 1 18:07:46 2024
*
* SPDX-License-Identifier: (WTFPL OR CC0-1.0) AND Apache-2.0
*
* Generator: C/C++
* Specification: egl
- * Extensions: 3
+ * Extensions: 4
*
* APIs:
* - egl=1.5
@@ -19,10 +19,10 @@
* - ON_DEMAND = False
*
* Commandline:
- * --api='egl=1.5' --extensions='EGL_ANDROID_blob_cache,EGL_KHR_platform_wayland,EGL_KHR_platform_x11' c --loader
+ * --api='egl=1.5' --extensions='EGL_ANDROID_blob_cache,EGL_EXT_platform_base,EGL_KHR_platform_wayland,EGL_KHR_platform_x11' c --loader
*
* Online:
- * http://glad.sh/#api=egl%3D1.5&extensions=EGL_ANDROID_blob_cache%2CEGL_KHR_platform_wayland%2CEGL_KHR_platform_x11&generator=c&options=LOADER
+ * http://glad.sh/#api=egl%3D1.5&extensions=EGL_ANDROID_blob_cache%2CEGL_EXT_platform_base%2CEGL_KHR_platform_wayland%2CEGL_KHR_platform_x11&generator=c&options=LOADER
*
*/
@@ -141,7 +141,7 @@ extern "C" {
#define GLAD_VERSION_MAJOR(version) (version / 10000)
#define GLAD_VERSION_MINOR(version) (version % 10000)
-#define GLAD_GENERATOR_VERSION "2.0.3"
+#define GLAD_GENERATOR_VERSION "2.0.6"
typedef void (*GLADapiproc)(void);
@@ -399,6 +399,8 @@ GLAD_API_CALL int GLAD_EGL_VERSION_1_4;
GLAD_API_CALL int GLAD_EGL_VERSION_1_5;
#define EGL_ANDROID_blob_cache 1
GLAD_API_CALL int GLAD_EGL_ANDROID_blob_cache;
+#define EGL_EXT_platform_base 1
+GLAD_API_CALL int GLAD_EGL_EXT_platform_base;
#define EGL_KHR_platform_wayland 1
GLAD_API_CALL int GLAD_EGL_KHR_platform_wayland;
#define EGL_KHR_platform_x11 1
@@ -416,7 +418,9 @@ typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPBUFFERFROMCLIENTBUFFERPROC)(EGLDi
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPBUFFERSURFACEPROC)(EGLDisplay dpy, EGLConfig config, const EGLint * attrib_list);
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPIXMAPSURFACEPROC)(EGLDisplay dpy, EGLConfig config, EGLNativePixmapType pixmap, const EGLint * attrib_list);
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPLATFORMPIXMAPSURFACEPROC)(EGLDisplay dpy, EGLConfig config, void * native_pixmap, const EGLAttrib * attrib_list);
+typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPLATFORMPIXMAPSURFACEEXTPROC)(EGLDisplay dpy, EGLConfig config, void * native_pixmap, const EGLint * attrib_list);
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPLATFORMWINDOWSURFACEPROC)(EGLDisplay dpy, EGLConfig config, void * native_window, const EGLAttrib * attrib_list);
+typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEPLATFORMWINDOWSURFACEEXTPROC)(EGLDisplay dpy, EGLConfig config, void * native_window, const EGLint * attrib_list);
typedef EGLSync (GLAD_API_PTR *PFNEGLCREATESYNCPROC)(EGLDisplay dpy, EGLenum type, const EGLAttrib * attrib_list);
typedef EGLSurface (GLAD_API_PTR *PFNEGLCREATEWINDOWSURFACEPROC)(EGLDisplay dpy, EGLConfig config, EGLNativeWindowType win, const EGLint * attrib_list);
typedef EGLBoolean (GLAD_API_PTR *PFNEGLDESTROYCONTEXTPROC)(EGLDisplay dpy, EGLContext ctx);
@@ -431,6 +435,7 @@ typedef EGLSurface (GLAD_API_PTR *PFNEGLGETCURRENTSURFACEPROC)(EGLint readdraw);
typedef EGLDisplay (GLAD_API_PTR *PFNEGLGETDISPLAYPROC)(EGLNativeDisplayType display_id);
typedef EGLint (GLAD_API_PTR *PFNEGLGETERRORPROC)(void);
typedef EGLDisplay (GLAD_API_PTR *PFNEGLGETPLATFORMDISPLAYPROC)(EGLenum platform, void * native_display, const EGLAttrib * attrib_list);
+typedef EGLDisplay (GLAD_API_PTR *PFNEGLGETPLATFORMDISPLAYEXTPROC)(EGLenum platform, void * native_display, const EGLint * attrib_list);
typedef __eglMustCastToProperFunctionPointerType (GLAD_API_PTR *PFNEGLGETPROCADDRESSPROC)(const char * procname);
typedef EGLBoolean (GLAD_API_PTR *PFNEGLGETSYNCATTRIBPROC)(EGLDisplay dpy, EGLSync sync, EGLint attribute, EGLAttrib * value);
typedef EGLBoolean (GLAD_API_PTR *PFNEGLINITIALIZEPROC)(EGLDisplay dpy, EGLint * major, EGLint * minor);
@@ -473,8 +478,12 @@ GLAD_API_CALL PFNEGLCREATEPIXMAPSURFACEPROC glad_eglCreatePixmapSurface;
#define eglCreatePixmapSurface glad_eglCreatePixmapSurface
GLAD_API_CALL PFNEGLCREATEPLATFORMPIXMAPSURFACEPROC glad_eglCreatePlatformPixmapSurface;
#define eglCreatePlatformPixmapSurface glad_eglCreatePlatformPixmapSurface
+GLAD_API_CALL PFNEGLCREATEPLATFORMPIXMAPSURFACEEXTPROC glad_eglCreatePlatformPixmapSurfaceEXT;
+#define eglCreatePlatformPixmapSurfaceEXT glad_eglCreatePlatformPixmapSurfaceEXT
GLAD_API_CALL PFNEGLCREATEPLATFORMWINDOWSURFACEPROC glad_eglCreatePlatformWindowSurface;
#define eglCreatePlatformWindowSurface glad_eglCreatePlatformWindowSurface
+GLAD_API_CALL PFNEGLCREATEPLATFORMWINDOWSURFACEEXTPROC glad_eglCreatePlatformWindowSurfaceEXT;
+#define eglCreatePlatformWindowSurfaceEXT glad_eglCreatePlatformWindowSurfaceEXT
GLAD_API_CALL PFNEGLCREATESYNCPROC glad_eglCreateSync;
#define eglCreateSync glad_eglCreateSync
GLAD_API_CALL PFNEGLCREATEWINDOWSURFACEPROC glad_eglCreateWindowSurface;
@@ -503,6 +512,8 @@ GLAD_API_CALL PFNEGLGETERRORPROC glad_eglGetError;
#define eglGetError glad_eglGetError
GLAD_API_CALL PFNEGLGETPLATFORMDISPLAYPROC glad_eglGetPlatformDisplay;
#define eglGetPlatformDisplay glad_eglGetPlatformDisplay
+GLAD_API_CALL PFNEGLGETPLATFORMDISPLAYEXTPROC glad_eglGetPlatformDisplayEXT;
+#define eglGetPlatformDisplayEXT glad_eglGetPlatformDisplayEXT
GLAD_API_CALL PFNEGLGETPROCADDRESSPROC glad_eglGetProcAddress;
#define eglGetProcAddress glad_eglGetProcAddress
GLAD_API_CALL PFNEGLGETSYNCATTRIBPROC glad_eglGetSyncAttrib;