mirror of
https://github.com/lightpanda-io/browser.git
synced 2025-12-14 23:38:57 +00:00
handle template's original content
When the document fragment is called via the content method on a templat, it must contain the original template's HTML nodes.
This commit is contained in:
@@ -390,7 +390,23 @@ pub const Node = struct {
|
|||||||
return parser.nodeHasChildNodes(self);
|
return parser.nodeHasChildNodes(self);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn is_template(self: *parser.Node) !bool {
|
||||||
|
if (parser.nodeType(self) != .element) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
const e = parser.nodeToElement(self);
|
||||||
|
return try parser.elementTag(e) == .template;
|
||||||
|
}
|
||||||
|
|
||||||
pub fn get_childNodes(self: *parser.Node, page: *Page) !NodeList {
|
pub fn get_childNodes(self: *parser.Node, page: *Page) !NodeList {
|
||||||
|
// special case for template:
|
||||||
|
// > The Node.childNodes property of the <template> element is always empty
|
||||||
|
// https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Elements/template#usage_notes
|
||||||
|
if (try is_template(self)) {
|
||||||
|
return .{};
|
||||||
|
}
|
||||||
|
|
||||||
const allocator = page.arena;
|
const allocator = page.arena;
|
||||||
var list: NodeList = .{};
|
var list: NodeList = .{};
|
||||||
|
|
||||||
|
|||||||
@@ -33,6 +33,8 @@ const DataSet = @import("DataSet.zig");
|
|||||||
const StyleSheet = @import("../cssom/StyleSheet.zig");
|
const StyleSheet = @import("../cssom/StyleSheet.zig");
|
||||||
const CSSStyleDeclaration = @import("../cssom/CSSStyleDeclaration.zig");
|
const CSSStyleDeclaration = @import("../cssom/CSSStyleDeclaration.zig");
|
||||||
|
|
||||||
|
const WalkerChildren = @import("../dom/walker.zig").WalkerChildren;
|
||||||
|
|
||||||
// HTMLElement interfaces
|
// HTMLElement interfaces
|
||||||
pub const Interfaces = .{
|
pub const Interfaces = .{
|
||||||
Element,
|
Element,
|
||||||
@@ -1200,11 +1202,22 @@ pub const HTMLTemplateElement = struct {
|
|||||||
pub const subtype = .node;
|
pub const subtype = .node;
|
||||||
|
|
||||||
pub fn get_content(self: *parser.Template, page: *Page) !*parser.DocumentFragment {
|
pub fn get_content(self: *parser.Template, page: *Page) !*parser.DocumentFragment {
|
||||||
const state = try page.getOrCreateNodeState(@ptrCast(@alignCast(self)));
|
const n: *parser.Node = @ptrCast(@alignCast(self));
|
||||||
|
const state = try page.getOrCreateNodeState(n);
|
||||||
if (state.template_content) |tc| {
|
if (state.template_content) |tc| {
|
||||||
return tc;
|
return tc;
|
||||||
}
|
}
|
||||||
const tc = try parser.documentCreateDocumentFragment(@ptrCast(page.window.document));
|
const tc = try parser.documentCreateDocumentFragment(@ptrCast(page.window.document));
|
||||||
|
const ntc: *parser.Node = @ptrCast(@alignCast(tc));
|
||||||
|
|
||||||
|
// move existing template's childnodes to the fragment.
|
||||||
|
const walker = WalkerChildren{};
|
||||||
|
var next: ?*parser.Node = null;
|
||||||
|
while (true) {
|
||||||
|
next = try walker.get_next(n, next) orelse break;
|
||||||
|
_ = try parser.nodeAppendChild(ntc, next.?);
|
||||||
|
}
|
||||||
|
|
||||||
state.template_content = tc;
|
state.template_content = tc;
|
||||||
return tc;
|
return tc;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -20,3 +20,19 @@
|
|||||||
testing.expectEqual('P', t.content.childNodes[1].tagName);
|
testing.expectEqual('P', t.content.childNodes[1].tagName);
|
||||||
testing.expectEqual('9000!', t.content.childNodes[1].innerHTML);
|
testing.expectEqual('9000!', t.content.childNodes[1].innerHTML);
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
<template id="hello"><p>hello, world</p></template>
|
||||||
|
|
||||||
|
<script id=template_parsing>
|
||||||
|
const tt = document.getElementById('hello');
|
||||||
|
testing.expectEqual('<p>hello, world</p>', tt.innerHTML);
|
||||||
|
|
||||||
|
// > The Node.childNodes property of the <template> element is always empty
|
||||||
|
// https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Elements/template#usage_notes
|
||||||
|
testing.expectEqual(0, tt.childNodes.length);
|
||||||
|
|
||||||
|
let out = document.createElement('div');
|
||||||
|
out.appendChild(tt.content.cloneNode(true));
|
||||||
|
|
||||||
|
testing.expectEqual('<p>hello, world</p>', out.innerHTML);
|
||||||
|
</script>
|
||||||
|
|||||||
Reference in New Issue
Block a user