/* Any copyright is dedicated to the Public Domain. http://creativecommons.org/publicdomain/zero/1.0/ */ "use strict"; function fillPopupAndGetItems() { let menupopup = document.getElementById("pageStyleMenu").menupopup; gPageStyleMenu.fillPopup(menupopup); return Array.from(menupopup.querySelectorAll("menuseparator ~ menuitem")); } function getRootColor() { return SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () { return content.document.defaultView.getComputedStyle( content.document.documentElement ).color; }); } const RED = "rgb(255, 0, 0)"; const LIME = "rgb(0, 255, 0)"; const BLUE = "rgb(0, 0, 255)"; const kStyleSheetsInPageStyleSample = 18; /* * Test that the right stylesheets do (and others don't) show up * in the page style menu. */ add_task(async function test_menu() { let tab = await BrowserTestUtils.openNewForegroundTab( gBrowser, "about:blank", false ); let browser = tab.linkedBrowser; BrowserTestUtils.loadURIString(browser, WEB_ROOT + "page_style_sample.html"); await promiseStylesheetsLoaded(browser, kStyleSheetsInPageStyleSample); let menuitems = fillPopupAndGetItems(); let items = menuitems.map(el => ({ label: el.getAttribute("label"), checked: el.getAttribute("checked") == "true", })); let validLinks = await SpecialPowers.spawn( gBrowser.selectedBrowser, [items], function (contentItems) { let contentValidLinks = 0; for (let el of content.document.querySelectorAll("link, style")) { var title = el.getAttribute("title"); var rel = el.getAttribute("rel"); var media = el.getAttribute("media"); var idstring = el.nodeName + " " + (title ? title : "without title and") + ' with rel="' + rel + '"' + (media ? ' and media="' + media + '"' : ""); var item = contentItems.filter(aItem => aItem.label == title); var found = item.length == 1; var checked = found && item[0].checked; switch (el.getAttribute("data-state")) { case "0": ok(!found, idstring + " should not show up in page style menu"); break; case "1": contentValidLinks++; ok(found, idstring + " should show up in page style menu"); ok(!checked, idstring + " should not be selected"); break; case "2": contentValidLinks++; ok(found, idstring + " should show up in page style menu"); ok(checked, idstring + " should be selected"); break; default: throw new Error( "data-state attribute is missing or has invalid value" ); } } return contentValidLinks; } ); ok(menuitems.length, "At least one item in the menu"); is(menuitems.length, validLinks, "all valid links found"); is(await getRootColor(), LIME, "Root should be lime (styles should apply)"); let disableStyles = document.getElementById("menu_pageStyleNoStyle"); let defaultStyles = document.getElementById("menu_pageStylePersistentOnly"); let otherStyles = menuitems[0].parentNode.querySelector("[label='28']"); // Assert that the menu works as expected. disableStyles.click(); await TestUtils.waitForCondition(async function () { let color = await getRootColor(); return color != LIME && color != BLUE; }, "ensuring disabled styles work"); otherStyles.click(); await TestUtils.waitForCondition(async function () { let color = await getRootColor(); return color == BLUE; }, "ensuring alternate styles work. clicking on: " + otherStyles.label); defaultStyles.click(); info("ensuring default styles work"); await TestUtils.waitForCondition(async function () { let color = await getRootColor(); return color == LIME; }, "ensuring default styles work"); BrowserTestUtils.removeTab(tab); }); add_task(async function test_default_style_with_no_sheets() { const PAGE = WEB_ROOT + "page_style_only_alternates.html"; await BrowserTestUtils.withNewTab( { gBrowser, url: PAGE, waitForLoad: true, }, async function (browser) { await promiseStylesheetsLoaded(browser, 2); let menuitems = fillPopupAndGetItems(); is(menuitems.length, 2, "Should've found two style sets"); is( await getRootColor(), BLUE, "First found style should become the preferred one and apply" ); // Reset the styles. document.getElementById("menu_pageStylePersistentOnly").click(); await TestUtils.waitForCondition(async function () { let color = await getRootColor(); return color != BLUE && color != RED; }); ok( true, "Should reset the style properly even if there are no non-alternate stylesheets" ); } ); }); add_task(async function test_page_style_file() { const FILE_PAGE = Services.io.newFileURI( new FileUtils.File(getTestFilePath("page_style_sample.html")) ).spec; await BrowserTestUtils.withNewTab(FILE_PAGE, async function (browser) { await promiseStylesheetsLoaded(browser, kStyleSheetsInPageStyleSample); let menuitems = fillPopupAndGetItems(); is( menuitems.length, kStyleSheetsInPageStyleSample, "Should have the right amount of items even for file: URI." ); }); });