1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-25 20:07:35 +00:00

LibWeb+LibJS: Make the EventTarget hierarchy (incl. DOM) GC-allocated

This is a monster patch that turns all EventTargets into GC-allocated
PlatformObjects. Their C++ wrapper classes are removed, and the LibJS
garbage collector is now responsible for their lifetimes.

There's a fair amount of hacks and band-aids in this patch, and we'll
have a lot of cleanup to do after this.
This commit is contained in:
Andreas Kling 2022-08-28 13:42:07 +02:00
parent bb547ce1c4
commit 6f433c8656
445 changed files with 4797 additions and 4268 deletions

View file

@ -4,6 +4,7 @@
* SPDX-License-Identifier: BSD-2-Clause
*/
#include <LibWeb/Bindings/TextPrototype.h>
#include <LibWeb/DOM/Range.h>
#include <LibWeb/DOM/Text.h>
#include <LibWeb/HTML/HTMLInputElement.h>
@ -15,27 +16,35 @@ namespace Web::DOM {
Text::Text(Document& document, String const& data)
: CharacterData(document, NodeType::TEXT_NODE, data)
{
set_prototype(&window().ensure_web_prototype<Bindings::TextPrototype>("Text"));
}
Text::Text(Document& document, NodeType type, String const& data)
: CharacterData(document, type, data)
{
set_prototype(&window().ensure_web_prototype<Bindings::TextPrototype>("Text"));
}
void Text::visit_edges(Cell::Visitor& visitor)
{
Base::visit_edges(visitor);
visitor.visit(m_owner_input_element.ptr());
}
// https://dom.spec.whatwg.org/#dom-text-text
NonnullRefPtr<Text> Text::create_with_global_object(Bindings::WindowObject& window, String const& data)
JS::NonnullGCPtr<Text> Text::create_with_global_object(HTML::Window& window, String const& data)
{
return make_ref_counted<Text>(window.impl().associated_document(), data);
return *window.heap().allocate<Text>(window.realm(), window.associated_document(), data);
}
void Text::set_owner_input_element(Badge<HTML::HTMLInputElement>, HTML::HTMLInputElement& input_element)
{
m_owner_input_element = input_element;
m_owner_input_element = &input_element;
}
// https://dom.spec.whatwg.org/#dom-text-splittext
// https://dom.spec.whatwg.org/#concept-text-split
ExceptionOr<NonnullRefPtr<Text>> Text::split_text(size_t offset)
ExceptionOr<JS::NonnullGCPtr<Text>> Text::split_text(size_t offset)
{
// 1. Let length be nodes length.
auto length = this->length();
@ -51,26 +60,26 @@ ExceptionOr<NonnullRefPtr<Text>> Text::split_text(size_t offset)
auto new_data = TRY(substring_data(offset, count));
// 5. Let new node be a new Text node, with the same node document as node. Set new nodes data to new data.
auto new_node = adopt_ref(*new Text(document(), new_data));
auto new_node = JS::NonnullGCPtr(*heap().allocate<Text>(realm(), document(), new_data));
// 6. Let parent be nodes parent.
RefPtr<Node> parent = this->parent();
JS::GCPtr<Node> parent = this->parent();
// 7. If parent is not null, then:
if (parent) {
// 1. Insert new node into parent before nodes next sibling.
parent->insert_before(new_node, next_sibling());
parent->insert_before(*new_node, next_sibling());
// 2. For each live range whose start node is node and start offset is greater than offset, set its start node to new node and decrease its start offset by offset.
for (auto& range : Range::live_ranges()) {
if (range->start_container() == this && range->start_offset() > offset)
range->set_start(new_node, range->start_offset() - offset);
range->set_start(*new_node, range->start_offset() - offset);
}
// 3. For each live range whose end node is node and end offset is greater than offset, set its end node to new node and decrease its end offset by offset.
for (auto& range : Range::live_ranges()) {
if (range->end_container() == this && range->end_offset() > offset)
range->set_end(new_node, range->end_offset() - offset);
range->set_end(*new_node, range->end_offset() - offset);
}
// 4. For each live range whose start node is parent and start offset is equal to the index of node plus 1, increase its start offset by 1.
@ -81,7 +90,7 @@ ExceptionOr<NonnullRefPtr<Text>> Text::split_text(size_t offset)
// 5. For each live range whose end node is parent and end offset is equal to the index of node plus 1, increase its end offset by 1.
for (auto& range : Range::live_ranges()) {
if (range->end_container() == parent && range->end_offset() == index() + 1) {
if (range->end_container() == parent.ptr() && range->end_offset() == index() + 1) {
range->set_end(*range->end_container(), range->end_offset() + 1);
}
}