mirror of
https://github.com/servo/servo.git
synced 2025-08-06 14:10:11 +01:00
Update web-platform-tests to revision b'02400d32d48521baa38663fe8601779994fcfb78'
This commit is contained in:
parent
bc8cea2495
commit
f0bb7a6f9c
483 changed files with 12767 additions and 2644 deletions
|
@ -0,0 +1,197 @@
|
|||
<!DOCTYPE HTML>
|
||||
<meta charset=UTF-8>
|
||||
<title>Test for the name attribute creating exclusive accordions from details elements</title>
|
||||
<link rel="author" title="L. David Baron" href="https://dbaron.org/">
|
||||
<link rel="author" title="Google" href="http://www.google.com/">
|
||||
<link rel="help" href="https://html.spec.whatwg.org/multipage/#the-details-element">
|
||||
<link rel="help" href="https://open-ui.org/components/accordion.explainer">
|
||||
<link rel="help" href="https://github.com/openui/open-ui/issues/725">
|
||||
<link rel="help" href="https://bugs.chromium.org/p/chromium/issues/detail?id=1444057">
|
||||
<script src="/resources/testharness.js"></script>
|
||||
<script src="/resources/testharnessreport.js"></script>
|
||||
|
||||
<div id="container">
|
||||
</div>
|
||||
|
||||
<script>
|
||||
|
||||
function assert_element_states(elements, expectations, description) {
|
||||
assert_array_equals(elements.map(e => Number(e.open)), expectations, description);
|
||||
}
|
||||
|
||||
let container = document.getElementById("container");
|
||||
|
||||
promise_test(async t => {
|
||||
container.innerHTML = `
|
||||
<details name="a">
|
||||
<summary>1</summary>
|
||||
This is the first item.
|
||||
</details>
|
||||
|
||||
<details name="a">
|
||||
<summary>2</summary>
|
||||
This is the second item.
|
||||
</details>
|
||||
`;
|
||||
let first = container.firstElementChild;
|
||||
let second = first.nextElementSibling;
|
||||
assert_false(first.open);
|
||||
assert_false(second.open);
|
||||
first.open = true;
|
||||
assert_true(first.open);
|
||||
assert_false(second.open);
|
||||
second.open = true;
|
||||
assert_false(first.open);
|
||||
assert_true(second.open);
|
||||
second.open = true;
|
||||
assert_false(first.open);
|
||||
assert_true(second.open);
|
||||
second.open = false;
|
||||
assert_false(first.open);
|
||||
assert_false(second.open);
|
||||
}, "basic handling of mutually exclusive details");
|
||||
|
||||
promise_test(async t => {
|
||||
container.innerHTML = `
|
||||
<details name="a" open>
|
||||
<summary>1</summary>
|
||||
This is the first item.
|
||||
</details>
|
||||
|
||||
<details name="a">
|
||||
<summary>2</summary>
|
||||
This is the second item.
|
||||
</details>
|
||||
|
||||
<details name="a" open>
|
||||
<summary>3</summary>
|
||||
This is the third item.
|
||||
</details>
|
||||
`;
|
||||
let first = container.firstElementChild;
|
||||
let second = first.nextElementSibling;
|
||||
let third = second.nextElementSibling;
|
||||
function assert_states(expected_first, expected_second, expected_third, description) {
|
||||
assert_array_equals([first.open, second.open, third.open], [expected_first, expected_second, expected_third], description);
|
||||
}
|
||||
|
||||
assert_states(true, false, true, "initial states from open attribute");
|
||||
first.open = true;
|
||||
assert_states(true, false, true, "non-mutation doesn't change state");
|
||||
second.open = true;
|
||||
assert_states(false, true, false, "mutation closes multiple open elements");
|
||||
third.setAttribute("open", "");
|
||||
assert_states(false, false, true, "setAttribute closes other open element");
|
||||
}, "more complex handling of mutually exclusive details");
|
||||
|
||||
promise_test(async t => {
|
||||
let details_elements_string = `
|
||||
<details name="a"></details>
|
||||
<details name="a" open></details>
|
||||
<details name="b"></details>
|
||||
<details name="b"></details>
|
||||
`;
|
||||
container.innerHTML = `
|
||||
${details_elements_string}
|
||||
<div id="shadow_host"></div>
|
||||
`;
|
||||
let shadow_root = document.getElementById("shadow_host").attachShadow({ mode: "open" });
|
||||
shadow_root.innerHTML = details_elements_string;
|
||||
let elements = Array.from(container.querySelectorAll("details")).concat(Array.from(shadow_root.querySelectorAll("details")));
|
||||
|
||||
assert_element_states(elements, [0, 1, 0, 0, 0, 1, 0, 0], "initial states from open attribute");
|
||||
elements[4].open = true;
|
||||
assert_element_states(elements, [0, 1, 0, 0, 1, 0, 0, 0], "after mutation in shadow tree");
|
||||
for (let i = 0; i < 8; ++i) {
|
||||
elements[i].open = true;
|
||||
}
|
||||
assert_element_states(elements, [0, 1, 0, 1, 0, 1, 0, 1], "after setting all elements open");
|
||||
elements[0].open = true;
|
||||
assert_element_states(elements, [1, 0, 0, 1, 0, 1, 0, 1], "after final mutation");
|
||||
}, "mutually exclusive details across multiple names and multiple tree scopes");
|
||||
|
||||
// The next two tests test characteristics of the design that are only
|
||||
// exposed via mutation events. If mutation events (for attribute
|
||||
// addition/removal) are removed from the web, these tests could be
|
||||
// removed, and some small simplifications could be made to the code
|
||||
// implementing this feature.
|
||||
function mutation_events_for_attribute_removal_supported() {
|
||||
container.innerHTML = `<div id="event-removal-test"></div>`;
|
||||
let element = container.firstChild;
|
||||
let event_fired = false;
|
||||
element.addEventListener("DOMSubtreeModified", event => event_fired = true);
|
||||
element.removeAttribute("id");
|
||||
return event_fired;
|
||||
}
|
||||
|
||||
promise_test(async t => {
|
||||
if (!mutation_events_for_attribute_removal_supported()) {
|
||||
return;
|
||||
}
|
||||
container.innerHTML = `
|
||||
<details name="a" id="e0" open></details>
|
||||
<details name="a" id="e1"></details>
|
||||
<details name="a" id="e3" open></details>
|
||||
`;
|
||||
let e2 = document.createElement("details");
|
||||
e2.id = "e2";
|
||||
e2.name = "a";
|
||||
e2.open = true;
|
||||
let elements = [ document.getElementById("e0"),
|
||||
document.getElementById("e1"),
|
||||
e2,
|
||||
document.getElementById("e3") ];
|
||||
container.insertBefore(e2, elements[3]);
|
||||
|
||||
let received_ids = [];
|
||||
let listener = event => {
|
||||
assert_equals(event.type, "DOMSubtreeModified");
|
||||
assert_equals(event.target.nodeType, Node.ELEMENT_NODE);
|
||||
let element = event.target;
|
||||
assert_equals(element.localName, "details");
|
||||
received_ids.push(element.id);
|
||||
};
|
||||
for (let element of elements) {
|
||||
element.addEventListener("DOMSubtreeModified", listener);
|
||||
}
|
||||
assert_array_equals(received_ids, []);
|
||||
assert_element_states(elements, [1, 0, 1, 1], "states before mutation");
|
||||
elements[1].open = true;
|
||||
assert_array_equals(received_ids, ["e0", "e3", "e2", "e1"],
|
||||
"removal events received in node insertion order, followed by addition event");
|
||||
assert_element_states(elements, [0, 1, 0, 0], "states after mutation");
|
||||
}, "mutation event order matches order of insertion in set of named elements");
|
||||
|
||||
promise_test(async t => {
|
||||
if (!mutation_events_for_attribute_removal_supported()) {
|
||||
return;
|
||||
}
|
||||
container.innerHTML = `
|
||||
<details name="a" id="e0" open></details>
|
||||
<details name="a" id="e1"></details>
|
||||
<details name="a" id="e2" open></details>
|
||||
`;
|
||||
let elements = [ document.getElementById("e0"),
|
||||
document.getElementById("e1"),
|
||||
document.getElementById("e2") ];
|
||||
|
||||
let received_ids = [];
|
||||
let listener = event => {
|
||||
received_ids.push(event.target.id);
|
||||
let i = 0;
|
||||
for (let element of elements) {
|
||||
element.setAttribute("name", `b${i++}`);
|
||||
}
|
||||
};
|
||||
for (let element of elements) {
|
||||
element.addEventListener("DOMSubtreeModified", listener);
|
||||
}
|
||||
assert_array_equals(received_ids, []);
|
||||
assert_element_states(elements, [1, 0, 1], "states before mutation");
|
||||
elements[1].open = true;
|
||||
assert_array_equals(received_ids, ["e0", "e2", "e1"],
|
||||
"removal events received in node insertion order, followed by addition event, despite changes to name during mutation event");
|
||||
assert_element_states(elements, [0, 1, 0], "states after mutation");
|
||||
}, "interaction of open attribute changes with mutation events");
|
||||
|
||||
</script>
|
|
@ -0,0 +1,71 @@
|
|||
<!DOCTYPE html>
|
||||
<link rel=author href="mailto:jarhar@chromium.org">
|
||||
<link rel=help href="https://github.com/whatwg/html/issues/8904">
|
||||
<script src="/resources/testharness.js"></script>
|
||||
<script src="/resources/testharnessreport.js"></script>
|
||||
<script src="/resources/declarative-shadow-dom-polyfill.js"></script>
|
||||
|
||||
<button id=b1>button 1</button>
|
||||
<button id=b2>button 2</button>
|
||||
<div id=host>
|
||||
<template shadowrootmode=open>
|
||||
<button>button in shadowroot outside dialog</button>
|
||||
</template>
|
||||
</div>
|
||||
<dialog id=mydialog>
|
||||
<button id=b3>button in dialog</button>
|
||||
<div id=dialoghost>
|
||||
<template shadowrootmode=open>
|
||||
<button>button in shadowroot in dialog</button>
|
||||
</template>
|
||||
</div>
|
||||
</dialog>
|
||||
|
||||
<div id=host2>
|
||||
<template shadowrootmode=open>
|
||||
<dialog>
|
||||
<slot></slot>
|
||||
</dialog>
|
||||
</template>
|
||||
<button id=host2button>button</button>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
polyfill_declarative_shadow_dom(document);
|
||||
|
||||
test(() => {
|
||||
b1.focus();
|
||||
mydialog.show();
|
||||
b2.focus();
|
||||
mydialog.close();
|
||||
assert_equals(document.activeElement, b2);
|
||||
}, 'Focus should not be restored if the currently focused element is not inside the dialog.');
|
||||
|
||||
test(() => {
|
||||
const shadowbutton = host.shadowRoot.querySelector('button');
|
||||
b2.focus();
|
||||
mydialog.show();
|
||||
shadowbutton.focus();
|
||||
mydialog.close();
|
||||
assert_equals(document.activeElement, host, 'document.activeElement should point at the shadow host.');
|
||||
assert_equals(host.shadowRoot.activeElement, shadowbutton, 'The button in the shadowroot should remain focused.');
|
||||
}, 'Focus restore should not occur when the focused element is in a shadowroot outside of the dialog.');
|
||||
|
||||
test(() => {
|
||||
const shadowbutton = dialoghost.shadowRoot.querySelector('button');
|
||||
b2.focus();
|
||||
mydialog.show();
|
||||
shadowbutton.focus();
|
||||
mydialog.close();
|
||||
assert_equals(document.activeElement, b2);
|
||||
}, 'Focus restore should occur when the focused element is in a shadowroot inside the dialog.');
|
||||
|
||||
test(() => {
|
||||
const dialog = host2.shadowRoot.querySelector('dialog');
|
||||
b2.focus();
|
||||
dialog.show();
|
||||
host2button.focus();
|
||||
dialog.close();
|
||||
assert_equals(document.activeElement, b2);
|
||||
}, 'Focus restore should occur when the focused element is slotted into a dialog.');
|
||||
</script>
|
|
@ -0,0 +1,29 @@
|
|||
<!DOCTYPE html>
|
||||
<link rel=author href="mailto:jarhar@chromium.org">
|
||||
<link rel=help href="https://github.com/whatwg/html/pull/9142">
|
||||
<script src="/resources/testharness.js"></script>
|
||||
<script src="/resources/testharnessreport.js"></script>
|
||||
|
||||
<dialog>hello</dialog>
|
||||
|
||||
<script>
|
||||
test(() => {
|
||||
const dialog = document.querySelector('dialog');
|
||||
|
||||
// calling close() on a dialog that is already closed should not throw.
|
||||
dialog.close();
|
||||
|
||||
dialog.show();
|
||||
// calling show() on a dialog that is already showing non-modal should not throw.
|
||||
dialog.show();
|
||||
assert_throws_dom('InvalidStateError', () => dialog.showModal(),
|
||||
'Calling showModal() on a dialog that is already showing non-modal should throw.');
|
||||
dialog.close();
|
||||
|
||||
dialog.showModal();
|
||||
assert_throws_dom('InvalidStateError', () => dialog.show(),
|
||||
'Calling show() on a dialog that is already showing modal should throw.');
|
||||
// calling showModal() on a dialog that is already showing modal should not throw.
|
||||
dialog.showModal();
|
||||
});
|
||||
</script>
|
Loading…
Add table
Add a link
Reference in a new issue