From 4143f6f906e8bb6059d06b93c2d7659f6fd542c5 Mon Sep 17 00:00:00 2001 From: thislooksfun Date: Tue, 26 Oct 2021 22:14:58 -0500 Subject: [PATCH] LibGUI: Make sure that children are actually widgets Previously this section of code would blindly add *anything* as a child as long as it has been registered as an object. Since there is no guarentee that those objects are, in fact, Widgets, this feels like a logical fallacy. For example, up until this change, this is perfectly valid GML: ``` @GUI::Widget { layout: @GUI::VerticalBoxLayout { } @GUI::VerticalBoxLayout { } } ``` What exactly does it do? Who knows! It doesn't seem to *break*, but I think we can all agree it shouldn't be valid. Instead, we now actually verify that the registered class inherets from GUI::Widget before adding it as a child. We also error if it's not, which should hopefully help new GML writers from forgetting to write 'layout: ' before the layout definition and being confused as to why it's not working. --- Userland/Libraries/LibGUI/Widget.cpp | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/Userland/Libraries/LibGUI/Widget.cpp b/Userland/Libraries/LibGUI/Widget.cpp index 897e35129e..cf2b2b3aa6 100644 --- a/Userland/Libraries/LibGUI/Widget.cpp +++ b/Userland/Libraries/LibGUI/Widget.cpp @@ -1108,6 +1108,7 @@ bool Widget::load_from_json(const JsonObject& json, RefPtr (*unreg }); } + auto& widget_class = *Core::ObjectClassRegistration::find("GUI::Widget"); auto children = json.get("children"); if (children.is_array()) { for (auto& child_json_value : children.as_array().values()) { @@ -1123,6 +1124,10 @@ bool Widget::load_from_json(const JsonObject& json, RefPtr (*unreg RefPtr child; if (auto* registration = Core::ObjectClassRegistration::find(class_name.as_string())) { child = registration->construct(); + if (!child || !registration->is_derived_from(widget_class)) { + dbgln("Invalid widget class: '{}'", class_name.to_string()); + return false; + } } else { child = unregistered_child_handler(class_name.as_string()); }