/* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ "use strict"; let NO_MOVE = { unexpected: [[EVENT_REORDER, "container"]] }; let MOVE = { expected: [[EVENT_REORDER, "container"]] }; // Set last ordinal child as aria-owned, should produce no reorder. addAccessibleTask( ``, async function (browser, accDoc) { let containerAcc = findAccessibleChildByID(accDoc, "container"); testChildrenIds(containerAcc, ["a"]); await contentSpawnMutation(browser, NO_MOVE, function () { // aria-own ordinal child in place, should be a no-op. content.document .getElementById("container") .setAttribute("aria-owns", "a"); }); testChildrenIds(containerAcc, ["a"]); } ); // Add a new ordinal child to a container with an aria-owned child. // Order should respect aria-owns. addAccessibleTask( ``, async function (browser, accDoc) { let containerAcc = findAccessibleChildByID(accDoc, "container"); testChildrenIds(containerAcc, ["a"]); await contentSpawnMutation(browser, MOVE, function () { let container = content.document.getElementById("container"); container.setAttribute("aria-owns", "a"); let aa = content.document.createElement("li"); aa.id = "aa"; container.appendChild(aa); }); testChildrenIds(containerAcc, ["aa", "a"]); await contentSpawnMutation(browser, MOVE, function () { content.document.getElementById("container").removeAttribute("aria-owns"); }); testChildrenIds(containerAcc, ["a", "aa"]); } ); // Remove a no-move aria-owns attribute, should result in a no-move. addAccessibleTask( ``, async function (browser, accDoc) { let containerAcc = findAccessibleChildByID(accDoc, "container"); testChildrenIds(containerAcc, ["a"]); await contentSpawnMutation(browser, NO_MOVE, function () { // remove aria-owned child that is already ordinal, should be no-op. content.document.getElementById("container").removeAttribute("aria-owns"); }); testChildrenIds(containerAcc, ["a"]); } ); // Attempt to steal an aria-owned child. The attempt should fail. addAccessibleTask( ` `, async function (browser, accDoc) { let containerAcc = findAccessibleChildByID(accDoc, "container"); testChildrenIds(containerAcc, []); await contentSpawnMutation(browser, NO_MOVE, function () { content.document .getElementById("container") .setAttribute("aria-owns", "a"); }); testChildrenIds(containerAcc, []); } ); // Don't aria-own children of `, async function (browser, accDoc) { let containerAcc = findAccessibleChildByID(accDoc, "container"); let selectAcc = findAccessibleChildByID(accDoc, "select"); testChildrenIds(containerAcc, []); testChildrenIds(selectAcc.firstChild, ["a", "b"]); } ); // Don't allow `, async function (browser, accDoc) { let containerAcc = findAccessibleChildByID(accDoc, "container"); let selectAcc = findAccessibleChildByID(accDoc, "select"); testChildrenIds(containerAcc, ["a", "b"]); testChildrenIds(selectAcc.firstChild, ["c"]); } ); // Don't allow one . addAccessibleTask( ` `, async function (browser, accDoc) { let selectAcc1 = findAccessibleChildByID(accDoc, "select1"); let selectAcc2 = findAccessibleChildByID(accDoc, "select2"); testChildrenIds(selectAcc1.firstChild, ["a", "b"]); testChildrenIds(selectAcc2.firstChild, ["c"]); } ); // Don't allow a `, async function (browser, accDoc) { let containerAcc = findAccessibleChildByID(accDoc, "container"); testChildrenIds(containerAcc.firstChild, ["a", "b", "c"]); await contentSpawnMutation(browser, NO_MOVE, function () { content.document .getElementById("container") .setAttribute("aria-owns", "a c b"); }); testChildrenIds(containerAcc.firstChild, ["a", "b", "c"]); } ); // Don't crash if ID in aria-owns does not exist addAccessibleTask( ` `, async function (browser, accDoc) { ok(true, "Did not crash"); } ); addAccessibleTask( ` `, async function (browser, accDoc) { let one = findAccessibleChildByID(accDoc, "one"); let two = findAccessibleChildByID(accDoc, "two"); let waitfor = { expected: [ [EVENT_REORDER, "one"], [EVENT_REORDER, "two"], ], }; await contentSpawnMutation(browser, waitfor, function () { // Put same id twice in aria-owns content.document.getElementById("two").setAttribute("aria-owns", "a a"); }); testChildrenIds(one, ["b", "c"]); testChildrenIds(two, ["a"]); await contentSpawnMutation(browser, waitfor, function () { // If the previous double-id aria-owns worked correctly, we should // be in a good state and all is fine.. content.document.getElementById("two").setAttribute("aria-owns", "a b"); }); testChildrenIds(one, ["c"]); testChildrenIds(two, ["a", "b"]); } ); addAccessibleTask( `
`, async function (browser, accDoc) { testChildrenIds(accDoc, ["a", "b"]); let waitFor = { expected: [[EVENT_REORDER, e => e.accessible == accDoc]], }; await contentSpawnMutation(browser, waitFor, function () { content.document.documentElement.style.display = "none"; content.document.documentElement.getBoundingClientRect(); content.document.body.setAttribute("aria-owns", "b a"); content.document.documentElement.remove(); }); testChildrenIds(accDoc, []); } ); // Don't allow ordinal child to be placed after aria-owned child (bug 1405796) addAccessibleTask( `
Hello
There
There
`, async function (browser, accDoc) { let containerAcc = findAccessibleChildByID(accDoc, "container"); testChildrenIds(containerAcc, ["a"]); await contentSpawnMutation(browser, MOVE, function () { content.document .getElementById("container") .setAttribute("aria-owns", "c"); }); testChildrenIds(containerAcc, ["a", "c"]); await contentSpawnMutation(browser, MOVE, function () { let span = content.document.createElement("span"); content.document.getElementById("container").appendChild(span); let b = content.document.createElement("div"); b.id = "b"; content.document.getElementById("container").appendChild(b); }); testChildrenIds(containerAcc, ["a", "b", "c"]); await contentSpawnMutation(browser, MOVE, function () { content.document .getElementById("container") .setAttribute("aria-owns", "c d"); }); testChildrenIds(containerAcc, ["a", "b", "c", "d"]); } );