diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-06-12 05:35:37 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-06-12 05:35:37 +0000 |
commit | a90a5cba08fdf6c0ceb95101c275108a152a3aed (patch) | |
tree | 532507288f3defd7f4dcf1af49698bcb76034855 /testing/web-platform/tests/dom/nodes/moveBefore | |
parent | Adding debian version 126.0.1-1. (diff) | |
download | firefox-a90a5cba08fdf6c0ceb95101c275108a152a3aed.tar.xz firefox-a90a5cba08fdf6c0ceb95101c275108a152a3aed.zip |
Merging upstream version 127.0.
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'testing/web-platform/tests/dom/nodes/moveBefore')
15 files changed, 961 insertions, 0 deletions
diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/Node-moveBefore.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/Node-moveBefore.html new file mode 100644 index 0000000000..8a1db6f93b --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/Node-moveBefore.html @@ -0,0 +1,297 @@ +<!DOCTYPE html> +<title>Node.moveBefore</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<div id="log"></div> +<!-- First test shared pre-insertion checks that work similarly for replaceChild + and moveBefore --> +<script> + var insertFunc = Node.prototype.moveBefore; +</script> +<script src="../../pre-insertion-validation-notfound.js"></script> +<script src="../../pre-insertion-validation-hierarchy.js"></script> +<script> +preInsertionValidateHierarchy("moveBefore"); + +function testLeafNode(nodeName, createNodeFunction) { + test(function() { + var node = createNodeFunction(); + assert_throws_js(TypeError, function() { node.moveBefore(null, null) }) + }, "Calling moveBefore with a non-Node first argument on a leaf node " + nodeName + " must throw TypeError.") + test(function() { + var node = createNodeFunction(); + assert_throws_dom("HIERARCHY_REQUEST_ERR", function() { node.moveBefore(document.createTextNode("fail"), null) }) + // Would be step 2. + assert_throws_dom("HIERARCHY_REQUEST_ERR", function() { node.moveBefore(node, null) }) + // Would be step 3. + assert_throws_dom("HIERARCHY_REQUEST_ERR", function() { node.moveBefore(node, document.createTextNode("child")) }) + }, "Calling moveBefore an a leaf node " + nodeName + " must throw HIERARCHY_REQUEST_ERR.") +} + +test(function() { + // WebIDL: first argument. + assert_throws_js(TypeError, function() { document.body.moveBefore(null, null) }) + assert_throws_js(TypeError, function() { document.body.moveBefore(null, document.body.firstChild) }) + assert_throws_js(TypeError, function() { document.body.moveBefore({'a':'b'}, document.body.firstChild) }) +}, "Calling moveBefore with a non-Node first argument must throw TypeError.") + +test(function() { + // WebIDL: second argument. + assert_throws_js(TypeError, function() { document.body.moveBefore(document.createTextNode("child")) }) + assert_throws_js(TypeError, function() { document.body.moveBefore(document.createTextNode("child"), {'a':'b'}) }) +}, "Calling moveBefore with second argument missing, or other than Node, null, or undefined, must throw TypeError.") + +testLeafNode("DocumentType", function () { return document.doctype; } ) +testLeafNode("Text", function () { return document.createTextNode("Foo") }) +testLeafNode("Comment", function () { return document.createComment("Foo") }) +testLeafNode("ProcessingInstruction", function () { return document.createProcessingInstruction("foo", "bar") }) + +test(function() { + // Step 2. + assert_throws_dom("HIERARCHY_REQUEST_ERR", function() { document.body.moveBefore(document.body, document.getElementById("log")) }) + assert_throws_dom("HIERARCHY_REQUEST_ERR", function() { document.body.moveBefore(document.documentElement, document.getElementById("log")) }) +}, "Calling moveBefore with an inclusive ancestor of the context object must throw HIERARCHY_REQUEST_ERR.") + +// Step 3. +test(function() { + var a = document.createElement("div"); + var b = document.createElement("div"); + var c = document.createElement("div"); + assert_throws_dom("NotFoundError", function() { + a.moveBefore(b, c); + }); +}, "Calling moveBefore with a reference child whose parent is not the context node must throw a NotFoundError.") + +// Step 4.1. +test(function() { + var doc = document.implementation.createHTMLDocument("title"); + var doc2 = document.implementation.createHTMLDocument("title2"); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(doc2, doc.documentElement); + }); + + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(doc.createTextNode("text"), doc.documentElement); + }); +}, "If the context node is a document, inserting a document or text node should throw a HierarchyRequestError.") + +// Step 4.2.1. +test(function() { + var doc = document.implementation.createHTMLDocument("title"); + doc.removeChild(doc.documentElement); + + var df = doc.createDocumentFragment(); + df.appendChild(doc.createElement("a")); + df.appendChild(doc.createElement("b")); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(df, doc.firstChild); + }); + + df = doc.createDocumentFragment(); + df.appendChild(doc.createTextNode("text")); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(df, doc.firstChild); + }); + + df = doc.createDocumentFragment(); + df.appendChild(doc.createComment("comment")); + df.appendChild(doc.createTextNode("text")); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(df, doc.firstChild); + }); +}, "If the context node is a document, inserting a DocumentFragment that contains a text node or too many elements should throw a HierarchyRequestError.") + +// Step 4.2.2. +test(function() { + // The context node has an element child. + var doc = document.implementation.createHTMLDocument("title"); + var comment = doc.appendChild(doc.createComment("foo")); + assert_array_equals(doc.childNodes, [doc.doctype, doc.documentElement, comment]); + + var df = doc.createDocumentFragment(); + df.appendChild(doc.createElement("a")); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(df, doc.doctype); + }); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(df, doc.documentElement); + }); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(df, comment); + }); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(df, null); + }); +}, "If the context node is a document, inserting a DocumentFragment with an element if there already is an element child should throw a HierarchyRequestError.") +test(function() { + // /child/ is a doctype. + var doc = document.implementation.createHTMLDocument("title"); + var comment = doc.moveBefore(doc.createComment("foo"), doc.firstChild); + doc.removeChild(doc.documentElement); + assert_array_equals(doc.childNodes, [comment, doc.doctype]); + + var df = doc.createDocumentFragment(); + df.appendChild(doc.createElement("a")); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(df, doc.doctype); + }); +}, "If the context node is a document and a doctype is following the reference child, inserting a DocumentFragment with an element should throw a HierarchyRequestError.") +test(function() { + // /child/ is not null and a doctype is following /child/. + var doc = document.implementation.createHTMLDocument("title"); + var comment = doc.moveBefore(doc.createComment("foo"), doc.firstChild); + doc.removeChild(doc.documentElement); + assert_array_equals(doc.childNodes, [comment, doc.doctype]); + + var df = doc.createDocumentFragment(); + df.appendChild(doc.createElement("a")); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(df, comment); + }); +}, "If the context node is a document, inserting a DocumentFragment with an element before the doctype should throw a HierarchyRequestError.") + +// Step 4.3. +test(function() { + // The context node has an element child. + var doc = document.implementation.createHTMLDocument("title"); + var comment = doc.appendChild(doc.createComment("foo")); + assert_array_equals(doc.childNodes, [doc.doctype, doc.documentElement, comment]); + + var a = doc.createElement("a"); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(a, doc.doctype); + }); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(a, doc.documentElement); + }); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(a, comment); + }); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(a, null); + }); +}, "If the context node is a document, inserting an element if there already is an element child should throw a HierarchyRequestError.") +test(function() { + // /child/ is a doctype. + var doc = document.implementation.createHTMLDocument("title"); + var comment = doc.moveBefore(doc.createComment("foo"), doc.firstChild); + doc.removeChild(doc.documentElement); + assert_array_equals(doc.childNodes, [comment, doc.doctype]); + + var a = doc.createElement("a"); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(a, doc.doctype); + }); +}, "If the context node is a document, inserting an element before the doctype should throw a HierarchyRequestError.") +test(function() { + // /child/ is not null and a doctype is following /child/. + var doc = document.implementation.createHTMLDocument("title"); + var comment = doc.moveBefore(doc.createComment("foo"), doc.firstChild); + doc.removeChild(doc.documentElement); + assert_array_equals(doc.childNodes, [comment, doc.doctype]); + + var a = doc.createElement("a"); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(a, comment); + }); +}, "If the context node is a document and a doctype is following the reference child, inserting an element should throw a HierarchyRequestError.") + +// Step 4.4. +test(function() { + var doc = document.implementation.createHTMLDocument("title"); + var comment = doc.moveBefore(doc.createComment("foo"), doc.firstChild); + assert_array_equals(doc.childNodes, [comment, doc.doctype, doc.documentElement]); + + var doctype = document.implementation.createDocumentType("html", "", ""); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(doctype, comment); + }); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(doctype, doc.doctype); + }); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(doctype, doc.documentElement); + }); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(doctype, null); + }); +}, "If the context node is a document, inserting a doctype if there already is a doctype child should throw a HierarchyRequestError.") +test(function() { + var doc = document.implementation.createHTMLDocument("title"); + var comment = doc.appendChild(doc.createComment("foo")); + doc.removeChild(doc.doctype); + assert_array_equals(doc.childNodes, [doc.documentElement, comment]); + + var doctype = document.implementation.createDocumentType("html", "", ""); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(doctype, comment); + }); +}, "If the context node is a document, inserting a doctype after the document element should throw a HierarchyRequestError.") +test(function() { + var doc = document.implementation.createHTMLDocument("title"); + var comment = doc.appendChild(doc.createComment("foo")); + doc.removeChild(doc.doctype); + assert_array_equals(doc.childNodes, [doc.documentElement, comment]); + + var doctype = document.implementation.createDocumentType("html", "", ""); + assert_throws_dom("HierarchyRequestError", function() { + doc.moveBefore(doctype, null); + }); +}, "If the context node is a document with and element child, appending a doctype should throw a HierarchyRequestError.") + +// Step 5. +test(function() { + var df = document.createDocumentFragment(); + var a = df.appendChild(document.createElement("a")); + + var doc = document.implementation.createHTMLDocument("title"); + assert_throws_dom("HierarchyRequestError", function() { + df.moveBefore(doc, a); + }); + assert_throws_dom("HierarchyRequestError", function() { + df.moveBefore(doc, null); + }); + + var doctype = document.implementation.createDocumentType("html", "", ""); + assert_throws_dom("HierarchyRequestError", function() { + df.moveBefore(doctype, a); + }); + assert_throws_dom("HierarchyRequestError", function() { + df.moveBefore(doctype, null); + }); +}, "If the context node is a DocumentFragment, inserting a document or a doctype should throw a HierarchyRequestError.") +test(function() { + var el = document.createElement("div"); + var a = el.appendChild(document.createElement("a")); + + var doc = document.implementation.createHTMLDocument("title"); + assert_throws_dom("HierarchyRequestError", function() { + el.moveBefore(doc, a); + }); + assert_throws_dom("HierarchyRequestError", function() { + el.moveBefore(doc, null); + }); + + var doctype = document.implementation.createDocumentType("html", "", ""); + assert_throws_dom("HierarchyRequestError", function() { + el.moveBefore(doctype, a); + }); + assert_throws_dom("HierarchyRequestError", function() { + el.moveBefore(doctype, null); + }); +}, "If the context node is an element, inserting a document or a doctype should throw a HierarchyRequestError.") + +// Step 7. +test(function() { + var a = document.createElement("div"); + var b = document.createElement("div"); + var c = document.createElement("div"); + a.appendChild(b); + a.appendChild(c); + assert_array_equals(a.childNodes, [b, c]); + assert_equals(a.moveBefore(b, b), b); + assert_array_equals(a.childNodes, [b, c]); + assert_equals(a.moveBefore(c, c), c); + assert_array_equals(a.childNodes, [b, c]); +}, "Inserting a node before itself should not move the node"); +</script> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/chrome-338071841-crash.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/chrome-338071841-crash.html new file mode 100644 index 0000000000..26adfb1cbf --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/chrome-338071841-crash.html @@ -0,0 +1,6 @@ +<!DOCTYPE html> +<link rel="help" href="https://crbug.com/338071841"> +<div id="p"><span></span><!-- comment --></div> +<script> + p.moveBefore(p.lastChild, p.firstChild); +</script> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-animation-left.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-animation-left.html new file mode 100644 index 0000000000..8c7f73e3c9 --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-animation-left.html @@ -0,0 +1,51 @@ +<!DOCTYPE html> +<title>Node.moveBefore should preserve CSS animation state (left)</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <section id="new-parent"> + </section> + <style> + @keyframes anim { + from { + left: 100px; + } + + to { + left: 400px; + } + } + + section { + position: absolute; + } + + #item { + position: relative; + width: 100px; + height: 100px; + background: green; + animation: 1s linear infinite alternate anim; + animation-delay: 100ms; + } + </style> + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + let num_events = 0; + await new Promise(resolve => addEventListener("animationstart", () => { + num_events++; + resolve(); + })); + + // Reparent item + document.body.querySelector("#new-parent").moveBefore(item, null); + await new Promise(resolve => requestAnimationFrame(() => resolve())); + assert_equals(num_events, 1); + assert_not_equals(getComputedStyle(item).left, "0px"); + }); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-animation-transform.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-animation-transform.html new file mode 100644 index 0000000000..e7a285893a --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-animation-transform.html @@ -0,0 +1,48 @@ +<!DOCTYPE html> +<title>Node.moveBefore should preserve CSS animation state (transform)</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <section id="new-parent"> + </section> + <style> + @keyframes anim { + from { + transform: translateX(100px); + } + + to { + transform: translateX(400px); + } + } + + #item { + position: relative; + width: 100px; + height: 100px; + background: green; + animation: 1s linear infinite alternate anim; + animation-delay: 100ms; + } + </style> + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + let num_events = 0; + await new Promise(resolve => addEventListener("animationstart", () => { + num_events++; + resolve(); + })); + + // Reparent item + document.body.querySelector("#new-parent").moveBefore(item, null); + await new Promise(resolve => requestAnimationFrame(() => resolve())); + assert_equals(num_events, 1); + assert_not_equals(getComputedStyle(item).transform, "none"); + }); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-left-pseudo.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-left-pseudo.html new file mode 100644 index 0000000000..fa51b16887 --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-left-pseudo.html @@ -0,0 +1,54 @@ +<!DOCTYPE html> +<title>Node.moveBefore should preserve CSS transition state on pseudo-elements (left)</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <section id="new-parent"> + </section> + <style> + #item { + width: 100px; + height: 100px; + background: green; + position: absolute; + left: 0; + } + + #item::before { + content: "Foo"; + width: 100px; + height: 100px; + background: green; + transition: left 60s steps(1, jump-both); + left: 0px; + position: absolute; + } + + #item.big::before { + left: 400px; + } + + section { + position: relative; + } + + body { + margin-left: 0; + } + </style> + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + assert_equals(item.getBoundingClientRect().x, 0); + item.classList.add("big"); + await new Promise(resolve => item.addEventListener("transitionstart", resolve)); + document.querySelector("#new-parent").moveBefore(item, null); + await new Promise(resolve => requestAnimationFrame(() => resolve())); + assert_equals(getComputedStyle(item, "::before").left, "200px"); + }); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-left.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-left.html new file mode 100644 index 0000000000..2b8e04b26e --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-left.html @@ -0,0 +1,41 @@ +<!DOCTYPE html> +<title>Node.moveBefore should preserve CSS transition state (left)</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <section id="new-parent"> + </section> + <style> + #item { + width: 100px; + height: 100px; + background: green; + transition: left 10s; + position: absolute; + left: 0; + } + + section { + position: relative; + } + + body { + margin-left: 0; + } + </style> + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + assert_equals(item.getBoundingClientRect().x, 0); + item.style.left = "400px"; + await new Promise(resolve => item.addEventListener("transitionstart", resolve)); + document.querySelector("#new-parent").moveBefore(item, null); + await new Promise(resolve => requestAnimationFrame(() => resolve())); + assert_less_than(item.getBoundingClientRect().x, 399); + }); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-transform-pseudo.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-transform-pseudo.html new file mode 100644 index 0000000000..d02c72561c --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-transform-pseudo.html @@ -0,0 +1,54 @@ +<!DOCTYPE html> +<title>Node.moveBefore should preserve CSS transition state on pseudo-elements (transform)</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <section id="new-parent"> + </section> + <style> + #item { + width: 100px; + height: 100px; + background: green; + position: absolute; + left: 0; + } + + #item::before { + content: "Foo"; + width: 100px; + height: 100px; + background: green; + transition: transform 60s steps(1, jump-both); + transform: none; + position: absolute; + } + + #item.big::before { + transform: translateX(400px); + } + + section { + position: relative; + } + + body { + margin-left: 0; + } + </style> + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + assert_equals(item.getBoundingClientRect().x, 0); + item.classList.add("big"); + await new Promise(resolve => item.addEventListener("transitionstart", resolve)); + document.querySelector("#new-parent").moveBefore(item, null); + await new Promise(resolve => requestAnimationFrame(() => resolve())); + assert_not_equals(getComputedStyle(item, "::before").transform, "none"); + }); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-transform.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-transform.html new file mode 100644 index 0000000000..f09edca144 --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/continue-css-transition-transform.html @@ -0,0 +1,36 @@ +<!DOCTYPE html> +<title>Node.moveBefore should preserve CSS transition state (transform)</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <section id="new-parent"> + </section> + <style> + #item { + width: 100px; + height: 100px; + background: green; + transition: transform 60s steps(1, jump-both); + } + + body { + margin-left: 0; + } + </style> + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + assert_equals(item.getBoundingClientRect().x, 0); + item.style.transform = "translateX(400px)"; + await new Promise(resolve => item.addEventListener("transitionstart", resolve)); + document.querySelector("#new-parent").moveBefore(item, null); + await new Promise(resolve => requestAnimationFrame(() => resolve())); + assert_equals(item.getBoundingClientRect().x, 200); + assert_equals(item.getAnimations().length, 1); + }); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-animation-commit-styles.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-animation-commit-styles.html new file mode 100644 index 0000000000..86bb7c33e4 --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-animation-commit-styles.html @@ -0,0 +1,45 @@ +<!DOCTYPE html> +<title>Calling commitStyles after Node.moveBefore should commit mid-transition value</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <section id="new-parent"> + </section> + <style> + @keyframes anim { + from { + transform: translateX(100px); + } + + to { + transform: translateX(400px); + } + } + + #item { + position: relative; + width: 100px; + height: 100px; + background: green; + animation: 1s linear infinite alternate anim; + animation-delay: 100ms; + } + </style> + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + await new Promise(resolve => item.addEventListener("animationstart", resolve)); + + // Reparent item + document.body.querySelector("#new-parent").moveBefore(item, null); + + item.getAnimations()[0].commitStyles(); + assert_true("transform" in item.style); + assert_not_equals(item.style.transform, "none"); + }); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-cross-document.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-cross-document.html new file mode 100644 index 0000000000..f3c8fafbfa --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-cross-document.html @@ -0,0 +1,45 @@ +<!DOCTYPE html> +<title>Node.moveBefore should not preserve CSS transition state when crossing document boundaries</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <iframe id="iframe"> + </iframe> + <section id="new-parent"> + </section> + <style id="style"> + #item { + width: 100px; + height: 100px; + background: green; + transition: left 10s; + position: absolute; + left: 0; + } + + section { + position: relative; + } + + body { + margin-left: 0; + } + </style> + <script> + promise_test(async t => { + const iframe = document.querySelector("#iframe"); + const style = document.querySelector("#style"); + iframe.contentDocument.head.append(style.cloneNode(true)); + const item = iframe.contentDocument.createElement("div"); + item.id = "item"; + iframe.contentDocument.body.append(item); + assert_equals(item.getBoundingClientRect().x, 0); + item.style.left = "400px"; + await new Promise(resolve => item.addEventListener("transitionstart", resolve)); + document.querySelector("#new-parent").moveBefore(item, null); + await new Promise(resolve => requestAnimationFrame(() => resolve())); + assert_greater_than(item.getBoundingClientRect().x, 399); + }, "Moving a transition across documents should reset its state"); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-cross-shadow.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-cross-shadow.html new file mode 100644 index 0000000000..145f40ba50 --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-cross-shadow.html @@ -0,0 +1,64 @@ +<!DOCTYPE html> +<title>Node.moveBefore should not preserve CSS transition state when crossing shadow boundaries</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <div id="shadow-container"> + <template shadowrootmode="open"> + <style> + #item { + width: 100px; + height: 100px; + background: green; + transition: left 10s; + position: absolute; + left: 0; + } + + section { + position: relative; + } + + body { + margin-left: 0; + } + </style> + <section id="new-parent"> + </section> + </template> + </div> + <style> + #item { + width: 100px; + height: 100px; + background: green; + transition: left 10s; + position: absolute; + left: 0; + } + + section { + position: relative; + } + + body { + margin-left: 0; + } + </style> + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + assert_equals(item.getBoundingClientRect().x, 0); + item.style.left = "400px"; + await new Promise(resolve => item.addEventListener("transitionstart", resolve)); + const shadowContainer = document.querySelector("#shadow-container"); + shadowContainer.shadowRoot.querySelector("#new-parent").moveBefore(item, null); + await new Promise(resolve => requestAnimationFrame(() => resolve())); + assert_greater_than(item.getBoundingClientRect().x, 399); + }, "Moving an element with a transition across shadow boundaries should reset the transition"); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-to-disconnected-document.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-to-disconnected-document.html new file mode 100644 index 0000000000..537edfe9b6 --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-to-disconnected-document.html @@ -0,0 +1,43 @@ +<!DOCTYPE html> +<title>Node.moveBefore should act like insertBefore when moving to a disconnected document</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <section id="new-parent"> + </section> + <style> + #item { + width: 100px; + height: 100px; + background: green; + transition: left 10s; + position: absolute; + left: 0; + } + + section { + position: relative; + } + + body { + margin-left: 0; + } + </style> + + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + assert_equals(item.getBoundingClientRect().x, 0); + item.style.left = "400px"; + await new Promise(resolve => item.addEventListener("transitionstart", resolve)); + const doc = document.implementation.createHTMLDocument(); + doc.body.moveBefore(item, null); + await new Promise(resolve => requestAnimationFrame(() => resolve())); + assert_equals(item.getBoundingClientRect().x, 0); + }, "Moving an element with a transition to a disconnected document should reset the transitionm state"); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-trigger.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-trigger.html new file mode 100644 index 0000000000..0cb5608a69 --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/css-transition-trigger.html @@ -0,0 +1,43 @@ +<!DOCTYPE html> +<title>Node.moveBefore should trigger CSS transition state (left) if needed</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<body> + <section id="old-parent"> + <div id="item"></div> + </section> + <section id="new-parent"> + </section> + <style> + #item { + width: 100px; + height: 100px; + background: green; + transition: left 10s steps(1, jump-both); + position: absolute; + left: 0; + } + + #new-parent #item { + left: 400px; + } + + section { + position: relative; + } + + body { + margin-left: 0; + } + </style> + <script> + promise_test(async t => { + const item = document.querySelector("#item"); + assert_equals(item.getBoundingClientRect().x, 0); + document.querySelector("#new-parent").moveBefore(item, null); + await new Promise(resolve => item.addEventListener("transitionstart", resolve)); + assert_equals(item.getBoundingClientRect().x, 200); + }); + </script> +</body> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/focus-preserve.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/focus-preserve.html new file mode 100644 index 0000000000..a00e8b7788 --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/focus-preserve.html @@ -0,0 +1,85 @@ +<!DOCTYPE html> +<title>moveBefore should not automatically clear focus</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<body> +<section id="old_parent"> +<button id="button" tabindex="1">Button</button> +</section> +<section id="new_parent"> +</section> +<section id="inert_parent" inert> +</section> +<section id="hidden_parent" hidden> +</section> +<script> + +function eventually_blurred(t, item, timeout = 1000) { + return new Promise((resolve, reject) => { + function onblur() { + resolve(); + item.removeEventListener("blur", onblur); + } + item.addEventListener("blur", onblur); + t.step_timeout(reject, timeout); + }); +} + +test(t => { + const old_parent = document.querySelector("#old_parent"); + const button = document.querySelector("#button"); + t.add_cleanup(() => old_parent.append(button)); + button.focus(); + assert_equals(document.activeElement, button); + new_parent.moveBefore(button, null); + assert_equals(document.activeElement, button); +}, "when reparenting an element, don't automatically reset the document focus"); + +promise_test(async t => { + const old_parent = document.querySelector("#old_parent"); + const button = document.querySelector("#button"); + t.add_cleanup(() => old_parent.append(button)); + const inert_parent = document.querySelector("#inert_parent"); + button.focus(); + assert_equals(document.activeElement, button); + inert_parent.moveBefore(button, null); + + // The button will still be considered the active element. It will blur asynchronously. + assert_equals(document.activeElement, button); + await eventually_blurred(t, button); + assert_equals(document.activeElement, document.body); +}, "when reparenting a focused element into an inert parent, reset the document focus"); + + +promise_test(async t => { + const old_parent = document.querySelector("#old_parent"); + const button = document.querySelector("#button"); + t.add_cleanup(() => old_parent.append(button)); + const hidden_parent = document.querySelector("#hidden_parent"); + button.focus(); + assert_equals(document.activeElement, button); + hidden_parent.moveBefore(button, null); + + // The button will still be considered the active element. It will blur asynchronously. + // This is similar to other operations that can cause a blur due to change in inert trees, + // e.g. a style change that makes an ancestor `display: none`. + assert_equals(document.activeElement, button); + await eventually_blurred(t, button); + assert_equals(document.activeElement, document.body); +}, "when reparenting a focused element into a hidden parent, reset the document focus"); + +promise_test(async t => { + const old_parent = document.querySelector("#old_parent"); + const button = document.querySelector("#button"); + t.add_cleanup(() => document.body.append(old_parent)); + const hidden_parent = document.querySelector("#hidden_parent"); + button.focus(); + assert_equals(document.activeElement, button); + hidden_parent.moveBefore(old_parent, null); + + // The button will still be considered the active element. It will blur asynchronously. + assert_equals(document.activeElement, button); + await eventually_blurred(t, button); + assert_equals(document.activeElement, document.body); +}, "when reparenting an ancestor of an focused element into a hidden parent, reset the document focus"); +</script> diff --git a/testing/web-platform/tests/dom/nodes/moveBefore/tentative/fullscreen-preserve.html b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/fullscreen-preserve.html new file mode 100644 index 0000000000..810eeac9af --- /dev/null +++ b/testing/web-platform/tests/dom/nodes/moveBefore/tentative/fullscreen-preserve.html @@ -0,0 +1,49 @@ +<!DOCTYPE html> +<title>Document#fullscreenElement</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/testdriver.js"></script> +<script src="/resources/testdriver-vendor.js"></script> +<script src="/fullscreen/trusted-click.js"></script> +<section id="old_parent"> + <div id="item"></div> +</section> +<section id="new_parent"> + <div id="item"></div> +</section> +<script> + promise_test(async function (t) { + const item = document.querySelector("#item"); + + await trusted_click(); + + assert_equals( + document.fullscreenElement, + null, + "fullscreenElement before requestFullscreen()" + ); + + await item.requestFullscreen(); + assert_equals( + document.fullscreenElement, + item, + "fullscreenElement before moveBefore()" + ); + + document.querySelector("#new_parent").moveBefore(item, null); + + assert_equals( + document.fullscreenElement, + item, + "fullscreenElement after moveBefore()" + ); + + await Promise.all([document.exitFullscreen(), fullScreenChange()]); + + assert_equals( + document.fullscreenElement, + null, + "fullscreenElement after exiting fullscreen" + ); + }); +</script> |