From b3af0b2a394d8671849ee8637007fc9c27e1c43f Mon Sep 17 00:00:00 2001 From: PouleyKetchoupp Date: Fri, 1 Nov 2019 15:17:40 +0100 Subject: [PATCH] Option in RichTextLabel for height to fit content (cherry picked from commit ad8081216c73b8a0ace555eeb96c1d4fbcb3e50e) --- doc/classes/RichTextLabel.xml | 4 ++++ scene/gui/rich_text_label.cpp | 35 +++++++++++++++++++++++++++++++---- scene/gui/rich_text_label.h | 7 ++++++- 3 files changed, 41 insertions(+), 5 deletions(-) diff --git a/doc/classes/RichTextLabel.xml b/doc/classes/RichTextLabel.xml index 409ef3f74ec..8b6ba4894d7 100644 --- a/doc/classes/RichTextLabel.xml +++ b/doc/classes/RichTextLabel.xml @@ -292,6 +292,10 @@ The currently installed custom effects. This is an array of [RichTextEffect]s. To add a custom effect, it's more convenient to use [method install_effect]. + + If [code]true[/code], the label's height will be automatically updated to fit its content. + [b]Note:[/b] This property is used as a workaround to fix issues with [RichTextLabel] in [Container]s, but it's unreliable in some cases and will be removed in future versions. + If [code]true[/code], the label underlines meta tags such as [code][url]{text}[/url][/code]. diff --git a/scene/gui/rich_text_label.cpp b/scene/gui/rich_text_label.cpp index 5fd664434d0..ab5f5bed0ba 100644 --- a/scene/gui/rich_text_label.cpp +++ b/scene/gui/rich_text_label.cpp @@ -1556,6 +1556,10 @@ void RichTextLabel::_validate_line_caches(ItemFrame *p_frame) { vscroll->set_value(total_height - size.height); updating_scroll = false; + + if (fit_content_height) { + minimum_size_changed(); + } } void RichTextLabel::_invalidate_current_line(ItemFrame *p_frame) { @@ -1985,6 +1989,17 @@ int RichTextLabel::get_tab_size() const { return tab_size; } +void RichTextLabel::set_fit_content_height(bool p_enabled) { + if (p_enabled != fit_content_height) { + fit_content_height = p_enabled; + minimum_size_changed(); + } +} + +bool RichTextLabel::is_fit_content_height_enabled() const { + return fit_content_height; +} + void RichTextLabel::set_meta_underline(bool p_underline) { underline_meta = p_underline; @@ -2702,7 +2717,7 @@ void RichTextLabel::install_effect(const Variant effect) { } } -int RichTextLabel::get_content_height() { +int RichTextLabel::get_content_height() const { int total_height = 0; if (main->lines.size()) total_height = main->lines[main->lines.size() - 1].height_accum_cache + get_stylebox("normal")->get_minimum_size().height; @@ -2758,6 +2773,9 @@ void RichTextLabel::_bind_methods() { ClassDB::bind_method(D_METHOD("set_tab_size", "spaces"), &RichTextLabel::set_tab_size); ClassDB::bind_method(D_METHOD("get_tab_size"), &RichTextLabel::get_tab_size); + ClassDB::bind_method(D_METHOD("set_fit_content_height", "enabled"), &RichTextLabel::set_fit_content_height); + ClassDB::bind_method(D_METHOD("is_fit_content_height_enabled"), &RichTextLabel::is_fit_content_height_enabled); + ClassDB::bind_method(D_METHOD("set_selection_enabled", "enabled"), &RichTextLabel::set_selection_enabled); ClassDB::bind_method(D_METHOD("is_selection_enabled"), &RichTextLabel::is_selection_enabled); @@ -2800,6 +2818,8 @@ void RichTextLabel::_bind_methods() { ADD_PROPERTY(PropertyInfo(Variant::INT, "tab_size", PROPERTY_HINT_RANGE, "0,24,1"), "set_tab_size", "get_tab_size"); ADD_PROPERTY(PropertyInfo(Variant::STRING, "text", PROPERTY_HINT_MULTILINE_TEXT), "set_text", "get_text"); + ADD_PROPERTY(PropertyInfo(Variant::BOOL, "fit_content_height"), "set_fit_content_height", "is_fit_content_height_enabled"); + ADD_PROPERTY(PropertyInfo(Variant::BOOL, "scroll_active"), "set_scroll_active", "is_scroll_active"); ADD_PROPERTY(PropertyInfo(Variant::BOOL, "scroll_following"), "set_scroll_follow", "is_scroll_following"); @@ -2866,12 +2886,17 @@ void RichTextLabel::set_fixed_size_to_width(int p_width) { Size2 RichTextLabel::get_minimum_size() const { + Size2 size(0, 0); if (fixed_width != -1) { - const_cast(this)->_validate_line_caches(main); - return Size2(fixed_width, const_cast(this)->get_content_height()); + size.x = fixed_width; } - return Size2(); + if (fixed_width != -1 || fit_content_height) { + const_cast(this)->_validate_line_caches(main); + size.y = get_content_height(); + } + + return size; } Ref RichTextLabel::_get_custom_effect_by_code(String p_bbcode_identifier) { @@ -2989,6 +3014,8 @@ RichTextLabel::RichTextLabel() { visible_line_count = 0; fixed_width = -1; + fit_content_height = false; + set_clip_contents(true); } diff --git a/scene/gui/rich_text_label.h b/scene/gui/rich_text_label.h index 61ac0bd86cb..618ab4351be 100644 --- a/scene/gui/rich_text_label.h +++ b/scene/gui/rich_text_label.h @@ -401,6 +401,8 @@ private: int fixed_width; + bool fit_content_height; + protected: void _notification(int p_what); @@ -454,13 +456,16 @@ public: void set_tab_size(int p_spaces); int get_tab_size() const; + void set_fit_content_height(bool p_enabled); + bool is_fit_content_height_enabled() const; + bool search(const String &p_string, bool p_from_selection = false, bool p_search_previous = false); void scroll_to_line(int p_line); int get_line_count() const; int get_visible_line_count() const; - int get_content_height(); + int get_content_height() const; VScrollBar *get_v_scroll() { return vscroll; }