diff options
Diffstat (limited to 'scene/gui')
37 files changed, 530 insertions, 225 deletions
diff --git a/scene/gui/aspect_ratio_container.cpp b/scene/gui/aspect_ratio_container.cpp new file mode 100644 index 0000000000..9f60131186 --- /dev/null +++ b/scene/gui/aspect_ratio_container.cpp @@ -0,0 +1,167 @@ +/*************************************************************************/ +/* aspect_ratio_container.cpp */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2020 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2020 Godot Engine contributors (cf. AUTHORS.md). */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#include "aspect_ratio_container.h" + +Size2 AspectRatioContainer::get_minimum_size() const { + Size2 ms; + for (int i = 0; i < get_child_count(); i++) { + Control *c = Object::cast_to<Control>(get_child(i)); + if (!c) { + continue; + } + if (c->is_set_as_top_level()) { + continue; + } + if (!c->is_visible()) { + continue; + } + Size2 minsize = c->get_combined_minimum_size(); + ms.width = MAX(ms.width, minsize.width); + ms.height = MAX(ms.height, minsize.height); + } + return ms; +} + +void AspectRatioContainer::set_ratio(float p_ratio) { + ratio = p_ratio; + queue_sort(); +} + +void AspectRatioContainer::set_stretch_mode(StretchMode p_mode) { + stretch_mode = p_mode; + queue_sort(); +} + +void AspectRatioContainer::set_alignment_horizontal(AlignMode p_alignment_horizontal) { + alignment_horizontal = p_alignment_horizontal; + queue_sort(); +} + +void AspectRatioContainer::set_alignment_vertical(AlignMode p_alignment_vertical) { + alignment_vertical = p_alignment_vertical; + queue_sort(); +} + +void AspectRatioContainer::_notification(int p_what) { + switch (p_what) { + case NOTIFICATION_SORT_CHILDREN: { + Size2 size = get_size(); + for (int i = 0; i < get_child_count(); i++) { + Control *c = Object::cast_to<Control>(get_child(i)); + if (!c) { + continue; + } + if (c->is_set_as_top_level()) { + continue; + } + Size2 child_minsize = c->get_combined_minimum_size(); + Size2 child_size = Size2(ratio, 1.0); + float scale_factor = 1.0; + + switch (stretch_mode) { + case STRETCH_WIDTH_CONTROLS_HEIGHT: { + scale_factor = size.x / child_size.x; + } break; + case STRETCH_HEIGHT_CONTROLS_WIDTH: { + scale_factor = size.y / child_size.y; + } break; + case STRETCH_FIT: { + scale_factor = MIN(size.x / child_size.x, size.y / child_size.y); + } break; + case STRETCH_COVER: { + scale_factor = MAX(size.x / child_size.x, size.y / child_size.y); + } break; + } + child_size *= scale_factor; + child_size.x = MAX(child_size.x, child_minsize.x); + child_size.y = MAX(child_size.y, child_minsize.y); + + float align_x = 0.5; + switch (alignment_horizontal) { + case ALIGN_BEGIN: { + align_x = 0.0; + } break; + case ALIGN_CENTER: { + align_x = 0.5; + } break; + case ALIGN_END: { + align_x = 1.0; + } break; + } + float align_y = 0.5; + switch (alignment_vertical) { + case ALIGN_BEGIN: { + align_y = 0.0; + } break; + case ALIGN_CENTER: { + align_y = 0.5; + } break; + case ALIGN_END: { + align_y = 1.0; + } break; + } + Vector2 offset = (size - child_size) * Vector2(align_x, align_y); + + fit_child_in_rect(c, Rect2(offset, child_size)); + } + } break; + } +} + +void AspectRatioContainer::_bind_methods() { + ClassDB::bind_method(D_METHOD("set_ratio", "ratio"), &AspectRatioContainer::set_ratio); + ClassDB::bind_method(D_METHOD("get_ratio"), &AspectRatioContainer::get_ratio); + + ClassDB::bind_method(D_METHOD("set_stretch_mode", "stretch_mode"), &AspectRatioContainer::set_stretch_mode); + ClassDB::bind_method(D_METHOD("get_stretch_mode"), &AspectRatioContainer::get_stretch_mode); + + ClassDB::bind_method(D_METHOD("set_alignment_horizontal", "alignment_horizontal"), &AspectRatioContainer::set_alignment_horizontal); + ClassDB::bind_method(D_METHOD("get_alignment_horizontal"), &AspectRatioContainer::get_alignment_horizontal); + + ClassDB::bind_method(D_METHOD("set_alignment_vertical", "alignment_vertical"), &AspectRatioContainer::set_alignment_vertical); + ClassDB::bind_method(D_METHOD("get_alignment_vertical"), &AspectRatioContainer::get_alignment_vertical); + + ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "ratio"), "set_ratio", "get_ratio"); + ADD_PROPERTY(PropertyInfo(Variant::INT, "stretch_mode", PROPERTY_HINT_ENUM, "Width controls height,Height controls width,Fit,Cover"), "set_stretch_mode", "get_stretch_mode"); + + ADD_GROUP("Alignment", "alignment_"); + ADD_PROPERTY(PropertyInfo(Variant::INT, "alignment_horizontal", PROPERTY_HINT_ENUM, "Begin,Center,End"), "set_alignment_horizontal", "get_alignment_horizontal"); + ADD_PROPERTY(PropertyInfo(Variant::INT, "alignment_vertical", PROPERTY_HINT_ENUM, "Begin,Center,End"), "set_alignment_vertical", "get_alignment_vertical"); + + BIND_ENUM_CONSTANT(STRETCH_WIDTH_CONTROLS_HEIGHT); + BIND_ENUM_CONSTANT(STRETCH_HEIGHT_CONTROLS_WIDTH); + BIND_ENUM_CONSTANT(STRETCH_FIT); + BIND_ENUM_CONSTANT(STRETCH_COVER); + + BIND_ENUM_CONSTANT(ALIGN_BEGIN); + BIND_ENUM_CONSTANT(ALIGN_CENTER); + BIND_ENUM_CONSTANT(ALIGN_END); +} diff --git a/scene/gui/aspect_ratio_container.h b/scene/gui/aspect_ratio_container.h new file mode 100644 index 0000000000..8ffc4363c3 --- /dev/null +++ b/scene/gui/aspect_ratio_container.h @@ -0,0 +1,80 @@ +/*************************************************************************/ +/* aspect_ratio_container.h */ +/*************************************************************************/ +/* This file is part of: */ +/* GODOT ENGINE */ +/* https://godotengine.org */ +/*************************************************************************/ +/* Copyright (c) 2007-2020 Juan Linietsky, Ariel Manzur. */ +/* Copyright (c) 2014-2020 Godot Engine contributors (cf. AUTHORS.md). */ +/* */ +/* Permission is hereby granted, free of charge, to any person obtaining */ +/* a copy of this software and associated documentation files (the */ +/* "Software"), to deal in the Software without restriction, including */ +/* without limitation the rights to use, copy, modify, merge, publish, */ +/* distribute, sublicense, and/or sell copies of the Software, and to */ +/* permit persons to whom the Software is furnished to do so, subject to */ +/* the following conditions: */ +/* */ +/* The above copyright notice and this permission notice shall be */ +/* included in all copies or substantial portions of the Software. */ +/* */ +/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */ +/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */ +/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/ +/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */ +/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */ +/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */ +/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ +/*************************************************************************/ + +#ifndef ASPECT_RATIO_CONTAINER_H +#define ASPECT_RATIO_CONTAINER_H + +#include "scene/gui/container.h" + +class AspectRatioContainer : public Container { + GDCLASS(AspectRatioContainer, Container); + +protected: + void _notification(int p_what); + static void _bind_methods(); + virtual Size2 get_minimum_size() const override; + +public: + enum StretchMode { + STRETCH_WIDTH_CONTROLS_HEIGHT, + STRETCH_HEIGHT_CONTROLS_WIDTH, + STRETCH_FIT, + STRETCH_COVER, + }; + enum AlignMode { + ALIGN_BEGIN, + ALIGN_CENTER, + ALIGN_END, + }; + +private: + float ratio = 1.0; + StretchMode stretch_mode = STRETCH_FIT; + AlignMode alignment_horizontal = ALIGN_CENTER; + AlignMode alignment_vertical = ALIGN_CENTER; + +public: + void set_ratio(float p_ratio); + float get_ratio() const { return ratio; } + + void set_stretch_mode(StretchMode p_mode); + StretchMode get_stretch_mode() const { return stretch_mode; } + + void set_alignment_horizontal(AlignMode p_alignment_horizontal); + AlignMode get_alignment_horizontal() const { return alignment_horizontal; } + + void set_alignment_vertical(AlignMode p_alignment_vertical); + AlignMode get_alignment_vertical() const { return alignment_vertical; } +}; + +VARIANT_ENUM_CAST(AspectRatioContainer::StretchMode); +VARIANT_ENUM_CAST(AspectRatioContainer::AlignMode); + +#endif // ASPECT_RATIO_CONTAINER_H diff --git a/scene/gui/button.cpp b/scene/gui/button.cpp index e400801b66..e86ad09aa6 100644 --- a/scene/gui/button.cpp +++ b/scene/gui/button.cpp @@ -30,7 +30,7 @@ #include "button.h" -#include "core/translation.h" +#include "core/string/translation.h" #include "servers/rendering_server.h" Size2 Button::get_minimum_size() const { diff --git a/scene/gui/check_button.cpp b/scene/gui/check_button.cpp index 1ddc730dd1..790faeb4fd 100644 --- a/scene/gui/check_button.cpp +++ b/scene/gui/check_button.cpp @@ -30,7 +30,7 @@ #include "check_button.h" -#include "core/print_string.h" +#include "core/string/print_string.h" #include "servers/rendering_server.h" Size2 CheckButton::get_icon_size() const { diff --git a/scene/gui/container.cpp b/scene/gui/container.cpp index 470a7db2dc..5643110b89 100644 --- a/scene/gui/container.cpp +++ b/scene/gui/container.cpp @@ -29,7 +29,7 @@ /*************************************************************************/ #include "container.h" -#include "core/message_queue.h" +#include "core/object/message_queue.h" #include "scene/scene_string_names.h" void Container::_child_minsize_changed() { diff --git a/scene/gui/control.cpp b/scene/gui/control.cpp index 476dccab7e..0381f69bcb 100644 --- a/scene/gui/control.cpp +++ b/scene/gui/control.cpp @@ -30,12 +30,12 @@ #include "control.h" +#include "core/config/project_settings.h" #include "core/math/geometry_2d.h" -#include "core/message_queue.h" +#include "core/object/message_queue.h" #include "core/os/keyboard.h" #include "core/os/os.h" -#include "core/print_string.h" -#include "core/project_settings.h" +#include "core/string/print_string.h" #include "scene/gui/label.h" #include "scene/gui/panel.h" #include "scene/main/canvas_layer.h" @@ -339,7 +339,6 @@ void Control::_get_property_list(List<PropertyInfo> *p_list) const { Ref<Theme> theme = Theme::get_default(); /* Using the default theme since the properties below are meant for editor only if (data.theme.is_valid()) { - theme = data.theme; } else { theme = Theme::get_default(); @@ -728,13 +727,13 @@ Size2 Control::get_minimum_size() const { } template <class T> -bool Control::_find_theme_item(Control *p_theme_owner, Window *p_theme_owner_window, T &r_ret, T (Theme::*get_func)(const StringName &, const StringName &) const, bool (Theme::*has_func)(const StringName &, const StringName &) const, const StringName &p_name, const StringName &p_type) { +bool Control::_find_theme_item(Control *p_theme_owner, Window *p_theme_owner_window, T &r_ret, T (Theme::*get_func)(const StringName &, const StringName &) const, bool (Theme::*has_func)(const StringName &, const StringName &) const, const StringName &p_name, const StringName &p_node_type) { // try with custom themes Control *theme_owner = p_theme_owner; Window *theme_owner_window = p_theme_owner_window; while (theme_owner || theme_owner_window) { - StringName class_name = p_type; + StringName class_name = p_node_type; while (class_name != StringName()) { if (theme_owner && (theme_owner->data.theme.operator->()->*has_func)(p_name, class_name)) { @@ -771,13 +770,13 @@ bool Control::_find_theme_item(Control *p_theme_owner, Window *p_theme_owner_win return false; } -bool Control::_has_theme_item(Control *p_theme_owner, Window *p_theme_owner_window, bool (Theme::*has_func)(const StringName &, const StringName &) const, const StringName &p_name, const StringName &p_type) { +bool Control::_has_theme_item(Control *p_theme_owner, Window *p_theme_owner_window, bool (Theme::*has_func)(const StringName &, const StringName &) const, const StringName &p_name, const StringName &p_node_type) { // try with custom themes Control *theme_owner = p_theme_owner; Window *theme_owner_window = p_theme_owner_window; while (theme_owner || theme_owner_window) { - StringName class_name = p_type; + StringName class_name = p_node_type; while (class_name != StringName()) { if (theme_owner && (theme_owner->data.theme.operator->()->*has_func)(p_name, class_name)) { @@ -812,176 +811,176 @@ bool Control::_has_theme_item(Control *p_theme_owner, Window *p_theme_owner_wind return false; } -Ref<Texture2D> Control::get_theme_icon(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +Ref<Texture2D> Control::get_theme_icon(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { const Ref<Texture2D> *tex = data.icon_override.getptr(p_name); if (tex) { return *tex; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return get_icons(data.theme_owner, data.theme_owner_window, p_name, type); } -Ref<Texture2D> Control::get_icons(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { +Ref<Texture2D> Control::get_icons(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { Ref<Texture2D> icon; - if (_find_theme_item(p_theme_owner, p_theme_owner_window, icon, &Theme::get_icon, &Theme::has_icon, p_name, p_type)) { + if (_find_theme_item(p_theme_owner, p_theme_owner_window, icon, &Theme::get_icon, &Theme::has_icon, p_name, p_node_type)) { return icon; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_icon(p_name, p_type)) { - return Theme::get_project_default()->get_icon(p_name, p_type); + if (Theme::get_project_default()->has_icon(p_name, p_node_type)) { + return Theme::get_project_default()->get_icon(p_name, p_node_type); } } - return Theme::get_default()->get_icon(p_name, p_type); + return Theme::get_default()->get_icon(p_name, p_node_type); } -Ref<Shader> Control::get_theme_shader(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +Ref<Shader> Control::get_theme_shader(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { const Ref<Shader> *sdr = data.shader_override.getptr(p_name); if (sdr) { return *sdr; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return get_shaders(data.theme_owner, data.theme_owner_window, p_name, type); } -Ref<Shader> Control::get_shaders(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { +Ref<Shader> Control::get_shaders(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { Ref<Shader> shader; - if (_find_theme_item(p_theme_owner, p_theme_owner_window, shader, &Theme::get_shader, &Theme::has_shader, p_name, p_type)) { + if (_find_theme_item(p_theme_owner, p_theme_owner_window, shader, &Theme::get_shader, &Theme::has_shader, p_name, p_node_type)) { return shader; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_shader(p_name, p_type)) { - return Theme::get_project_default()->get_shader(p_name, p_type); + if (Theme::get_project_default()->has_shader(p_name, p_node_type)) { + return Theme::get_project_default()->get_shader(p_name, p_node_type); } } - return Theme::get_default()->get_shader(p_name, p_type); + return Theme::get_default()->get_shader(p_name, p_node_type); } -Ref<StyleBox> Control::get_theme_stylebox(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +Ref<StyleBox> Control::get_theme_stylebox(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { const Ref<StyleBox> *style = data.style_override.getptr(p_name); if (style) { return *style; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return get_styleboxs(data.theme_owner, data.theme_owner_window, p_name, type); } -Ref<StyleBox> Control::get_styleboxs(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { +Ref<StyleBox> Control::get_styleboxs(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { Ref<StyleBox> stylebox; - if (_find_theme_item(p_theme_owner, p_theme_owner_window, stylebox, &Theme::get_stylebox, &Theme::has_stylebox, p_name, p_type)) { + if (_find_theme_item(p_theme_owner, p_theme_owner_window, stylebox, &Theme::get_stylebox, &Theme::has_stylebox, p_name, p_node_type)) { return stylebox; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_stylebox(p_name, p_type)) { - return Theme::get_project_default()->get_stylebox(p_name, p_type); + if (Theme::get_project_default()->has_stylebox(p_name, p_node_type)) { + return Theme::get_project_default()->get_stylebox(p_name, p_node_type); } } - return Theme::get_default()->get_stylebox(p_name, p_type); + return Theme::get_default()->get_stylebox(p_name, p_node_type); } -Ref<Font> Control::get_theme_font(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +Ref<Font> Control::get_theme_font(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { const Ref<Font> *font = data.font_override.getptr(p_name); if (font) { return *font; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return get_fonts(data.theme_owner, data.theme_owner_window, p_name, type); } -Ref<Font> Control::get_fonts(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { +Ref<Font> Control::get_fonts(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { Ref<Font> font; - if (_find_theme_item(p_theme_owner, p_theme_owner_window, font, &Theme::get_font, &Theme::has_font, p_name, p_type)) { + if (_find_theme_item(p_theme_owner, p_theme_owner_window, font, &Theme::get_font, &Theme::has_font, p_name, p_node_type)) { return font; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_font(p_name, p_type)) { - return Theme::get_project_default()->get_font(p_name, p_type); + if (Theme::get_project_default()->has_font(p_name, p_node_type)) { + return Theme::get_project_default()->get_font(p_name, p_node_type); } } - return Theme::get_default()->get_font(p_name, p_type); + return Theme::get_default()->get_font(p_name, p_node_type); } -Color Control::get_theme_color(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +Color Control::get_theme_color(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { const Color *color = data.color_override.getptr(p_name); if (color) { return *color; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return get_colors(data.theme_owner, data.theme_owner_window, p_name, type); } -Color Control::get_colors(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { +Color Control::get_colors(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { Color color; - if (_find_theme_item(p_theme_owner, p_theme_owner_window, color, &Theme::get_color, &Theme::has_color, p_name, p_type)) { + if (_find_theme_item(p_theme_owner, p_theme_owner_window, color, &Theme::get_color, &Theme::has_color, p_name, p_node_type)) { return color; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_color(p_name, p_type)) { - return Theme::get_project_default()->get_color(p_name, p_type); + if (Theme::get_project_default()->has_color(p_name, p_node_type)) { + return Theme::get_project_default()->get_color(p_name, p_node_type); } } - return Theme::get_default()->get_color(p_name, p_type); + return Theme::get_default()->get_color(p_name, p_node_type); } -int Control::get_theme_constant(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +int Control::get_theme_constant(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { const int *constant = data.constant_override.getptr(p_name); if (constant) { return *constant; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return get_constants(data.theme_owner, data.theme_owner_window, p_name, type); } -int Control::get_constants(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { +int Control::get_constants(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { int constant; - if (_find_theme_item(p_theme_owner, p_theme_owner_window, constant, &Theme::get_constant, &Theme::has_constant, p_name, p_type)) { + if (_find_theme_item(p_theme_owner, p_theme_owner_window, constant, &Theme::get_constant, &Theme::has_constant, p_name, p_node_type)) { return constant; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_constant(p_name, p_type)) { - return Theme::get_project_default()->get_constant(p_name, p_type); + if (Theme::get_project_default()->has_constant(p_name, p_node_type)) { + return Theme::get_project_default()->get_constant(p_name, p_node_type); } } - return Theme::get_default()->get_constant(p_name, p_type); + return Theme::get_default()->get_constant(p_name, p_node_type); } bool Control::has_theme_icon_override(const StringName &p_name) const { @@ -1014,154 +1013,154 @@ bool Control::has_theme_constant_override(const StringName &p_name) const { return constant != nullptr; } -bool Control::has_theme_icon(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +bool Control::has_theme_icon(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { if (has_theme_icon_override(p_name)) { return true; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return has_icons(data.theme_owner, data.theme_owner_window, p_name, type); } -bool Control::has_icons(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { - if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_icon, p_name, p_type)) { +bool Control::has_icons(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { + if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_icon, p_name, p_node_type)) { return true; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_color(p_name, p_type)) { + if (Theme::get_project_default()->has_color(p_name, p_node_type)) { return true; } } - return Theme::get_default()->has_icon(p_name, p_type); + return Theme::get_default()->has_icon(p_name, p_node_type); } -bool Control::has_theme_shader(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +bool Control::has_theme_shader(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { if (has_theme_shader_override(p_name)) { return true; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return has_shaders(data.theme_owner, data.theme_owner_window, p_name, type); } -bool Control::has_shaders(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { - if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_shader, p_name, p_type)) { +bool Control::has_shaders(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { + if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_shader, p_name, p_node_type)) { return true; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_shader(p_name, p_type)) { + if (Theme::get_project_default()->has_shader(p_name, p_node_type)) { return true; } } - return Theme::get_default()->has_shader(p_name, p_type); + return Theme::get_default()->has_shader(p_name, p_node_type); } -bool Control::has_theme_stylebox(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +bool Control::has_theme_stylebox(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { if (has_theme_stylebox_override(p_name)) { return true; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return has_styleboxs(data.theme_owner, data.theme_owner_window, p_name, type); } -bool Control::has_styleboxs(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { - if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_stylebox, p_name, p_type)) { +bool Control::has_styleboxs(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { + if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_stylebox, p_name, p_node_type)) { return true; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_stylebox(p_name, p_type)) { + if (Theme::get_project_default()->has_stylebox(p_name, p_node_type)) { return true; } } - return Theme::get_default()->has_stylebox(p_name, p_type); + return Theme::get_default()->has_stylebox(p_name, p_node_type); } -bool Control::has_theme_font(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +bool Control::has_theme_font(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { if (has_theme_font_override(p_name)) { return true; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return has_fonts(data.theme_owner, data.theme_owner_window, p_name, type); } -bool Control::has_fonts(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { - if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_font, p_name, p_type)) { +bool Control::has_fonts(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { + if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_font, p_name, p_node_type)) { return true; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_font(p_name, p_type)) { + if (Theme::get_project_default()->has_font(p_name, p_node_type)) { return true; } } - return Theme::get_default()->has_font(p_name, p_type); + return Theme::get_default()->has_font(p_name, p_node_type); } -bool Control::has_theme_color(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +bool Control::has_theme_color(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { if (has_theme_color_override(p_name)) { return true; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); return has_colors(data.theme_owner, data.theme_owner_window, p_name, type); } -bool Control::has_colors(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { - if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_color, p_name, p_type)) { +bool Control::has_colors(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { + if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_color, p_name, p_node_type)) { return true; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_color(p_name, p_type)) { + if (Theme::get_project_default()->has_color(p_name, p_node_type)) { return true; } } - return Theme::get_default()->has_color(p_name, p_type); + return Theme::get_default()->has_color(p_name, p_node_type); } -bool Control::has_theme_constant(const StringName &p_name, const StringName &p_type) const { - if (p_type == StringName() || p_type == get_class_name()) { +bool Control::has_theme_constant(const StringName &p_name, const StringName &p_node_type) const { + if (p_node_type == StringName() || p_node_type == get_class_name()) { if (has_theme_constant_override(p_name)) { return true; } } - StringName type = p_type ? p_type : get_class_name(); + StringName type = p_node_type ? p_node_type : get_class_name(); - return has_constants(data.theme_owner, data.theme_owner_window, p_name, p_type); + return has_constants(data.theme_owner, data.theme_owner_window, p_name, p_node_type); } -bool Control::has_constants(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type) { - if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_constant, p_name, p_type)) { +bool Control::has_constants(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type) { + if (_has_theme_item(p_theme_owner, p_theme_owner_window, &Theme::has_constant, p_name, p_node_type)) { return true; } if (Theme::get_project_default().is_valid()) { - if (Theme::get_project_default()->has_constant(p_name, p_type)) { + if (Theme::get_project_default()->has_constant(p_name, p_node_type)) { return true; } } - return Theme::get_default()->has_constant(p_name, p_type); + return Theme::get_default()->has_constant(p_name, p_node_type); } Rect2 Control::get_parent_anchorable_rect() const { @@ -2738,7 +2737,9 @@ void Control::_bind_methods() { BIND_VMETHOD(MethodInfo(Variant::BOOL, "can_drop_data", PropertyInfo(Variant::VECTOR2, "position"), PropertyInfo(Variant::NIL, "data"))); BIND_VMETHOD(MethodInfo("drop_data", PropertyInfo(Variant::VECTOR2, "position"), PropertyInfo(Variant::NIL, "data"))); - BIND_VMETHOD(MethodInfo(Variant::OBJECT, "_make_custom_tooltip", PropertyInfo(Variant::STRING, "for_text"))); + BIND_VMETHOD(MethodInfo( + PropertyInfo(Variant::OBJECT, "control", PROPERTY_HINT_RESOURCE_TYPE, "Control"), + "_make_custom_tooltip", PropertyInfo(Variant::STRING, "for_text"))); BIND_VMETHOD(MethodInfo(Variant::BOOL, "_clips_input")); ADD_GROUP("Anchor", "anchor_"); diff --git a/scene/gui/control.h b/scene/gui/control.h index 83e79f908f..e4fe0bb25d 100644 --- a/scene/gui/control.h +++ b/scene/gui/control.h @@ -32,7 +32,7 @@ #define CONTROL_H #include "core/math/transform_2d.h" -#include "core/rid.h" +#include "core/templates/rid.h" #include "scene/gui/shortcut.h" #include "scene/main/canvas_item.h" #include "scene/main/node.h" @@ -49,7 +49,6 @@ class Control : public CanvasItem { public: enum Anchor { - ANCHOR_BEGIN = 0, ANCHOR_END = 1 }; @@ -67,7 +66,6 @@ public: }; enum SizeFlags { - SIZE_FILL = 1, SIZE_EXPAND = 2, SIZE_EXPAND_FILL = SIZE_EXPAND | SIZE_FILL, @@ -159,8 +157,6 @@ private: Vector2 scale; Vector2 pivot_offset; - bool pending_resize; - int h_size_flags; int v_size_flags; float expand; @@ -236,23 +232,23 @@ private: static void _propagate_theme_changed(Node *p_at, Control *p_owner, Window *p_owner_window, bool p_assign = true); template <class T> - _FORCE_INLINE_ static bool _find_theme_item(Control *p_theme_owner, Window *p_theme_owner_window, T &, T (Theme::*get_func)(const StringName &, const StringName &) const, bool (Theme::*has_func)(const StringName &, const StringName &) const, const StringName &p_name, const StringName &p_type); + _FORCE_INLINE_ static bool _find_theme_item(Control *p_theme_owner, Window *p_theme_owner_window, T &, T (Theme::*get_func)(const StringName &, const StringName &) const, bool (Theme::*has_func)(const StringName &, const StringName &) const, const StringName &p_name, const StringName &p_node_type); - _FORCE_INLINE_ static bool _has_theme_item(Control *p_theme_owner, Window *p_theme_owner_window, bool (Theme::*has_func)(const StringName &, const StringName &) const, const StringName &p_name, const StringName &p_type); + _FORCE_INLINE_ static bool _has_theme_item(Control *p_theme_owner, Window *p_theme_owner_window, bool (Theme::*has_func)(const StringName &, const StringName &) const, const StringName &p_name, const StringName &p_node_type); - static Ref<Texture2D> get_icons(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static Ref<Shader> get_shaders(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static Ref<StyleBox> get_styleboxs(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static Ref<Font> get_fonts(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static Color get_colors(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static int get_constants(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); + static Ref<Texture2D> get_icons(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static Ref<Shader> get_shaders(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static Ref<StyleBox> get_styleboxs(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static Ref<Font> get_fonts(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static Color get_colors(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static int get_constants(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); - static bool has_icons(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static bool has_shaders(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static bool has_styleboxs(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static bool has_fonts(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static bool has_colors(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); - static bool has_constants(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_type = StringName()); + static bool has_icons(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static bool has_shaders(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static bool has_styleboxs(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static bool has_fonts(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static bool has_colors(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); + static bool has_constants(Control *p_theme_owner, Window *p_theme_owner_window, const StringName &p_name, const StringName &p_node_type = StringName()); protected: virtual void add_child_notify(Node *p_child) override; @@ -272,7 +268,6 @@ protected: public: enum { - /* NOTIFICATION_DRAW=30, NOTIFICATION_VISIBILITY_CHANGED=38*/ NOTIFICATION_RESIZED = 40, @@ -429,12 +424,12 @@ public: void add_theme_color_override(const StringName &p_name, const Color &p_color); void add_theme_constant_override(const StringName &p_name, int p_constant); - Ref<Texture2D> get_theme_icon(const StringName &p_name, const StringName &p_type = StringName()) const; - Ref<Shader> get_theme_shader(const StringName &p_name, const StringName &p_type = StringName()) const; - Ref<StyleBox> get_theme_stylebox(const StringName &p_name, const StringName &p_type = StringName()) const; - Ref<Font> get_theme_font(const StringName &p_name, const StringName &p_type = StringName()) const; - Color get_theme_color(const StringName &p_name, const StringName &p_type = StringName()) const; - int get_theme_constant(const StringName &p_name, const StringName &p_type = StringName()) const; + Ref<Texture2D> get_theme_icon(const StringName &p_name, const StringName &p_node_type = StringName()) const; + Ref<Shader> get_theme_shader(const StringName &p_name, const StringName &p_node_type = StringName()) const; + Ref<StyleBox> get_theme_stylebox(const StringName &p_name, const StringName &p_node_type = StringName()) const; + Ref<Font> get_theme_font(const StringName &p_name, const StringName &p_node_type = StringName()) const; + Color get_theme_color(const StringName &p_name, const StringName &p_node_type = StringName()) const; + int get_theme_constant(const StringName &p_name, const StringName &p_node_type = StringName()) const; bool has_theme_icon_override(const StringName &p_name) const; bool has_theme_shader_override(const StringName &p_name) const; @@ -443,12 +438,12 @@ public: bool has_theme_color_override(const StringName &p_name) const; bool has_theme_constant_override(const StringName &p_name) const; - bool has_theme_icon(const StringName &p_name, const StringName &p_type = StringName()) const; - bool has_theme_shader(const StringName &p_name, const StringName &p_type = StringName()) const; - bool has_theme_stylebox(const StringName &p_name, const StringName &p_type = StringName()) const; - bool has_theme_font(const StringName &p_name, const StringName &p_type = StringName()) const; - bool has_theme_color(const StringName &p_name, const StringName &p_type = StringName()) const; - bool has_theme_constant(const StringName &p_name, const StringName &p_type = StringName()) const; + bool has_theme_icon(const StringName &p_name, const StringName &p_node_type = StringName()) const; + bool has_theme_shader(const StringName &p_name, const StringName &p_node_type = StringName()) const; + bool has_theme_stylebox(const StringName &p_name, const StringName &p_node_type = StringName()) const; + bool has_theme_font(const StringName &p_name, const StringName &p_node_type = StringName()) const; + bool has_theme_color(const StringName &p_name, const StringName &p_node_type = StringName()) const; + bool has_theme_constant(const StringName &p_name, const StringName &p_node_type = StringName()) const; /* TOOLTIP */ diff --git a/scene/gui/dialogs.cpp b/scene/gui/dialogs.cpp index 430e98d50e..4f59f4a36a 100644 --- a/scene/gui/dialogs.cpp +++ b/scene/gui/dialogs.cpp @@ -31,8 +31,8 @@ #include "dialogs.h" #include "core/os/keyboard.h" -#include "core/print_string.h" -#include "core/translation.h" +#include "core/string/print_string.h" +#include "core/string/translation.h" #include "line_edit.h" #ifdef TOOLS_ENABLED diff --git a/scene/gui/file_dialog.cpp b/scene/gui/file_dialog.cpp index 2da61bdde7..7ce4e90f28 100644 --- a/scene/gui/file_dialog.cpp +++ b/scene/gui/file_dialog.cpp @@ -31,7 +31,7 @@ #include "file_dialog.h" #include "core/os/keyboard.h" -#include "core/print_string.h" +#include "core/string/print_string.h" #include "scene/gui/label.h" FileDialog::GetIconFunc FileDialog::get_icon_func = nullptr; diff --git a/scene/gui/gradient_edit.cpp b/scene/gui/gradient_edit.cpp index ecd4ad17ea..53d7ead548 100644 --- a/scene/gui/gradient_edit.cpp +++ b/scene/gui/gradient_edit.cpp @@ -357,7 +357,7 @@ void GradientEdit::_notification(int p_what) { //Draw point markers for (int i = 0; i < points.size(); i++) { - Color col = points[i].color.contrasted(); + Color col = points[i].color.inverted(); col.a = 0.9; draw_line(Vector2(points[i].offset * total_w, 0), Vector2(points[i].offset * total_w, h / 2), col); diff --git a/scene/gui/item_list.cpp b/scene/gui/item_list.cpp index 54150d130d..6708b18e0a 100644 --- a/scene/gui/item_list.cpp +++ b/scene/gui/item_list.cpp @@ -29,8 +29,8 @@ /*************************************************************************/ #include "item_list.h" +#include "core/config/project_settings.h" #include "core/os/os.h" -#include "core/project_settings.h" void ItemList::add_item(const String &p_item, const Ref<Texture2D> &p_texture, bool p_selectable) { Item item; diff --git a/scene/gui/label.cpp b/scene/gui/label.cpp index 9e3418a5c9..9df63a3c71 100644 --- a/scene/gui/label.cpp +++ b/scene/gui/label.cpp @@ -30,9 +30,9 @@ #include "label.h" -#include "core/print_string.h" -#include "core/project_settings.h" -#include "core/translation.h" +#include "core/config/project_settings.h" +#include "core/string/print_string.h" +#include "core/string/translation.h" void Label::set_autowrap(bool p_autowrap) { if (autowrap == p_autowrap) { diff --git a/scene/gui/label.h b/scene/gui/label.h index 510a716f5d..df78a1b34c 100644 --- a/scene/gui/label.h +++ b/scene/gui/label.h @@ -38,7 +38,6 @@ class Label : public Control { public: enum Align { - ALIGN_LEFT, ALIGN_CENTER, ALIGN_RIGHT, @@ -46,7 +45,6 @@ public: }; enum VAlign { - VALIGN_TOP, VALIGN_CENTER, VALIGN_BOTTOM, diff --git a/scene/gui/line_edit.cpp b/scene/gui/line_edit.cpp index 1b8f04297d..857c96bea3 100644 --- a/scene/gui/line_edit.cpp +++ b/scene/gui/line_edit.cpp @@ -30,11 +30,11 @@ #include "line_edit.h" -#include "core/message_queue.h" +#include "core/object/message_queue.h" #include "core/os/keyboard.h" #include "core/os/os.h" -#include "core/print_string.h" -#include "core/translation.h" +#include "core/string/print_string.h" +#include "core/string/translation.h" #include "label.h" #include "servers/display_server.h" #ifdef TOOLS_ENABLED @@ -70,6 +70,7 @@ void LineEdit::_gui_input(Ref<InputEvent> p_event) { if (!text.empty() && is_editable() && _is_over_clear_button(b->get_position())) { clear_button_status.press_attempt = true; clear_button_status.pressing_inside = true; + update(); return; } @@ -679,7 +680,7 @@ void LineEdit::_notification(int p_what) { } break; #endif case NOTIFICATION_RESIZED: { - window_pos = 0; + scroll_offset = 0; set_cursor_position(get_cursor_position()); } break; @@ -735,7 +736,7 @@ void LineEdit::_notification(int p_what) { x_ofs = style->get_offset().x; } break; case ALIGN_CENTER: { - if (window_pos != 0) { + if (scroll_offset != 0) { x_ofs = style->get_offset().x; } else { x_ofs = MAX(style->get_margin(MARGIN_LEFT), int(size.width - (cached_text_width)) / 2); @@ -747,7 +748,7 @@ void LineEdit::_notification(int p_what) { } int ofs_max = width - style->get_margin(MARGIN_RIGHT); - int char_ofs = window_pos; + int char_ofs = scroll_offset; int y_area = height - style->get_minimum_size().height; int y_ofs = style->get_offset().y + (y_area - font->get_height()) / 2; @@ -780,7 +781,7 @@ void LineEdit::_notification(int p_what) { r_icon->draw(ci, Point2(width - r_icon->get_width() - style->get_margin(MARGIN_RIGHT), height / 2 - r_icon->get_height() / 2), color_icon); if (align == ALIGN_CENTER) { - if (window_pos == 0) { + if (scroll_offset == 0) { x_ofs = MAX(style->get_margin(MARGIN_LEFT), int(size.width - cached_text_width - r_icon->get_width() - style->get_margin(MARGIN_RIGHT) * 2) / 2); } } else { @@ -1023,7 +1024,7 @@ void LineEdit::undo() { TextOperation op = undo_stack_pos->get(); text = op.text; cached_width = op.cached_width; - window_pos = op.window_pos; + scroll_offset = op.scroll_offset; set_cursor_position(op.cursor_pos); if (expand_to_text_length) { @@ -1044,7 +1045,7 @@ void LineEdit::redo() { TextOperation op = undo_stack_pos->get(); text = op.text; cached_width = op.cached_width; - window_pos = op.window_pos; + scroll_offset = op.scroll_offset; set_cursor_position(op.cursor_pos); if (expand_to_text_length) { @@ -1071,7 +1072,7 @@ void LineEdit::shift_selection_check_post(bool p_shift) { void LineEdit::set_cursor_at_pixel_pos(int p_x) { Ref<Font> font = get_theme_font("font"); - int ofs = window_pos; + int ofs = scroll_offset; Ref<StyleBox> style = get_theme_stylebox("normal"); int pixel_ofs = 0; Size2 size = get_size(); @@ -1084,7 +1085,7 @@ void LineEdit::set_cursor_at_pixel_pos(int p_x) { pixel_ofs = int(style->get_offset().x); } break; case ALIGN_CENTER: { - if (window_pos != 0) { + if (scroll_offset != 0) { pixel_ofs = int(style->get_offset().x); } else { pixel_ofs = int(size.width - (cached_width)) / 2; @@ -1122,7 +1123,7 @@ void LineEdit::set_cursor_at_pixel_pos(int p_x) { int LineEdit::get_cursor_pixel_pos() { Ref<Font> font = get_theme_font("font"); - int ofs = window_pos; + int ofs = scroll_offset; Ref<StyleBox> style = get_theme_stylebox("normal"); int pixel_ofs = 0; Size2 size = get_size(); @@ -1135,7 +1136,7 @@ int LineEdit::get_cursor_pixel_pos() { pixel_ofs = int(style->get_offset().x); } break; case ALIGN_CENTER: { - if (window_pos != 0) { + if (scroll_offset != 0) { pixel_ofs = int(style->get_offset().x); } else { pixel_ofs = int(size.width - (cached_width)) / 2; @@ -1236,7 +1237,7 @@ void LineEdit::delete_char() { set_cursor_position(get_cursor_position() - 1); if (align == ALIGN_CENTER || align == ALIGN_RIGHT) { - window_pos = CLAMP(window_pos - 1, 0, MAX(text.length() - 1, 0)); + scroll_offset = CLAMP(scroll_offset - 1, 0, MAX(text.length() - 1, 0)); } _text_changed(); @@ -1262,12 +1263,12 @@ void LineEdit::delete_text(int p_from_column, int p_to_column) { if (cursor_pos >= text.length()) { cursor_pos = text.length(); } - if (window_pos > cursor_pos) { - window_pos = cursor_pos; + if (scroll_offset > cursor_pos) { + scroll_offset = cursor_pos; } if (align == ALIGN_CENTER || align == ALIGN_RIGHT) { - window_pos = CLAMP(window_pos - (p_to_column - p_from_column), 0, MAX(text.length() - 1, 0)); + scroll_offset = CLAMP(scroll_offset - (p_to_column - p_from_column), 0, MAX(text.length() - 1, 0)); } if (!text_changed_dirty) { @@ -1288,7 +1289,7 @@ void LineEdit::set_text(String p_text) { update(); cursor_pos = 0; - window_pos = 0; + scroll_offset = 0; } void LineEdit::clear() { @@ -1332,16 +1333,16 @@ void LineEdit::set_cursor_position(int p_pos) { cursor_pos = p_pos; if (!is_inside_tree()) { - window_pos = cursor_pos; + scroll_offset = cursor_pos; return; } Ref<StyleBox> style = get_theme_stylebox("normal"); Ref<Font> font = get_theme_font("font"); - if (cursor_pos <= window_pos) { + if (cursor_pos <= scroll_offset) { // Adjust window if cursor goes too much to the left. - set_window_pos(MAX(0, cursor_pos - 1)); + set_scroll_offset(MAX(0, cursor_pos - 1)); } else { // Adjust window if cursor goes too much to the right. int window_width = get_size().width - style->get_minimum_size().width; @@ -1354,12 +1355,12 @@ void LineEdit::set_cursor_position(int p_pos) { if (window_width < 0) { return; } - int wp = window_pos; + int wp = scroll_offset; if (font.is_valid()) { int accum_width = 0; - for (int i = cursor_pos; i >= window_pos; i--) { + for (int i = cursor_pos; i >= scroll_offset; i--) { if (i >= text.length()) { // Do not do this, because if the cursor is at the end, its just fine that it takes no space. // accum_width = font->get_char_size(' ').width; @@ -1378,8 +1379,8 @@ void LineEdit::set_cursor_position(int p_pos) { } } - if (wp != window_pos) { - set_window_pos(wp); + if (wp != scroll_offset) { + set_scroll_offset(wp); } } update(); @@ -1389,13 +1390,17 @@ int LineEdit::get_cursor_position() const { return cursor_pos; } -void LineEdit::set_window_pos(int p_pos) { - window_pos = p_pos; - if (window_pos < 0) { - window_pos = 0; +void LineEdit::set_scroll_offset(int p_pos) { + scroll_offset = p_pos; + if (scroll_offset < 0) { + scroll_offset = 0; } } +int LineEdit::get_scroll_offset() const { + return scroll_offset; +} + void LineEdit::append_at_cursor(String p_text) { if ((max_length <= 0) || (text.length() + p_text.length() <= max_length)) { String pre = text.substr(0, cursor_pos); @@ -1413,7 +1418,7 @@ void LineEdit::clear_internal() { _clear_undo_stack(); cached_width = 0; cursor_pos = 0; - window_pos = 0; + scroll_offset = 0; undo_text = ""; text = ""; update(); @@ -1644,7 +1649,7 @@ void LineEdit::_editor_settings_changed() { void LineEdit::set_expand_to_text_length(bool p_enabled) { expand_to_text_length = p_enabled; minimum_size_changed(); - set_window_pos(0); + set_scroll_offset(0); } bool LineEdit::get_expand_to_text_length() const { @@ -1771,7 +1776,7 @@ void LineEdit::_create_undo_state() { op.text = text; op.cached_width = cached_width; op.cursor_pos = cursor_pos; - op.window_pos = window_pos; + op.scroll_offset = scroll_offset; undo_stack.push_back(op); } @@ -1816,6 +1821,7 @@ void LineEdit::_bind_methods() { ClassDB::bind_method(D_METHOD("get_placeholder_alpha"), &LineEdit::get_placeholder_alpha); ClassDB::bind_method(D_METHOD("set_cursor_position", "position"), &LineEdit::set_cursor_position); ClassDB::bind_method(D_METHOD("get_cursor_position"), &LineEdit::get_cursor_position); + ClassDB::bind_method(D_METHOD("get_scroll_offset"), &LineEdit::get_scroll_offset); ClassDB::bind_method(D_METHOD("set_expand_to_text_length", "enabled"), &LineEdit::set_expand_to_text_length); ClassDB::bind_method(D_METHOD("get_expand_to_text_length"), &LineEdit::get_expand_to_text_length); ClassDB::bind_method(D_METHOD("cursor_set_blink_enabled", "enabled"), &LineEdit::cursor_set_blink_enabled); @@ -1898,7 +1904,7 @@ LineEdit::LineEdit() { cached_width = 0; cached_placeholder_width = 0; cursor_pos = 0; - window_pos = 0; + scroll_offset = 0; window_has_focus = true; max_length = 0; pass = false; diff --git a/scene/gui/line_edit.h b/scene/gui/line_edit.h index d6cc1f1f11..5fceedbf26 100644 --- a/scene/gui/line_edit.h +++ b/scene/gui/line_edit.h @@ -39,7 +39,6 @@ class LineEdit : public Control { public: enum Align { - ALIGN_LEFT, ALIGN_CENTER, ALIGN_RIGHT, @@ -80,7 +79,7 @@ private: PopupMenu *menu; int cursor_pos; - int window_pos; + int scroll_offset; int max_length; // 0 for no maximum. int cached_width; @@ -106,7 +105,7 @@ private: struct TextOperation { int cursor_pos; - int window_pos; + int scroll_offset; int cached_width; String text; }; @@ -144,7 +143,8 @@ private: void shift_selection_check_post(bool); void selection_fill_at_cursor(); - void set_window_pos(int p_pos); + void set_scroll_offset(int p_pos); + int get_scroll_offset() const; void set_cursor_at_pixel_pos(int p_x); int get_cursor_pixel_pos(); diff --git a/scene/gui/option_button.cpp b/scene/gui/option_button.cpp index 5780cc5e71..f0e69a94a4 100644 --- a/scene/gui/option_button.cpp +++ b/scene/gui/option_button.cpp @@ -30,7 +30,7 @@ #include "option_button.h" -#include "core/print_string.h" +#include "core/string/print_string.h" Size2 OptionButton::get_minimum_size() const { Size2 minsize = Button::get_minimum_size(); diff --git a/scene/gui/panel.cpp b/scene/gui/panel.cpp index d8d9beca2b..acbb6d7ab5 100644 --- a/scene/gui/panel.cpp +++ b/scene/gui/panel.cpp @@ -30,7 +30,7 @@ #include "panel.h" -#include "core/print_string.h" +#include "core/string/print_string.h" void Panel::_notification(int p_what) { if (p_what == NOTIFICATION_DRAW) { diff --git a/scene/gui/popup.cpp b/scene/gui/popup.cpp index de866fa956..791c78e2b4 100644 --- a/scene/gui/popup.cpp +++ b/scene/gui/popup.cpp @@ -30,7 +30,7 @@ #include "popup.h" -#include "core/engine.h" +#include "core/config/engine.h" #include "core/os/keyboard.h" #include "scene/gui/panel.h" @@ -93,7 +93,7 @@ void Popup::_notification(int p_what) { } void Popup::_parent_focused() { - if (popped_up) { + if (popped_up && close_on_parent_focus) { _close_pressed(); } } @@ -112,7 +112,19 @@ void Popup::set_as_minsize() { set_size(get_contents_minimum_size()); } +void Popup::set_close_on_parent_focus(bool p_close) { + close_on_parent_focus = p_close; +} + +bool Popup::get_close_on_parent_focus() { + return close_on_parent_focus; +} + void Popup::_bind_methods() { + ClassDB::bind_method(D_METHOD("set_close_on_parent_focus", "close"), &Popup::set_close_on_parent_focus); + ClassDB::bind_method(D_METHOD("get_close_on_parent_focus"), &Popup::get_close_on_parent_focus); + ADD_PROPERTY(PropertyInfo(Variant::BOOL, "close_on_parent_focus"), "set_close_on_parent_focus", "get_close_on_parent_focus"); + ADD_SIGNAL(MethodInfo("popup_hide")); } diff --git a/scene/gui/popup.h b/scene/gui/popup.h index 3e5b89ccf3..48e7ea9452 100644 --- a/scene/gui/popup.h +++ b/scene/gui/popup.h @@ -33,13 +33,14 @@ #include "scene/main/window.h" -#include "core/local_vector.h" +#include "core/templates/local_vector.h" class Popup : public Window { GDCLASS(Popup, Window); LocalVector<Window *> visible_parents; bool popped_up = false; + bool close_on_parent_focus = true; void _input_from_window(const Ref<InputEvent> &p_event); @@ -57,6 +58,10 @@ protected: public: void set_as_minsize(); + + void set_close_on_parent_focus(bool p_close); + bool get_close_on_parent_focus(); + Popup(); ~Popup(); }; diff --git a/scene/gui/popup_menu.cpp b/scene/gui/popup_menu.cpp index 578d8a96e8..7baf32173f 100644 --- a/scene/gui/popup_menu.cpp +++ b/scene/gui/popup_menu.cpp @@ -33,8 +33,8 @@ #include "core/input/input.h" #include "core/os/keyboard.h" #include "core/os/os.h" -#include "core/print_string.h" -#include "core/translation.h" +#include "core/string/print_string.h" +#include "core/string/translation.h" String PopupMenu::_get_accel_text(int p_item) const { ERR_FAIL_INDEX_V(p_item, items.size(), String()); @@ -173,11 +173,11 @@ int PopupMenu::_get_mouse_over(const Point2 &p_over) const { return -1; } -void PopupMenu::_activate_submenu(int over) { - Node *n = get_node(items[over].submenu); - ERR_FAIL_COND_MSG(!n, "Item subnode does not exist: " + items[over].submenu + "."); +void PopupMenu::_activate_submenu(int p_over) { + Node *n = get_node(items[p_over].submenu); + ERR_FAIL_COND_MSG(!n, "Item subnode does not exist: " + items[p_over].submenu + "."); Popup *submenu_popup = Object::cast_to<Popup>(n); - ERR_FAIL_COND_MSG(!submenu_popup, "Item subnode is not a Popup: " + items[over].submenu + "."); + ERR_FAIL_COND_MSG(!submenu_popup, "Item subnode is not a Popup: " + items[p_over].submenu + "."); if (submenu_popup->is_visible()) { return; //already visible! } @@ -190,7 +190,7 @@ void PopupMenu::_activate_submenu(int over) { float scroll_offset = control->get_position().y; - Point2 submenu_pos = this_pos + Point2(this_rect.size.width, items[over]._ofs_cache + scroll_offset); + Point2 submenu_pos = this_pos + Point2(this_rect.size.width, items[p_over]._ofs_cache + scroll_offset); Size2 submenu_size = submenu_popup->get_size(); // Fix pos if going outside parent rect @@ -198,6 +198,7 @@ void PopupMenu::_activate_submenu(int over) { submenu_pos.x = this_pos.x - submenu_size.width; } + submenu_popup->set_close_on_parent_focus(false); submenu_popup->set_position(submenu_pos); submenu_popup->set_as_minsize(); // Shrink the popup size to it's contents. submenu_popup->popup(); @@ -210,11 +211,11 @@ void PopupMenu::_activate_submenu(int over) { // Autohide area above the submenu item submenu_pum->clear_autohide_areas(); - submenu_pum->add_autohide_area(Rect2(this_rect.position.x, this_rect.position.y, this_rect.size.x, items[over]._ofs_cache + scroll_offset + style->get_offset().height - vsep / 2)); + submenu_pum->add_autohide_area(Rect2(this_rect.position.x, this_rect.position.y, this_rect.size.x, items[p_over]._ofs_cache + scroll_offset + style->get_offset().height - vsep / 2)); // If there is an area below the submenu item, add an autohide area there. - if (items[over]._ofs_cache + items[over]._height_cache + scroll_offset <= control->get_size().height) { - int from = items[over]._ofs_cache + items[over]._height_cache + scroll_offset + vsep / 2 + style->get_offset().height; + if (items[p_over]._ofs_cache + items[p_over]._height_cache + scroll_offset <= control->get_size().height) { + int from = items[p_over]._ofs_cache + items[p_over]._height_cache + scroll_offset + vsep / 2 + style->get_offset().height; submenu_pum->add_autohide_area(Rect2(this_rect.position.x, this_rect.position.y + from, this_rect.size.x, this_rect.size.y - from)); } } @@ -547,6 +548,31 @@ void PopupMenu::_draw_background() { style->draw(ci2, Rect2(Point2(), margin_container->get_size())); } +void PopupMenu::_minimum_lifetime_timeout() { + close_allowed = true; + // If the mouse still isn't in this popup after timer expires, close. + if (!get_visible_rect().has_point(get_mouse_position())) { + _close_pressed(); + } +} + +void PopupMenu::_close_pressed() { + // Only apply minimum lifetime to submenus. + PopupMenu *parent_pum = Object::cast_to<PopupMenu>(get_parent()); + if (!parent_pum) { + Popup::_close_pressed(); + return; + } + + // If the timer has expired, close. If timer is still running, do nothing. + if (close_allowed) { + close_allowed = false; + Popup::_close_pressed(); + } else if (minimum_lifetime_timer->is_stopped()) { + minimum_lifetime_timer->start(); + } +} + void PopupMenu::_notification(int p_what) { switch (p_what) { case NOTIFICATION_ENTER_TREE: { @@ -566,7 +592,7 @@ void PopupMenu::_notification(int p_what) { control->update(); } break; case NOTIFICATION_WM_MOUSE_ENTER: { - //grab_focus(); + grab_focus(); } break; case NOTIFICATION_WM_MOUSE_EXIT: { if (mouse_over >= 0 && (items[mouse_over].submenu == "" || submenu_over != -1)) { @@ -1484,6 +1510,12 @@ PopupMenu::PopupMenu() { submenu_timer->set_one_shot(true); submenu_timer->connect("timeout", callable_mp(this, &PopupMenu::_submenu_timeout)); add_child(submenu_timer); + + minimum_lifetime_timer = memnew(Timer); + minimum_lifetime_timer->set_wait_time(0.3); + minimum_lifetime_timer->set_one_shot(true); + minimum_lifetime_timer->connect("timeout", callable_mp(this, &PopupMenu::_minimum_lifetime_timeout)); + add_child(minimum_lifetime_timer); } PopupMenu::~PopupMenu() { diff --git a/scene/gui/popup_menu.h b/scene/gui/popup_menu.h index e8f82ba869..a2e7d7e6cd 100644 --- a/scene/gui/popup_menu.h +++ b/scene/gui/popup_menu.h @@ -86,6 +86,9 @@ class PopupMenu : public Popup { } }; + bool close_allowed = false; + + Timer *minimum_lifetime_timer = nullptr; Timer *submenu_timer; List<Rect2> autohide_areas; Vector<Item> items; @@ -102,7 +105,7 @@ class PopupMenu : public Popup { void _scroll_to_item(int p_item); void _gui_input(const Ref<InputEvent> &p_event); - void _activate_submenu(int over); + void _activate_submenu(int p_over); void _submenu_timeout(); uint64_t popup_time_msec = 0; @@ -130,6 +133,9 @@ class PopupMenu : public Popup { void _draw_items(); void _draw_background(); + void _minimum_lifetime_timeout(); + void _close_pressed(); + protected: friend class MenuButton; void _notification(int p_what); diff --git a/scene/gui/reference_rect.cpp b/scene/gui/reference_rect.cpp index 32ec0049f0..773acb2713 100644 --- a/scene/gui/reference_rect.cpp +++ b/scene/gui/reference_rect.cpp @@ -30,7 +30,7 @@ #include "reference_rect.h" -#include "core/engine.h" +#include "core/config/engine.h" void ReferenceRect::_notification(int p_what) { if (p_what == NOTIFICATION_DRAW) { diff --git a/scene/gui/rich_text_effect.cpp b/scene/gui/rich_text_effect.cpp index 2628e5ab0f..76ca8abcc7 100644 --- a/scene/gui/rich_text_effect.cpp +++ b/scene/gui/rich_text_effect.cpp @@ -30,7 +30,7 @@ #include "rich_text_effect.h" -#include "core/script_language.h" +#include "core/object/script_language.h" void RichTextEffect::_bind_methods() { BIND_VMETHOD(MethodInfo(Variant::BOOL, "_process_custom_fx", PropertyInfo(Variant::OBJECT, "char_fx", PROPERTY_HINT_RESOURCE_TYPE, "CharFXTransform"))); diff --git a/scene/gui/rich_text_effect.h b/scene/gui/rich_text_effect.h index a5401f7eaa..e6b9f09e4d 100644 --- a/scene/gui/rich_text_effect.h +++ b/scene/gui/rich_text_effect.h @@ -31,7 +31,7 @@ #ifndef RICH_TEXT_EFFECT_H #define RICH_TEXT_EFFECT_H -#include "core/resource.h" +#include "core/io/resource.h" class RichTextEffect : public Resource { GDCLASS(RichTextEffect, Resource); diff --git a/scene/gui/rich_text_label.h b/scene/gui/rich_text_label.h index c5ed1cb3ef..67a3f466a6 100644 --- a/scene/gui/rich_text_label.h +++ b/scene/gui/rich_text_label.h @@ -39,7 +39,6 @@ class RichTextLabel : public Control { public: enum Align { - ALIGN_LEFT, ALIGN_CENTER, ALIGN_RIGHT, @@ -47,14 +46,12 @@ public: }; enum ListType { - LIST_NUMBERS, LIST_LETTERS, LIST_DOTS }; enum ItemType { - ITEM_FRAME, ITEM_TEXT, ITEM_IMAGE, @@ -344,7 +341,6 @@ private: }; enum ProcessMode { - PROCESS_CACHE, PROCESS_DRAW, PROCESS_POINTER diff --git a/scene/gui/scroll_bar.cpp b/scene/gui/scroll_bar.cpp index 0e9ef71892..9340d98ede 100644 --- a/scene/gui/scroll_bar.cpp +++ b/scene/gui/scroll_bar.cpp @@ -32,7 +32,7 @@ #include "core/os/keyboard.h" #include "core/os/os.h" -#include "core/print_string.h" +#include "core/string/print_string.h" #include "scene/main/window.h" bool ScrollBar::focus_by_default = false; diff --git a/scene/gui/scroll_container.cpp b/scene/gui/scroll_container.cpp index f4e31c45d2..8aad5f262d 100644 --- a/scene/gui/scroll_container.cpp +++ b/scene/gui/scroll_container.cpp @@ -414,12 +414,12 @@ void ScrollContainer::update_scrollbars() { bool hide_scroll_v = !scroll_v || min.height <= size.height; bool hide_scroll_h = !scroll_h || min.width <= size.width; + v_scroll->set_max(min.height); if (hide_scroll_v) { v_scroll->hide(); scroll.y = 0; } else { v_scroll->show(); - v_scroll->set_max(min.height); if (hide_scroll_h) { v_scroll->set_page(size.height); } else { @@ -429,12 +429,12 @@ void ScrollContainer::update_scrollbars() { scroll.y = v_scroll->get_value(); } + h_scroll->set_max(min.width); if (hide_scroll_h) { h_scroll->hide(); scroll.x = 0; } else { h_scroll->show(); - h_scroll->set_max(min.width); if (hide_scroll_v) { h_scroll->set_page(size.width); } else { diff --git a/scene/gui/shortcut.h b/scene/gui/shortcut.h index 0d7809e5cf..176958b397 100644 --- a/scene/gui/shortcut.h +++ b/scene/gui/shortcut.h @@ -32,7 +32,7 @@ #define SHORTCUT_H #include "core/input/input_event.h" -#include "core/resource.h" +#include "core/io/resource.h" class Shortcut : public Resource { GDCLASS(Shortcut, Resource); diff --git a/scene/gui/subviewport_container.cpp b/scene/gui/subviewport_container.cpp index 4e1ad2ae05..c5f56fe8e2 100644 --- a/scene/gui/subviewport_container.cpp +++ b/scene/gui/subviewport_container.cpp @@ -30,7 +30,7 @@ #include "subviewport_container.h" -#include "core/engine.h" +#include "core/config/engine.h" #include "scene/main/viewport.h" Size2 SubViewportContainer::get_minimum_size() const { diff --git a/scene/gui/tab_container.cpp b/scene/gui/tab_container.cpp index bd9c2da5bc..d92f41af2d 100644 --- a/scene/gui/tab_container.cpp +++ b/scene/gui/tab_container.cpp @@ -30,7 +30,7 @@ #include "tab_container.h" -#include "core/message_queue.h" +#include "core/object/message_queue.h" #include "scene/gui/box_container.h" #include "scene/gui/label.h" #include "scene/gui/texture_rect.h" diff --git a/scene/gui/tab_container.h b/scene/gui/tab_container.h index 6ac07b5845..f82f594875 100644 --- a/scene/gui/tab_container.h +++ b/scene/gui/tab_container.h @@ -38,7 +38,6 @@ class TabContainer : public Container { public: enum TabAlign { - ALIGN_LEFT, ALIGN_CENTER, ALIGN_RIGHT diff --git a/scene/gui/tabs.cpp b/scene/gui/tabs.cpp index d47f771d1d..eefe8cc3bc 100644 --- a/scene/gui/tabs.cpp +++ b/scene/gui/tabs.cpp @@ -30,7 +30,7 @@ #include "tabs.h" -#include "core/message_queue.h" +#include "core/object/message_queue.h" #include "scene/gui/box_container.h" #include "scene/gui/label.h" #include "scene/gui/texture_rect.h" diff --git a/scene/gui/tabs.h b/scene/gui/tabs.h index b94c4a37a1..62142e1cde 100644 --- a/scene/gui/tabs.h +++ b/scene/gui/tabs.h @@ -38,7 +38,6 @@ class Tabs : public Control { public: enum TabAlign { - ALIGN_LEFT, ALIGN_CENTER, ALIGN_RIGHT, @@ -46,7 +45,6 @@ public: }; enum CloseButtonDisplayPolicy { - CLOSE_BUTTON_SHOW_NEVER, CLOSE_BUTTON_SHOW_ACTIVE_ONLY, CLOSE_BUTTON_SHOW_ALWAYS, diff --git a/scene/gui/text_edit.cpp b/scene/gui/text_edit.cpp index fb397759aa..77ac3d6702 100644 --- a/scene/gui/text_edit.cpp +++ b/scene/gui/text_edit.cpp @@ -30,12 +30,12 @@ #include "text_edit.h" +#include "core/config/project_settings.h" #include "core/input/input.h" -#include "core/message_queue.h" +#include "core/object/message_queue.h" +#include "core/object/script_language.h" #include "core/os/keyboard.h" #include "core/os/os.h" -#include "core/project_settings.h" -#include "core/script_language.h" #include "scene/main/window.h" #ifdef TOOLS_ENABLED @@ -1559,7 +1559,19 @@ void TextEdit::_notification(int p_what) { } if (DisplayServer::get_singleton()->has_feature(DisplayServer::FEATURE_VIRTUAL_KEYBOARD) && virtual_keyboard_enabled) { - DisplayServer::get_singleton()->virtual_keyboard_show(get_text(), get_global_rect(), true); + String text = _base_get_text(0, 0, selection.selecting_line, selection.selecting_column); + int cursor_start = text.length(); + int cursor_end = -1; + + if (selection.active) { + String selected_text = _base_get_text(selection.from_line, selection.from_column, selection.to_line, selection.to_column); + + if (selected_text.length() > 0) { + cursor_end = cursor_start + selected_text.length(); + } + } + + DisplayServer::get_singleton()->virtual_keyboard_show(get_text(), get_global_rect(), true, -1, cursor_start, cursor_end); } } break; case NOTIFICATION_FOCUS_EXIT: { diff --git a/scene/gui/texture_progress.cpp b/scene/gui/texture_progress.cpp index 484b14d11c..e0d98d1c22 100644 --- a/scene/gui/texture_progress.cpp +++ b/scene/gui/texture_progress.cpp @@ -30,7 +30,7 @@ #include "texture_progress.h" -#include "core/engine.h" +#include "core/config/engine.h" void TextureProgress::set_under_texture(const Ref<Texture2D> &p_texture) { under = p_texture; diff --git a/scene/gui/tree.cpp b/scene/gui/tree.cpp index 318496df70..31030765e0 100644 --- a/scene/gui/tree.cpp +++ b/scene/gui/tree.cpp @@ -30,12 +30,12 @@ #include "tree.h" +#include "core/config/project_settings.h" #include "core/input/input.h" #include "core/math/math_funcs.h" #include "core/os/keyboard.h" #include "core/os/os.h" -#include "core/print_string.h" -#include "core/project_settings.h" +#include "core/string/print_string.h" #include "scene/main/window.h" #include "box_container.h" @@ -1813,7 +1813,6 @@ int Tree::propagate_mouse_event(const Point2i &p_pos, int x_ofs, int y_ofs, bool case TreeItem::CELL_MODE_RANGE: { if (c.text != "") { //if (x >= (get_column_width(col)-item_h/2)) { - popup_menu->clear(); for (int i = 0; i < c.text.get_slice_count(","); i++) { String s = c.text.get_slicec(',', i); diff --git a/scene/gui/tree.h b/scene/gui/tree.h index c0910a8fe0..9554bb4665 100644 --- a/scene/gui/tree.h +++ b/scene/gui/tree.h @@ -44,7 +44,6 @@ class TreeItem : public Object { public: enum TreeCellMode { - CELL_MODE_STRING, ///< just a string CELL_MODE_CHECK, ///< string + check CELL_MODE_RANGE, ///< Contains a range |