From bba9c8f65296160ec0603842a0b365505705c3e8 Mon Sep 17 00:00:00 2001 From: Karl Seguin Date: Thu, 17 Jul 2025 10:00:38 +0800 Subject: [PATCH 1/2] Add element.remove() (needed by reddit) --- src/browser/dom/element.zig | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/src/browser/dom/element.zig b/src/browser/dom/element.zig index f1c9eb3a..02ad9e7f 100644 --- a/src/browser/dom/element.zig +++ b/src/browser/dom/element.zig @@ -508,6 +508,12 @@ pub const Element = struct { _ = opts; return Animation.constructor(effect, null); } + + pub fn _remove(self: *parser.Element) !void { + const as_node: *parser.Node = @ptrCast(self); + const parent = try parser.nodeParentNode(as_node) orelse return; + _ = try Node._removeChild(parent, as_node); + } }; // Tests @@ -767,4 +773,13 @@ test "Browser.DOM.Element" { .{ "fc; (fc = document.createElement('div')).innerHTML = '

hello

" }, }, .{}); + + try runner.testCases(&.{ + .{ "const rm = document.createElement('div')", null }, + .{ "rm.id = 'to-remove'", null }, + .{ "document.getElementsByTagName('body')[0].appendChild(rm)", null }, + .{ "document.getElementById('to-remove') != null", "true" }, + .{ "rm.remove()", "undefined" }, + .{ "document.getElementById('to-remove') != null", "false" }, + }, .{}); } From 9c0d26bc843cc241e26eae73151fae600d50e520 Mon Sep 17 00:00:00 2001 From: Karl Seguin Date: Thu, 17 Jul 2025 20:51:05 +0800 Subject: [PATCH 2/2] add note about incomplete removal --- src/browser/dom/element.zig | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/browser/dom/element.zig b/src/browser/dom/element.zig index 02ad9e7f..41c882e8 100644 --- a/src/browser/dom/element.zig +++ b/src/browser/dom/element.zig @@ -510,6 +510,10 @@ pub const Element = struct { } pub fn _remove(self: *parser.Element) !void { + // TODO: This hasn't been tested to make sure all references to this + // node are properly updated. A lot of libdom is lazy and will look + // for related elements JIT by walking the tree, but there could be + // cases in libdom or the Zig WebAPI where this reference is kept const as_node: *parser.Node = @ptrCast(self); const parent = try parser.nodeParentNode(as_node) orelse return; _ = try Node._removeChild(parent, as_node);