From 7e34b88ed406dc38fec5875188bc8f912412a128 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?kleines=20Filmr=C3=B6llchen?= Date: Fri, 18 Mar 2022 22:57:05 +0100 Subject: [PATCH] LibGUI: Fully support TabWidget in GML TabWidgets couldn't be used in GML properly, as the GML creation routines didn't actually call the necessary functions in the TabWidget to get a new tab added. This commit fixes that by making the name of the tab a normal property, the previously introduced "title", which can be trivially set from GML. Therefore, try_add_widget() loses an argument (while try_add_tab doesn't, because it newly constructs the widget). This allows us to get rid of the silly "fixing my widget tree after the fact" code in Help and will make it super easy to use TabWidget in future GML. :^) --- Userland/Applications/Help/HelpWindow.gml | 2 ++ Userland/Applications/Help/MainWidget.cpp | 3 --- Userland/Applications/SystemMonitor/main.cpp | 12 ++++++++---- .../DevTools/HackStudio/Debugger/DebugInfoWidget.cpp | 6 ++++-- Userland/Libraries/LibGUI/TabWidget.cpp | 8 ++++---- Userland/Libraries/LibGUI/TabWidget.h | 10 ++++++---- Userland/Libraries/LibGUI/Widget.cpp | 10 ++++++++++ 7 files changed, 34 insertions(+), 17 deletions(-) diff --git a/Userland/Applications/Help/HelpWindow.gml b/Userland/Applications/Help/HelpWindow.gml index 5c1dfa8e53..1180b88c68 100644 --- a/Userland/Applications/Help/HelpWindow.gml +++ b/Userland/Applications/Help/HelpWindow.gml @@ -22,10 +22,12 @@ @GUI::TreeView { name: "browse_view" + title: "Browse" } @GUI::Widget { name: "search_container" + title: "Search" layout: @GUI::VerticalBoxLayout {} @GUI::TextBox { diff --git a/Userland/Applications/Help/MainWidget.cpp b/Userland/Applications/Help/MainWidget.cpp index 9429864202..1b93b5d982 100644 --- a/Userland/Applications/Help/MainWidget.cpp +++ b/Userland/Applications/Help/MainWidget.cpp @@ -255,9 +255,6 @@ ErrorOr MainWidget::initialize_fallibles(GUI::Window& window) TRY(m_context_menu->try_add_action(*m_copy_action)); TRY(m_context_menu->try_add_action(*m_select_all_action)); - TRY(m_tab_widget->try_add_widget("Browse", *m_browse_view)); - TRY(m_tab_widget->try_add_widget("Search", *m_search_container)); - m_manual_model = TRY(ManualModel::create()); m_browse_view->set_model(*m_manual_model); m_filter_model = TRY(GUI::FilteringProxyModel::create(*m_manual_model)); diff --git a/Userland/Applications/SystemMonitor/main.cpp b/Userland/Applications/SystemMonitor/main.cpp index e3f96643b1..7df0eaa925 100644 --- a/Userland/Applications/SystemMonitor/main.cpp +++ b/Userland/Applications/SystemMonitor/main.cpp @@ -168,16 +168,20 @@ ErrorOr serenity_main(Main::Arguments arguments) auto& process_table_container = tabwidget.add_tab("Processes"); auto performance_widget = build_performance_tab(); - tabwidget.add_widget("Performance", performance_widget); + performance_widget->set_title("Performance"); + tabwidget.add_widget(performance_widget); auto storage_widget = build_storage_widget(); - tabwidget.add_widget("Storage", storage_widget); + storage_widget->set_title("Storage"); + tabwidget.add_widget(storage_widget); auto network_stats_widget = NetworkStatisticsWidget::construct(); - tabwidget.add_widget("Network", network_stats_widget); + network_stats_widget->set_title("Network"); + tabwidget.add_widget(network_stats_widget); auto hardware_widget = build_hardware_tab(); - tabwidget.add_widget("Hardware", hardware_widget); + hardware_widget->set_title("Hardware"); + tabwidget.add_widget(hardware_widget); process_table_container.set_layout(); process_table_container.layout()->set_margins(4); diff --git a/Userland/DevTools/HackStudio/Debugger/DebugInfoWidget.cpp b/Userland/DevTools/HackStudio/Debugger/DebugInfoWidget.cpp index 4ff7c4148c..a6e1c7aab0 100644 --- a/Userland/DevTools/HackStudio/Debugger/DebugInfoWidget.cpp +++ b/Userland/DevTools/HackStudio/Debugger/DebugInfoWidget.cpp @@ -61,8 +61,8 @@ DebugInfoWidget::DebugInfoWidget() m_backtrace_view = splitter.add(); auto& variables_tab_widget = splitter.add(); variables_tab_widget.set_tab_position(GUI::TabWidget::TabPosition::Bottom); - variables_tab_widget.add_widget("Variables", build_variables_tab()); - variables_tab_widget.add_widget("Registers", build_registers_tab()); + variables_tab_widget.add_widget(build_variables_tab()); + variables_tab_widget.add_widget(build_registers_tab()); m_backtrace_view->on_selection_change = [this] { const auto& index = m_backtrace_view->selection().first(); @@ -132,6 +132,7 @@ RefPtr DebugInfoWidget::get_context_menu_for_variable(const GUI::Mode NonnullRefPtr DebugInfoWidget::build_variables_tab() { auto variables_widget = GUI::Widget::construct(); + variables_widget->set_title("Variables"); variables_widget->set_layout(); m_variables_view = variables_widget->add(); @@ -148,6 +149,7 @@ NonnullRefPtr DebugInfoWidget::build_variables_tab() NonnullRefPtr DebugInfoWidget::build_registers_tab() { auto registers_widget = GUI::Widget::construct(); + registers_widget->set_title("Registers"); registers_widget->set_layout(); m_registers_view = registers_widget->add(); diff --git a/Userland/Libraries/LibGUI/TabWidget.cpp b/Userland/Libraries/LibGUI/TabWidget.cpp index 2d97c4a9d1..b12847d594 100644 --- a/Userland/Libraries/LibGUI/TabWidget.cpp +++ b/Userland/Libraries/LibGUI/TabWidget.cpp @@ -41,9 +41,9 @@ TabWidget::TabWidget() }); } -ErrorOr TabWidget::try_add_widget(String title, Widget& widget) +ErrorOr TabWidget::try_add_widget(Widget& widget) { - m_tabs.append({ move(title), nullptr, &widget }); + m_tabs.append({ widget.title(), nullptr, &widget }); add_child(widget); update_focus_policy(); if (on_tab_count_change) @@ -51,9 +51,9 @@ ErrorOr TabWidget::try_add_widget(String title, Widget& widget) return {}; } -void TabWidget::add_widget(String title, Widget& widget) +void TabWidget::add_widget(Widget& widget) { - MUST(try_add_widget(move(title), widget)); + MUST(try_add_widget(widget)); } void TabWidget::remove_widget(Widget& widget) diff --git a/Userland/Libraries/LibGUI/TabWidget.h b/Userland/Libraries/LibGUI/TabWidget.h index f7f37031c5..d032ad5717 100644 --- a/Userland/Libraries/LibGUI/TabWidget.h +++ b/Userland/Libraries/LibGUI/TabWidget.h @@ -37,16 +37,17 @@ public: GUI::Margins const& container_margins() const { return m_container_margins; } void set_container_margins(GUI::Margins const&); - ErrorOr try_add_widget(String, Widget&); + ErrorOr try_add_widget(Widget&); - void add_widget(String, Widget&); + void add_widget(Widget&); void remove_widget(Widget&); template ErrorOr> try_add_tab(String title, Args&&... args) { auto t = TRY(T::try_create(forward(args)...)); - TRY(try_add_widget(move(title), *t)); + t->set_title(move(title)); + TRY(try_add_widget(*t)); return *t; } @@ -54,7 +55,8 @@ public: T& add_tab(String title, Args&&... args) { auto t = T::construct(forward(args)...); - add_widget(move(title), *t); + t->set_title(move(title)); + add_widget(*t); return *t; } diff --git a/Userland/Libraries/LibGUI/Widget.cpp b/Userland/Libraries/LibGUI/Widget.cpp index 7fa06d9935..ad445ecd44 100644 --- a/Userland/Libraries/LibGUI/Widget.cpp +++ b/Userland/Libraries/LibGUI/Widget.cpp @@ -21,6 +21,7 @@ #include #include #include +#include #include #include #include @@ -1132,6 +1133,7 @@ bool Widget::load_from_gml_ast(NonnullRefPtr ast, RefPtr(*this); object->for_each_child_object_interruptible([&](auto child_data) { auto class_name = child_data->name(); @@ -1147,9 +1149,17 @@ bool Widget::load_from_gml_ast(NonnullRefPtr ast, RefPtr(child)->load_from_gml_ast(child_data, unregistered_child_handler); + + if (is_tab_widget) { + // FIXME: We need to have the child added before loading it so that it can access us. But the TabWidget logic requires the child to not be present yet. + remove_child(*child); + reinterpret_cast(this)->add_widget(*static_ptr_cast(child)); + } + return IterationDecision::Continue; });