diff --git a/core/config/project_settings.cpp b/core/config/project_settings.cpp index 93934f23205..ffe30a6ecb6 100644 --- a/core/config/project_settings.cpp +++ b/core/config/project_settings.cpp @@ -1387,7 +1387,7 @@ ProjectSettings::ProjectSettings() { GLOBAL_DEF_RST(PropertyInfo(Variant::INT, "rendering/occlusion_culling/bvh_build_quality", PROPERTY_HINT_ENUM, "Low,Medium,High"), 2); GLOBAL_DEF(PropertyInfo(Variant::INT, "memory/limits/multithreaded_server/rid_pool_prealloc", PROPERTY_HINT_RANGE, "0,500,1"), 60); // No negative and limit to 500 due to crashes. GLOBAL_DEF_RST("internationalization/rendering/force_right_to_left_layout_direction", false); - GLOBAL_DEF_BASIC(PropertyInfo(Variant::INT, "internationalization/rendering/root_node_layout_direction", PROPERTY_HINT_ENUM, "Based on Locale,Left-to-Right,Right-to-Left"), 0); + GLOBAL_DEF_BASIC(PropertyInfo(Variant::INT, "internationalization/rendering/root_node_layout_direction", PROPERTY_HINT_ENUM, "Based on Application Locale,Left-to-Right,Right-to-Left,Based on System Locale"), 0); GLOBAL_DEF(PropertyInfo(Variant::INT, "gui/timers/incremental_search_max_interval_msec", PROPERTY_HINT_RANGE, "0,10000,1,or_greater"), 2000); diff --git a/doc/classes/EditorSettings.xml b/doc/classes/EditorSettings.xml index 6edd8af7cc9..45f383dc20e 100644 --- a/doc/classes/EditorSettings.xml +++ b/doc/classes/EditorSettings.xml @@ -599,6 +599,9 @@ If [code]true[/code], embed modal windows such as docks inside the main editor window. When single-window mode is enabled, tooltips will also be embedded inside the main editor window, which means they can't be displayed outside of the editor window. + + Editor UI default layout direction. + When the editor window is unfocused, the amount of sleeping between frames when the low-processor usage mode is enabled (in microseconds). Higher values will result in lower CPU/GPU usage, which can improve battery life on laptops (in addition to improving the running project's performance if the editor has to redraw continuously). However, higher values will result in a less responsive editor. The default value is set to limit the editor to 20 FPS when the editor window is unfocused. See also [member interface/editor/low_processor_mode_sleep_usec]. diff --git a/editor/editor_node.cpp b/editor/editor_node.cpp index 119e684f1e8..66abb895a71 100644 --- a/editor/editor_node.cpp +++ b/editor/editor_node.cpp @@ -6909,6 +6909,10 @@ EditorNode::EditorNode() { AcceptDialog::set_swap_cancel_ok(swap_cancel_ok == 2); } + int ed_root_dir = EDITOR_GET("interface/editor/ui_layout_direction"); + Control::set_root_layout_direction(ed_root_dir); + Window::set_root_layout_direction(ed_root_dir); + ResourceLoader::set_abort_on_missing_resources(false); ResourceLoader::set_error_notify_func(&EditorNode::add_io_error); ResourceLoader::set_dependency_error_notify_func(&EditorNode::_dependency_error_report); diff --git a/editor/editor_settings.cpp b/editor/editor_settings.cpp index 1eaeee97a57..dab0ff12bd5 100644 --- a/editor/editor_settings.cpp +++ b/editor/editor_settings.cpp @@ -400,6 +400,8 @@ void EditorSettings::_load_defaults(Ref p_extra_config) { const String display_scale_hint_string = vformat("Auto (%d%%),75%%,100%%,125%%,150%%,175%%,200%%,Custom", Math::round(get_auto_display_scale() * 100)); EDITOR_SETTING_USAGE(Variant::INT, PROPERTY_HINT_ENUM, "interface/editor/display_scale", 0, display_scale_hint_string, PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_RESTART_IF_CHANGED) + EDITOR_SETTING_USAGE(Variant::INT, PROPERTY_HINT_ENUM, "interface/editor/ui_layout_direction", 0, "Based on Application Locale,Left-to-Right,Right-to-Left,Based on System Locale", PROPERTY_USAGE_DEFAULT | PROPERTY_USAGE_RESTART_IF_CHANGED) + String ed_screen_hints = "Screen With Mouse Pointer:-4,Screen With Keyboard Focus:-3,Primary Screen:-2"; // Note: Main Window Screen:-1 is not used for the main window. for (int i = 0; i < DisplayServer::get_singleton()->get_screen_count(); i++) { ed_screen_hints += ",Screen " + itos(i + 1) + ":" + itos(i); diff --git a/editor/project_manager.cpp b/editor/project_manager.cpp index 40c482eb90b..f337428a229 100644 --- a/editor/project_manager.cpp +++ b/editor/project_manager.cpp @@ -2847,6 +2847,10 @@ ProjectManager::ProjectManager() { AcceptDialog::set_swap_cancel_ok(swap_cancel_ok == 2); } + int pm_root_dir = EDITOR_GET("interface/editor/ui_layout_direction"); + Control::set_root_layout_direction(pm_root_dir); + Window::set_root_layout_direction(pm_root_dir); + EditorColorMap::create(); EditorTheme::initialize(); Ref theme = create_custom_theme(); diff --git a/scene/gui/control.cpp b/scene/gui/control.cpp index ed54bd000cb..84ca6bac5ba 100644 --- a/scene/gui/control.cpp +++ b/scene/gui/control.cpp @@ -197,6 +197,12 @@ void Control::reparent(Node *p_parent, bool p_keep_global_transform) { // Editor integration. +int Control::root_layout_direction = 0; + +void Control::set_root_layout_direction(int p_root_dir) { + root_layout_direction = p_root_dir; +} + void Control::get_argument_options(const StringName &p_function, int p_idx, List *r_options) const { ERR_READ_THREAD_GUARD; Node::get_argument_options(p_function, p_idx, r_options); @@ -3024,10 +3030,35 @@ bool Control::is_layout_rtl() const { if (data.is_rtl_dirty) { const_cast(this)->data.is_rtl_dirty = false; if (data.layout_dir == LAYOUT_DIRECTION_INHERITED) { +#ifdef TOOLS_ENABLED + if (is_part_of_edited_scene() && GLOBAL_GET(SNAME("internationalization/rendering/force_right_to_left_layout_direction"))) { + const_cast(this)->data.is_rtl = true; + return data.is_rtl; + } + if (is_inside_tree()) { + Node *edited_scene_root = get_tree()->get_edited_scene_root(); + if (edited_scene_root == this) { + int proj_root_layout_direction = GLOBAL_GET(SNAME("internationalization/rendering/root_node_layout_direction")); + if (proj_root_layout_direction == 1) { + const_cast(this)->data.is_rtl = false; + } else if (proj_root_layout_direction == 2) { + const_cast(this)->data.is_rtl = true; + } else if (proj_root_layout_direction == 3) { + String locale = OS::get_singleton()->get_locale(); + const_cast(this)->data.is_rtl = TS->is_locale_right_to_left(locale); + } else { + String locale = TranslationServer::get_singleton()->get_tool_locale(); + const_cast(this)->data.is_rtl = TS->is_locale_right_to_left(locale); + } + return data.is_rtl; + } + } +#else if (GLOBAL_GET(SNAME("internationalization/rendering/force_right_to_left_layout_direction"))) { const_cast(this)->data.is_rtl = true; return data.is_rtl; } +#endif Node *parent_node = get_parent(); while (parent_node) { Control *parent_control = Object::cast_to(parent_node); @@ -3044,11 +3075,13 @@ bool Control::is_layout_rtl() const { parent_node = parent_node->get_parent(); } - int root_dir = GLOBAL_GET(SNAME("internationalization/rendering/root_node_layout_direction")); - if (root_dir == 1) { + if (root_layout_direction == 1) { const_cast(this)->data.is_rtl = false; - } else if (root_dir == 2) { + } else if (root_layout_direction == 2) { const_cast(this)->data.is_rtl = true; + } else if (root_layout_direction == 3) { + String locale = OS::get_singleton()->get_locale(); + const_cast(this)->data.is_rtl = TS->is_locale_right_to_left(locale); } else { String locale = TranslationServer::get_singleton()->get_tool_locale(); const_cast(this)->data.is_rtl = TS->is_locale_right_to_left(locale); diff --git a/scene/gui/control.h b/scene/gui/control.h index db1bd3a346a..aec61dc2fe9 100644 --- a/scene/gui/control.h +++ b/scene/gui/control.h @@ -317,6 +317,8 @@ private: // Extra properties. + static int root_layout_direction; + String get_tooltip_text() const; protected: @@ -403,6 +405,8 @@ public: // Editor integration. + static void set_root_layout_direction(int p_root_dir); + virtual void get_argument_options(const StringName &p_function, int p_idx, List *r_options) const override; PackedStringArray get_configuration_warnings() const override; diff --git a/scene/main/window.cpp b/scene/main/window.cpp index 2c28dc31d60..a3474ebc488 100644 --- a/scene/main/window.cpp +++ b/scene/main/window.cpp @@ -40,6 +40,14 @@ #include "scene/theme/theme_db.h" #include "scene/theme/theme_owner.h" +// Editor integration. + +int Window::root_layout_direction = 0; + +void Window::set_root_layout_direction(int p_root_dir) { + root_layout_direction = p_root_dir; +} + // Dynamic properties. bool Window::_set(const StringName &p_name, const Variant &p_value) { @@ -2517,9 +2525,32 @@ Window::LayoutDirection Window::get_layout_direction() const { bool Window::is_layout_rtl() const { ERR_READ_THREAD_GUARD_V(false); if (layout_dir == LAYOUT_DIRECTION_INHERITED) { +#ifdef TOOLS_ENABLED + if (is_part_of_edited_scene() && GLOBAL_GET(SNAME("internationalization/rendering/force_right_to_left_layout_direction"))) { + return true; + } + if (is_inside_tree()) { + Node *edited_scene_root = get_tree()->get_edited_scene_root(); + if (edited_scene_root == this) { + int proj_root_layout_direction = GLOBAL_GET(SNAME("internationalization/rendering/root_node_layout_direction")); + if (proj_root_layout_direction == 1) { + return false; + } else if (proj_root_layout_direction == 2) { + return true; + } else if (proj_root_layout_direction == 3) { + String locale = OS::get_singleton()->get_locale(); + return TS->is_locale_right_to_left(locale); + } else { + String locale = TranslationServer::get_singleton()->get_tool_locale(); + return TS->is_locale_right_to_left(locale); + } + } + } +#else if (GLOBAL_GET(SNAME("internationalization/rendering/force_right_to_left_layout_direction"))) { return true; } +#endif Node *parent_node = get_parent(); while (parent_node) { Control *parent_control = Object::cast_to(parent_node); @@ -2534,11 +2565,13 @@ bool Window::is_layout_rtl() const { parent_node = parent_node->get_parent(); } - int root_dir = GLOBAL_GET(SNAME("internationalization/rendering/root_node_layout_direction")); - if (root_dir == 1) { + if (root_layout_direction == 1) { return false; - } else if (root_dir == 2) { + } else if (root_layout_direction == 2) { return true; + } else if (root_layout_direction == 3) { + String locale = OS::get_singleton()->get_locale(); + return TS->is_locale_right_to_left(locale); } else { String locale = TranslationServer::get_singleton()->get_tool_locale(); return TS->is_locale_right_to_left(locale); diff --git a/scene/main/window.h b/scene/main/window.h index 8a54b6c7d3e..1292f94f916 100644 --- a/scene/main/window.h +++ b/scene/main/window.h @@ -234,6 +234,8 @@ private: Ref debugger_stop_shortcut; + static int root_layout_direction; + protected: virtual Rect2i _popup_adjust_rect() const { return Rect2i(); } virtual void _post_popup() {} @@ -260,6 +262,8 @@ public: NOTIFICATION_THEME_CHANGED = 32 }; + static void set_root_layout_direction(int p_root_dir); + void set_title(const String &p_title); String get_title() const; diff --git a/scene/register_scene_types.cpp b/scene/register_scene_types.cpp index 3727c788fde..e3a4a966de1 100644 --- a/scene/register_scene_types.cpp +++ b/scene/register_scene_types.cpp @@ -454,6 +454,10 @@ void register_scene_types() { AcceptDialog::set_swap_cancel_ok(swap_cancel_ok); #endif + int root_dir = GLOBAL_GET("internationalization/rendering/root_node_layout_direction"); + Control::set_root_layout_direction(root_dir); + Window::set_root_layout_direction(root_dir); + /* REGISTER ANIMATION */ GDREGISTER_CLASS(Tween); GDREGISTER_ABSTRACT_CLASS(Tweener);