mirror of
https://github.com/mozilla/gecko-dev.git
synced 2025-02-10 17:24:29 +00:00
Bug 1349689 - Remove old preferences fork r=jaws
MozReview-Commit-ID: GNPcQGUTUKJ --HG-- rename : browser/components/preferences/in-content-new/findInPage.js => browser/components/preferences/in-content/findInPage.js rename : browser/components/preferences/in-content-new/searchResults.xul => browser/components/preferences/in-content/searchResults.xul rename : browser/components/preferences/in-content-new/tests/browser_checkspelling.js => browser/components/preferences/in-content/tests/browser_checkspelling.js rename : browser/components/preferences/in-content-new/tests/browser_engines.js => browser/components/preferences/in-content/tests/browser_engines.js rename : browser/components/preferences/in-content-new/tests/browser_layersacceleration.js => browser/components/preferences/in-content/tests/browser_layersacceleration.js rename : browser/components/preferences/in-content-new/tests/browser_masterpassword.js => browser/components/preferences/in-content/tests/browser_masterpassword.js rename : browser/components/preferences/in-content-new/tests/browser_permissions_dialog.js => browser/components/preferences/in-content/tests/browser_permissions_dialog.js rename : browser/components/preferences/in-content-new/tests/browser_search_subdialogs_within_preferences_1.js => browser/components/preferences/in-content/tests/browser_search_subdialogs_within_preferences_1.js rename : browser/components/preferences/in-content-new/tests/browser_search_subdialogs_within_preferences_2.js => browser/components/preferences/in-content/tests/browser_search_subdialogs_within_preferences_2.js rename : browser/components/preferences/in-content-new/tests/browser_search_subdialogs_within_preferences_3.js => browser/components/preferences/in-content/tests/browser_search_subdialogs_within_preferences_3.js rename : browser/components/preferences/in-content-new/tests/browser_search_subdialogs_within_preferences_4.js => browser/components/preferences/in-content/tests/browser_search_subdialogs_within_preferences_4.js rename : browser/components/preferences/in-content-new/tests/browser_search_subdialogs_within_preferences_5.js => browser/components/preferences/in-content/tests/browser_search_subdialogs_within_preferences_5.js rename : browser/components/preferences/in-content-new/tests/browser_search_subdialogs_within_preferences_6.js => browser/components/preferences/in-content/tests/browser_search_subdialogs_within_preferences_6.js rename : browser/components/preferences/in-content-new/tests/browser_search_subdialogs_within_preferences_7.js => browser/components/preferences/in-content/tests/browser_search_subdialogs_within_preferences_7.js rename : browser/components/preferences/in-content-new/tests/browser_search_subdialogs_within_preferences_8.js => browser/components/preferences/in-content/tests/browser_search_subdialogs_within_preferences_8.js rename : browser/components/preferences/in-content-new/tests/browser_search_within_preferences_2.js => browser/components/preferences/in-content/tests/browser_search_within_preferences_2.js rename : browser/components/preferences/in-content-new/tests/browser_search_within_preferences_command.js => browser/components/preferences/in-content/tests/browser_search_within_preferences_command.js rename : browser/components/preferences/in-content-new/tests/browser_security-1.js => browser/components/preferences/in-content/tests/browser_security-1.js rename : browser/components/preferences/in-content-new/tests/browser_security-2.js => browser/components/preferences/in-content/tests/browser_security-2.js extra : rebase_source : 9adc8231c896f93f7f262a09482b44a2875bd5fd
This commit is contained in:
parent
51133fbff6
commit
daac97d466
@ -725,9 +725,6 @@ pref("browser.preferences.instantApply", true);
|
||||
// Toggling Search bar on and off in about:preferences
|
||||
pref("browser.preferences.search", true);
|
||||
|
||||
// Use the new in-content about:preferences in Nightly only for now
|
||||
pref("browser.preferences.useOldOrganization", false);
|
||||
|
||||
// Once the Storage Management is completed.
|
||||
// (The Storage Management-related prefs are browser.storageManager.* )
|
||||
// The Offline(Appcache) Group section in about:preferences will be hidden.
|
||||
|
@ -63,13 +63,7 @@ var gDataNotificationInfoBar = {
|
||||
popup: null,
|
||||
callback: () => {
|
||||
this._actionTaken = true;
|
||||
// The advanced subpanes are only supported in the old organization, which will
|
||||
// be removed by bug 1349689.
|
||||
if (Services.prefs.getBoolPref("browser.preferences.useOldOrganization")) {
|
||||
window.openAdvancedPreferences("dataChoicesTab", {origin: "dataReporting"});
|
||||
} else {
|
||||
window.openPreferences("privacy-reports", {origin: "dataReporting"});
|
||||
}
|
||||
window.openPreferences("privacy-reports", {origin: "dataReporting"});
|
||||
},
|
||||
}];
|
||||
|
||||
|
@ -169,11 +169,7 @@ var gEMEHandler = {
|
||||
label: gNavigatorBundle.getString(btnLabelId),
|
||||
accessKey: gNavigatorBundle.getString(btnAccessKeyId),
|
||||
callback() {
|
||||
if (Services.prefs.getBoolPref("browser.preferences.useOldOrganization")) {
|
||||
openPreferences("paneContent", {origin: "browserMedia"});
|
||||
} else {
|
||||
openPreferences("general-drm", {origin: "browserMedia"});
|
||||
}
|
||||
openPreferences("general-drm", {origin: "browserMedia"});
|
||||
},
|
||||
dismiss: true
|
||||
};
|
||||
|
@ -548,11 +548,7 @@ const gStoragePressureObserver = {
|
||||
// The advanced subpanes are only supported in the old organization, which will
|
||||
// be removed by bug 1349689.
|
||||
let win = gBrowser.ownerGlobal;
|
||||
if (Services.prefs.getBoolPref("browser.preferences.useOldOrganization")) {
|
||||
win.openAdvancedPreferences("networkTab", {origin: "storagePressure"});
|
||||
} else {
|
||||
win.openPreferences("panePrivacy", {origin: "storagePressure"});
|
||||
}
|
||||
win.openPreferences("panePrivacy", { origin: "storagePressure" });
|
||||
}
|
||||
});
|
||||
}
|
||||
@ -6532,13 +6528,7 @@ var OfflineApps = {
|
||||
},
|
||||
|
||||
manage() {
|
||||
// The advanced subpanes are only supported in the old organization, which will
|
||||
// be removed by bug 1349689.
|
||||
if (Services.prefs.getBoolPref("browser.preferences.useOldOrganization")) {
|
||||
openAdvancedPreferences("networkTab", {origin: "offlineApps"});
|
||||
} else {
|
||||
openPreferences("panePrivacy", {origin: "offlineApps"});
|
||||
}
|
||||
openPreferences("panePrivacy", { origin: "offlineApps" });
|
||||
},
|
||||
|
||||
receiveMessage(msg) {
|
||||
|
@ -1,10 +1,7 @@
|
||||
"use strict";
|
||||
|
||||
var notificationURL = "http://example.org/browser/browser/base/content/test/alerts/file_dom_notifications.html";
|
||||
var useOldPrefs = Services.prefs.getBoolPref("browser.preferences.useOldOrganization");
|
||||
var expectedURL = useOldPrefs ? "about:preferences#content"
|
||||
: "about:preferences#privacy";
|
||||
|
||||
var expectedURL = "about:preferences#privacy";
|
||||
|
||||
add_task(async function test_settingsOpen_observer() {
|
||||
info("Opening a dummy tab so openPreferences=>switchToTabHavingURI doesn't use the blank tab.");
|
||||
@ -12,13 +9,6 @@ add_task(async function test_settingsOpen_observer() {
|
||||
gBrowser,
|
||||
url: "about:robots"
|
||||
}, async function dummyTabTask(aBrowser) {
|
||||
// Ensure preferences is loaded before removing the tab. In the "new prefs", all categories
|
||||
// get initialized on page load since we need to be able to search them. Sync is *very*
|
||||
// slow to load and therefore we need to wait for it to load when testing the "new prefs".
|
||||
// For "old prefs" we only load the actual visited categories so we don't have this problem,
|
||||
// as well, the "sync-pane-loaded" notification is not sent on "old prefs".
|
||||
let syncPaneLoadedPromise = useOldPrefs || TestUtils.topicObserved("sync-pane-loaded", () => true);
|
||||
|
||||
let tabPromise = BrowserTestUtils.waitForNewTab(gBrowser, expectedURL);
|
||||
info("simulate a notifications-open-settings notification");
|
||||
let uri = NetUtil.newURI("https://example.com");
|
||||
@ -26,7 +16,6 @@ add_task(async function test_settingsOpen_observer() {
|
||||
Services.obs.notifyObservers(principal, "notifications-open-settings");
|
||||
let tab = await tabPromise;
|
||||
ok(tab, "The notification settings tab opened");
|
||||
await syncPaneLoadedPromise;
|
||||
await BrowserTestUtils.removeTab(tab);
|
||||
});
|
||||
});
|
||||
@ -41,13 +30,6 @@ add_task(async function test_settingsOpen_button() {
|
||||
gBrowser,
|
||||
url: notificationURL
|
||||
}, async function tabTask(aBrowser) {
|
||||
// Ensure preferences is loaded before removing the tab. In the "new prefs", all categories
|
||||
// get initialized on page load since we need to be able to search them. Sync is *very*
|
||||
// slow to load and therefore we need to wait for it to load when testing the "new prefs".
|
||||
// For "old prefs" we only load the actual visited categories so we don't have this problem,
|
||||
// as well, the "sync-pane-loaded" notification is not sent on "old prefs".
|
||||
let syncPaneLoadedPromise = useOldPrefs || TestUtils.topicObserved("sync-pane-loaded", () => true);
|
||||
|
||||
info("Waiting for notification");
|
||||
await openNotification(aBrowser, "showNotification2");
|
||||
|
||||
@ -67,7 +49,6 @@ add_task(async function test_settingsOpen_button() {
|
||||
let tab = await tabPromise;
|
||||
ok(tab, "The notification settings tab opened");
|
||||
|
||||
await syncPaneLoadedPromise;
|
||||
await closePromise;
|
||||
await BrowserTestUtils.removeTab(tab);
|
||||
});
|
||||
|
@ -83,15 +83,10 @@ var checkInfobarButton = async function(aNotification) {
|
||||
Assert.equal(buttons.length, 1, "There is 1 button in the data reporting notification.");
|
||||
let button = buttons[0];
|
||||
|
||||
// Add an observer to ensure the "advanced" pane opened (but don't bother
|
||||
// closing it - we close the entire window when done.)
|
||||
let paneLoadedPromise = promiseTopicObserved("advanced-pane-loaded");
|
||||
|
||||
// Click on the button.
|
||||
button.click();
|
||||
|
||||
// Wait for the preferences panel to open.
|
||||
await paneLoadedPromise;
|
||||
await promiseNextTick();
|
||||
};
|
||||
|
||||
|
@ -15,7 +15,6 @@ registerCleanupFunction(function() {
|
||||
Services.perms.removeFromPrincipal(principal, "offline-app");
|
||||
Services.prefs.clearUserPref("offline-apps.quota.warn");
|
||||
Services.prefs.clearUserPref("offline-apps.allow_by_default");
|
||||
Services.prefs.clearUserPref("browser.preferences.useOldOrganization");
|
||||
let {OfflineAppCacheHelper} = Components.utils.import("resource:///modules/offlineAppCache.jsm", {});
|
||||
OfflineAppCacheHelper.clear();
|
||||
});
|
||||
@ -34,7 +33,6 @@ function checkInContentPreferences(win) {
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.useOldOrganization", false);
|
||||
Services.prefs.setBoolPref("offline-apps.allow_by_default", false);
|
||||
|
||||
// Open a new tab.
|
||||
|
@ -13,40 +13,13 @@ function notifyStoragePressure(usage = 100) {
|
||||
}
|
||||
|
||||
function openAboutPrefPromise() {
|
||||
let useOldOrganization = Services.prefs.getBoolPref("browser.preferences.useOldOrganization");
|
||||
let targetURL = useOldOrganization ? "about:preferences#advanced" : "about:preferences#privacy";
|
||||
let promises = [
|
||||
BrowserTestUtils.waitForLocationChange(gBrowser, targetURL),
|
||||
TestUtils.topicObserved("advanced-pane-loaded", () => true)
|
||||
BrowserTestUtils.waitForLocationChange(gBrowser, "about:preferences#privacy"),
|
||||
TestUtils.topicObserved("privacy-pane-loaded", () => true)
|
||||
];
|
||||
return Promise.all(promises);
|
||||
}
|
||||
|
||||
async function testOverUsageThresholdNotification() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.pressureNotification.minIntervalMS", 0]]});
|
||||
let tab = await BrowserTestUtils.openNewForegroundTab(gBrowser, "https://example.com");
|
||||
|
||||
const BYTES_IN_GIGABYTE = 1073741824;
|
||||
const USAGE_THRESHOLD_BYTES = BYTES_IN_GIGABYTE *
|
||||
Services.prefs.getIntPref("browser.storageManager.pressureNotification.usageThresholdGB");
|
||||
await notifyStoragePressure(USAGE_THRESHOLD_BYTES);
|
||||
let notificationbox = document.getElementById("high-priority-global-notificationbox");
|
||||
let notification = notificationbox.getNotificationWithValue("storage-pressure-notification");
|
||||
ok(notification instanceof XULElement, "Should display storage pressure notification");
|
||||
|
||||
let prefBtn = notification.getElementsByTagName("button")[1];
|
||||
let aboutPrefPromise = openAboutPrefPromise();
|
||||
prefBtn.doCommand();
|
||||
await aboutPrefPromise;
|
||||
let aboutPrefTab = gBrowser.selectedTab;
|
||||
let prefDoc = gBrowser.selectedBrowser.contentDocument;
|
||||
let siteDataGroup = prefDoc.getElementById("siteDataGroup");
|
||||
is_element_visible(siteDataGroup, "Should open to the siteDataGroup section in about:preferences");
|
||||
await BrowserTestUtils.removeTab(aboutPrefTab);
|
||||
await BrowserTestUtils.removeTab(tab);
|
||||
}
|
||||
|
||||
// Test only displaying notification once within the given interval
|
||||
add_task(async function() {
|
||||
const TEST_NOTIFICATION_INTERVAL_MS = 2000;
|
||||
@ -72,12 +45,28 @@ add_task(async function() {
|
||||
|
||||
// Test guiding user to the about:preferences when usage exceeds the given threshold
|
||||
add_task(async function() {
|
||||
// Test for the old about:preferences
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.preferences.useOldOrganization", true]]});
|
||||
await testOverUsageThresholdNotification();
|
||||
// Test for the new about:preferences
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.preferences.useOldOrganization", false]]});
|
||||
await testOverUsageThresholdNotification();
|
||||
await SpecialPowers.pushPrefEnv({ set: [["browser.storageManager.enabled", true]] });
|
||||
await SpecialPowers.pushPrefEnv({ set: [["browser.storageManager.pressureNotification.minIntervalMS", 0]] });
|
||||
let tab = await BrowserTestUtils.openNewForegroundTab(gBrowser, "https://example.com");
|
||||
|
||||
const BYTES_IN_GIGABYTE = 1073741824;
|
||||
const USAGE_THRESHOLD_BYTES = BYTES_IN_GIGABYTE *
|
||||
Services.prefs.getIntPref("browser.storageManager.pressureNotification.usageThresholdGB");
|
||||
await notifyStoragePressure(USAGE_THRESHOLD_BYTES);
|
||||
let notificationbox = document.getElementById("high-priority-global-notificationbox");
|
||||
let notification = notificationbox.getNotificationWithValue("storage-pressure-notification");
|
||||
ok(notification instanceof XULElement, "Should display storage pressure notification");
|
||||
|
||||
let prefBtn = notification.getElementsByTagName("button")[1];
|
||||
let aboutPrefPromise = openAboutPrefPromise();
|
||||
prefBtn.doCommand();
|
||||
await aboutPrefPromise;
|
||||
let aboutPrefTab = gBrowser.selectedTab;
|
||||
let prefDoc = gBrowser.selectedBrowser.contentDocument;
|
||||
let siteDataGroup = prefDoc.getElementById("siteDataGroup");
|
||||
is_element_visible(siteDataGroup, "Should open to the siteDataGroup section in about:preferences");
|
||||
await BrowserTestUtils.removeTab(aboutPrefTab);
|
||||
await BrowserTestUtils.removeTab(tab);
|
||||
});
|
||||
|
||||
// Test not displaying the 2nd notification if one is already being displayed
|
||||
|
@ -11,7 +11,7 @@ add_task(async function clearURLBarAfterParentProcessURL() {
|
||||
let tab = await new Promise(resolve => {
|
||||
gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, "about:preferences");
|
||||
let newTabBrowser = gBrowser.getBrowserForTab(gBrowser.selectedTab);
|
||||
newTabBrowser.addEventListener("Initialized", function() {
|
||||
newTabBrowser.addEventListener("Initialized", async function() {
|
||||
resolve(gBrowser.selectedTab);
|
||||
}, {capture: true, once: true});
|
||||
});
|
||||
@ -30,7 +30,7 @@ add_task(async function clearURLBarAfterParentProcessURLInExistingTab() {
|
||||
let tab = await new Promise(resolve => {
|
||||
gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser);
|
||||
let newTabBrowser = gBrowser.getBrowserForTab(gBrowser.selectedTab);
|
||||
newTabBrowser.addEventListener("Initialized", function() {
|
||||
newTabBrowser.addEventListener("Initialized", async function() {
|
||||
resolve(gBrowser.selectedTab);
|
||||
}, {capture: true, once: true});
|
||||
newTabBrowser.loadURI("about:preferences");
|
||||
|
@ -736,17 +736,6 @@ function openPreferences(paneID, extraArgs) {
|
||||
} else {
|
||||
histogram.add("other");
|
||||
}
|
||||
function switchToAdvancedSubPane(doc) {
|
||||
if (extraArgs && extraArgs.advancedTab) {
|
||||
// After the Preferences reorg works in Bug 1335907, no more advancedPrefs element.
|
||||
// The old Preference is pref-off behind `browser.preferences.useOldOrganization` on Nightly.
|
||||
// During the transition between the old and new Preferences, should do checking before proceeding.
|
||||
let advancedPaneTabs = doc.getElementById("advancedPrefs");
|
||||
if (advancedPaneTabs) {
|
||||
advancedPaneTabs.selectedTab = doc.getElementById(extraArgs.advancedTab);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// This function is duplicated from preferences.js.
|
||||
function internalPrefCategoryNameToFriendlyName(aName) {
|
||||
@ -766,21 +755,21 @@ function openPreferences(paneID, extraArgs) {
|
||||
}
|
||||
}
|
||||
let preferencesURL = "about:preferences" + (params ? "?" + params : "") +
|
||||
(friendlyCategoryName ? "#" + friendlyCategoryName : "");
|
||||
(friendlyCategoryName ? "#" + friendlyCategoryName : "");
|
||||
let newLoad = true;
|
||||
let browser = null;
|
||||
if (!win) {
|
||||
const Cc = Components.classes;
|
||||
const Ci = Components.interfaces;
|
||||
let windowArguments = Cc["@mozilla.org/array;1"]
|
||||
.createInstance(Ci.nsIMutableArray);
|
||||
.createInstance(Ci.nsIMutableArray);
|
||||
let supportsStringPrefURL = Cc["@mozilla.org/supports-string;1"]
|
||||
.createInstance(Ci.nsISupportsString);
|
||||
.createInstance(Ci.nsISupportsString);
|
||||
supportsStringPrefURL.data = preferencesURL;
|
||||
windowArguments.appendElement(supportsStringPrefURL);
|
||||
|
||||
win = Services.ww.openWindow(null, Services.prefs.getCharPref("browser.chromeURL"),
|
||||
"_blank", "chrome,dialog=no,all", windowArguments);
|
||||
"_blank", "chrome,dialog=no,all", windowArguments);
|
||||
} else {
|
||||
let shouldReplaceFragment = friendlyCategoryName ? "whenComparingAndReplace" : "whenComparing";
|
||||
newLoad = !win.switchToTabHavingURI(preferencesURL, true, {
|
||||
@ -792,28 +781,20 @@ function openPreferences(paneID, extraArgs) {
|
||||
}
|
||||
|
||||
if (newLoad) {
|
||||
Services.obs.addObserver(function advancedPaneLoadedObs(prefWin, topic, data) {
|
||||
Services.obs.addObserver(function panesLoadedObs(prefWin, topic, data) {
|
||||
if (!browser) {
|
||||
browser = win.gBrowser.selectedBrowser;
|
||||
}
|
||||
if (prefWin != browser.contentWindow) {
|
||||
return;
|
||||
}
|
||||
Services.obs.removeObserver(advancedPaneLoadedObs, "advanced-pane-loaded");
|
||||
switchToAdvancedSubPane(browser.contentDocument);
|
||||
}, "advanced-pane-loaded");
|
||||
} else {
|
||||
if (paneID) {
|
||||
browser.contentWindow.gotoPref(paneID);
|
||||
}
|
||||
switchToAdvancedSubPane(browser.contentDocument);
|
||||
Services.obs.removeObserver(panesLoadedObs, "sync-pane-loaded");
|
||||
}, "sync-pane-loaded");
|
||||
} else if (paneID) {
|
||||
browser.contentWindow.gotoPref(paneID);
|
||||
}
|
||||
}
|
||||
|
||||
function openAdvancedPreferences(tabID, origin) {
|
||||
openPreferences("paneAdvanced", { "advancedTab": tabID, origin });
|
||||
}
|
||||
|
||||
/**
|
||||
* Opens the troubleshooting information (about:support) page for this version
|
||||
* of the application.
|
||||
|
@ -21,7 +21,6 @@ namespace browser {
|
||||
|
||||
NS_IMPL_ISUPPORTS(AboutRedirector, nsIAboutModule)
|
||||
|
||||
bool AboutRedirector::sUseOldPreferences = false;
|
||||
bool AboutRedirector::sActivityStreamEnabled = false;
|
||||
bool AboutRedirector::sActivityStreamAboutHomeEnabled = false;
|
||||
|
||||
@ -150,12 +149,6 @@ AboutRedirector::NewChannel(nsIURI* aURI,
|
||||
nsCOMPtr<nsIIOService> ioService = do_GetIOService(&rv);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
static bool sPrefCacheInited = false;
|
||||
if (!sPrefCacheInited) {
|
||||
Preferences::AddBoolVarCache(&sUseOldPreferences,
|
||||
"browser.preferences.useOldOrganization");
|
||||
sPrefCacheInited = true;
|
||||
}
|
||||
LoadActivityStreamPrefs();
|
||||
|
||||
for (auto & redir : kRedirMap) {
|
||||
@ -170,8 +163,6 @@ AboutRedirector::NewChannel(nsIURI* aURI,
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
rv = aboutNewTabService->GetDefaultURL(url);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
} else if (path.EqualsLiteral("preferences") && !sUseOldPreferences) {
|
||||
url.AssignASCII("chrome://browser/content/preferences/in-content-new/preferences.xul");
|
||||
}
|
||||
// fall back to the specified url in the map
|
||||
if (url.IsEmpty()) {
|
||||
|
@ -26,7 +26,6 @@ protected:
|
||||
virtual ~AboutRedirector() {}
|
||||
|
||||
private:
|
||||
static bool sUseOldPreferences;
|
||||
static bool sActivityStreamEnabled;
|
||||
static bool sActivityStreamAboutHomeEnabled;
|
||||
|
||||
|
@ -44,12 +44,13 @@ function waitForPageLoad(aTab) {
|
||||
reject("Page didn't load within " + 20000 + "ms");
|
||||
}, 20000);
|
||||
|
||||
function onTabLoad(event) {
|
||||
async function onTabLoad(event) {
|
||||
clearTimeout(timeoutId);
|
||||
aTab.linkedBrowser.removeEventListener("load", onTabLoad, true);
|
||||
info("Tab event received: load");
|
||||
resolve();
|
||||
}
|
||||
}
|
||||
|
||||
aTab.linkedBrowser.addEventListener("load", onTabLoad, true, true);
|
||||
});
|
||||
}
|
||||
|
@ -92,7 +92,7 @@ async function openPrefsFromMenuPanel(expectedPanelId, entryPoint) {
|
||||
setupButton.click();
|
||||
|
||||
await new Promise(resolve => {
|
||||
let handler = (e) => {
|
||||
let handler = async(e) => {
|
||||
if (e.originalTarget != gBrowser.selectedBrowser.contentDocument ||
|
||||
e.target.location.href == "about:blank") {
|
||||
info("Skipping spurious 'load' event for " + e.target.location.href);
|
||||
|
@ -829,7 +829,7 @@ FeedWriter.prototype = {
|
||||
case "FeedWriter:PreferenceUpdated":
|
||||
// This is called when browser-feeds.js spots a pref change
|
||||
// This will happen when
|
||||
// - about:preferences#applications changes
|
||||
// - about:preferences#general changes
|
||||
// - another feed reader page changes the preference
|
||||
// - when this page itself changes the select and there isn't a redirect
|
||||
// bookmarks and launching an external app means the page stays open after subscribe
|
||||
|
@ -301,11 +301,7 @@ BrowserGlue.prototype = {
|
||||
observe: function BG_observe(subject, topic, data) {
|
||||
switch (topic) {
|
||||
case "notifications-open-settings":
|
||||
if (Services.prefs.getBoolPref("browser.preferences.useOldOrganization")) {
|
||||
this._openPreferences("content", { origin: "notifOpenSettings" });
|
||||
} else {
|
||||
this._openPreferences("privacy", { origin: "notifOpenSettings" });
|
||||
}
|
||||
this._openPreferences("privacy", { origin: "notifOpenSettings" });
|
||||
break;
|
||||
case "prefservice:after-app-defaults":
|
||||
this._onAppDefaults();
|
||||
|
@ -2,7 +2,7 @@
|
||||
// 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/.
|
||||
|
||||
/* import-globals-from in-content/applications.js */
|
||||
/* import-globals-from in-content/main.js */
|
||||
|
||||
var Cc = Components.classes;
|
||||
var Ci = Components.interfaces;
|
||||
@ -12,19 +12,9 @@ var gAppManagerDialog = {
|
||||
|
||||
init: function appManager_init() {
|
||||
this.handlerInfo = window.arguments[0];
|
||||
// The applicationManager will be used
|
||||
// in in-content's gApplicationsPane and in-content-new's gMainPane.
|
||||
// Remove this once we use the in-content-new preferences page.
|
||||
var pane;
|
||||
if (Services.prefs.getBoolPref("browser.preferences.useOldOrganization")) {
|
||||
Services.scriptloader.loadSubScript("chrome://browser/content/preferences/in-content/applications.js",
|
||||
window);
|
||||
pane = gApplicationsPane;
|
||||
} else {
|
||||
Services.scriptloader.loadSubScript("chrome://browser/content/preferences/in-content-new/main.js",
|
||||
window);
|
||||
pane = gMainPane;
|
||||
}
|
||||
Services.scriptloader.loadSubScript("chrome://browser/content/preferences/in-content/main.js",
|
||||
window);
|
||||
var pane = gMainPane;
|
||||
var bundle = document.getElementById("appManagerBundle");
|
||||
var contentText;
|
||||
if (this.handlerInfo.type == TYPE_MAYBE_FEED)
|
||||
|
@ -3,7 +3,7 @@
|
||||
<!-- 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/. -->
|
||||
<!-- import-globals-from in-content/applications.js -->
|
||||
<!-- import-globals-from in-content/main.js -->
|
||||
|
||||
<!DOCTYPE overlay [
|
||||
<!ENTITY % brandDTD SYSTEM "chrome://branding/locale/brand.dtd">
|
||||
@ -56,9 +56,7 @@
|
||||
<xul:hbox flex="1">
|
||||
<xul:menulist class="actionsMenu" flex="1" crop="end" selectedIndex="1"
|
||||
xbl:inherits="tooltiptext=actionDescription"
|
||||
oncommand="Services.prefs.getBoolPref('browser.preferences.useOldOrganization') ?
|
||||
gApplicationsPane.onSelectAction(event.originalTarget) :
|
||||
gMainPane.onSelectAction(event.originalTarget)">
|
||||
oncommand="gMainPane.onSelectAction(event.originalTarget)">
|
||||
<xul:menupopup/>
|
||||
</xul:menulist>
|
||||
</xul:hbox>
|
||||
@ -67,11 +65,7 @@
|
||||
|
||||
<implementation>
|
||||
<constructor>
|
||||
if (Services.prefs.getBoolPref("browser.preferences.useOldOrganization")) {
|
||||
gApplicationsPane.rebuildActionsMenu();
|
||||
} else {
|
||||
gMainPane.rebuildActionsMenu();
|
||||
}
|
||||
gMainPane.rebuildActionsMenu();
|
||||
</constructor>
|
||||
</implementation>
|
||||
|
||||
|
@ -1,99 +0,0 @@
|
||||
/* 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/. */
|
||||
|
||||
/* import-globals-from preferences.js */
|
||||
|
||||
Components.utils.import("resource://gre/modules/AppConstants.jsm");
|
||||
Components.utils.import("resource://gre/modules/ContextualIdentityService.jsm");
|
||||
|
||||
const containersBundle = Services.strings.createBundle("chrome://browser/locale/preferences/containers.properties");
|
||||
|
||||
const defaultContainerIcon = "fingerprint";
|
||||
const defaultContainerColor = "blue";
|
||||
|
||||
let gContainersPane = {
|
||||
|
||||
init() {
|
||||
this._list = document.getElementById("containersView");
|
||||
|
||||
document.getElementById("backContainersLink").addEventListener("click", function() {
|
||||
gotoPref("general");
|
||||
});
|
||||
|
||||
this._rebuildView();
|
||||
},
|
||||
|
||||
_rebuildView() {
|
||||
const containers = ContextualIdentityService.getPublicIdentities();
|
||||
while (this._list.firstChild) {
|
||||
this._list.firstChild.remove();
|
||||
}
|
||||
for (let container of containers) {
|
||||
let item = document.createElement("richlistitem");
|
||||
item.setAttribute("containerName", ContextualIdentityService.getUserContextLabel(container.userContextId));
|
||||
item.setAttribute("containerIcon", container.icon);
|
||||
item.setAttribute("containerColor", container.color);
|
||||
item.setAttribute("userContextId", container.userContextId);
|
||||
|
||||
this._list.appendChild(item);
|
||||
}
|
||||
},
|
||||
|
||||
async onRemoveClick(button) {
|
||||
let userContextId = parseInt(button.getAttribute("value"), 10);
|
||||
|
||||
let count = ContextualIdentityService.countContainerTabs(userContextId);
|
||||
if (count > 0) {
|
||||
let bundlePreferences = document.getElementById("bundlePreferences");
|
||||
|
||||
let title = bundlePreferences.getString("removeContainerAlertTitle");
|
||||
let message = PluralForm.get(count, bundlePreferences.getString("removeContainerMsg"))
|
||||
.replace("#S", count)
|
||||
let okButton = bundlePreferences.getString("removeContainerOkButton");
|
||||
let cancelButton = bundlePreferences.getString("removeContainerButton2");
|
||||
|
||||
let buttonFlags = (Ci.nsIPrompt.BUTTON_TITLE_IS_STRING * Ci.nsIPrompt.BUTTON_POS_0) +
|
||||
(Ci.nsIPrompt.BUTTON_TITLE_IS_STRING * Ci.nsIPrompt.BUTTON_POS_1);
|
||||
|
||||
let rv = Services.prompt.confirmEx(window, title, message, buttonFlags,
|
||||
okButton, cancelButton, null, null, {});
|
||||
if (rv != 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
await ContextualIdentityService.closeContainerTabs(userContextId);
|
||||
}
|
||||
|
||||
ContextualIdentityService.remove(userContextId);
|
||||
this._rebuildView();
|
||||
},
|
||||
|
||||
onPreferenceClick(button) {
|
||||
this.openPreferenceDialog(button.getAttribute("value"));
|
||||
},
|
||||
|
||||
onAddButtonClick(button) {
|
||||
this.openPreferenceDialog(null);
|
||||
},
|
||||
|
||||
openPreferenceDialog(userContextId) {
|
||||
let identity = {
|
||||
name: "",
|
||||
icon: defaultContainerIcon,
|
||||
color: defaultContainerColor
|
||||
};
|
||||
let title;
|
||||
if (userContextId) {
|
||||
identity = ContextualIdentityService.getPublicIdentityFromId(userContextId);
|
||||
// This is required to get the translation string from defaults
|
||||
identity.name = ContextualIdentityService.getUserContextLabel(identity.userContextId);
|
||||
title = containersBundle.formatStringFromName("containers.updateContainerTitle", [identity.name], 1);
|
||||
}
|
||||
|
||||
const params = { userContextId, identity, windowTitle: title };
|
||||
gSubDialog.open("chrome://browser/content/preferences/containers.xul",
|
||||
null, params);
|
||||
}
|
||||
|
||||
};
|
@ -1,45 +0,0 @@
|
||||
# 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/.
|
||||
|
||||
<!-- Containers panel -->
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content-new/containers.js"/>
|
||||
|
||||
<preferences id="containerPreferences" hidden="true" data-category="paneContainer">
|
||||
<!-- Containers -->
|
||||
<preference id="privacy.userContext.enabled"
|
||||
name="privacy.userContext.enabled"
|
||||
type="bool"/>
|
||||
|
||||
</preferences>
|
||||
|
||||
<hbox hidden="true"
|
||||
class="container-header-links"
|
||||
data-category="paneContainers">
|
||||
<label class="text-link" id="backContainersLink">&backLink2.label;</label>
|
||||
</hbox>
|
||||
|
||||
<hbox id="header-containers"
|
||||
class="header"
|
||||
hidden="true"
|
||||
data-category="paneContainers">
|
||||
<label class="header-name" flex="1">&paneContainers.title;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Containers -->
|
||||
<groupbox id="browserContainersGroupPane" data-category="paneContainers" hidden="true"
|
||||
data-hidden-from-search="true" data-subpanel="true">
|
||||
<vbox id="browserContainersbox">
|
||||
|
||||
<richlistbox id="containersView" orient="vertical" persist="lastSelectedType"
|
||||
flex="1">
|
||||
</richlistbox>
|
||||
</vbox>
|
||||
<vbox>
|
||||
<hbox flex="1">
|
||||
<button onclick="gContainersPane.onAddButtonClick();" accesskey="&addButton.accesskey;" label="&addButton.label;"/>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</groupbox>
|
@ -1,15 +0,0 @@
|
||||
# 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/.
|
||||
|
||||
browser.jar:
|
||||
content/browser/preferences/in-content-new/preferences.js
|
||||
* content/browser/preferences/in-content-new/preferences.xul
|
||||
content/browser/preferences/in-content-new/subdialogs.js
|
||||
|
||||
content/browser/preferences/in-content-new/main.js
|
||||
content/browser/preferences/in-content-new/search.js
|
||||
content/browser/preferences/in-content-new/privacy.js
|
||||
content/browser/preferences/in-content-new/containers.js
|
||||
content/browser/preferences/in-content-new/sync.js
|
||||
content/browser/preferences/in-content-new/findInPage.js
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -1,13 +0,0 @@
|
||||
# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
|
||||
# vim: set filetype=python:
|
||||
# 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/.
|
||||
|
||||
for var in ('MOZ_APP_NAME', 'MOZ_MACBUNDLE_NAME'):
|
||||
DEFINES[var] = CONFIG[var]
|
||||
|
||||
if CONFIG['MOZ_WIDGET_TOOLKIT'] in ('windows', 'gtk2', 'gtk3', 'cocoa'):
|
||||
DEFINES['HAVE_SHELL_SERVICE'] = 1
|
||||
|
||||
JAR_MANIFESTS += ['jar.mn']
|
@ -1,363 +0,0 @@
|
||||
/* - 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/. */
|
||||
|
||||
// Import globals from the files imported by the .xul files.
|
||||
/* import-globals-from subdialogs.js */
|
||||
/* import-globals-from main.js */
|
||||
/* import-globals-from search.js */
|
||||
/* import-globals-from containers.js */
|
||||
/* import-globals-from privacy.js */
|
||||
/* import-globals-from sync.js */
|
||||
/* import-globals-from findInPage.js */
|
||||
/* import-globals-from ../../../base/content/utilityOverlay.js */
|
||||
|
||||
"use strict";
|
||||
|
||||
var Cc = Components.classes;
|
||||
var Ci = Components.interfaces;
|
||||
var Cu = Components.utils;
|
||||
var Cr = Components.results;
|
||||
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/AppConstants.jsm");
|
||||
|
||||
var gLastHash = "";
|
||||
|
||||
var gCategoryInits = new Map();
|
||||
function init_category_if_required(category) {
|
||||
let categoryInfo = gCategoryInits.get(category);
|
||||
if (!categoryInfo) {
|
||||
throw "Unknown in-content prefs category! Can't init " + category;
|
||||
}
|
||||
if (categoryInfo.inited) {
|
||||
return;
|
||||
}
|
||||
categoryInfo.init();
|
||||
}
|
||||
|
||||
function register_module(categoryName, categoryObject) {
|
||||
gCategoryInits.set(categoryName, {
|
||||
inited: false,
|
||||
init() {
|
||||
categoryObject.init();
|
||||
this.inited = true;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
document.addEventListener("DOMContentLoaded", init_all, {once: true});
|
||||
|
||||
function init_all() {
|
||||
document.documentElement.instantApply = true;
|
||||
|
||||
gSubDialog.init();
|
||||
register_module("paneGeneral", gMainPane);
|
||||
register_module("paneSearch", gSearchPane);
|
||||
register_module("panePrivacy", gPrivacyPane);
|
||||
register_module("paneContainers", gContainersPane);
|
||||
register_module("paneSync", gSyncPane);
|
||||
register_module("paneSearchResults", gSearchResultsPane);
|
||||
gSearchResultsPane.init();
|
||||
|
||||
let categories = document.getElementById("categories");
|
||||
categories.addEventListener("select", event => gotoPref(event.target.value));
|
||||
|
||||
document.documentElement.addEventListener("keydown", function(event) {
|
||||
if (event.keyCode == KeyEvent.DOM_VK_TAB) {
|
||||
categories.setAttribute("keyboard-navigation", "true");
|
||||
}
|
||||
});
|
||||
categories.addEventListener("mousedown", function() {
|
||||
this.removeAttribute("keyboard-navigation");
|
||||
});
|
||||
|
||||
window.addEventListener("hashchange", onHashChange);
|
||||
gotoPref();
|
||||
|
||||
init_dynamic_padding();
|
||||
|
||||
var initFinished = new CustomEvent("Initialized", {
|
||||
"bubbles": true,
|
||||
"cancelable": true
|
||||
});
|
||||
document.dispatchEvent(initFinished);
|
||||
|
||||
let helpButton = document.querySelector(".help-button");
|
||||
let helpUrl = Services.urlFormatter.formatURLPref("app.support.baseURL") + "preferences";
|
||||
helpButton.setAttribute("href", helpUrl);
|
||||
|
||||
// Wait until initialization of all preferences are complete before
|
||||
// notifying observers that the UI is now ready.
|
||||
Services.obs.notifyObservers(window, "advanced-pane-loaded");
|
||||
}
|
||||
|
||||
// Make the space above the categories list shrink on low window heights
|
||||
function init_dynamic_padding() {
|
||||
let categories = document.getElementById("categories");
|
||||
let catPadding = Number.parseInt(getComputedStyle(categories)
|
||||
.getPropertyValue("padding-top"));
|
||||
let helpButton = document.querySelector(".help-button");
|
||||
let helpButtonCS = getComputedStyle(helpButton);
|
||||
let helpHeight = Number.parseInt(helpButtonCS.height);
|
||||
let helpBottom = Number.parseInt(helpButtonCS.bottom);
|
||||
// Reduce the padding to account for less space, but due
|
||||
// to bug 1357841, the status panel will overlap the link.
|
||||
const reducedHelpButtonBottomFactor = .75;
|
||||
let reducedHelpButtonBottom = helpBottom * reducedHelpButtonBottomFactor;
|
||||
let fullHelpHeight = helpHeight + reducedHelpButtonBottom;
|
||||
let fullHeight = categories.lastElementChild.getBoundingClientRect().bottom +
|
||||
fullHelpHeight;
|
||||
let mediaRule = `
|
||||
@media (max-height: ${fullHeight}px) {
|
||||
#categories {
|
||||
padding-top: calc(100vh - ${fullHeight - catPadding}px);
|
||||
padding-bottom: ${fullHelpHeight}px;
|
||||
}
|
||||
.help-button {
|
||||
bottom: ${reducedHelpButtonBottom / 2}px;
|
||||
}
|
||||
}
|
||||
`;
|
||||
let mediaStyle = document.createElementNS("http://www.w3.org/1999/xhtml", "html:style");
|
||||
mediaStyle.setAttribute("type", "text/css");
|
||||
mediaStyle.appendChild(document.createCDATASection(mediaRule));
|
||||
document.documentElement.appendChild(mediaStyle);
|
||||
}
|
||||
|
||||
function telemetryBucketForCategory(category) {
|
||||
category = category.toLowerCase();
|
||||
switch (category) {
|
||||
case "containers":
|
||||
case "general":
|
||||
case "privacy":
|
||||
case "search":
|
||||
case "sync":
|
||||
case "searchresults":
|
||||
return category;
|
||||
default:
|
||||
return "unknown";
|
||||
}
|
||||
}
|
||||
|
||||
function onHashChange() {
|
||||
gotoPref();
|
||||
}
|
||||
|
||||
function gotoPref(aCategory) {
|
||||
let categories = document.getElementById("categories");
|
||||
const kDefaultCategoryInternalName = "paneGeneral";
|
||||
const kDefaultCategory = "general";
|
||||
let hash = document.location.hash;
|
||||
|
||||
let category = aCategory || hash.substr(1) || kDefaultCategoryInternalName;
|
||||
let breakIndex = category.indexOf("-");
|
||||
// Subcategories allow for selecting smaller sections of the preferences
|
||||
// until proper search support is enabled (bug 1353954).
|
||||
let subcategory = breakIndex != -1 && category.substring(breakIndex + 1);
|
||||
if (subcategory) {
|
||||
category = category.substring(0, breakIndex);
|
||||
}
|
||||
category = friendlyPrefCategoryNameToInternalName(category);
|
||||
if (category != "paneSearchResults") {
|
||||
gSearchResultsPane.searchInput.value = "";
|
||||
gSearchResultsPane.getFindSelection(window).removeAllRanges();
|
||||
gSearchResultsPane.removeAllSearchTooltips();
|
||||
gSearchResultsPane.removeAllSearchMenuitemIndicators();
|
||||
} else if (!gSearchResultsPane.searchInput.value) {
|
||||
// Something tried to send us to the search results pane without
|
||||
// a query string. Default to the General pane instead.
|
||||
category = kDefaultCategoryInternalName;
|
||||
document.location.hash = kDefaultCategory;
|
||||
gSearchResultsPane.query = null;
|
||||
}
|
||||
|
||||
// Updating the hash (below) or changing the selected category
|
||||
// will re-enter gotoPref.
|
||||
if (gLastHash == category && !subcategory)
|
||||
return;
|
||||
|
||||
let item;
|
||||
if (category != "paneSearchResults") {
|
||||
item = categories.querySelector(".category[value=" + category + "]");
|
||||
if (!item) {
|
||||
category = kDefaultCategoryInternalName;
|
||||
item = categories.querySelector(".category[value=" + category + "]");
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
init_category_if_required(category);
|
||||
} catch (ex) {
|
||||
Cu.reportError("Error initializing preference category " + category + ": " + ex);
|
||||
throw ex;
|
||||
}
|
||||
|
||||
let friendlyName = internalPrefCategoryNameToFriendlyName(category);
|
||||
if (gLastHash || category != kDefaultCategoryInternalName || subcategory) {
|
||||
document.location.hash = friendlyName;
|
||||
}
|
||||
// Need to set the gLastHash before setting categories.selectedItem since
|
||||
// the categories 'select' event will re-enter the gotoPref codepath.
|
||||
gLastHash = category;
|
||||
if (item) {
|
||||
categories.selectedItem = item;
|
||||
} else {
|
||||
categories.clearSelection();
|
||||
}
|
||||
window.history.replaceState(category, document.title);
|
||||
search(category, "data-category", subcategory, "data-subcategory");
|
||||
|
||||
let mainContent = document.querySelector(".main-content");
|
||||
mainContent.scrollTop = 0;
|
||||
|
||||
Services.telemetry
|
||||
.getHistogramById("FX_PREFERENCES_CATEGORY_OPENED_V2")
|
||||
.add(telemetryBucketForCategory(friendlyName));
|
||||
}
|
||||
|
||||
function search(aQuery, aAttribute, aSubquery, aSubAttribute) {
|
||||
let mainPrefPane = document.getElementById("mainPrefPane");
|
||||
let elements = mainPrefPane.children;
|
||||
for (let element of elements) {
|
||||
// If the "data-hidden-from-search" is "true", the
|
||||
// element will not get considered during search. This
|
||||
// should only be used when an element is still under
|
||||
// development and should not be shown for any reason.
|
||||
if (element.getAttribute("data-hidden-from-search") != "true" ||
|
||||
element.getAttribute("data-subpanel") == "true") {
|
||||
let attributeValue = element.getAttribute(aAttribute);
|
||||
if (attributeValue == aQuery) {
|
||||
if (!element.classList.contains("header") &&
|
||||
element.localName !== "preferences" &&
|
||||
aSubquery && aSubAttribute) {
|
||||
let subAttributeValue = element.getAttribute(aSubAttribute);
|
||||
element.hidden = subAttributeValue != aSubquery;
|
||||
} else {
|
||||
element.hidden = false;
|
||||
}
|
||||
} else {
|
||||
element.hidden = true;
|
||||
}
|
||||
}
|
||||
element.classList.remove("visually-hidden");
|
||||
}
|
||||
|
||||
let keysets = mainPrefPane.getElementsByTagName("keyset");
|
||||
for (let element of keysets) {
|
||||
let attributeValue = element.getAttribute(aAttribute);
|
||||
if (attributeValue == aQuery)
|
||||
element.removeAttribute("disabled");
|
||||
else
|
||||
element.setAttribute("disabled", true);
|
||||
}
|
||||
}
|
||||
|
||||
function helpButtonCommand() {
|
||||
let pane = history.state;
|
||||
let categories = document.getElementById("categories");
|
||||
let helpTopic = categories.querySelector(".category[value=" + pane + "]")
|
||||
.getAttribute("helpTopic");
|
||||
openHelpLink(helpTopic);
|
||||
}
|
||||
|
||||
function friendlyPrefCategoryNameToInternalName(aName) {
|
||||
if (aName.startsWith("pane"))
|
||||
return aName;
|
||||
return "pane" + aName.substring(0, 1).toUpperCase() + aName.substr(1);
|
||||
}
|
||||
|
||||
// This function is duplicated inside of utilityOverlay.js's openPreferences.
|
||||
function internalPrefCategoryNameToFriendlyName(aName) {
|
||||
return (aName || "").replace(/^pane./, function(toReplace) { return toReplace[4].toLowerCase(); });
|
||||
}
|
||||
|
||||
// Put up a confirm dialog with "ok to restart", "revert without restarting"
|
||||
// and "restart later" buttons and returns the index of the button chosen.
|
||||
// We can choose not to display the "restart later", or "revert" buttons,
|
||||
// altough the later still lets us revert by using the escape key.
|
||||
//
|
||||
// The constants are useful to interpret the return value of the function.
|
||||
const CONFIRM_RESTART_PROMPT_RESTART_NOW = 0;
|
||||
const CONFIRM_RESTART_PROMPT_CANCEL = 1;
|
||||
const CONFIRM_RESTART_PROMPT_RESTART_LATER = 2;
|
||||
function confirmRestartPrompt(aRestartToEnable, aDefaultButtonIndex,
|
||||
aWantRevertAsCancelButton,
|
||||
aWantRestartLaterButton) {
|
||||
let brandName = document.getElementById("bundleBrand").getString("brandShortName");
|
||||
let bundle = document.getElementById("bundlePreferences");
|
||||
let msg = bundle.getFormattedString(aRestartToEnable ?
|
||||
"featureEnableRequiresRestart" :
|
||||
"featureDisableRequiresRestart",
|
||||
[brandName]);
|
||||
let title = bundle.getFormattedString("shouldRestartTitle", [brandName]);
|
||||
let prompts = Cc["@mozilla.org/embedcomp/prompt-service;1"].getService(Ci.nsIPromptService);
|
||||
|
||||
// Set up the first (index 0) button:
|
||||
let button0Text = bundle.getFormattedString("okToRestartButton", [brandName]);
|
||||
let buttonFlags = (Services.prompt.BUTTON_POS_0 *
|
||||
Services.prompt.BUTTON_TITLE_IS_STRING);
|
||||
|
||||
|
||||
// Set up the second (index 1) button:
|
||||
let button1Text = null;
|
||||
if (aWantRevertAsCancelButton) {
|
||||
button1Text = bundle.getString("revertNoRestartButton");
|
||||
buttonFlags += (Services.prompt.BUTTON_POS_1 *
|
||||
Services.prompt.BUTTON_TITLE_IS_STRING);
|
||||
} else {
|
||||
buttonFlags += (Services.prompt.BUTTON_POS_1 *
|
||||
Services.prompt.BUTTON_TITLE_CANCEL);
|
||||
}
|
||||
|
||||
// Set up the third (index 2) button:
|
||||
let button2Text = null;
|
||||
if (aWantRestartLaterButton) {
|
||||
button2Text = bundle.getString("restartLater");
|
||||
buttonFlags += (Services.prompt.BUTTON_POS_2 *
|
||||
Services.prompt.BUTTON_TITLE_IS_STRING);
|
||||
}
|
||||
|
||||
switch (aDefaultButtonIndex) {
|
||||
case 0:
|
||||
buttonFlags += Services.prompt.BUTTON_POS_0_DEFAULT;
|
||||
break;
|
||||
case 1:
|
||||
buttonFlags += Services.prompt.BUTTON_POS_1_DEFAULT;
|
||||
break;
|
||||
case 2:
|
||||
buttonFlags += Services.prompt.BUTTON_POS_2_DEFAULT;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
let buttonIndex = prompts.confirmEx(window, title, msg, buttonFlags,
|
||||
button0Text, button1Text, button2Text,
|
||||
null, {});
|
||||
|
||||
// If we have the second confirmation dialog for restart, see if the user
|
||||
// cancels out at that point.
|
||||
if (buttonIndex == CONFIRM_RESTART_PROMPT_RESTART_NOW) {
|
||||
let cancelQuit = Cc["@mozilla.org/supports-PRBool;1"]
|
||||
.createInstance(Ci.nsISupportsPRBool);
|
||||
Services.obs.notifyObservers(cancelQuit, "quit-application-requested",
|
||||
"restart");
|
||||
if (cancelQuit.data) {
|
||||
buttonIndex = CONFIRM_RESTART_PROMPT_CANCEL;
|
||||
}
|
||||
}
|
||||
return buttonIndex;
|
||||
}
|
||||
|
||||
// This function is used to append search keywords found
|
||||
// in the related subdialog to the button that will activate the subdialog.
|
||||
function appendSearchKeywords(aId, keywords) {
|
||||
let element = document.getElementById(aId);
|
||||
let searchKeywords = element.getAttribute("searchkeywords");
|
||||
if (searchKeywords) {
|
||||
keywords.push(searchKeywords);
|
||||
}
|
||||
element.setAttribute("searchkeywords", keywords.join(" "));
|
||||
}
|
@ -1,215 +0,0 @@
|
||||
<?xml version="1.0"?>
|
||||
<!-- 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/. -->
|
||||
|
||||
<?xml-stylesheet href="chrome://global/skin/global.css"?>
|
||||
|
||||
<?xml-stylesheet href="chrome://browser/skin/preferences/preferences.css"?>
|
||||
<?xml-stylesheet href="chrome://global/skin/in-content/common.css"?>
|
||||
<?xml-stylesheet
|
||||
href="chrome://browser/skin/preferences/in-content-new/preferences.css"?>
|
||||
<?xml-stylesheet
|
||||
href="chrome://browser/content/preferences/handlers.css"?>
|
||||
<?xml-stylesheet href="chrome://browser/skin/preferences/applications.css"?>
|
||||
<?xml-stylesheet href="chrome://browser/skin/preferences/in-content-new/search.css"?>
|
||||
<?xml-stylesheet href="chrome://browser/skin/preferences/in-content-new/containers.css"?>
|
||||
<?xml-stylesheet href="chrome://browser/skin/preferences/in-content-new/privacy.css"?>
|
||||
|
||||
<!DOCTYPE page [
|
||||
<!ENTITY % brandDTD SYSTEM "chrome://branding/locale/brand.dtd">
|
||||
<!ENTITY % globalPreferencesDTD SYSTEM "chrome://global/locale/preferences.dtd">
|
||||
<!ENTITY % preferencesDTD SYSTEM
|
||||
"chrome://browser/locale/preferences/preferences.dtd">
|
||||
<!ENTITY % selectBookmarkDTD SYSTEM
|
||||
"chrome://browser/locale/preferences/selectBookmark.dtd">
|
||||
<!ENTITY % languagesDTD SYSTEM "chrome://browser/locale/preferences/languages.dtd">
|
||||
<!ENTITY % fontDTD SYSTEM "chrome://browser/locale/preferences/fonts.dtd">
|
||||
<!ENTITY % colorsDTD SYSTEM "chrome://browser/locale/preferences/colors.dtd">
|
||||
<!ENTITY % permissionsDTD SYSTEM "chrome://browser/locale/preferences/permissions.dtd">
|
||||
<!ENTITY % passwordManagerDTD SYSTEM "chrome://passwordmgr/locale/passwordManager.dtd">
|
||||
<!ENTITY % historyDTD SYSTEM "chrome://mozapps/locale/update/history.dtd">
|
||||
<!ENTITY % certManagerDTD SYSTEM "chrome://pippki/locale/certManager.dtd">
|
||||
<!ENTITY % deviceManangerDTD SYSTEM "chrome://pippki/locale/deviceManager.dtd">
|
||||
<!ENTITY % connectionDTD SYSTEM "chrome://browser/locale/preferences/connection.dtd">
|
||||
<!ENTITY % siteDataSettingsDTD SYSTEM
|
||||
"chrome://browser/locale/preferences/siteDataSettings.dtd" >
|
||||
<!ENTITY % privacyDTD SYSTEM "chrome://browser/locale/preferences/privacy.dtd">
|
||||
<!ENTITY % tabsDTD SYSTEM "chrome://browser/locale/preferences/tabs.dtd">
|
||||
<!ENTITY % searchDTD SYSTEM "chrome://browser/locale/preferences/search.dtd">
|
||||
<!ENTITY % syncBrandDTD SYSTEM "chrome://browser/locale/syncBrand.dtd">
|
||||
<!ENTITY % syncDTD SYSTEM "chrome://browser/locale/preferences/sync.dtd">
|
||||
<!ENTITY % securityDTD SYSTEM
|
||||
"chrome://browser/locale/preferences/security.dtd">
|
||||
<!ENTITY % containersDTD SYSTEM
|
||||
"chrome://browser/locale/preferences/containers.dtd">
|
||||
<!ENTITY % sanitizeDTD SYSTEM "chrome://browser/locale/sanitize.dtd">
|
||||
<!ENTITY % mainDTD SYSTEM "chrome://browser/locale/preferences/main.dtd">
|
||||
<!ENTITY % aboutHomeDTD SYSTEM "chrome://browser/locale/aboutHome.dtd">
|
||||
<!ENTITY % contentDTD SYSTEM "chrome://browser/locale/preferences/content.dtd">
|
||||
<!ENTITY % applicationsDTD SYSTEM
|
||||
"chrome://browser/locale/preferences/applications.dtd">
|
||||
<!ENTITY % advancedDTD SYSTEM
|
||||
"chrome://browser/locale/preferences/advanced.dtd">
|
||||
<!ENTITY % aboutDialogDTD SYSTEM "chrome://browser/locale/aboutDialog.dtd" >
|
||||
%aboutDialogDTD;
|
||||
%brandDTD;
|
||||
%globalPreferencesDTD;
|
||||
%preferencesDTD;
|
||||
%selectBookmarkDTD;
|
||||
%languagesDTD;
|
||||
%fontDTD;
|
||||
%colorsDTD;
|
||||
%permissionsDTD;
|
||||
%passwordManagerDTD;
|
||||
%historyDTD;
|
||||
%certManagerDTD;
|
||||
%deviceManangerDTD;
|
||||
%connectionDTD;
|
||||
%siteDataSettingsDTD;
|
||||
%privacyDTD;
|
||||
%tabsDTD;
|
||||
%searchDTD;
|
||||
%syncBrandDTD;
|
||||
%syncDTD;
|
||||
%securityDTD;
|
||||
%containersDTD;
|
||||
%sanitizeDTD;
|
||||
%mainDTD;
|
||||
%aboutHomeDTD;
|
||||
%contentDTD;
|
||||
%applicationsDTD;
|
||||
%advancedDTD;
|
||||
]>
|
||||
|
||||
#ifdef XP_WIN
|
||||
#define USE_WIN_TITLE_STYLE
|
||||
#endif
|
||||
|
||||
<page xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
|
||||
xmlns:html="http://www.w3.org/1999/xhtml"
|
||||
disablefastfind="true"
|
||||
#ifdef USE_WIN_TITLE_STYLE
|
||||
title="&prefWindow.titleWin;">
|
||||
#else
|
||||
title="&prefWindow.title;">
|
||||
#endif
|
||||
|
||||
<html:link rel="shortcut icon"
|
||||
href="chrome://browser/skin/settings.svg"/>
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/utilityOverlay.js"/>
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content-new/preferences.js"/>
|
||||
<script src="chrome://browser/content/preferences/in-content-new/findInPage.js"/>
|
||||
<script src="chrome://browser/content/preferences/in-content-new/subdialogs.js"/>
|
||||
|
||||
<stringbundle id="bundleBrand"
|
||||
src="chrome://branding/locale/brand.properties"/>
|
||||
<stringbundle id="bundlePreferences"
|
||||
src="chrome://browser/locale/preferences/preferences.properties"/>
|
||||
<stringbundle id="pkiBundle"
|
||||
src="chrome://pippki/locale/pippki.properties"/>
|
||||
<stringbundle id="browserBundle"
|
||||
src="chrome://browser/locale/browser.properties"/>
|
||||
|
||||
<stringbundleset id="appManagerBundleset">
|
||||
<stringbundle id="appManagerBundle"
|
||||
src="chrome://browser/locale/preferences/applicationManager.properties"/>
|
||||
</stringbundleset>
|
||||
|
||||
<stack flex="1">
|
||||
<hbox flex="1">
|
||||
|
||||
<!-- category list -->
|
||||
<richlistbox id="categories">
|
||||
<richlistitem id="category-general"
|
||||
class="category"
|
||||
value="paneGeneral"
|
||||
helpTopic="prefs-main"
|
||||
tooltiptext="&paneGeneral.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&paneGeneral.title;</label>
|
||||
</richlistitem>
|
||||
|
||||
<richlistitem id="category-search"
|
||||
class="category"
|
||||
value="paneSearch"
|
||||
helpTopic="prefs-search"
|
||||
tooltiptext="&paneSearch.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&paneSearch.title;</label>
|
||||
</richlistitem>
|
||||
|
||||
<richlistitem id="category-containers"
|
||||
class="category"
|
||||
value="paneContainers"
|
||||
helpTopic="prefs-containers"
|
||||
hidden="true"/>
|
||||
|
||||
<richlistitem id="category-privacy"
|
||||
class="category"
|
||||
value="panePrivacy"
|
||||
helpTopic="prefs-privacy"
|
||||
tooltiptext="&panePrivacySecurity.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&panePrivacySecurity.title;</label>
|
||||
</richlistitem>
|
||||
|
||||
<richlistitem id="category-sync"
|
||||
class="category"
|
||||
value="paneSync"
|
||||
helpTopic="prefs-weave"
|
||||
tooltiptext="&paneSync1.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&paneSync1.title;</label>
|
||||
</richlistitem>
|
||||
</richlistbox>
|
||||
|
||||
<keyset>
|
||||
<key key="&focusSearch1.key;" modifiers="accel" id="focusSearch1" oncommand="gSearchResultsPane.searchInput.focus();"/>
|
||||
</keyset>
|
||||
|
||||
<html:a class="help-button" target="_blank" aria-label="&helpButton2.label;">&helpButton2.label;</html:a>
|
||||
|
||||
<vbox class="main-content" flex="1" align="start">
|
||||
<vbox class="pane-container">
|
||||
<hbox class="search-container" pack="end">
|
||||
<textbox type="search" id="searchInput" hidden="true" clickSelectsAll="true"/>
|
||||
</hbox>
|
||||
<prefpane id="mainPrefPane">
|
||||
#include searchResults.xul
|
||||
#include main.xul
|
||||
#include search.xul
|
||||
#include privacy.xul
|
||||
#include containers.xul
|
||||
#include sync.xul
|
||||
</prefpane>
|
||||
</vbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
|
||||
<stack id="dialogStack" hidden="true"/>
|
||||
<vbox id="dialogTemplate" class="dialogOverlay" align="center" pack="center" topmost="true" hidden="true">
|
||||
<groupbox class="dialogBox"
|
||||
orient="vertical"
|
||||
pack="end"
|
||||
role="dialog"
|
||||
aria-labelledby="dialogTitle">
|
||||
<caption flex="1" align="center">
|
||||
<label class="dialogTitle" flex="1"></label>
|
||||
<button class="dialogClose close-icon"
|
||||
aria-label="&preferencesCloseButton.label;"/>
|
||||
</caption>
|
||||
<browser class="dialogFrame"
|
||||
autoscroll="false"
|
||||
disablehistory="true"/>
|
||||
</groupbox>
|
||||
</vbox>
|
||||
</stack>
|
||||
</page>
|
File diff suppressed because it is too large
Load Diff
@ -1,862 +0,0 @@
|
||||
# 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/.
|
||||
|
||||
<!-- Privacy panel -->
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content-new/privacy.js"/>
|
||||
|
||||
<preferences id="privacyPreferences" hidden="true" data-category="panePrivacy">
|
||||
|
||||
<!-- Tracking -->
|
||||
<preference id="privacy.trackingprotection.enabled"
|
||||
name="privacy.trackingprotection.enabled"
|
||||
type="bool"/>
|
||||
<preference id="privacy.trackingprotection.pbmode.enabled"
|
||||
name="privacy.trackingprotection.pbmode.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<!-- XXX button prefs -->
|
||||
<preference id="pref.privacy.disable_button.cookie_exceptions"
|
||||
name="pref.privacy.disable_button.cookie_exceptions"
|
||||
type="bool"/>
|
||||
<preference id="pref.privacy.disable_button.view_cookies"
|
||||
name="pref.privacy.disable_button.view_cookies"
|
||||
type="bool"/>
|
||||
<preference id="pref.privacy.disable_button.change_blocklist"
|
||||
name="pref.privacy.disable_button.change_blocklist"
|
||||
type="bool"/>
|
||||
<preference id="pref.privacy.disable_button.tracking_protection_exceptions"
|
||||
name="pref.privacy.disable_button.tracking_protection_exceptions"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Location Bar -->
|
||||
<preference id="browser.urlbar.autocomplete.enabled"
|
||||
name="browser.urlbar.autocomplete.enabled"
|
||||
type="bool"/>
|
||||
<preference id="browser.urlbar.suggest.bookmark"
|
||||
name="browser.urlbar.suggest.bookmark"
|
||||
type="bool"/>
|
||||
<preference id="browser.urlbar.suggest.history"
|
||||
name="browser.urlbar.suggest.history"
|
||||
type="bool"/>
|
||||
<preference id="browser.urlbar.suggest.openpage"
|
||||
name="browser.urlbar.suggest.openpage"
|
||||
type="bool"/>
|
||||
|
||||
<!-- History -->
|
||||
<preference id="places.history.enabled"
|
||||
name="places.history.enabled"
|
||||
type="bool"/>
|
||||
<preference id="browser.formfill.enable"
|
||||
name="browser.formfill.enable"
|
||||
type="bool"/>
|
||||
<preference id="privacy.history.custom"
|
||||
name="privacy.history.custom"
|
||||
type="bool"/>
|
||||
<!-- Cookies -->
|
||||
<preference id="network.cookie.cookieBehavior"
|
||||
name="network.cookie.cookieBehavior"
|
||||
type="int"/>
|
||||
<preference id="network.cookie.lifetimePolicy"
|
||||
name="network.cookie.lifetimePolicy"
|
||||
type="int"/>
|
||||
<preference id="network.cookie.blockFutureCookies"
|
||||
name="network.cookie.blockFutureCookies"
|
||||
type="bool"/>
|
||||
<!-- Clear Private Data -->
|
||||
<preference id="privacy.sanitize.sanitizeOnShutdown"
|
||||
name="privacy.sanitize.sanitizeOnShutdown"
|
||||
type="bool"/>
|
||||
<preference id="privacy.sanitize.timeSpan"
|
||||
name="privacy.sanitize.timeSpan"
|
||||
type="int"/>
|
||||
<!-- Private Browsing -->
|
||||
<preference id="browser.privatebrowsing.autostart"
|
||||
name="browser.privatebrowsing.autostart"
|
||||
type="bool"/>
|
||||
<!-- Do not track -->
|
||||
<preference id="privacy.donottrackheader.enabled"
|
||||
name="privacy.donottrackheader.enabled"
|
||||
type="bool"/>
|
||||
<!-- Popups -->
|
||||
<preference id="dom.disable_open_during_load"
|
||||
name="dom.disable_open_during_load"
|
||||
type="bool"/>
|
||||
<!-- Passwords -->
|
||||
<preference id="signon.rememberSignons" name="signon.rememberSignons" type="bool"/>
|
||||
|
||||
<!-- XXX buttons -->
|
||||
<preference id="pref.privacy.disable_button.view_passwords"
|
||||
name="pref.privacy.disable_button.view_passwords"
|
||||
type="bool"/>
|
||||
<preference id="pref.privacy.disable_button.view_passwords_exceptions"
|
||||
name="pref.privacy.disable_button.view_passwords_exceptions"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Certificates tab
|
||||
* security.default_personal_cert
|
||||
- a string:
|
||||
"Select Automatically" select a certificate automatically when a site
|
||||
requests one
|
||||
"Ask Every Time" present a dialog to the user so he can select
|
||||
the certificate to use on a site which
|
||||
requests one -->
|
||||
<preference id="security.default_personal_cert"
|
||||
name="security.default_personal_cert"
|
||||
type="string"/>
|
||||
|
||||
<preference id="security.disable_button.openCertManager"
|
||||
name="security.disable_button.openCertManager"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="security.disable_button.openDeviceManager"
|
||||
name="security.disable_button.openDeviceManager"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="security.OCSP.enabled"
|
||||
name="security.OCSP.enabled"
|
||||
type="int"/>
|
||||
|
||||
<!-- Add-ons, malware, phishing -->
|
||||
<preference id="xpinstall.whitelist.required"
|
||||
name="xpinstall.whitelist.required"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.safebrowsing.malware.enabled"
|
||||
name="browser.safebrowsing.malware.enabled"
|
||||
type="bool"/>
|
||||
<preference id="browser.safebrowsing.phishing.enabled"
|
||||
name="browser.safebrowsing.phishing.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.safebrowsing.downloads.enabled"
|
||||
name="browser.safebrowsing.downloads.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="urlclassifier.malwareTable"
|
||||
name="urlclassifier.malwareTable"
|
||||
type="string"/>
|
||||
|
||||
<preference id="browser.safebrowsing.downloads.remote.block_potentially_unwanted"
|
||||
name="browser.safebrowsing.downloads.remote.block_potentially_unwanted"
|
||||
type="bool"/>
|
||||
<preference id="browser.safebrowsing.downloads.remote.block_uncommon"
|
||||
name="browser.safebrowsing.downloads.remote.block_uncommon"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Network tab -->
|
||||
<preference id="browser.cache.disk.capacity"
|
||||
name="browser.cache.disk.capacity"
|
||||
type="int"/>
|
||||
<preference id="browser.offline-apps.notify"
|
||||
name="browser.offline-apps.notify"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.cache.disk.smart_size.enabled"
|
||||
name="browser.cache.disk.smart_size.enabled"
|
||||
inverted="true"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Data Choices tab -->
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
<preference id="browser.crashReports.unsubmittedCheck.autoSubmit"
|
||||
name="browser.crashReports.unsubmittedCheck.autoSubmit"
|
||||
type="bool"/>
|
||||
#endif
|
||||
|
||||
</preferences>
|
||||
|
||||
<stringbundle id="bundlePreferences" src="chrome://browser/locale/preferences/preferences.properties"/>
|
||||
<stringbundle id="signonBundle" src="chrome://passwordmgr/locale/passwordmgr.properties"/>
|
||||
|
||||
<hbox id="browserPrivacyCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="panePrivacy">
|
||||
<label class="header-name" flex="1">&browserPrivacy.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Passwords -->
|
||||
<groupbox id="passwordsGroup" orient="vertical" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&formsAndPasswords.label;</label></caption>
|
||||
|
||||
<vbox id="passwordSettings">
|
||||
<hbox id="savePasswordsBox">
|
||||
<checkbox id="savePasswords"
|
||||
label="&rememberLogins2.label;" accesskey="&rememberLogins2.accesskey;"
|
||||
preference="signon.rememberSignons"
|
||||
onsyncfrompreference="return gPrivacyPane.readSavePasswords();"
|
||||
flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="passwordExceptions"
|
||||
class="accessory-button"
|
||||
label="&passwordExceptions.label;"
|
||||
accesskey="&passwordExceptions.accesskey;"
|
||||
preference="pref.privacy.disable_button.view_passwords_exceptions"
|
||||
searchkeywords="&address2.label;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<hbox id="showPasswordBox" pack="end">
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="showPasswords"
|
||||
class="accessory-button"
|
||||
label="&savedLogins.label;" accesskey="&savedLogins.accesskey;"
|
||||
preference="pref.privacy.disable_button.view_passwords"
|
||||
searchkeywords="&savedLogins.title;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
</vbox>
|
||||
<hbox id="masterPasswordRow">
|
||||
<checkbox id="useMasterPassword"
|
||||
label="&useMasterPassword.label;"
|
||||
accesskey="&useMasterPassword.accesskey;"
|
||||
flex="1"/>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="changeMasterPassword"
|
||||
class="accessory-button"
|
||||
label="&changeMasterPassword.label;"
|
||||
accesskey="&changeMasterPassword.accesskey;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- History -->
|
||||
<groupbox id="historyGroup" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&history.label;</label></caption>
|
||||
<hbox align="center">
|
||||
<label id="historyModeLabel"
|
||||
control="historyMode"
|
||||
accesskey="&historyHeader2.pre.accesskey;">&historyHeader2.pre.label;
|
||||
</label>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<menulist id="historyMode">
|
||||
<menupopup>
|
||||
<menuitem label="&historyHeader.remember.label;" value="remember" searchkeywords="&rememberDescription.label;
|
||||
&rememberActions.pre.label;
|
||||
&rememberActions.clearHistory.label;
|
||||
&rememberActions.middle.label;
|
||||
&rememberActions.removeCookies.label;
|
||||
&rememberActions.post.label;"/>
|
||||
<menuitem label="&historyHeader.dontremember.label;" value="dontremember" searchkeywords="&dontrememberDescription.label;
|
||||
&dontrememberActions.pre.label;
|
||||
&dontrememberActions.clearHistory.label;
|
||||
&dontrememberActions.post.label;"/>
|
||||
<menuitem label="&historyHeader.custom.label;" value="custom" searchkeywords="&privateBrowsingPermanent2.label;
|
||||
&rememberHistory2.label;
|
||||
&rememberSearchForm.label;
|
||||
&acceptCookies2.label;
|
||||
&cookieExceptions.label;
|
||||
&acceptThirdParty2.pre.label;
|
||||
&acceptThirdParty.always.label;
|
||||
&acceptThirdParty.visited.label;
|
||||
&acceptThirdParty.never.label;
|
||||
&keepUntil2.label;
|
||||
&expire.label;
|
||||
&close.label;
|
||||
&showCookies.label;
|
||||
&clearOnClose.label;
|
||||
&clearOnCloseSettings.label;"/>
|
||||
</menupopup>
|
||||
</menulist>
|
||||
</hbox>
|
||||
<label>&historyHeader.post.label;</label>
|
||||
</hbox>
|
||||
<deck id="historyPane">
|
||||
<vbox id="historyRememberPane">
|
||||
<hbox align="center" flex="1">
|
||||
<vbox flex="1">
|
||||
<description>&rememberDescription.label;</description>
|
||||
<separator class="thin"/>
|
||||
<description>&rememberActions.pre.label;<label
|
||||
class="text-link" id="historyRememberClear"
|
||||
>&rememberActions.clearHistory.label;</label>&rememberActions.middle.label;<label
|
||||
class="text-link" id="historyRememberCookies"
|
||||
>&rememberActions.removeCookies.label;</label>&rememberActions.post.label;</description>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</vbox>
|
||||
<vbox id="historyDontRememberPane">
|
||||
<hbox align="center" flex="1">
|
||||
<vbox flex="1">
|
||||
<description>&dontrememberDescription.label;</description>
|
||||
<separator class="thin"/>
|
||||
<description>&dontrememberActions.pre.label;<label
|
||||
class="text-link" id="historyDontRememberClear"
|
||||
>&dontrememberActions.clearHistory.label;</label>&dontrememberActions.post.label;</description>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</vbox>
|
||||
<vbox id="historyCustomPane">
|
||||
<separator class="thin"/>
|
||||
<vbox>
|
||||
<checkbox id="privateBrowsingAutoStart"
|
||||
label="&privateBrowsingPermanent2.label;"
|
||||
accesskey="&privateBrowsingPermanent2.accesskey;"
|
||||
preference="browser.privatebrowsing.autostart"/>
|
||||
<vbox class="indent">
|
||||
<checkbox id="rememberHistory"
|
||||
label="&rememberHistory2.label;"
|
||||
accesskey="&rememberHistory2.accesskey;"
|
||||
preference="places.history.enabled"/>
|
||||
<checkbox id="rememberForms"
|
||||
label="&rememberSearchForm.label;"
|
||||
accesskey="&rememberSearchForm.accesskey;"
|
||||
preference="browser.formfill.enable"/>
|
||||
<hbox id="cookiesBox">
|
||||
<checkbox id="acceptCookies" label="&acceptCookies2.label;"
|
||||
preference="network.cookie.cookieBehavior"
|
||||
accesskey="&acceptCookies2.accesskey;"
|
||||
onsyncfrompreference="return gPrivacyPane.readAcceptCookies();"
|
||||
onsynctopreference="return gPrivacyPane.writeAcceptCookies();"
|
||||
flex="1" />
|
||||
<button id="cookieExceptions"
|
||||
class="accessory-button"
|
||||
label="&cookieExceptions.label;" accesskey="&cookieExceptions.accesskey;"
|
||||
preference="pref.privacy.disable_button.cookie_exceptions"/>
|
||||
</hbox>
|
||||
<hbox id="acceptThirdPartyRow"
|
||||
class="indent"
|
||||
align="center">
|
||||
<label id="acceptThirdPartyLabel" control="acceptThirdPartyMenu"
|
||||
accesskey="&acceptThirdParty2.pre.accesskey;">&acceptThirdParty2.pre.label;</label>
|
||||
<menulist id="acceptThirdPartyMenu" preference="network.cookie.cookieBehavior"
|
||||
onsyncfrompreference="return gPrivacyPane.readAcceptThirdPartyCookies();"
|
||||
onsynctopreference="return gPrivacyPane.writeAcceptThirdPartyCookies();">
|
||||
<menupopup>
|
||||
<menuitem label="&acceptThirdParty.always.label;" value="always"/>
|
||||
<menuitem label="&acceptThirdParty.visited.label;" value="visited"/>
|
||||
<menuitem label="&acceptThirdParty.never.label;" value="never"/>
|
||||
</menupopup>
|
||||
</menulist>
|
||||
</hbox>
|
||||
<hbox id="keepRow"
|
||||
class="indent"
|
||||
align="center">
|
||||
<label id="keepUntil"
|
||||
control="keepCookiesUntil"
|
||||
accesskey="&keepUntil2.accesskey;">&keepUntil2.label;</label>
|
||||
<menulist id="keepCookiesUntil"
|
||||
preference="network.cookie.lifetimePolicy">
|
||||
<menupopup>
|
||||
<menuitem label="&expire.label;" value="0"/>
|
||||
<menuitem label="&close.label;" value="2"/>
|
||||
</menupopup>
|
||||
</menulist>
|
||||
<spacer flex="1"/>
|
||||
<button id="showCookiesButton"
|
||||
class="accessory-button"
|
||||
label="&showCookies.label;" accesskey="&showCookies.accesskey;"
|
||||
preference="pref.privacy.disable_button.view_cookies"/>
|
||||
</hbox>
|
||||
<hbox id="clearDataBox"
|
||||
align="center">
|
||||
<checkbox id="alwaysClear"
|
||||
preference="privacy.sanitize.sanitizeOnShutdown"
|
||||
label="&clearOnClose.label;"
|
||||
accesskey="&clearOnClose.accesskey;"
|
||||
flex="1" />
|
||||
<button id="clearDataSettings"
|
||||
class="accessory-button"
|
||||
label="&clearOnCloseSettings.label;"
|
||||
accesskey="&clearOnCloseSettings.accesskey;"/>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</vbox>
|
||||
</vbox>
|
||||
</deck>
|
||||
</groupbox>
|
||||
|
||||
<!-- Address Bar -->
|
||||
<groupbox id="locationBarGroup"
|
||||
data-category="panePrivacy"
|
||||
hidden="true">
|
||||
<caption><label>&addressBar.label;</label></caption>
|
||||
<label id="locationBarSuggestionLabel">&addressBar.suggest.label;</label>
|
||||
<checkbox id="historySuggestion" label="&locbar.history2.label;"
|
||||
accesskey="&locbar.history2.accesskey;"
|
||||
preference="browser.urlbar.suggest.history"/>
|
||||
<checkbox id="bookmarkSuggestion" label="&locbar.bookmarks.label;"
|
||||
accesskey="&locbar.bookmarks.accesskey;"
|
||||
preference="browser.urlbar.suggest.bookmark"/>
|
||||
<checkbox id="openpageSuggestion" label="&locbar.openpage.label;"
|
||||
accesskey="&locbar.openpage.accesskey;"
|
||||
preference="browser.urlbar.suggest.openpage"/>
|
||||
<label class="text-link" onclick="gotoPref('search')">
|
||||
&suggestionSettings2.label;
|
||||
</label>
|
||||
</groupbox>
|
||||
|
||||
<!-- Cache -->
|
||||
<groupbox id="cacheGroup" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&httpCache.label;</label></caption>
|
||||
|
||||
<hbox align="center">
|
||||
<label id="actualDiskCacheSize" flex="1"/>
|
||||
<button id="clearCacheButton"
|
||||
class="accessory-button"
|
||||
icon="clear"
|
||||
label="&clearCacheNow.label;" accesskey="&clearCacheNow.accesskey;"/>
|
||||
</hbox>
|
||||
<checkbox preference="browser.cache.disk.smart_size.enabled"
|
||||
id="allowSmartSize"
|
||||
onsyncfrompreference="return gPrivacyPane.readSmartSizeEnabled();"
|
||||
label="&overrideSmartCacheSize.label;"
|
||||
accesskey="&overrideSmartCacheSize.accesskey;"/>
|
||||
<hbox align="center" class="indent">
|
||||
<label id="useCacheBefore" control="cacheSize"
|
||||
accesskey="&limitCacheSizeBefore.accesskey;">
|
||||
&limitCacheSizeBefore.label;
|
||||
</label>
|
||||
<textbox id="cacheSize" type="number" size="4" max="1024"
|
||||
aria-labelledby="useCacheBefore cacheSize useCacheAfter"/>
|
||||
<label id="useCacheAfter" flex="1">&limitCacheSizeAfter.label;</label>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Site Data -->
|
||||
<groupbox id="siteDataGroup" hidden="true" data-category="panePrivacy" data-hidden-from-search="true">
|
||||
<caption><label>&siteData.label;</label></caption>
|
||||
|
||||
<hbox align="baseline">
|
||||
<vbox flex="1">
|
||||
<description flex="1">
|
||||
<label id="totalSiteDataSize"></label>
|
||||
<label id="siteDataLearnMoreLink" class="learnMore text-link">&siteDataLearnMoreLink.label;</label>
|
||||
</description>
|
||||
</vbox>
|
||||
<vbox align="end">
|
||||
<button id="siteDataSettings"
|
||||
class="accessory-button"
|
||||
label="&siteDataSettings.label;"
|
||||
accesskey="&siteDataSettings.accesskey;"
|
||||
searchkeywords="&window.title;
|
||||
&hostCol.label;
|
||||
&statusCol.label;
|
||||
&usageCol.label;"/>
|
||||
<button id="clearSiteDataButton"
|
||||
class="accessory-button"
|
||||
icon="clear"
|
||||
label="&clearSiteData.label;" accesskey="&clearSiteData.accesskey;"/>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Tracking -->
|
||||
<groupbox id="trackingGroup" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&trackingProtectionHeader2.label;</label></caption>
|
||||
<vbox>
|
||||
<hbox align="start">
|
||||
<vbox flex="1">
|
||||
<description>
|
||||
&trackingProtection2.description;
|
||||
</description>
|
||||
</vbox>
|
||||
<spacer flex="1"/>
|
||||
</hbox>
|
||||
<hbox>
|
||||
<vbox id="trackingProtectionBox" flex="1" hidden="true">
|
||||
<description id="trackingProtectionDesc"
|
||||
control="trackingProtectionRadioGroup">
|
||||
&trackingProtection2.radioGroupLabel;
|
||||
<label id="trackingProtectionLearnMore" class="learnMore text-link">&trackingProtectionLearnMore.label;</label>
|
||||
</description>
|
||||
<radiogroup id="trackingProtectionRadioGroup" aria-labelledby="trackingProtectionDesc">
|
||||
<radio value="always"
|
||||
label="&trackingProtectionAlways.label;"
|
||||
accesskey="&trackingProtectionAlways.accesskey;"/>
|
||||
<radio value="private"
|
||||
label="&trackingProtectionPrivate.label;"
|
||||
accesskey="&trackingProtectionPrivate.accesskey;"/>
|
||||
<radio value="never"
|
||||
label="&trackingProtectionNever.label;"
|
||||
accesskey="&trackingProtectionNever.accesskey;"/>
|
||||
</radiogroup>
|
||||
</vbox>
|
||||
<vbox id="trackingProtectionPBMBox" flex="1">
|
||||
<hbox align="center">
|
||||
<checkbox id="trackingProtectionPBM"
|
||||
preference="privacy.trackingprotection.pbmode.enabled"
|
||||
accesskey="&trackingProtectionPBM6.accesskey;"/>
|
||||
<label flex="1">&trackingProtectionPBM6.label;<label id="trackingProtectionPBMLearnMore"
|
||||
class="learnMore text-link">&trackingProtectionPBMLearnMore.label;</label>
|
||||
</label>
|
||||
</hbox>
|
||||
</vbox>
|
||||
<vbox id="trackingProtectionAdvancedSettings">
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="trackingProtectionExceptions"
|
||||
class="accessory-button"
|
||||
flex="1"
|
||||
hidden="true"
|
||||
label="&trackingProtectionExceptions.label;"
|
||||
accesskey="&trackingProtectionExceptions.accesskey;"
|
||||
preference="pref.privacy.disable_button.tracking_protection_exceptions"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="changeBlockList"
|
||||
class="accessory-button"
|
||||
flex="1"
|
||||
label="&changeBlockList2.label;"
|
||||
accesskey="&changeBlockList2.accesskey;"
|
||||
preference="pref.privacy.disable_button.change_blocklist"
|
||||
searchkeywords="&button.cancel.label; &button.ok.label;"/>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
<vbox id="doNotTrackLearnMoreBox">
|
||||
<label>&doNotTrack.description;<label
|
||||
class="learnMore text-link" href="https://www.mozilla.org/dnt"
|
||||
>&doNotTrack.learnMore.label;</label></label>
|
||||
<radiogroup id="doNotTrackRadioGroup" aria-labelledby="doNotTrackDesc" preference="privacy.donottrackheader.enabled">
|
||||
<radio value="false" label="&doNotTrack.default.label;"/>
|
||||
<radio value="true" label="&doNotTrack.always.label;"/>
|
||||
</radiogroup>
|
||||
</vbox>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<hbox id="permissionsCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="panePrivacy">
|
||||
<label class="header-name" flex="1">&permissions.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Permissions -->
|
||||
<groupbox id="permissionsGroup" data-category="panePrivacy" hidden="true">
|
||||
<caption class="search-header" hidden="true"><label>&permissions.label;</label></caption>
|
||||
|
||||
<grid>
|
||||
<columns>
|
||||
<column flex="1"/>
|
||||
<column/>
|
||||
</columns>
|
||||
<rows>
|
||||
<row id="locationSettingsRow" align="center">
|
||||
<description flex="1">
|
||||
<image class="geo-icon permission-icon" />
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label id="locationPermissionsLabel">&locationPermissions.label;</label>
|
||||
</description>
|
||||
<hbox pack="end">
|
||||
<button id="locationSettingsButton"
|
||||
class="accessory-button"
|
||||
label="&locationSettingsButton.label;"
|
||||
accesskey="&locationSettingsButton.accesskey;"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
|
||||
<row id="cameraSettingsRow" align="center">
|
||||
<description flex="1">
|
||||
<image class="camera-icon permission-icon" />
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label id="cameraPermissionsLabel">&cameraPermissions.label;</label>
|
||||
</description>
|
||||
<hbox pack="end">
|
||||
<button id="cameraSettingsButton"
|
||||
class="accessory-button"
|
||||
label="&cameraSettingsButton.label;"
|
||||
accesskey="&cameraSettingsButton.accesskey;"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
|
||||
<row id="microphoneSettingsRow" align="center">
|
||||
<description flex="1">
|
||||
<image class="microphone-icon permission-icon" />
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label id="microphonePermissionsLabel">µphonePermissions.label;</label>
|
||||
</description>
|
||||
<hbox pack="end">
|
||||
<button id="microphoneSettingsButton"
|
||||
class="accessory-button"
|
||||
label="µphoneSettingsButton.label;"
|
||||
accesskey="µphoneSettingsButton.accesskey;"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
|
||||
<row id="notificationSettingsRow" align="center">
|
||||
<description flex="1">
|
||||
<image class="desktop-notification-icon permission-icon" />
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label id="notificationPermissionsLabel">¬ificationPermissions.label;</label>
|
||||
<label id="notificationPermissionsLearnMore"
|
||||
class="learnMore text-link">¬ificationPermissionsLearnMore.label;</label>
|
||||
</description>
|
||||
<hbox pack="end">
|
||||
<button id="notificationSettingsButton"
|
||||
class="accessory-button"
|
||||
label="¬ificationSettingsButton.label;"
|
||||
accesskey="¬ificationSettingsButton.accesskey;"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
</rows>
|
||||
</grid>
|
||||
|
||||
<separator flex="1"/>
|
||||
|
||||
<vbox id="notificationsDoNotDisturbBox" hidden="true">
|
||||
<checkbox id="notificationsDoNotDisturb" label="¬ificationsDoNotDisturb.label;"
|
||||
accesskey="¬ificationsDoNotDisturb.accesskey;"/>
|
||||
<label id="notificationsDoNotDisturbDetails"
|
||||
class="indent">¬ificationsDoNotDisturbDetails.value;</label>
|
||||
</vbox>
|
||||
|
||||
<hbox align="start">
|
||||
<checkbox id="popupPolicy" preference="dom.disable_open_during_load"
|
||||
label="&blockPopups.label;" accesskey="&blockPopups.accesskey;"
|
||||
onsyncfrompreference="return gPrivacyPane.updateButtons('popupPolicyButton',
|
||||
'dom.disable_open_during_load');"
|
||||
flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="popupPolicyButton"
|
||||
class="accessory-button"
|
||||
label="&popupExceptions.label;"
|
||||
accesskey="&popupExceptions.accesskey;"
|
||||
searchkeywords="&address2.label; &button.cancel.label; &button.ok.label;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
|
||||
<hbox id="addonInstallBox">
|
||||
<checkbox id="warnAddonInstall"
|
||||
label="&warnOnAddonInstall2.label;"
|
||||
accesskey="&warnOnAddonInstall2.accesskey;"
|
||||
preference="xpinstall.whitelist.required"
|
||||
onsyncfrompreference="return gPrivacyPane.readWarnAddonInstall();"
|
||||
flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="addonExceptions"
|
||||
class="accessory-button"
|
||||
label="&addonExceptions.label;"
|
||||
accesskey="&addonExceptions.accesskey;"
|
||||
searchkeywords="&address2.label;
|
||||
&allow.label;
|
||||
&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
|
||||
<vbox id="a11yPermissionsBox">
|
||||
<description flex="1">
|
||||
<checkbox id="a11yPrivacyCheckbox" label="&a11yPrivacy.checkbox.label;"
|
||||
accesskey="&a11yPrivacy.checkbox.accesskey;"
|
||||
oncommand="return gPrivacyPane.updateA11yPrefs(this.checked)"/>
|
||||
<label id="a11yLearnMoreLink" class="learnMore text-link"
|
||||
value="&a11yPrivacy.learnmore.label;"></label>
|
||||
</description>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<hbox id="dataCollectionCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="panePrivacy"
|
||||
data-subcategory="reports">
|
||||
<label class="header-name" flex="1">&dataCollection.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Firefox Data Collection and Use -->
|
||||
#ifdef MOZ_DATA_REPORTING
|
||||
<groupbox id="dataCollectionGroup" data-category="panePrivacy" data-subcategory="reports" hidden="true">
|
||||
<caption class="search-header" hidden="true"><label>&dataCollection.label;</label></caption>
|
||||
|
||||
<vbox>
|
||||
<description>
|
||||
&dataCollectionDesc.label;<label id="dataCollectionPrivacyNotice" class="learnMore text-link">&dataCollectionPrivacyNotice.label;</label>
|
||||
</description>
|
||||
<description flex="1">
|
||||
<checkbox id="submitHealthReportBox" label="&enableHealthReport1.label;"
|
||||
accesskey="&enableHealthReport1.accesskey;"/>
|
||||
<label id="FHRLearnMore"
|
||||
class="learnMore text-link">&healthReportLearnMore.label;</label>
|
||||
</description>
|
||||
#ifndef MOZ_TELEMETRY_REPORTING
|
||||
<description id="TelemetryDisabledDesc" class="indent" control="telemetryGroup">&healthReportingDisabled.label;</description>
|
||||
#endif
|
||||
</vbox>
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
<hbox align="center">
|
||||
<checkbox id="automaticallySubmitCrashesBox"
|
||||
preference="browser.crashReports.unsubmittedCheck.autoSubmit"
|
||||
label="&alwaysSubmitCrashReports1.label;"
|
||||
accesskey="&alwaysSubmitCrashReports1.accesskey;"/>
|
||||
<label id="crashReporterLearnMore"
|
||||
class="learnMore text-link">&crashReporterLearnMore.label;</label>
|
||||
</hbox>
|
||||
#endif
|
||||
</groupbox>
|
||||
#endif
|
||||
|
||||
<hbox id="securityCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="panePrivacy">
|
||||
<label class="header-name" flex="1">&security.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- addons, forgery (phishing) UI Security -->
|
||||
<groupbox id="addonsPhishingGroup" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&phishingProtection.label;</label></caption>
|
||||
<checkbox id="enableSafeBrowsing"
|
||||
label="&enableSafeBrowsing.label;"
|
||||
accesskey="&enableSafeBrowsing.accesskey;" />
|
||||
<vbox class="indent">
|
||||
<checkbox id="blockDownloads"
|
||||
label="&blockDownloads.label;"
|
||||
accesskey="&blockDownloads.accesskey;" />
|
||||
<checkbox id="blockUncommonUnwanted"
|
||||
label="&blockUncommonAndUnwanted.label;"
|
||||
accesskey="&blockUncommonAndUnwanted.accesskey;" />
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Certificates -->
|
||||
<groupbox id="certSelection" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&certificateTab.label;</label></caption>
|
||||
<description id="CertSelectionDesc" control="certSelection">&certPersonal2.description;</description>
|
||||
|
||||
<!--
|
||||
The values on these radio buttons may look like l10n issues, but
|
||||
they're not - this preference uses *those strings* as its values.
|
||||
I KID YOU NOT.
|
||||
-->
|
||||
<radiogroup id="certSelection"
|
||||
preftype="string"
|
||||
preference="security.default_personal_cert"
|
||||
aria-labelledby="CertSelectionDesc">
|
||||
<radio label="&selectCerts.auto;"
|
||||
accesskey="&selectCerts.auto.accesskey;"
|
||||
value="Select Automatically"/>
|
||||
<radio label="&selectCerts.ask;"
|
||||
accesskey="&selectCerts.ask.accesskey;"
|
||||
value="Ask Every Time"/>
|
||||
</radiogroup>
|
||||
<hbox align="start">
|
||||
<checkbox id="enableOCSP"
|
||||
label="&enableOCSP.label;"
|
||||
accesskey="&enableOCSP.accesskey;"
|
||||
onsyncfrompreference="return gPrivacyPane.readEnableOCSP();"
|
||||
onsynctopreference="return gPrivacyPane.writeEnableOCSP();"
|
||||
preference="security.OCSP.enabled"
|
||||
flex="1" />
|
||||
<vbox>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox pack="end">
|
||||
<button id="viewCertificatesButton"
|
||||
class="accessory-button"
|
||||
label="&viewCerts2.label;"
|
||||
accesskey="&viewCerts2.accesskey;"
|
||||
preference="security.disable_button.openCertManager"
|
||||
searchkeywords="&certmgr.tab.mine;
|
||||
&certmgr.tab.others2;
|
||||
&certmgr.tab.websites3;
|
||||
&certmgr.tab.ca;
|
||||
&certmgr.tab.orphan2;
|
||||
&certmgr.mine2;
|
||||
&certmgr.others2;
|
||||
&certmgr.websites3;
|
||||
&certmgr.cas2;
|
||||
&certmgr.orphans2;
|
||||
&certmgr.certname;
|
||||
&certmgr.tokenname;
|
||||
&certmgr.view2.label;
|
||||
&certmgr.export.label;
|
||||
&certmgr.delete2.label;"/>
|
||||
</hbox>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox pack="end">
|
||||
<button id="viewSecurityDevicesButton"
|
||||
class="accessory-button"
|
||||
label="&viewSecurityDevices2.label;"
|
||||
accesskey="&viewSecurityDevices2.accesskey;"
|
||||
preference="security.disable_button.openDeviceManager"
|
||||
searchkeywords="&devmgr.title;
|
||||
&devmgr.devlist.label;
|
||||
&devmgr.details.title;
|
||||
&devmgr.details.title2;
|
||||
&devmgr.button.login.label;
|
||||
&devmgr.button.logout.label;
|
||||
&devmgr.button.changepw.label;
|
||||
&devmgr.button.load.label;
|
||||
&devmgr.button.unload.label;"/>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Offline apps -->
|
||||
<groupbox id="offlineGroup" data-category="panePrivacy" hidden="true" data-hidden-from-search="true">
|
||||
<caption><label>&offlineStorage2.label;</label></caption>
|
||||
|
||||
<hbox align="center">
|
||||
<label id="actualAppCacheSize" flex="1"/>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="clearOfflineAppCacheButton"
|
||||
class="accessory-button"
|
||||
icon="clear"
|
||||
label="&clearOfflineAppCacheNow.label;" accesskey="&clearOfflineAppCacheNow.accesskey;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<hbox align="center">
|
||||
<checkbox id="offlineNotify"
|
||||
label="&offlineStorageNotify.label;" accesskey="&offlineStorageNotify.accesskey;"
|
||||
preference="browser.offline-apps.notify"
|
||||
onsyncfrompreference="return gPrivacyPane.readOfflineNotify();"
|
||||
flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="offlineNotifyExceptions"
|
||||
class="accessory-button"
|
||||
label="&offlineStorageNotifyExceptions.label;"
|
||||
accesskey="&offlineStorageNotifyExceptions.accesskey;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<hbox>
|
||||
<vbox flex="1">
|
||||
<label id="offlineAppsListLabel">&offlineAppsList3.label;</label>
|
||||
<listbox id="offlineAppsList"
|
||||
flex="1"
|
||||
aria-labelledby="offlineAppsListLabel">
|
||||
</listbox>
|
||||
</vbox>
|
||||
<vbox pack="end">
|
||||
<button id="offlineAppsListRemove"
|
||||
class="accessory-button"
|
||||
disabled="true"
|
||||
label="&offlineAppsListRemove.label;"
|
||||
accesskey="&offlineAppsListRemove.accesskey;"/>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</groupbox>
|
@ -1,604 +0,0 @@
|
||||
/* 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/. */
|
||||
|
||||
/* import-globals-from preferences.js */
|
||||
|
||||
Components.utils.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "PlacesUtils",
|
||||
"resource://gre/modules/PlacesUtils.jsm");
|
||||
|
||||
const ENGINE_FLAVOR = "text/x-moz-search-engine";
|
||||
|
||||
var gEngineView = null;
|
||||
|
||||
var gSearchPane = {
|
||||
|
||||
/**
|
||||
* Initialize autocomplete to ensure prefs are in sync.
|
||||
*/
|
||||
_initAutocomplete() {
|
||||
Components.classes["@mozilla.org/autocomplete/search;1?name=unifiedcomplete"]
|
||||
.getService(Components.interfaces.mozIPlacesAutoComplete);
|
||||
},
|
||||
|
||||
init() {
|
||||
gEngineView = new EngineView(new EngineStore());
|
||||
document.getElementById("engineList").view = gEngineView;
|
||||
this.buildDefaultEngineDropDown();
|
||||
|
||||
let addEnginesLink = document.getElementById("addEngines");
|
||||
let searchEnginesURL = Services.wm.getMostRecentWindow("navigator:browser")
|
||||
.BrowserSearch.searchEnginesURL;
|
||||
addEnginesLink.setAttribute("href", searchEnginesURL);
|
||||
|
||||
window.addEventListener("click", this);
|
||||
window.addEventListener("command", this);
|
||||
window.addEventListener("dragstart", this);
|
||||
window.addEventListener("keypress", this);
|
||||
window.addEventListener("select", this);
|
||||
window.addEventListener("blur", this, true);
|
||||
|
||||
Services.obs.addObserver(this, "browser-search-engine-modified");
|
||||
window.addEventListener("unload", () => {
|
||||
Services.obs.removeObserver(this, "browser-search-engine-modified");
|
||||
});
|
||||
|
||||
this._initAutocomplete();
|
||||
|
||||
let suggestsPref =
|
||||
document.getElementById("browser.search.suggest.enabled");
|
||||
suggestsPref.addEventListener("change", () => {
|
||||
this.updateSuggestsCheckbox();
|
||||
});
|
||||
this.updateSuggestsCheckbox();
|
||||
},
|
||||
|
||||
updateSuggestsCheckbox() {
|
||||
let suggestsPref =
|
||||
document.getElementById("browser.search.suggest.enabled");
|
||||
let permanentPB =
|
||||
Services.prefs.getBoolPref("browser.privatebrowsing.autostart");
|
||||
let urlbarSuggests = document.getElementById("urlBarSuggestion");
|
||||
urlbarSuggests.disabled = !suggestsPref.value || permanentPB;
|
||||
|
||||
let urlbarSuggestsPref =
|
||||
document.getElementById("browser.urlbar.suggest.searches");
|
||||
urlbarSuggests.checked = urlbarSuggestsPref.value;
|
||||
if (urlbarSuggests.disabled) {
|
||||
urlbarSuggests.checked = false;
|
||||
}
|
||||
|
||||
let permanentPBLabel =
|
||||
document.getElementById("urlBarSuggestionPermanentPBLabel");
|
||||
permanentPBLabel.hidden = urlbarSuggests.hidden || !permanentPB;
|
||||
},
|
||||
|
||||
buildDefaultEngineDropDown() {
|
||||
// This is called each time something affects the list of engines.
|
||||
let list = document.getElementById("defaultEngine");
|
||||
// Set selection to the current default engine.
|
||||
let currentEngine = Services.search.currentEngine.name;
|
||||
|
||||
// If the current engine isn't in the list any more, select the first item.
|
||||
let engines = gEngineView._engineStore._engines;
|
||||
if (!engines.some(e => e.name == currentEngine))
|
||||
currentEngine = engines[0].name;
|
||||
|
||||
// Now clean-up and rebuild the list.
|
||||
list.removeAllItems();
|
||||
gEngineView._engineStore._engines.forEach(e => {
|
||||
let item = list.appendItem(e.name);
|
||||
item.setAttribute("class", "menuitem-iconic searchengine-menuitem menuitem-with-favicon");
|
||||
if (e.iconURI) {
|
||||
item.setAttribute("image", e.iconURI.spec);
|
||||
}
|
||||
item.engine = e;
|
||||
if (e.name == currentEngine)
|
||||
list.selectedItem = item;
|
||||
});
|
||||
},
|
||||
|
||||
handleEvent(aEvent) {
|
||||
switch (aEvent.type) {
|
||||
case "click":
|
||||
if (aEvent.target.id != "engineChildren" &&
|
||||
!aEvent.target.classList.contains("searchEngineAction")) {
|
||||
let engineList = document.getElementById("engineList");
|
||||
// We don't want to toggle off selection while editing keyword
|
||||
// so proceed only when the input field is hidden.
|
||||
// We need to check that engineList.view is defined here
|
||||
// because the "click" event listener is on <window> and the
|
||||
// view might have been destroyed if the pane has been navigated
|
||||
// away from.
|
||||
if (engineList.inputField.hidden && engineList.view) {
|
||||
let selection = engineList.view.selection;
|
||||
if (selection.count > 0) {
|
||||
selection.toggleSelect(selection.currentIndex);
|
||||
}
|
||||
engineList.blur();
|
||||
}
|
||||
}
|
||||
break;
|
||||
case "command":
|
||||
switch (aEvent.target.id) {
|
||||
case "":
|
||||
if (aEvent.target.parentNode &&
|
||||
aEvent.target.parentNode.parentNode &&
|
||||
aEvent.target.parentNode.parentNode.id == "defaultEngine") {
|
||||
gSearchPane.setDefaultEngine();
|
||||
}
|
||||
break;
|
||||
case "restoreDefaultSearchEngines":
|
||||
gSearchPane.onRestoreDefaults();
|
||||
break;
|
||||
case "removeEngineButton":
|
||||
Services.search.removeEngine(gEngineView.selectedEngine.originalEngine);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case "dragstart":
|
||||
if (aEvent.target.id == "engineChildren") {
|
||||
onDragEngineStart(aEvent);
|
||||
}
|
||||
break;
|
||||
case "keypress":
|
||||
if (aEvent.target.id == "engineList") {
|
||||
gSearchPane.onTreeKeyPress(aEvent);
|
||||
}
|
||||
break;
|
||||
case "select":
|
||||
if (aEvent.target.id == "engineList") {
|
||||
gSearchPane.onTreeSelect();
|
||||
}
|
||||
break;
|
||||
case "blur":
|
||||
if (aEvent.target.id == "engineList" &&
|
||||
aEvent.target.inputField == document.getBindingParent(aEvent.originalTarget)) {
|
||||
gSearchPane.onInputBlur();
|
||||
}
|
||||
break;
|
||||
}
|
||||
},
|
||||
|
||||
observe(aEngine, aTopic, aVerb) {
|
||||
if (aTopic == "browser-search-engine-modified") {
|
||||
aEngine.QueryInterface(Components.interfaces.nsISearchEngine);
|
||||
switch (aVerb) {
|
||||
case "engine-added":
|
||||
gEngineView._engineStore.addEngine(aEngine);
|
||||
gEngineView.rowCountChanged(gEngineView.lastIndex, 1);
|
||||
gSearchPane.buildDefaultEngineDropDown();
|
||||
break;
|
||||
case "engine-changed":
|
||||
gEngineView._engineStore.reloadIcons();
|
||||
gEngineView.invalidate();
|
||||
break;
|
||||
case "engine-removed":
|
||||
gSearchPane.remove(aEngine);
|
||||
break;
|
||||
case "engine-current":
|
||||
// If the user is going through the drop down using up/down keys, the
|
||||
// dropdown may still be open (eg. on Windows) when engine-current is
|
||||
// fired, so rebuilding the list unconditionally would get in the way.
|
||||
let selectedEngine =
|
||||
document.getElementById("defaultEngine").selectedItem.engine;
|
||||
if (selectedEngine.name != aEngine.name)
|
||||
gSearchPane.buildDefaultEngineDropDown();
|
||||
break;
|
||||
case "engine-default":
|
||||
// Not relevant
|
||||
break;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
onInputBlur(aEvent) {
|
||||
let tree = document.getElementById("engineList");
|
||||
if (!tree.hasAttribute("editing"))
|
||||
return;
|
||||
|
||||
// Accept input unless discarded.
|
||||
let accept = aEvent.charCode != KeyEvent.DOM_VK_ESCAPE;
|
||||
tree.stopEditing(accept);
|
||||
},
|
||||
|
||||
onTreeSelect() {
|
||||
document.getElementById("removeEngineButton").disabled =
|
||||
!gEngineView.isEngineSelectedAndRemovable();
|
||||
},
|
||||
|
||||
onTreeKeyPress(aEvent) {
|
||||
let index = gEngineView.selectedIndex;
|
||||
let tree = document.getElementById("engineList");
|
||||
if (tree.hasAttribute("editing"))
|
||||
return;
|
||||
|
||||
if (aEvent.charCode == KeyEvent.DOM_VK_SPACE) {
|
||||
// Space toggles the checkbox.
|
||||
let newValue = !gEngineView._engineStore.engines[index].shown;
|
||||
gEngineView.setCellValue(index, tree.columns.getFirstColumn(),
|
||||
newValue.toString());
|
||||
// Prevent page from scrolling on the space key.
|
||||
aEvent.preventDefault();
|
||||
} else {
|
||||
let isMac = Services.appinfo.OS == "Darwin";
|
||||
if ((isMac && aEvent.keyCode == KeyEvent.DOM_VK_RETURN) ||
|
||||
(!isMac && aEvent.keyCode == KeyEvent.DOM_VK_F2)) {
|
||||
tree.startEditing(index, tree.columns.getLastColumn());
|
||||
} else if (aEvent.keyCode == KeyEvent.DOM_VK_DELETE ||
|
||||
(isMac && aEvent.shiftKey &&
|
||||
aEvent.keyCode == KeyEvent.DOM_VK_BACK_SPACE &&
|
||||
gEngineView.isEngineSelectedAndRemovable())) {
|
||||
// Delete and Shift+Backspace (Mac) removes selected engine.
|
||||
Services.search.removeEngine(gEngineView.selectedEngine.originalEngine);
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
onRestoreDefaults() {
|
||||
let num = gEngineView._engineStore.restoreDefaultEngines();
|
||||
gEngineView.rowCountChanged(0, num);
|
||||
gEngineView.invalidate();
|
||||
},
|
||||
|
||||
showRestoreDefaults(aEnable) {
|
||||
document.getElementById("restoreDefaultSearchEngines").disabled = !aEnable;
|
||||
},
|
||||
|
||||
remove(aEngine) {
|
||||
let index = gEngineView._engineStore.removeEngine(aEngine);
|
||||
gEngineView.rowCountChanged(index, -1);
|
||||
gEngineView.invalidate();
|
||||
gEngineView.selection.select(Math.min(index, gEngineView.lastIndex));
|
||||
gEngineView.ensureRowIsVisible(gEngineView.currentIndex);
|
||||
document.getElementById("engineList").focus();
|
||||
},
|
||||
|
||||
async editKeyword(aEngine, aNewKeyword) {
|
||||
let keyword = aNewKeyword.trim();
|
||||
if (keyword) {
|
||||
let eduplicate = false;
|
||||
let dupName = "";
|
||||
|
||||
// Check for duplicates in Places keywords.
|
||||
let bduplicate = !!(await PlacesUtils.keywords.fetch(keyword));
|
||||
|
||||
// Check for duplicates in changes we haven't committed yet
|
||||
let engines = gEngineView._engineStore.engines;
|
||||
let lc_keyword = keyword.toLocaleLowerCase();
|
||||
for (let engine of engines) {
|
||||
if (engine.alias &&
|
||||
engine.alias.toLocaleLowerCase() == lc_keyword &&
|
||||
engine.name != aEngine.name) {
|
||||
eduplicate = true;
|
||||
dupName = engine.name;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Notify the user if they have chosen an existing engine/bookmark keyword
|
||||
if (eduplicate || bduplicate) {
|
||||
let strings = document.getElementById("engineManagerBundle");
|
||||
let dtitle = strings.getString("duplicateTitle");
|
||||
let bmsg = strings.getString("duplicateBookmarkMsg");
|
||||
let emsg = strings.getFormattedString("duplicateEngineMsg", [dupName]);
|
||||
|
||||
Services.prompt.alert(window, dtitle, eduplicate ? emsg : bmsg);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
gEngineView._engineStore.changeEngine(aEngine, "alias", keyword);
|
||||
gEngineView.invalidate();
|
||||
return true;
|
||||
},
|
||||
|
||||
saveOneClickEnginesList() {
|
||||
let hiddenList = [];
|
||||
for (let engine of gEngineView._engineStore.engines) {
|
||||
if (!engine.shown)
|
||||
hiddenList.push(engine.name);
|
||||
}
|
||||
document.getElementById("browser.search.hiddenOneOffs").value =
|
||||
hiddenList.join(",");
|
||||
},
|
||||
|
||||
setDefaultEngine() {
|
||||
Services.search.currentEngine =
|
||||
document.getElementById("defaultEngine").selectedItem.engine;
|
||||
}
|
||||
};
|
||||
|
||||
function onDragEngineStart(event) {
|
||||
var selectedIndex = gEngineView.selectedIndex;
|
||||
var tree = document.getElementById("engineList");
|
||||
var row = { }, col = { }, child = { };
|
||||
tree.treeBoxObject.getCellAt(event.clientX, event.clientY, row, col, child);
|
||||
if (selectedIndex >= 0 && !gEngineView.isCheckBox(row.value, col.value)) {
|
||||
event.dataTransfer.setData(ENGINE_FLAVOR, selectedIndex.toString());
|
||||
event.dataTransfer.effectAllowed = "move";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
function EngineStore() {
|
||||
let pref = document.getElementById("browser.search.hiddenOneOffs").value;
|
||||
this.hiddenList = pref ? pref.split(",") : [];
|
||||
|
||||
this._engines = Services.search.getVisibleEngines().map(this._cloneEngine, this);
|
||||
this._defaultEngines = Services.search.getDefaultEngines().map(this._cloneEngine, this);
|
||||
|
||||
// check if we need to disable the restore defaults button
|
||||
var someHidden = this._defaultEngines.some(e => e.hidden);
|
||||
gSearchPane.showRestoreDefaults(someHidden);
|
||||
}
|
||||
EngineStore.prototype = {
|
||||
_engines: null,
|
||||
_defaultEngines: null,
|
||||
|
||||
get engines() {
|
||||
return this._engines;
|
||||
},
|
||||
set engines(val) {
|
||||
this._engines = val;
|
||||
return val;
|
||||
},
|
||||
|
||||
_getIndexForEngine(aEngine) {
|
||||
return this._engines.indexOf(aEngine);
|
||||
},
|
||||
|
||||
_getEngineByName(aName) {
|
||||
return this._engines.find(engine => engine.name == aName);
|
||||
},
|
||||
|
||||
_cloneEngine(aEngine) {
|
||||
var clonedObj = {};
|
||||
for (var i in aEngine)
|
||||
clonedObj[i] = aEngine[i];
|
||||
clonedObj.originalEngine = aEngine;
|
||||
clonedObj.shown = this.hiddenList.indexOf(clonedObj.name) == -1;
|
||||
return clonedObj;
|
||||
},
|
||||
|
||||
// Callback for Array's some(). A thisObj must be passed to some()
|
||||
_isSameEngine(aEngineClone) {
|
||||
return aEngineClone.originalEngine == this.originalEngine;
|
||||
},
|
||||
|
||||
addEngine(aEngine) {
|
||||
this._engines.push(this._cloneEngine(aEngine));
|
||||
},
|
||||
|
||||
moveEngine(aEngine, aNewIndex) {
|
||||
if (aNewIndex < 0 || aNewIndex > this._engines.length - 1)
|
||||
throw new Error("ES_moveEngine: invalid aNewIndex!");
|
||||
var index = this._getIndexForEngine(aEngine);
|
||||
if (index == -1)
|
||||
throw new Error("ES_moveEngine: invalid engine?");
|
||||
|
||||
if (index == aNewIndex)
|
||||
return; // nothing to do
|
||||
|
||||
// Move the engine in our internal store
|
||||
var removedEngine = this._engines.splice(index, 1)[0];
|
||||
this._engines.splice(aNewIndex, 0, removedEngine);
|
||||
|
||||
Services.search.moveEngine(aEngine.originalEngine, aNewIndex);
|
||||
},
|
||||
|
||||
removeEngine(aEngine) {
|
||||
if (this._engines.length == 1) {
|
||||
throw new Error("Cannot remove last engine!");
|
||||
}
|
||||
|
||||
let engineName = aEngine.name;
|
||||
let index = this._engines.findIndex(element => element.name == engineName);
|
||||
|
||||
if (index == -1)
|
||||
throw new Error("invalid engine?");
|
||||
|
||||
let removedEngine = this._engines.splice(index, 1)[0];
|
||||
|
||||
if (this._defaultEngines.some(this._isSameEngine, removedEngine))
|
||||
gSearchPane.showRestoreDefaults(true);
|
||||
gSearchPane.buildDefaultEngineDropDown();
|
||||
return index;
|
||||
},
|
||||
|
||||
restoreDefaultEngines() {
|
||||
var added = 0;
|
||||
|
||||
for (var i = 0; i < this._defaultEngines.length; ++i) {
|
||||
var e = this._defaultEngines[i];
|
||||
|
||||
// If the engine is already in the list, just move it.
|
||||
if (this._engines.some(this._isSameEngine, e)) {
|
||||
this.moveEngine(this._getEngineByName(e.name), i);
|
||||
} else {
|
||||
// Otherwise, add it back to our internal store
|
||||
|
||||
// The search service removes the alias when an engine is hidden,
|
||||
// so clear any alias we may have cached before unhiding the engine.
|
||||
e.alias = "";
|
||||
|
||||
this._engines.splice(i, 0, e);
|
||||
let engine = e.originalEngine;
|
||||
engine.hidden = false;
|
||||
Services.search.moveEngine(engine, i);
|
||||
added++;
|
||||
}
|
||||
}
|
||||
Services.search.resetToOriginalDefaultEngine();
|
||||
gSearchPane.showRestoreDefaults(false);
|
||||
gSearchPane.buildDefaultEngineDropDown();
|
||||
return added;
|
||||
},
|
||||
|
||||
changeEngine(aEngine, aProp, aNewValue) {
|
||||
var index = this._getIndexForEngine(aEngine);
|
||||
if (index == -1)
|
||||
throw new Error("invalid engine?");
|
||||
|
||||
this._engines[index][aProp] = aNewValue;
|
||||
aEngine.originalEngine[aProp] = aNewValue;
|
||||
},
|
||||
|
||||
reloadIcons() {
|
||||
this._engines.forEach(function(e) {
|
||||
e.uri = e.originalEngine.uri;
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
function EngineView(aEngineStore) {
|
||||
this._engineStore = aEngineStore;
|
||||
}
|
||||
EngineView.prototype = {
|
||||
_engineStore: null,
|
||||
tree: null,
|
||||
|
||||
get lastIndex() {
|
||||
return this.rowCount - 1;
|
||||
},
|
||||
get selectedIndex() {
|
||||
var seln = this.selection;
|
||||
if (seln.getRangeCount() > 0) {
|
||||
var min = {};
|
||||
seln.getRangeAt(0, min, {});
|
||||
return min.value;
|
||||
}
|
||||
return -1;
|
||||
},
|
||||
get selectedEngine() {
|
||||
return this._engineStore.engines[this.selectedIndex];
|
||||
},
|
||||
|
||||
// Helpers
|
||||
rowCountChanged(index, count) {
|
||||
this.tree.rowCountChanged(index, count);
|
||||
},
|
||||
|
||||
invalidate() {
|
||||
this.tree.invalidate();
|
||||
},
|
||||
|
||||
ensureRowIsVisible(index) {
|
||||
this.tree.ensureRowIsVisible(index);
|
||||
},
|
||||
|
||||
getSourceIndexFromDrag(dataTransfer) {
|
||||
return parseInt(dataTransfer.getData(ENGINE_FLAVOR));
|
||||
},
|
||||
|
||||
isCheckBox(index, column) {
|
||||
return column.id == "engineShown";
|
||||
},
|
||||
|
||||
isEngineSelectedAndRemovable() {
|
||||
return this.selectedIndex != -1 && this.lastIndex != 0;
|
||||
},
|
||||
|
||||
// nsITreeView
|
||||
get rowCount() {
|
||||
return this._engineStore.engines.length;
|
||||
},
|
||||
|
||||
getImageSrc(index, column) {
|
||||
if (column.id == "engineName") {
|
||||
if (this._engineStore.engines[index].iconURI)
|
||||
return this._engineStore.engines[index].iconURI.spec;
|
||||
|
||||
if (window.devicePixelRatio > 1)
|
||||
return "chrome://browser/skin/search-engine-placeholder@2x.png";
|
||||
return "chrome://browser/skin/search-engine-placeholder.png";
|
||||
}
|
||||
|
||||
return "";
|
||||
},
|
||||
|
||||
getCellText(index, column) {
|
||||
if (column.id == "engineName")
|
||||
return this._engineStore.engines[index].name;
|
||||
else if (column.id == "engineKeyword")
|
||||
return this._engineStore.engines[index].alias;
|
||||
return "";
|
||||
},
|
||||
|
||||
setTree(tree) {
|
||||
this.tree = tree;
|
||||
},
|
||||
|
||||
canDrop(targetIndex, orientation, dataTransfer) {
|
||||
var sourceIndex = this.getSourceIndexFromDrag(dataTransfer);
|
||||
return (sourceIndex != -1 &&
|
||||
sourceIndex != targetIndex &&
|
||||
sourceIndex != targetIndex + orientation);
|
||||
},
|
||||
|
||||
drop(dropIndex, orientation, dataTransfer) {
|
||||
var sourceIndex = this.getSourceIndexFromDrag(dataTransfer);
|
||||
var sourceEngine = this._engineStore.engines[sourceIndex];
|
||||
|
||||
const nsITreeView = Components.interfaces.nsITreeView;
|
||||
if (dropIndex > sourceIndex) {
|
||||
if (orientation == nsITreeView.DROP_BEFORE)
|
||||
dropIndex--;
|
||||
} else if (orientation == nsITreeView.DROP_AFTER) {
|
||||
dropIndex++;
|
||||
}
|
||||
|
||||
this._engineStore.moveEngine(sourceEngine, dropIndex);
|
||||
gSearchPane.showRestoreDefaults(true);
|
||||
gSearchPane.buildDefaultEngineDropDown();
|
||||
|
||||
// Redraw, and adjust selection
|
||||
this.invalidate();
|
||||
this.selection.select(dropIndex);
|
||||
},
|
||||
|
||||
selection: null,
|
||||
getRowProperties(index) { return ""; },
|
||||
getCellProperties(index, column) { return ""; },
|
||||
getColumnProperties(column) { return ""; },
|
||||
isContainer(index) { return false; },
|
||||
isContainerOpen(index) { return false; },
|
||||
isContainerEmpty(index) { return false; },
|
||||
isSeparator(index) { return false; },
|
||||
isSorted(index) { return false; },
|
||||
getParentIndex(index) { return -1; },
|
||||
hasNextSibling(parentIndex, index) { return false; },
|
||||
getLevel(index) { return 0; },
|
||||
getProgressMode(index, column) { },
|
||||
getCellValue(index, column) {
|
||||
if (column.id == "engineShown")
|
||||
return this._engineStore.engines[index].shown;
|
||||
return undefined;
|
||||
},
|
||||
toggleOpenState(index) { },
|
||||
cycleHeader(column) { },
|
||||
selectionChanged() { },
|
||||
cycleCell(row, column) { },
|
||||
isEditable(index, column) { return column.id != "engineName"; },
|
||||
isSelectable(index, column) { return false; },
|
||||
setCellValue(index, column, value) {
|
||||
if (column.id == "engineShown") {
|
||||
this._engineStore.engines[index].shown = value == "true";
|
||||
gEngineView.invalidate();
|
||||
gSearchPane.saveOneClickEnginesList();
|
||||
}
|
||||
},
|
||||
setCellText(index, column, value) {
|
||||
if (column.id == "engineKeyword") {
|
||||
gSearchPane.editKeyword(this._engineStore.engines[index], value)
|
||||
.then(valid => {
|
||||
if (!valid)
|
||||
document.getElementById("engineList").startEditing(index, column);
|
||||
});
|
||||
}
|
||||
},
|
||||
performAction(action) { },
|
||||
performActionOnRow(action, index) { },
|
||||
performActionOnCell(action, index, column) { }
|
||||
};
|
@ -1,87 +0,0 @@
|
||||
<preferences id="searchPreferences" hidden="true" data-category="paneSearch">
|
||||
|
||||
<preference id="browser.search.suggest.enabled"
|
||||
name="browser.search.suggest.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.urlbar.suggest.searches"
|
||||
name="browser.urlbar.suggest.searches"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.search.hiddenOneOffs"
|
||||
name="browser.search.hiddenOneOffs"
|
||||
type="unichar"/>
|
||||
|
||||
</preferences>
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content-new/search.js"/>
|
||||
|
||||
<stringbundle id="engineManagerBundle" src="chrome://browser/locale/engineManager.properties"/>
|
||||
|
||||
<hbox id="searchCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneSearch">
|
||||
<label class="header-name" flex="1">&paneSearch.title;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Default Search Engine -->
|
||||
<groupbox id="defaultEngineGroup" data-category="paneSearch">
|
||||
<caption><label>&defaultSearchEngine.label;</label></caption>
|
||||
<description>&chooseYourDefaultSearchEngine2.label;</description>
|
||||
<hbox>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<menulist id="defaultEngine">
|
||||
<menupopup/>
|
||||
</menulist>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<checkbox id="suggestionsInSearchFieldsCheckbox"
|
||||
label="&provideSearchSuggestions.label;"
|
||||
accesskey="&provideSearchSuggestions.accesskey;"
|
||||
preference="browser.search.suggest.enabled"/>
|
||||
<vbox class="indent">
|
||||
<checkbox id="urlBarSuggestion" label="&showURLBarSuggestions2.label;"
|
||||
accesskey="&showURLBarSuggestions2.accesskey;"
|
||||
preference="browser.urlbar.suggest.searches"/>
|
||||
<hbox id="urlBarSuggestionPermanentPBLabel"
|
||||
align="center" class="indent">
|
||||
<label flex="1">&urlBarSuggestionsPermanentPB.label;</label>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<groupbox id="oneClickSearchProvidersGroup" data-category="paneSearch">
|
||||
<caption><label>&oneClickSearchEngines.label;</label></caption>
|
||||
<description>&chooseWhichOneToDisplay2.label;</description>
|
||||
|
||||
<tree id="engineList" flex="1" rows="8" hidecolumnpicker="true" editable="true"
|
||||
seltype="single">
|
||||
<treechildren id="engineChildren" flex="1"/>
|
||||
<treecols>
|
||||
<treecol id="engineShown" type="checkbox" editable="true" sortable="false"/>
|
||||
<treecol id="engineName" flex="4" label="&engineNameColumn.label;" sortable="false"/>
|
||||
<treecol id="engineKeyword" flex="1" label="&engineKeywordColumn.label;" editable="true"
|
||||
sortable="false"/>
|
||||
</treecols>
|
||||
</tree>
|
||||
|
||||
<hbox>
|
||||
<button id="restoreDefaultSearchEngines"
|
||||
label="&restoreDefaultSearchEngines.label;"
|
||||
accesskey="&restoreDefaultSearchEngines.accesskey;"
|
||||
/>
|
||||
<spacer flex="1"/>
|
||||
<button id="removeEngineButton"
|
||||
class="searchEngineAction"
|
||||
label="&removeEngine.label;"
|
||||
accesskey="&removeEngine.accesskey;"
|
||||
disabled="true"
|
||||
/>
|
||||
</hbox>
|
||||
<hbox id="addEnginesBox" pack="start">
|
||||
<label id="addEngines" class="text-link">&findMoreSearchEngines.label;</label>
|
||||
</hbox>
|
||||
</groupbox>
|
@ -1,598 +0,0 @@
|
||||
/* - 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/. */
|
||||
|
||||
/* import-globals-from ../../../base/content/utilityOverlay.js */
|
||||
/* import-globals-from preferences.js */
|
||||
|
||||
"use strict";
|
||||
|
||||
/**
|
||||
* SubDialog constructor creates a new subdialog from a template and appends
|
||||
* it to the parentElement.
|
||||
* @param {DOMNode} template: The template is copied to create a new dialog.
|
||||
* @param {DOMNode} parentElement: New dialog is appended onto parentElement.
|
||||
* @param {String} id: A unique identifier for the dialog.
|
||||
*/
|
||||
function SubDialog({template, parentElement, id}) {
|
||||
this._id = id;
|
||||
|
||||
this._overlay = template.cloneNode(true);
|
||||
this._frame = this._overlay.querySelector(".dialogFrame");
|
||||
this._box = this._overlay.querySelector(".dialogBox");
|
||||
this._closeButton = this._overlay.querySelector(".dialogClose");
|
||||
this._titleElement = this._overlay.querySelector(".dialogTitle");
|
||||
|
||||
this._overlay.id = `dialogOverlay-${id}`;
|
||||
this._frame.setAttribute("name", `dialogFrame-${id}`);
|
||||
this._frameCreated = new Promise(resolve => {
|
||||
this._frame.addEventListener("load", resolve, {once: true});
|
||||
});
|
||||
|
||||
parentElement.appendChild(this._overlay);
|
||||
this._overlay.hidden = false;
|
||||
}
|
||||
|
||||
SubDialog.prototype = {
|
||||
_closingCallback: null,
|
||||
_closingEvent: null,
|
||||
_isClosing: false,
|
||||
_frame: null,
|
||||
_frameCreated: null,
|
||||
_overlay: null,
|
||||
_box: null,
|
||||
_openedURL: null,
|
||||
_injectedStyleSheets: [
|
||||
"chrome://browser/skin/preferences/preferences.css",
|
||||
"chrome://global/skin/in-content/common.css",
|
||||
"chrome://browser/skin/preferences/in-content-new/preferences.css",
|
||||
"chrome://browser/skin/preferences/in-content-new/dialog.css",
|
||||
],
|
||||
_resizeObserver: null,
|
||||
_template: null,
|
||||
_id: null,
|
||||
_titleElement: null,
|
||||
_closeButton: null,
|
||||
|
||||
updateTitle(aEvent) {
|
||||
if (aEvent.target != this._frame.contentDocument)
|
||||
return;
|
||||
this._titleElement.textContent = this._frame.contentDocument.title;
|
||||
},
|
||||
|
||||
injectXMLStylesheet(aStylesheetURL) {
|
||||
let contentStylesheet = this._frame.contentDocument.createProcessingInstruction(
|
||||
"xml-stylesheet",
|
||||
'href="' + aStylesheetURL + '" type="text/css"'
|
||||
);
|
||||
this._frame.contentDocument.insertBefore(contentStylesheet,
|
||||
this._frame.contentDocument.documentElement);
|
||||
},
|
||||
|
||||
async open(aURL, aFeatures = null, aParams = null, aClosingCallback = null) {
|
||||
// Wait until frame is ready to prevent browser crash in tests
|
||||
await this._frameCreated;
|
||||
// If we're open on some (other) URL or we're closing, open when closing has finished.
|
||||
if (this._openedURL || this._isClosing) {
|
||||
if (!this._isClosing) {
|
||||
this.close();
|
||||
}
|
||||
let args = Array.from(arguments);
|
||||
this._closingPromise.then(() => {
|
||||
this.open.apply(this, args);
|
||||
});
|
||||
return;
|
||||
}
|
||||
this._addDialogEventListeners();
|
||||
|
||||
let features = (aFeatures ? aFeatures + "," : "") + "resizable,dialog=no,centerscreen";
|
||||
let dialog = window.openDialog(aURL, `dialogFrame-${this._id}`, features, aParams);
|
||||
if (aClosingCallback) {
|
||||
this._closingCallback = aClosingCallback.bind(dialog);
|
||||
}
|
||||
|
||||
this._closingEvent = null;
|
||||
this._isClosing = false;
|
||||
this._openedURL = aURL;
|
||||
|
||||
features = features.replace(/,/g, "&");
|
||||
let featureParams = new URLSearchParams(features.toLowerCase());
|
||||
this._box.setAttribute("resizable", featureParams.has("resizable") &&
|
||||
featureParams.get("resizable") != "no" &&
|
||||
featureParams.get("resizable") != "0");
|
||||
},
|
||||
|
||||
close(aEvent = null) {
|
||||
if (this._isClosing) {
|
||||
return;
|
||||
}
|
||||
this._isClosing = true;
|
||||
this._closingPromise = new Promise(resolve => {
|
||||
this._resolveClosePromise = resolve;
|
||||
});
|
||||
|
||||
if (this._closingCallback) {
|
||||
try {
|
||||
this._closingCallback.call(null, aEvent);
|
||||
} catch (ex) {
|
||||
Cu.reportError(ex);
|
||||
}
|
||||
this._closingCallback = null;
|
||||
}
|
||||
|
||||
this._removeDialogEventListeners();
|
||||
|
||||
this._overlay.style.visibility = "";
|
||||
// Clear the sizing inline styles.
|
||||
this._frame.removeAttribute("style");
|
||||
// Clear the sizing attributes
|
||||
this._box.removeAttribute("width");
|
||||
this._box.removeAttribute("height");
|
||||
this._box.style.removeProperty("min-height");
|
||||
this._box.style.removeProperty("min-width");
|
||||
|
||||
this._overlay.dispatchEvent(new CustomEvent("dialogclose", {
|
||||
bubbles: true,
|
||||
detail: { dialog: this },
|
||||
}));
|
||||
|
||||
setTimeout(() => {
|
||||
// Unload the dialog after the event listeners run so that the load of about:blank isn't
|
||||
// cancelled by the ESC <key>.
|
||||
let onBlankLoad = e => {
|
||||
if (this._frame.contentWindow.location.href == "about:blank") {
|
||||
this._frame.removeEventListener("load", onBlankLoad);
|
||||
// We're now officially done closing, so update the state to reflect that.
|
||||
this._openedURL = null;
|
||||
this._isClosing = false;
|
||||
this._resolveClosePromise();
|
||||
}
|
||||
};
|
||||
this._frame.addEventListener("load", onBlankLoad);
|
||||
this._frame.loadURI("about:blank");
|
||||
}, 0);
|
||||
},
|
||||
|
||||
handleEvent(aEvent) {
|
||||
switch (aEvent.type) {
|
||||
case "click":
|
||||
// Close the dialog if the user clicked the overlay background, just
|
||||
// like when the user presses the ESC key (case "command" below).
|
||||
if (aEvent.target === this._overlay) {
|
||||
this._frame.contentWindow.close();
|
||||
}
|
||||
break;
|
||||
case "command":
|
||||
this._frame.contentWindow.close();
|
||||
break;
|
||||
case "dialogclosing":
|
||||
this._onDialogClosing(aEvent);
|
||||
break;
|
||||
case "DOMTitleChanged":
|
||||
this.updateTitle(aEvent);
|
||||
break;
|
||||
case "DOMFrameContentLoaded":
|
||||
this._onContentLoaded(aEvent);
|
||||
break;
|
||||
case "load":
|
||||
this._onLoad(aEvent);
|
||||
break;
|
||||
case "unload":
|
||||
this._onUnload(aEvent);
|
||||
break;
|
||||
case "keydown":
|
||||
this._onKeyDown(aEvent);
|
||||
break;
|
||||
case "focus":
|
||||
this._onParentWinFocus(aEvent);
|
||||
break;
|
||||
}
|
||||
},
|
||||
|
||||
/* Private methods */
|
||||
|
||||
_onUnload(aEvent) {
|
||||
if (aEvent.target.location.href == this._openedURL) {
|
||||
this._frame.contentWindow.close();
|
||||
}
|
||||
},
|
||||
|
||||
_onContentLoaded(aEvent) {
|
||||
if (aEvent.target != this._frame || aEvent.target.contentWindow.location == "about:blank") {
|
||||
return;
|
||||
}
|
||||
|
||||
for (let styleSheetURL of this._injectedStyleSheets) {
|
||||
this.injectXMLStylesheet(styleSheetURL);
|
||||
}
|
||||
|
||||
// Provide the ability for the dialog to know that it is being loaded "in-content".
|
||||
this._frame.contentDocument.documentElement.setAttribute("subdialog", "true");
|
||||
|
||||
this._frame.contentWindow.addEventListener("dialogclosing", this);
|
||||
|
||||
let oldResizeBy = this._frame.contentWindow.resizeBy;
|
||||
this._frame.contentWindow.resizeBy = (resizeByWidth, resizeByHeight) => {
|
||||
// Only handle resizeByHeight currently.
|
||||
let frameHeight = this._frame.clientHeight;
|
||||
let boxMinHeight = parseFloat(getComputedStyle(this._box).minHeight, 10);
|
||||
|
||||
this._frame.style.height = (frameHeight + resizeByHeight) + "px";
|
||||
this._box.style.minHeight = (boxMinHeight + resizeByHeight) + "px";
|
||||
|
||||
oldResizeBy.call(this._frame.contentWindow, resizeByWidth, resizeByHeight);
|
||||
};
|
||||
|
||||
// Make window.close calls work like dialog closing.
|
||||
let oldClose = this._frame.contentWindow.close;
|
||||
this._frame.contentWindow.close = () => {
|
||||
var closingEvent = this._closingEvent;
|
||||
if (!closingEvent) {
|
||||
closingEvent = new CustomEvent("dialogclosing", {
|
||||
bubbles: true,
|
||||
detail: { button: null },
|
||||
});
|
||||
|
||||
this._frame.contentWindow.dispatchEvent(closingEvent);
|
||||
}
|
||||
|
||||
this.close(closingEvent);
|
||||
oldClose.call(this._frame.contentWindow);
|
||||
};
|
||||
|
||||
// XXX: Hack to make focus during the dialog's load functions work. Make the element visible
|
||||
// sooner in DOMContentLoaded but mostly invisible instead of changing visibility just before
|
||||
// the dialog's load event.
|
||||
this._overlay.style.visibility = "visible";
|
||||
this._overlay.style.opacity = "0.01";
|
||||
},
|
||||
|
||||
_onLoad(aEvent) {
|
||||
if (aEvent.target.contentWindow.location == "about:blank") {
|
||||
return;
|
||||
}
|
||||
|
||||
// Do this on load to wait for the CSS to load and apply before calculating the size.
|
||||
let docEl = this._frame.contentDocument.documentElement;
|
||||
|
||||
let groupBoxTitle = document.getAnonymousElementByAttribute(this._box, "class", "groupbox-title");
|
||||
let groupBoxTitleHeight = groupBoxTitle.clientHeight +
|
||||
parseFloat(getComputedStyle(groupBoxTitle).borderBottomWidth);
|
||||
|
||||
let groupBoxBody = document.getAnonymousElementByAttribute(this._box, "class", "groupbox-body");
|
||||
// These are deduced from styles which we don't change, so it's safe to get them now:
|
||||
let boxVerticalPadding = 2 * parseFloat(getComputedStyle(groupBoxBody).paddingTop);
|
||||
let boxHorizontalPadding = 2 * parseFloat(getComputedStyle(groupBoxBody).paddingLeft);
|
||||
let boxHorizontalBorder = 2 * parseFloat(getComputedStyle(this._box).borderLeftWidth);
|
||||
let boxVerticalBorder = 2 * parseFloat(getComputedStyle(this._box).borderTopWidth);
|
||||
|
||||
// The difference between the frame and box shouldn't change, either:
|
||||
let boxRect = this._box.getBoundingClientRect();
|
||||
let frameRect = this._frame.getBoundingClientRect();
|
||||
let frameSizeDifference = (frameRect.top - boxRect.top) + (boxRect.bottom - frameRect.bottom);
|
||||
|
||||
// Then determine and set a bunch of width stuff:
|
||||
let frameMinWidth = docEl.style.width || docEl.scrollWidth + "px";
|
||||
let frameWidth = docEl.getAttribute("width") ? docEl.getAttribute("width") + "px" :
|
||||
frameMinWidth;
|
||||
this._frame.style.width = frameWidth;
|
||||
this._box.style.minWidth = "calc(" +
|
||||
(boxHorizontalBorder + boxHorizontalPadding) +
|
||||
"px + " + frameMinWidth + ")";
|
||||
|
||||
// Now do the same but for the height. We need to do this afterwards because otherwise
|
||||
// XUL assumes we'll optimize for height and gives us "wrong" values which then are no
|
||||
// longer correct after we set the width:
|
||||
let frameMinHeight = docEl.style.height || docEl.scrollHeight + "px";
|
||||
let frameHeight = docEl.getAttribute("height") ? docEl.getAttribute("height") + "px" :
|
||||
frameMinHeight;
|
||||
|
||||
// Now check if the frame height we calculated is possible at this window size,
|
||||
// accounting for titlebar, padding/border and some spacing.
|
||||
let maxHeight = window.innerHeight - frameSizeDifference - 30;
|
||||
// Do this with a frame height in pixels...
|
||||
let comparisonFrameHeight;
|
||||
if (frameHeight.endsWith("em")) {
|
||||
let fontSize = parseFloat(getComputedStyle(this._frame).fontSize);
|
||||
comparisonFrameHeight = parseFloat(frameHeight, 10) * fontSize;
|
||||
} else if (frameHeight.endsWith("px")) {
|
||||
comparisonFrameHeight = parseFloat(frameHeight, 10);
|
||||
} else {
|
||||
Cu.reportError("This dialog (" + this._frame.contentWindow.location.href + ") " +
|
||||
"set a height in non-px-non-em units ('" + frameHeight + "'), " +
|
||||
"which is likely to lead to bad sizing in in-content preferences. " +
|
||||
"Please consider changing this.");
|
||||
comparisonFrameHeight = parseFloat(frameHeight);
|
||||
}
|
||||
|
||||
if (comparisonFrameHeight > maxHeight) {
|
||||
// If the height is bigger than that of the window, we should let the contents scroll:
|
||||
frameHeight = maxHeight + "px";
|
||||
frameMinHeight = maxHeight + "px";
|
||||
let containers = this._frame.contentDocument.querySelectorAll(".largeDialogContainer");
|
||||
for (let container of containers) {
|
||||
container.classList.add("doScroll");
|
||||
}
|
||||
}
|
||||
|
||||
this._frame.style.height = frameHeight;
|
||||
this._box.style.minHeight = "calc(" +
|
||||
(boxVerticalBorder + groupBoxTitleHeight + boxVerticalPadding) +
|
||||
"px + " + frameMinHeight + ")";
|
||||
|
||||
this._overlay.dispatchEvent(new CustomEvent("dialogopen", {
|
||||
bubbles: true,
|
||||
detail: { dialog: this },
|
||||
}));
|
||||
this._overlay.style.visibility = "visible";
|
||||
this._overlay.style.opacity = ""; // XXX: focus hack continued from _onContentLoaded
|
||||
|
||||
if (this._box.getAttribute("resizable") == "true") {
|
||||
this._onResize = this._onResize.bind(this);
|
||||
this._resizeObserver = new MutationObserver(this._onResize);
|
||||
this._resizeObserver.observe(this._box, {attributes: true});
|
||||
}
|
||||
|
||||
this._trapFocus();
|
||||
|
||||
// Search within main document and highlight matched keyword.
|
||||
gSearchResultsPane.searchWithinNode(this._titleElement, gSearchResultsPane.query);
|
||||
|
||||
// Search within sub-dialog document and highlight matched keyword.
|
||||
gSearchResultsPane.searchWithinNode(this._frame.contentDocument.firstElementChild,
|
||||
gSearchResultsPane.query);
|
||||
|
||||
// Creating tooltips for all the instances found
|
||||
for (let node of gSearchResultsPane.listSearchTooltips) {
|
||||
if (!node.tooltipNode) {
|
||||
gSearchResultsPane.createSearchTooltip(node, gSearchResultsPane.query);
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
_onResize(mutations) {
|
||||
let frame = this._frame;
|
||||
// The width and height styles are needed for the initial
|
||||
// layout of the frame, but afterward they need to be removed
|
||||
// or their presence will restrict the contents of the <browser>
|
||||
// from resizing to a smaller size.
|
||||
frame.style.removeProperty("width");
|
||||
frame.style.removeProperty("height");
|
||||
|
||||
let docEl = frame.contentDocument.documentElement;
|
||||
let persistedAttributes = docEl.getAttribute("persist");
|
||||
if (!persistedAttributes ||
|
||||
(!persistedAttributes.includes("width") &&
|
||||
!persistedAttributes.includes("height"))) {
|
||||
return;
|
||||
}
|
||||
|
||||
for (let mutation of mutations) {
|
||||
if (mutation.attributeName == "width") {
|
||||
docEl.setAttribute("width", docEl.scrollWidth);
|
||||
} else if (mutation.attributeName == "height") {
|
||||
docEl.setAttribute("height", docEl.scrollHeight);
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
_onDialogClosing(aEvent) {
|
||||
this._frame.contentWindow.removeEventListener("dialogclosing", this);
|
||||
this._closingEvent = aEvent;
|
||||
},
|
||||
|
||||
_onKeyDown(aEvent) {
|
||||
if (aEvent.currentTarget == window && aEvent.keyCode == aEvent.DOM_VK_ESCAPE &&
|
||||
!aEvent.defaultPrevented) {
|
||||
this.close(aEvent);
|
||||
return;
|
||||
}
|
||||
if (aEvent.keyCode != aEvent.DOM_VK_TAB ||
|
||||
aEvent.ctrlKey || aEvent.altKey || aEvent.metaKey) {
|
||||
return;
|
||||
}
|
||||
|
||||
let fm = Services.focus;
|
||||
|
||||
let isLastFocusableElement = el => {
|
||||
// XXXgijs unfortunately there is no way to get the last focusable element without asking
|
||||
// the focus manager to move focus to it.
|
||||
let rv = el == fm.moveFocus(this._frame.contentWindow, null, fm.MOVEFOCUS_LAST, 0);
|
||||
fm.setFocus(el, 0);
|
||||
return rv;
|
||||
};
|
||||
|
||||
let forward = !aEvent.shiftKey;
|
||||
// check if focus is leaving the frame (incl. the close button):
|
||||
if ((aEvent.target == this._closeButton && !forward) ||
|
||||
(isLastFocusableElement(aEvent.originalTarget) && forward)) {
|
||||
aEvent.preventDefault();
|
||||
aEvent.stopImmediatePropagation();
|
||||
let parentWin = this._getBrowser().ownerGlobal;
|
||||
if (forward) {
|
||||
fm.moveFocus(parentWin, null, fm.MOVEFOCUS_FIRST, fm.FLAG_BYKEY);
|
||||
} else {
|
||||
// Somehow, moving back 'past' the opening doc is not trivial. Cheat by doing it in 2 steps:
|
||||
fm.moveFocus(window, null, fm.MOVEFOCUS_ROOT, fm.FLAG_BYKEY);
|
||||
fm.moveFocus(parentWin, null, fm.MOVEFOCUS_BACKWARD, fm.FLAG_BYKEY);
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
_onParentWinFocus(aEvent) {
|
||||
// Explicitly check for the focus target of |window| to avoid triggering this when the window
|
||||
// is refocused
|
||||
if (aEvent.target != this._closeButton && aEvent.target != window) {
|
||||
this._closeButton.focus();
|
||||
}
|
||||
},
|
||||
|
||||
_addDialogEventListeners() {
|
||||
// Make the close button work.
|
||||
this._closeButton.addEventListener("command", this);
|
||||
|
||||
// DOMTitleChanged isn't fired on the frame, only on the chromeEventHandler
|
||||
let chromeBrowser = this._getBrowser();
|
||||
chromeBrowser.addEventListener("DOMTitleChanged", this, true);
|
||||
|
||||
// Similarly DOMFrameContentLoaded only fires on the top window
|
||||
window.addEventListener("DOMFrameContentLoaded", this, true);
|
||||
|
||||
// Wait for the stylesheets injected during DOMContentLoaded to load before showing the dialog
|
||||
// otherwise there is a flicker of the stylesheet applying.
|
||||
this._frame.addEventListener("load", this);
|
||||
|
||||
chromeBrowser.addEventListener("unload", this, true);
|
||||
|
||||
// Ensure we get <esc> keypresses even if nothing in the subdialog is focusable
|
||||
// (happens on OS X when only text inputs and lists are focusable, and
|
||||
// the subdialog only has checkboxes/radiobuttons/buttons)
|
||||
window.addEventListener("keydown", this, true);
|
||||
|
||||
this._overlay.addEventListener("click", this, true);
|
||||
},
|
||||
|
||||
_removeDialogEventListeners() {
|
||||
let chromeBrowser = this._getBrowser();
|
||||
chromeBrowser.removeEventListener("DOMTitleChanged", this, true);
|
||||
chromeBrowser.removeEventListener("unload", this, true);
|
||||
|
||||
this._closeButton.removeEventListener("command", this);
|
||||
|
||||
window.removeEventListener("DOMFrameContentLoaded", this, true);
|
||||
this._frame.removeEventListener("load", this);
|
||||
this._frame.contentWindow.removeEventListener("dialogclosing", this);
|
||||
window.removeEventListener("keydown", this, true);
|
||||
|
||||
this._overlay.removeEventListener("click", this, true);
|
||||
|
||||
if (this._resizeObserver) {
|
||||
this._resizeObserver.disconnect();
|
||||
this._resizeObserver = null;
|
||||
}
|
||||
this._untrapFocus();
|
||||
},
|
||||
|
||||
_trapFocus() {
|
||||
let fm = Services.focus;
|
||||
fm.moveFocus(this._frame.contentWindow, null, fm.MOVEFOCUS_FIRST, 0);
|
||||
this._frame.contentDocument.addEventListener("keydown", this, true);
|
||||
this._closeButton.addEventListener("keydown", this);
|
||||
|
||||
window.addEventListener("focus", this, true);
|
||||
},
|
||||
|
||||
_untrapFocus() {
|
||||
this._frame.contentDocument.removeEventListener("keydown", this, true);
|
||||
this._closeButton.removeEventListener("keydown", this);
|
||||
window.removeEventListener("focus", this);
|
||||
},
|
||||
|
||||
_getBrowser() {
|
||||
return window.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIWebNavigation)
|
||||
.QueryInterface(Ci.nsIDocShell)
|
||||
.chromeEventHandler;
|
||||
},
|
||||
};
|
||||
|
||||
var gSubDialog = {
|
||||
/**
|
||||
* New dialogs are stacked on top of the existing ones, and they are pushed
|
||||
* to the end of the _dialogs array.
|
||||
* @type {Array}
|
||||
*/
|
||||
_dialogs: [],
|
||||
_dialogStack: null,
|
||||
_dialogTemplate: null,
|
||||
_nextDialogID: 0,
|
||||
_preloadDialog: null,
|
||||
get _topDialog() {
|
||||
return this._dialogs.length > 0 ? this._dialogs[this._dialogs.length - 1] : undefined;
|
||||
},
|
||||
|
||||
init() {
|
||||
this._dialogStack = document.getElementById("dialogStack");
|
||||
this._dialogTemplate = document.getElementById("dialogTemplate");
|
||||
this._preloadDialog = new SubDialog({template: this._dialogTemplate,
|
||||
parentElement: this._dialogStack,
|
||||
id: this._nextDialogID++});
|
||||
},
|
||||
|
||||
open(aURL, aFeatures = null, aParams = null, aClosingCallback = null) {
|
||||
// If we're already open/opening on this URL, do nothing.
|
||||
if (this._topDialog && this._topDialog._openedURL == aURL) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._preloadDialog.open(aURL, aFeatures, aParams, aClosingCallback);
|
||||
this._dialogs.push(this._preloadDialog);
|
||||
this._preloadDialog = new SubDialog({template: this._dialogTemplate,
|
||||
parentElement: this._dialogStack,
|
||||
id: this._nextDialogID++});
|
||||
|
||||
if (this._dialogs.length == 1) {
|
||||
this._dialogStack.hidden = false;
|
||||
this._ensureStackEventListeners();
|
||||
}
|
||||
},
|
||||
|
||||
close() {
|
||||
this._topDialog.close();
|
||||
},
|
||||
|
||||
handleEvent(aEvent) {
|
||||
switch (aEvent.type) {
|
||||
case "dialogopen": {
|
||||
this._onDialogOpen();
|
||||
break;
|
||||
}
|
||||
case "dialogclose": {
|
||||
this._onDialogClose(aEvent.detail.dialog);
|
||||
break;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
_onDialogOpen() {
|
||||
let lowerDialog = this._dialogs.length > 1 ? this._dialogs[this._dialogs.length - 2] : undefined;
|
||||
if (lowerDialog) {
|
||||
lowerDialog._overlay.removeAttribute("topmost");
|
||||
lowerDialog._removeDialogEventListeners();
|
||||
}
|
||||
},
|
||||
|
||||
_onDialogClose(dialog) {
|
||||
let fm = Services.focus;
|
||||
if (this._topDialog == dialog) {
|
||||
// XXX: When a top-most dialog is closed, we reuse the closed dialog and
|
||||
// remove the preloadDialog. This is a temporary solution before we
|
||||
// rewrite all the test cases in Bug 1359023.
|
||||
this._preloadDialog._overlay.remove();
|
||||
this._preloadDialog = this._dialogs.pop();
|
||||
} else {
|
||||
dialog._overlay.remove();
|
||||
this._dialogs.splice(this._dialogs.indexOf(dialog), 1);
|
||||
}
|
||||
|
||||
if (this._topDialog) {
|
||||
fm.moveFocus(this._topDialog._frame.contentWindow, null, fm.MOVEFOCUS_FIRST, fm.FLAG_BYKEY);
|
||||
this._topDialog._overlay.setAttribute("topmost", true);
|
||||
this._topDialog._addDialogEventListeners();
|
||||
} else {
|
||||
fm.moveFocus(window, null, fm.MOVEFOCUS_ROOT, fm.FLAG_BYKEY);
|
||||
this._dialogStack.hidden = true;
|
||||
this._removeStackEventListeners();
|
||||
}
|
||||
},
|
||||
|
||||
_ensureStackEventListeners() {
|
||||
this._dialogStack.addEventListener("dialogopen", this);
|
||||
this._dialogStack.addEventListener("dialogclose", this);
|
||||
},
|
||||
|
||||
_removeStackEventListeners() {
|
||||
this._dialogStack.removeEventListener("dialogopen", this);
|
||||
this._dialogStack.removeEventListener("dialogclose", this);
|
||||
},
|
||||
};
|
@ -1,514 +0,0 @@
|
||||
/* 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/. */
|
||||
|
||||
/* import-globals-from preferences.js */
|
||||
|
||||
Components.utils.import("resource://services-sync/main.js");
|
||||
Components.utils.import("resource://gre/modules/Services.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "FxAccountsCommon", function() {
|
||||
return Components.utils.import("resource://gre/modules/FxAccountsCommon.js", {});
|
||||
});
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "fxAccounts",
|
||||
"resource://gre/modules/FxAccounts.jsm");
|
||||
|
||||
const FXA_PAGE_LOGGED_OUT = 0;
|
||||
const FXA_PAGE_LOGGED_IN = 1;
|
||||
|
||||
// Indexes into the "login status" deck.
|
||||
// We are in a successful verified state - everything should work!
|
||||
const FXA_LOGIN_VERIFIED = 0;
|
||||
// We have logged in to an unverified account.
|
||||
const FXA_LOGIN_UNVERIFIED = 1;
|
||||
// We are logged in locally, but the server rejected our credentials.
|
||||
const FXA_LOGIN_FAILED = 2;
|
||||
|
||||
var gSyncPane = {
|
||||
get page() {
|
||||
return document.getElementById("weavePrefsDeck").selectedIndex;
|
||||
},
|
||||
|
||||
set page(val) {
|
||||
document.getElementById("weavePrefsDeck").selectedIndex = val;
|
||||
},
|
||||
|
||||
init() {
|
||||
this._setupEventListeners();
|
||||
this._adjustForPrefs();
|
||||
|
||||
// If the Service hasn't finished initializing, wait for it.
|
||||
let xps = Components.classes["@mozilla.org/weave/service;1"]
|
||||
.getService(Components.interfaces.nsISupports)
|
||||
.wrappedJSObject;
|
||||
|
||||
if (xps.ready) {
|
||||
this._init();
|
||||
return;
|
||||
}
|
||||
|
||||
// it may take some time before we can determine what provider to use
|
||||
// and the state of that provider, so show the "please wait" page.
|
||||
this._showLoadPage(xps);
|
||||
|
||||
let onUnload = function() {
|
||||
window.removeEventListener("unload", onUnload);
|
||||
try {
|
||||
Services.obs.removeObserver(onReady, "weave:service:ready");
|
||||
} catch (e) {}
|
||||
};
|
||||
|
||||
let onReady = () => {
|
||||
Services.obs.removeObserver(onReady, "weave:service:ready");
|
||||
window.removeEventListener("unload", onUnload);
|
||||
this._init();
|
||||
};
|
||||
|
||||
Services.obs.addObserver(onReady, "weave:service:ready");
|
||||
window.addEventListener("unload", onUnload);
|
||||
|
||||
xps.ensureLoaded();
|
||||
},
|
||||
|
||||
// make whatever tweaks we need based on preferences.
|
||||
_adjustForPrefs() {
|
||||
// These 2 engines are unique in that there are prefs that make the
|
||||
// entire engine unavailable (which is distinct from "disabled").
|
||||
let enginePrefs = [
|
||||
["services.sync.engine.addresses.available", "engine.addresses"],
|
||||
["services.sync.engine.creditcards.available", "engine.creditcards"],
|
||||
];
|
||||
let numHidden = 0;
|
||||
for (let [availablePref, prefName] of enginePrefs) {
|
||||
if (!Services.prefs.getBoolPref(availablePref)) {
|
||||
let checkbox = document.querySelector("[preference=\"" + prefName + "\"]");
|
||||
checkbox.hidden = true;
|
||||
numHidden += 1;
|
||||
}
|
||||
}
|
||||
// If we hid both, the list of prefs is unbalanced, so move "history" to
|
||||
// the second column. (If we only moved one, it's still unbalanced, but
|
||||
// there's an odd number of engines so that can't be avoided)
|
||||
if (numHidden == 2) {
|
||||
let history = document.querySelector("[preference=\"engine.history\"]");
|
||||
let addons = document.querySelector("[preference=\"engine.addons\"]");
|
||||
addons.parentNode.insertBefore(history, addons);
|
||||
}
|
||||
},
|
||||
|
||||
_showLoadPage(xps) {
|
||||
let username = Services.prefs.getCharPref("services.sync.username", "");
|
||||
if (!username) {
|
||||
this.page = FXA_PAGE_LOGGED_OUT;
|
||||
return;
|
||||
}
|
||||
|
||||
// Use cached values while we wait for the up-to-date values
|
||||
let cachedComputerName = Services.prefs.getCharPref("services.sync.client.name", "");
|
||||
document.querySelector(".fxaEmailAddress").value = username;
|
||||
this._populateComputerName(cachedComputerName);
|
||||
this.page = FXA_PAGE_LOGGED_IN;
|
||||
},
|
||||
|
||||
_init() {
|
||||
let topics = ["weave:service:login:error",
|
||||
"weave:service:login:finish",
|
||||
"weave:service:start-over:finish",
|
||||
"weave:service:setup-complete",
|
||||
"weave:service:logout:finish",
|
||||
FxAccountsCommon.ONVERIFIED_NOTIFICATION,
|
||||
FxAccountsCommon.ONLOGIN_NOTIFICATION,
|
||||
FxAccountsCommon.ON_ACCOUNT_STATE_CHANGE_NOTIFICATION,
|
||||
FxAccountsCommon.ON_PROFILE_CHANGE_NOTIFICATION,
|
||||
];
|
||||
// Add the observers now and remove them on unload
|
||||
// XXXzpao This should use Services.obs.* but Weave's Obs does nice handling
|
||||
// of `this`. Fix in a followup. (bug 583347)
|
||||
topics.forEach(function(topic) {
|
||||
Weave.Svc.Obs.add(topic, this.updateWeavePrefs, this);
|
||||
}, this);
|
||||
|
||||
window.addEventListener("unload", function() {
|
||||
topics.forEach(function(topic) {
|
||||
Weave.Svc.Obs.remove(topic, this.updateWeavePrefs, this);
|
||||
}, gSyncPane);
|
||||
});
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "_accountsStringBundle", () => {
|
||||
return Services.strings.createBundle("chrome://browser/locale/accounts.properties");
|
||||
});
|
||||
|
||||
let url = Services.prefs.getCharPref("identity.mobilepromo.android") + "sync-preferences";
|
||||
document.getElementById("fxaMobilePromo-android").setAttribute("href", url);
|
||||
document.getElementById("fxaMobilePromo-android-hasFxaAccount").setAttribute("href", url);
|
||||
url = Services.prefs.getCharPref("identity.mobilepromo.ios") + "sync-preferences";
|
||||
document.getElementById("fxaMobilePromo-ios").setAttribute("href", url);
|
||||
document.getElementById("fxaMobilePromo-ios-hasFxaAccount").setAttribute("href", url);
|
||||
|
||||
document.getElementById("tosPP-small-ToS").setAttribute("href", Weave.Svc.Prefs.get("fxa.termsURL"));
|
||||
document.getElementById("tosPP-small-PP").setAttribute("href", Weave.Svc.Prefs.get("fxa.privacyURL"));
|
||||
|
||||
fxAccounts.promiseAccountsManageURI(this._getEntryPoint()).then(accountsManageURI => {
|
||||
document.getElementById("verifiedManage").setAttribute("href", accountsManageURI);
|
||||
});
|
||||
|
||||
this.updateWeavePrefs();
|
||||
|
||||
// Notify observers that the UI is now ready
|
||||
Components.classes["@mozilla.org/observer-service;1"]
|
||||
.getService(Components.interfaces.nsIObserverService)
|
||||
.notifyObservers(window, "sync-pane-loaded");
|
||||
},
|
||||
|
||||
_toggleComputerNameControls(editMode) {
|
||||
let textbox = document.getElementById("fxaSyncComputerName");
|
||||
textbox.disabled = !editMode;
|
||||
document.getElementById("fxaChangeDeviceName").hidden = editMode;
|
||||
document.getElementById("fxaCancelChangeDeviceName").hidden = !editMode;
|
||||
document.getElementById("fxaSaveChangeDeviceName").hidden = !editMode;
|
||||
},
|
||||
|
||||
_focusComputerNameTextbox() {
|
||||
let textbox = document.getElementById("fxaSyncComputerName");
|
||||
let valLength = textbox.value.length;
|
||||
textbox.focus();
|
||||
textbox.setSelectionRange(valLength, valLength);
|
||||
},
|
||||
|
||||
_blurComputerNameTextbox() {
|
||||
document.getElementById("fxaSyncComputerName").blur();
|
||||
},
|
||||
|
||||
_focusAfterComputerNameTextbox() {
|
||||
// Focus the most appropriate element that's *not* the "computer name" box.
|
||||
Services.focus.moveFocus(window,
|
||||
document.getElementById("fxaSyncComputerName"),
|
||||
Services.focus.MOVEFOCUS_FORWARD, 0);
|
||||
},
|
||||
|
||||
_updateComputerNameValue(save) {
|
||||
if (save) {
|
||||
let textbox = document.getElementById("fxaSyncComputerName");
|
||||
Weave.Service.clientsEngine.localName = textbox.value;
|
||||
}
|
||||
this._populateComputerName(Weave.Service.clientsEngine.localName);
|
||||
},
|
||||
|
||||
_setupEventListeners() {
|
||||
function setEventListener(aId, aEventType, aCallback) {
|
||||
document.getElementById(aId)
|
||||
.addEventListener(aEventType, aCallback.bind(gSyncPane));
|
||||
}
|
||||
|
||||
setEventListener("fxaChangeDeviceName", "command", function() {
|
||||
this._toggleComputerNameControls(true);
|
||||
this._focusComputerNameTextbox();
|
||||
});
|
||||
setEventListener("fxaCancelChangeDeviceName", "command", function() {
|
||||
// We explicitly blur the textbox because of bug 75324, then after
|
||||
// changing the state of the buttons, force focus to whatever the focus
|
||||
// manager thinks should be next (which on the mac, depends on an OSX
|
||||
// keyboard access preference)
|
||||
this._blurComputerNameTextbox();
|
||||
this._toggleComputerNameControls(false);
|
||||
this._updateComputerNameValue(false);
|
||||
this._focusAfterComputerNameTextbox();
|
||||
});
|
||||
setEventListener("fxaSaveChangeDeviceName", "command", function() {
|
||||
// Work around bug 75324 - see above.
|
||||
this._blurComputerNameTextbox();
|
||||
this._toggleComputerNameControls(false);
|
||||
this._updateComputerNameValue(true);
|
||||
this._focusAfterComputerNameTextbox();
|
||||
});
|
||||
setEventListener("noFxaSignIn", "command", function() {
|
||||
gSyncPane.signIn();
|
||||
return false;
|
||||
});
|
||||
setEventListener("fxaUnlinkButton", "command", function() {
|
||||
gSyncPane.unlinkFirefoxAccount(true);
|
||||
});
|
||||
setEventListener("verifyFxaAccount", "command",
|
||||
gSyncPane.verifyFirefoxAccount);
|
||||
setEventListener("unverifiedUnlinkFxaAccount", "command", function() {
|
||||
/* no warning as account can't have previously synced */
|
||||
gSyncPane.unlinkFirefoxAccount(false);
|
||||
});
|
||||
setEventListener("rejectReSignIn", "command",
|
||||
gSyncPane.reSignIn);
|
||||
setEventListener("rejectUnlinkFxaAccount", "command", function() {
|
||||
gSyncPane.unlinkFirefoxAccount(true);
|
||||
});
|
||||
setEventListener("fxaSyncComputerName", "keypress", function(e) {
|
||||
if (e.keyCode == KeyEvent.DOM_VK_RETURN) {
|
||||
document.getElementById("fxaSaveChangeDeviceName").click();
|
||||
} else if (e.keyCode == KeyEvent.DOM_VK_ESCAPE) {
|
||||
document.getElementById("fxaCancelChangeDeviceName").click();
|
||||
}
|
||||
});
|
||||
},
|
||||
|
||||
updateWeavePrefs() {
|
||||
let service = Components.classes["@mozilla.org/weave/service;1"]
|
||||
.getService(Components.interfaces.nsISupports)
|
||||
.wrappedJSObject;
|
||||
|
||||
let displayNameLabel = document.getElementById("fxaDisplayName");
|
||||
let fxaEmailAddressLabels = document.querySelectorAll(".fxaEmailAddress");
|
||||
displayNameLabel.hidden = true;
|
||||
|
||||
// determine the fxa status...
|
||||
this._showLoadPage(service);
|
||||
|
||||
fxAccounts.getSignedInUser().then(data => {
|
||||
if (!data) {
|
||||
this.page = FXA_PAGE_LOGGED_OUT;
|
||||
return false;
|
||||
}
|
||||
this.page = FXA_PAGE_LOGGED_IN;
|
||||
// We are logged in locally, but maybe we are in a state where the
|
||||
// server rejected our credentials (eg, password changed on the server)
|
||||
let fxaLoginStatus = document.getElementById("fxaLoginStatus");
|
||||
let syncReady;
|
||||
// Not Verfied implies login error state, so check that first.
|
||||
if (!data.verified) {
|
||||
fxaLoginStatus.selectedIndex = FXA_LOGIN_UNVERIFIED;
|
||||
syncReady = false;
|
||||
// So we think we are logged in, so login problems are next.
|
||||
// (Although if the Sync identity manager is still initializing, we
|
||||
// ignore login errors and assume all will eventually be good.)
|
||||
// LOGIN_FAILED_LOGIN_REJECTED explicitly means "you must log back in".
|
||||
// All other login failures are assumed to be transient and should go
|
||||
// away by themselves, so aren't reflected here.
|
||||
} else if (Weave.Status.login == Weave.LOGIN_FAILED_LOGIN_REJECTED) {
|
||||
fxaLoginStatus.selectedIndex = FXA_LOGIN_FAILED;
|
||||
syncReady = false;
|
||||
// Else we must be golden (or in an error state we expect to magically
|
||||
// resolve itself)
|
||||
} else {
|
||||
fxaLoginStatus.selectedIndex = FXA_LOGIN_VERIFIED;
|
||||
syncReady = true;
|
||||
}
|
||||
fxaEmailAddressLabels.forEach((label) => {
|
||||
label.value = data.email;
|
||||
});
|
||||
this._populateComputerName(Weave.Service.clientsEngine.localName);
|
||||
let engines = document.getElementById("fxaSyncEngines")
|
||||
for (let checkbox of engines.querySelectorAll("checkbox")) {
|
||||
checkbox.disabled = !syncReady;
|
||||
}
|
||||
document.getElementById("fxaChangeDeviceName").disabled = !syncReady;
|
||||
|
||||
// Clear the profile image (if any) of the previously logged in account.
|
||||
document.querySelector("#fxaLoginVerified > .fxaProfileImage").style.removeProperty("list-style-image");
|
||||
|
||||
// If the account is verified the next promise in the chain will
|
||||
// fetch profile data.
|
||||
return data.verified;
|
||||
}).then(isVerified => {
|
||||
if (isVerified) {
|
||||
return fxAccounts.getSignedInUserProfile();
|
||||
}
|
||||
return null;
|
||||
}).then(data => {
|
||||
let fxaLoginStatus = document.getElementById("fxaLoginStatus");
|
||||
if (data) {
|
||||
if (data.email) {
|
||||
// A hack to handle that the user's email address may have changed.
|
||||
// This can probably be removed as part of bug 1383663.
|
||||
fxaEmailAddressLabels.forEach((label) => {
|
||||
label.value = data.email;
|
||||
});
|
||||
}
|
||||
if (data.displayName) {
|
||||
fxaLoginStatus.setAttribute("hasName", true);
|
||||
displayNameLabel.hidden = false;
|
||||
displayNameLabel.textContent = data.displayName;
|
||||
} else {
|
||||
fxaLoginStatus.removeAttribute("hasName");
|
||||
}
|
||||
if (data.avatar) {
|
||||
let bgImage = "url(\"" + data.avatar + "\")";
|
||||
let profileImageElement = document.querySelector("#fxaLoginVerified > .fxaProfileImage");
|
||||
profileImageElement.style.listStyleImage = bgImage;
|
||||
|
||||
let img = new Image();
|
||||
img.onerror = () => {
|
||||
// Clear the image if it has trouble loading. Since this callback is asynchronous
|
||||
// we check to make sure the image is still the same before we clear it.
|
||||
if (profileImageElement.style.listStyleImage === bgImage) {
|
||||
profileImageElement.style.removeProperty("list-style-image");
|
||||
}
|
||||
};
|
||||
img.src = data.avatar;
|
||||
}
|
||||
} else {
|
||||
fxaLoginStatus.removeAttribute("hasName");
|
||||
}
|
||||
}, err => {
|
||||
FxAccountsCommon.log.error(err);
|
||||
}).catch(err => {
|
||||
// If we get here something's really busted
|
||||
Cu.reportError(String(err));
|
||||
});
|
||||
},
|
||||
|
||||
_getEntryPoint() {
|
||||
let params = new URLSearchParams(document.URL.split("#")[0].split("?")[1] || "");
|
||||
return params.get("entrypoint") || "preferences";
|
||||
},
|
||||
|
||||
_openAboutAccounts(action) {
|
||||
let entryPoint = this._getEntryPoint();
|
||||
let params = new URLSearchParams();
|
||||
if (action) {
|
||||
params.set("action", action);
|
||||
}
|
||||
params.set("entrypoint", entryPoint);
|
||||
|
||||
this.replaceTabWithUrl("about:accounts?" + params);
|
||||
},
|
||||
|
||||
openContentInBrowser(url, options) {
|
||||
let win = Services.wm.getMostRecentWindow("navigator:browser");
|
||||
if (!win) {
|
||||
openUILinkIn(url, "tab");
|
||||
return;
|
||||
}
|
||||
win.switchToTabHavingURI(url, true, options);
|
||||
},
|
||||
|
||||
// Replace the current tab with the specified URL.
|
||||
replaceTabWithUrl(url) {
|
||||
// Get the <browser> element hosting us.
|
||||
let browser = window.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIWebNavigation)
|
||||
.QueryInterface(Ci.nsIDocShell)
|
||||
.chromeEventHandler;
|
||||
// And tell it to load our URL.
|
||||
browser.loadURI(url);
|
||||
},
|
||||
|
||||
signUp() {
|
||||
this._openAboutAccounts("signup");
|
||||
},
|
||||
|
||||
signIn() {
|
||||
this._openAboutAccounts("signin");
|
||||
},
|
||||
|
||||
reSignIn() {
|
||||
this._openAboutAccounts("reauth");
|
||||
},
|
||||
|
||||
|
||||
clickOrSpaceOrEnterPressed(event) {
|
||||
// Note: charCode is deprecated, but 'char' not yet implemented.
|
||||
// Replace charCode with char when implemented, see Bug 680830
|
||||
return ((event.type == "click" && event.button == 0) ||
|
||||
(event.type == "keypress" &&
|
||||
(event.charCode == KeyEvent.DOM_VK_SPACE || event.keyCode == KeyEvent.DOM_VK_RETURN)));
|
||||
},
|
||||
|
||||
openChangeProfileImage(event) {
|
||||
if (this.clickOrSpaceOrEnterPressed(event)) {
|
||||
fxAccounts.promiseAccountsChangeProfileURI(this._getEntryPoint(), "avatar")
|
||||
.then(url => {
|
||||
this.openContentInBrowser(url, {
|
||||
replaceQueryString: true,
|
||||
triggeringPrincipal: Services.scriptSecurityManager.getSystemPrincipal(),
|
||||
});
|
||||
});
|
||||
// Prevent page from scrolling on the space key.
|
||||
event.preventDefault();
|
||||
}
|
||||
},
|
||||
|
||||
openManageFirefoxAccount(event) {
|
||||
if (this.clickOrSpaceOrEnterPressed(event)) {
|
||||
this.manageFirefoxAccount();
|
||||
// Prevent page from scrolling on the space key.
|
||||
event.preventDefault();
|
||||
}
|
||||
},
|
||||
|
||||
manageFirefoxAccount() {
|
||||
fxAccounts.promiseAccountsManageURI(this._getEntryPoint())
|
||||
.then(url => {
|
||||
this.openContentInBrowser(url, {
|
||||
replaceQueryString: true,
|
||||
triggeringPrincipal: Services.scriptSecurityManager.getSystemPrincipal(),
|
||||
});
|
||||
});
|
||||
},
|
||||
|
||||
verifyFirefoxAccount() {
|
||||
let showVerifyNotification = (data) => {
|
||||
let isError = !data;
|
||||
let maybeNot = isError ? "Not" : "";
|
||||
let sb = this._accountsStringBundle;
|
||||
let title = sb.GetStringFromName("verification" + maybeNot + "SentTitle");
|
||||
let email = !isError && data ? data.email : "";
|
||||
let body = sb.formatStringFromName("verification" + maybeNot + "SentBody", [email], 1);
|
||||
new Notification(title, { body })
|
||||
}
|
||||
|
||||
let onError = () => {
|
||||
showVerifyNotification();
|
||||
};
|
||||
|
||||
let onSuccess = data => {
|
||||
if (data) {
|
||||
showVerifyNotification(data);
|
||||
} else {
|
||||
onError();
|
||||
}
|
||||
};
|
||||
|
||||
fxAccounts.resendVerificationEmail()
|
||||
.then(fxAccounts.getSignedInUser, onError)
|
||||
.then(onSuccess, onError);
|
||||
},
|
||||
|
||||
unlinkFirefoxAccount(confirm) {
|
||||
if (confirm) {
|
||||
// We use a string bundle shared with aboutAccounts.
|
||||
let sb = Services.strings.createBundle("chrome://browser/locale/syncSetup.properties");
|
||||
let disconnectLabel = sb.GetStringFromName("disconnect.label");
|
||||
let title = sb.GetStringFromName("disconnect.verify.title");
|
||||
let body = sb.GetStringFromName("disconnect.verify.bodyHeading") +
|
||||
"\n\n" +
|
||||
sb.GetStringFromName("disconnect.verify.bodyText");
|
||||
let ps = Services.prompt;
|
||||
let buttonFlags = (ps.BUTTON_POS_0 * ps.BUTTON_TITLE_IS_STRING) +
|
||||
(ps.BUTTON_POS_1 * ps.BUTTON_TITLE_CANCEL) +
|
||||
ps.BUTTON_POS_1_DEFAULT;
|
||||
|
||||
let factory = Cc["@mozilla.org/prompter;1"]
|
||||
.getService(Ci.nsIPromptFactory);
|
||||
let prompt = factory.getPrompt(window, Ci.nsIPrompt);
|
||||
let bag = prompt.QueryInterface(Ci.nsIWritablePropertyBag2);
|
||||
bag.setPropertyAsBool("allowTabModal", true);
|
||||
|
||||
let pressed = prompt.confirmEx(title, body, buttonFlags,
|
||||
disconnectLabel, null, null, null, {});
|
||||
|
||||
if (pressed != 0) { // 0 is the "continue" button
|
||||
return;
|
||||
}
|
||||
}
|
||||
fxAccounts.signOut().then(() => {
|
||||
this.updateWeavePrefs();
|
||||
});
|
||||
},
|
||||
|
||||
_populateComputerName(value) {
|
||||
let textbox = document.getElementById("fxaSyncComputerName");
|
||||
if (!textbox.hasAttribute("placeholder")) {
|
||||
textbox.setAttribute("placeholder",
|
||||
Weave.Utils.getDefaultDeviceName());
|
||||
}
|
||||
textbox.value = value;
|
||||
},
|
||||
};
|
@ -1,242 +0,0 @@
|
||||
# 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/.
|
||||
|
||||
<!-- Sync panel -->
|
||||
|
||||
<preferences id="syncEnginePrefs" hidden="true" data-category="paneSync">
|
||||
<preference id="engine.addons"
|
||||
name="services.sync.engine.addons"
|
||||
type="bool"/>
|
||||
<preference id="engine.bookmarks"
|
||||
name="services.sync.engine.bookmarks"
|
||||
type="bool"/>
|
||||
<preference id="engine.history"
|
||||
name="services.sync.engine.history"
|
||||
type="bool"/>
|
||||
<preference id="engine.tabs"
|
||||
name="services.sync.engine.tabs"
|
||||
type="bool"/>
|
||||
<preference id="engine.prefs"
|
||||
name="services.sync.engine.prefs"
|
||||
type="bool"/>
|
||||
<preference id="engine.passwords"
|
||||
name="services.sync.engine.passwords"
|
||||
type="bool"/>
|
||||
<preference id="engine.addresses"
|
||||
name="services.sync.engine.addresses"
|
||||
type="bool"/>
|
||||
<preference id="engine.creditcards"
|
||||
name="services.sync.engine.creditcards"
|
||||
type="bool"/>
|
||||
</preferences>
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content-new/sync.js"/>
|
||||
|
||||
<hbox id="firefoxAccountCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneSync">
|
||||
<label class="header-name" flex="1">&paneSync1.title;</label>
|
||||
</hbox>
|
||||
|
||||
<deck id="weavePrefsDeck" data-category="paneSync" hidden="true">
|
||||
<groupbox id="noFxaAccount">
|
||||
<hbox>
|
||||
<vbox flex="1">
|
||||
<label id="noFxaCaption">&signedOut.caption;</label>
|
||||
<description id="noFxaDescription" flex="1">&signedOut.description;</description>
|
||||
</vbox>
|
||||
<vbox>
|
||||
<image class="fxaSyncIllustration"/>
|
||||
</vbox>
|
||||
</hbox>
|
||||
<hbox id="fxaNoLoginStatus" align="center" flex="1">
|
||||
<vbox>
|
||||
<image class="fxaProfileImage"/>
|
||||
</vbox>
|
||||
<vbox flex="1">
|
||||
<hbox align="center" flex="1">
|
||||
<hbox align="center" flex="1">
|
||||
<label id="signedOutAccountBoxTitle">&signedOut.accountBox.title;</label>
|
||||
</hbox>
|
||||
<button id="noFxaSignIn"
|
||||
class="accessory-button"
|
||||
label="&signedOut.accountBox.signin2;"
|
||||
accesskey="&signedOut.accountBox.signin2.accesskey;"/>
|
||||
</hbox>
|
||||
<hbox align="center" flex="1">
|
||||
<html:a id="noFxaSignUp"
|
||||
class="openLink"
|
||||
accesskey="&signedOut.accountBox.create2.accesskey;"
|
||||
onclick="gSyncPane.signUp();"
|
||||
onkeypress="gSyncPane.signUp();">&signedOut.accountBox.create2;</html:a>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
<label class="fxaMobilePromo">
|
||||
&mobilePromo3.start;<!-- We put these comments to avoid inserting white spaces
|
||||
--><image class="androidLink"></image><label id="fxaMobilePromo-android"
|
||||
class="text-link"><!--
|
||||
-->&mobilePromo3.androidLink;</label><!--
|
||||
-->&mobilePromo3.iOSBefore;<!--
|
||||
--><image class="iOSLink"></image><label id="fxaMobilePromo-ios"
|
||||
class="text-link"><!--
|
||||
-->&mobilePromo3.iOSLink;</label><!--
|
||||
-->&mobilePromo3.end;
|
||||
</label>
|
||||
</groupbox>
|
||||
|
||||
<vbox id="hasFxaAccount">
|
||||
<hbox>
|
||||
<vbox id="fxaContentWrapper" flex="1">
|
||||
<groupbox id="fxaGroup">
|
||||
<caption class="search-header" hidden="true"><label>&paneSync1.title;</label></caption>
|
||||
|
||||
<deck id="fxaLoginStatus" flex="1">
|
||||
|
||||
<!-- logged in and verified and all is good -->
|
||||
<hbox id="fxaLoginVerified" align="center" flex="1">
|
||||
<image class="fxaProfileImage actionable"
|
||||
role="button"
|
||||
onclick="gSyncPane.openChangeProfileImage(event);"
|
||||
onkeypress="gSyncPane.openChangeProfileImage(event);"
|
||||
tooltiptext="&profilePicture.tooltip;"/>
|
||||
<vbox flex="1" pack="center">
|
||||
<hbox flex="1" align="center">
|
||||
<label id="fxaDisplayName" hidden="true"/>
|
||||
<label class="fxaEmailAddress" flex="1" crop="end"/>
|
||||
<button id="fxaUnlinkButton"
|
||||
class="accessory-button"
|
||||
label="&disconnect3.label;"
|
||||
accesskey="&disconnect3.accesskey;"/>
|
||||
</hbox>
|
||||
<hbox>
|
||||
<html:a id="verifiedManage" class="openLink"
|
||||
accesskey="&verifiedManage.accesskey;"
|
||||
onkeypress="gSyncPane.openManageFirefoxAccount(event);">&verifiedManage.label;</html:a>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
|
||||
<!-- logged in to an unverified account -->
|
||||
<hbox id="fxaLoginUnverified">
|
||||
<vbox>
|
||||
<image class="fxaProfileImage"/>
|
||||
</vbox>
|
||||
<vbox flex="1" pack="center">
|
||||
<hbox>
|
||||
<image class="fxaLoginRejectedWarning"/>
|
||||
<description flex="1">
|
||||
&signedInUnverified.beforename.label;
|
||||
<label class="fxaEmailAddress"/>
|
||||
&signedInUnverified.aftername.label;
|
||||
</description>
|
||||
</hbox>
|
||||
<hbox class="fxaAccountBoxButtons">
|
||||
<button id="verifyFxaAccount" label="&verify.label;" accesskey="&verify.accesskey;"></button>
|
||||
<button id="unverifiedUnlinkFxaAccount" label="&forget.label;" accesskey="&forget.accesskey;"></button>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
|
||||
<!-- logged in locally but server rejected credentials -->
|
||||
<hbox id="fxaLoginRejected">
|
||||
<vbox>
|
||||
<image class="fxaProfileImage"/>
|
||||
</vbox>
|
||||
<vbox flex="1" pack="center">
|
||||
<hbox>
|
||||
<image class="fxaLoginRejectedWarning"/>
|
||||
<description flex="1">
|
||||
&signedInLoginFailure.beforename.label;
|
||||
<label class="fxaEmailAddress"/>
|
||||
&signedInLoginFailure.aftername.label;
|
||||
</description>
|
||||
</hbox>
|
||||
<hbox class="fxaAccountBoxButtons">
|
||||
<button id="rejectReSignIn" label="&signIn.label;" accesskey="&signIn.accesskey;"></button>
|
||||
<button id="rejectUnlinkFxaAccount" label="&forget.label;" accesskey="&forget.accesskey;"></button>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</deck>
|
||||
</groupbox>
|
||||
<groupbox id="syncOptions">
|
||||
<caption><label>&signedIn.settings.label;</label></caption>
|
||||
<description>&signedIn.settings.description;</description>
|
||||
<hbox id="fxaSyncEngines">
|
||||
<vbox flex="1">
|
||||
<checkbox label="&engine.tabs.label2;"
|
||||
accesskey="&engine.tabs.accesskey;"
|
||||
preference="engine.tabs"/>
|
||||
<checkbox label="&engine.bookmarks.label;"
|
||||
accesskey="&engine.bookmarks.accesskey;"
|
||||
preference="engine.bookmarks"/>
|
||||
<checkbox label="&engine.logins.label;"
|
||||
accesskey="&engine.logins.accesskey;"
|
||||
preference="engine.passwords"/>
|
||||
<checkbox label="&engine.history.label;"
|
||||
accesskey="&engine.history.accesskey;"
|
||||
preference="engine.history"/>
|
||||
</vbox>
|
||||
<vbox flex="1">
|
||||
<checkbox label="&engine.addons.label;"
|
||||
accesskey="&engine.addons.accesskey;"
|
||||
preference="engine.addons"/>
|
||||
<checkbox label="&engine.prefs.label;"
|
||||
accesskey="&engine.prefs.accesskey;"
|
||||
preference="engine.prefs"/>
|
||||
<checkbox label="&engine.addresses.label;"
|
||||
accesskey="&engine.addresses.accesskey;"
|
||||
preference="engine.addresses"/>
|
||||
<checkbox label="&engine.creditcards.label;"
|
||||
accesskey="&engine.creditcards.accesskey;"
|
||||
preference="engine.creditcards"/>
|
||||
</vbox>
|
||||
<spacer/>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
<groupbox>
|
||||
<caption>
|
||||
<label control="fxaSyncComputerName">
|
||||
&fxaSyncDeviceName.label;
|
||||
</label>
|
||||
</caption>
|
||||
<hbox id="fxaDeviceName">
|
||||
<textbox id="fxaSyncComputerName" flex="1" disabled="true"/>
|
||||
<button id="fxaChangeDeviceName"
|
||||
label="&changeSyncDeviceName2.label;"
|
||||
accesskey="&changeSyncDeviceName2.accesskey;"/>
|
||||
<button id="fxaCancelChangeDeviceName"
|
||||
label="&cancelChangeSyncDeviceName.label;"
|
||||
accesskey="&cancelChangeSyncDeviceName.accesskey;"
|
||||
hidden="true"/>
|
||||
<button id="fxaSaveChangeDeviceName"
|
||||
label="&saveChangeSyncDeviceName.label;"
|
||||
accesskey="&saveChangeSyncDeviceName.accesskey;"
|
||||
hidden="true"/>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
<label class="fxaMobilePromo">
|
||||
&mobilePromo3.start;<!-- We put these comments to avoid inserting white spaces
|
||||
--><image class="androidLink"></image><label class="text-link" id="fxaMobilePromo-android-hasFxaAccount"><!--
|
||||
-->&mobilePromo3.androidLink;</label><!--
|
||||
-->&mobilePromo3.iOSBefore;<!--
|
||||
--><image class="iOSLink"></image><label class="text-link" id="fxaMobilePromo-ios-hasFxaAccount"><!--
|
||||
-->&mobilePromo3.iOSLink;</label><!--
|
||||
-->&mobilePromo3.end;
|
||||
</label>
|
||||
<vbox id="tosPP-small" align="start">
|
||||
<label id="tosPP-small-ToS" class="text-link">
|
||||
&prefs.tosLink.label;
|
||||
</label>
|
||||
<label id="tosPP-small-PP" class="text-link">
|
||||
&fxaPrivacyNotice.link.label;
|
||||
</label>
|
||||
</vbox>
|
||||
</vbox>
|
||||
</deck>
|
@ -1,7 +0,0 @@
|
||||
"use strict";
|
||||
|
||||
module.exports = {
|
||||
"extends": [
|
||||
"plugin:mozilla/browser-test"
|
||||
]
|
||||
};
|
@ -1,80 +0,0 @@
|
||||
[DEFAULT]
|
||||
support-files =
|
||||
head.js
|
||||
privacypane_tests_perwindow.js
|
||||
site_data_test.html
|
||||
offline/offline.html
|
||||
offline/manifest.appcache
|
||||
|
||||
[browser_applications_selection.js]
|
||||
skip-if = os == 'linux' # bug 1382057
|
||||
[browser_advanced_update.js]
|
||||
skip-if = !updater
|
||||
[browser_basic_rebuild_fonts_test.js]
|
||||
[browser_bug410900.js]
|
||||
[browser_bug705422.js]
|
||||
[browser_bug731866.js]
|
||||
[browser_search_within_preferences_1.js]
|
||||
[browser_search_within_preferences_2.js]
|
||||
[browser_search_within_preferences_command.js]
|
||||
[browser_search_subdialogs_within_preferences_1.js]
|
||||
[browser_search_subdialogs_within_preferences_2.js]
|
||||
[browser_search_subdialogs_within_preferences_3.js]
|
||||
[browser_search_subdialogs_within_preferences_4.js]
|
||||
[browser_search_subdialogs_within_preferences_5.js]
|
||||
[browser_search_subdialogs_within_preferences_6.js]
|
||||
[browser_search_subdialogs_within_preferences_7.js]
|
||||
[browser_search_subdialogs_within_preferences_8.js]
|
||||
[browser_bug795764_cachedisabled.js]
|
||||
[browser_bug1018066_resetScrollPosition.js]
|
||||
[browser_bug1020245_openPreferences_to_paneContent.js]
|
||||
[browser_bug1184989_prevent_scrolling_when_preferences_flipped.js]
|
||||
[browser_engines.js]
|
||||
support-files =
|
||||
browser_bug1184989_prevent_scrolling_when_preferences_flipped.xul
|
||||
[browser_change_app_handler.js]
|
||||
skip-if = os != "win" || (os == "win" && os_version == "6.1")
|
||||
# This test tests the windows-specific app selection dialog, so can't run on non-Windows.
|
||||
# Skip the test on Window 7, see the detail at Bug 1381706.
|
||||
[browser_checkspelling.js]
|
||||
[browser_connection.js]
|
||||
[browser_connection_bug388287.js]
|
||||
[browser_cookies_exceptions.js]
|
||||
[browser_defaultbrowser_alwayscheck.js]
|
||||
[browser_healthreport.js]
|
||||
skip-if = true || !healthreport # Bug 1185403 for the "true"
|
||||
[browser_homepages_filter_aboutpreferences.js]
|
||||
[browser_layersacceleration.js]
|
||||
[browser_masterpassword.js]
|
||||
[browser_notifications_do_not_disturb.js]
|
||||
[browser_password_management.js]
|
||||
[browser_performance.js]
|
||||
skip-if = !e10s
|
||||
[browser_performance_e10srollout.js]
|
||||
skip-if = !e10s
|
||||
[browser_performance_non_e10s.js]
|
||||
skip-if = e10s
|
||||
[browser_permissions_urlFieldHidden.js]
|
||||
[browser_proxy_backup.js]
|
||||
[browser_privacypane_1.js]
|
||||
[browser_privacypane_3.js]
|
||||
[browser_privacypane_4.js]
|
||||
[browser_privacypane_5.js]
|
||||
[browser_privacypane_8.js]
|
||||
[browser_sanitizeOnShutdown_prefLocked.js]
|
||||
[browser_searchsuggestions.js]
|
||||
[browser_security-1.js]
|
||||
[browser_security-2.js]
|
||||
[browser_siteData.js]
|
||||
[browser_siteData2.js]
|
||||
[browser_siteData3.js]
|
||||
[browser_site_login_exceptions.js]
|
||||
[browser_permissions_dialog.js]
|
||||
[browser_cookies_dialog.js]
|
||||
[browser_subdialogs.js]
|
||||
support-files =
|
||||
subdialog.xul
|
||||
subdialog2.xul
|
||||
[browser_telemetry.js]
|
||||
# Skip this test on Android as FHR and Telemetry are separate systems there.
|
||||
skip-if = !healthreport || !telemetry || (os == 'linux' && debug) || (os == 'android')
|
@ -1,161 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
"use strict";
|
||||
|
||||
const { classes: Cc, interfaces: Ci, manager: Cm, utils: Cu, results: Cr } = Components;
|
||||
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
const uuidGenerator = Cc["@mozilla.org/uuid-generator;1"].getService(Ci.nsIUUIDGenerator);
|
||||
|
||||
const mockUpdateManager = {
|
||||
contractId: "@mozilla.org/updates/update-manager;1",
|
||||
|
||||
_mockClassId: uuidGenerator.generateUUID(),
|
||||
|
||||
_originalClassId: "",
|
||||
|
||||
_originalFactory: null,
|
||||
|
||||
QueryInterface: XPCOMUtils.generateQI([Ci.nsIUpdateManager]),
|
||||
|
||||
createInstance(outer, iiD) {
|
||||
if (outer) {
|
||||
throw Cr.NS_ERROR_NO_AGGREGATION;
|
||||
}
|
||||
return this.QueryInterface(iiD);
|
||||
},
|
||||
|
||||
register() {
|
||||
let registrar = Cm.QueryInterface(Ci.nsIComponentRegistrar);
|
||||
if (!registrar.isCIDRegistered(this._mockClassId)) {
|
||||
this._originalClassId = registrar.contractIDToCID(this.contractId);
|
||||
this._originalFactory = Cm.getClassObject(Cc[this.contractId], Ci.nsIFactory);
|
||||
registrar.unregisterFactory(this._originalClassId, this._originalFactory);
|
||||
registrar.registerFactory(this._mockClassId, "Unregister after testing", this.contractId, this);
|
||||
}
|
||||
},
|
||||
|
||||
unregister() {
|
||||
let registrar = Cm.QueryInterface(Ci.nsIComponentRegistrar);
|
||||
registrar.unregisterFactory(this._mockClassId, this);
|
||||
registrar.registerFactory(this._originalClassId, "", this.contractId, this._originalFactory);
|
||||
},
|
||||
|
||||
get updateCount() {
|
||||
return this._updates.length;
|
||||
},
|
||||
|
||||
getUpdateAt(index) {
|
||||
return this._updates[index];
|
||||
},
|
||||
|
||||
_updates: [
|
||||
{
|
||||
name: "Firefox Developer Edition 49.0a2",
|
||||
statusText: "The Update was successfully installed",
|
||||
buildID: "20160728004010",
|
||||
type: "minor",
|
||||
installDate: 1469763105156,
|
||||
detailsURL: "https://www.mozilla.org/firefox/aurora/"
|
||||
},
|
||||
{
|
||||
name: "Firefox Developer Edition 43.0a2",
|
||||
statusText: "The Update was successfully installed",
|
||||
buildID: "20150929004011",
|
||||
type: "minor",
|
||||
installDate: 1443585886224,
|
||||
detailsURL: "https://www.mozilla.org/firefox/aurora/"
|
||||
},
|
||||
{
|
||||
name: "Firefox Developer Edition 42.0a2",
|
||||
statusText: "The Update was successfully installed",
|
||||
buildID: "20150920004018",
|
||||
type: "major",
|
||||
installDate: 1442818147544,
|
||||
detailsURL: "https://www.mozilla.org/firefox/aurora/"
|
||||
}
|
||||
]
|
||||
};
|
||||
|
||||
function resetPreferences() {
|
||||
Services.prefs.clearUserPref("browser.search.update");
|
||||
}
|
||||
|
||||
function formatInstallDate(sec) {
|
||||
var date = new Date(sec);
|
||||
const dtOptions = { year: "numeric", month: "long", day: "numeric",
|
||||
hour: "numeric", minute: "numeric", second: "numeric" };
|
||||
return date.toLocaleString(undefined, dtOptions);
|
||||
}
|
||||
|
||||
registerCleanupFunction(resetPreferences);
|
||||
|
||||
add_task(async function() {
|
||||
await openPreferencesViaOpenPreferencesAPI("advanced", { leaveOpen: true });
|
||||
resetPreferences();
|
||||
Services.prefs.setBoolPref("browser.search.update", false);
|
||||
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let enableSearchUpdate = doc.getElementById("enableSearchUpdate");
|
||||
is_element_visible(enableSearchUpdate, "Check search update preference is visible");
|
||||
|
||||
// Ensure that the update pref dialog reflects the actual pref value.
|
||||
ok(!enableSearchUpdate.checked, "Ensure search updates are disabled");
|
||||
Services.prefs.setBoolPref("browser.search.update", true);
|
||||
ok(enableSearchUpdate.checked, "Ensure search updates are enabled");
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
await openPreferencesViaOpenPreferencesAPI("advanced", { leaveOpen: true });
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
|
||||
let showBtn = doc.getElementById("showUpdateHistory");
|
||||
let dialogOverlay = content.gSubDialog._preloadDialog._overlay;
|
||||
|
||||
// XXX: For unknown reasons, this mock cannot be loaded by
|
||||
// XPCOMUtils.defineLazyServiceGetter() called in aboutDialog-appUpdater.js.
|
||||
// It is registered here so that we could assert update history subdialog
|
||||
// without stopping the preferences advanced pane from loading.
|
||||
// See bug 1361929.
|
||||
mockUpdateManager.register();
|
||||
|
||||
// Test the dialog window opens
|
||||
is(dialogOverlay.style.visibility, "", "The dialog should be invisible");
|
||||
let promiseSubDialogLoaded = promiseLoadSubDialog("chrome://mozapps/content/update/history.xul");
|
||||
showBtn.doCommand();
|
||||
await promiseSubDialogLoaded;
|
||||
is(dialogOverlay.style.visibility, "visible", "The dialog should be visible");
|
||||
|
||||
let dialogFrame = dialogOverlay.querySelector(".dialogFrame");
|
||||
let frameDoc = dialogFrame.contentDocument;
|
||||
let updates = frameDoc.querySelectorAll("update");
|
||||
|
||||
// Test the update history numbers are correct
|
||||
is(updates.length, mockUpdateManager.updateCount, "The update count is incorrect.");
|
||||
|
||||
// Test the updates are displayed correctly
|
||||
let update = null;
|
||||
let updateData = null;
|
||||
for (let i = 0; i < updates.length; ++i) {
|
||||
update = updates[i];
|
||||
updateData = mockUpdateManager.getUpdateAt(i);
|
||||
|
||||
is(update.name, updateData.name + " (" + updateData.buildID + ")", "Wrong update name");
|
||||
is(update.type, updateData.type == "major" ? "New Version" : "Security Update", "Wrong update type");
|
||||
is(update.installDate, formatInstallDate(updateData.installDate), "Wrong update installDate");
|
||||
is(update.detailsURL, updateData.detailsURL, "Wrong update detailsURL");
|
||||
is(update.status, updateData.statusText, "Wrong update status");
|
||||
}
|
||||
|
||||
// Test the dialog window closes
|
||||
let closeBtn = dialogOverlay.querySelector(".dialogClose");
|
||||
closeBtn.doCommand();
|
||||
is(dialogOverlay.style.visibility, "", "The dialog should be invisible");
|
||||
|
||||
mockUpdateManager.unregister();
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
@ -1,161 +0,0 @@
|
||||
var win;
|
||||
var feedItem;
|
||||
var container;
|
||||
|
||||
SimpleTest.requestCompleteLog();
|
||||
|
||||
add_task(async function setup() {
|
||||
await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
info("Preferences page opened on the paneGeneral pane.");
|
||||
|
||||
registerCleanupFunction(() => {
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
||||
});
|
||||
|
||||
add_task(async function getFeedItem() {
|
||||
win = gBrowser.selectedBrowser.contentWindow;
|
||||
|
||||
container = win.document.getElementById("handlersView");
|
||||
feedItem = container.querySelector("richlistitem[type='application/vnd.mozilla.maybe.feed']");
|
||||
Assert.ok(feedItem, "feedItem is present in handlersView.");
|
||||
});
|
||||
|
||||
add_task(async function selectInternalOptionForFeed() {
|
||||
// Select the item.
|
||||
feedItem.scrollIntoView();
|
||||
container.selectItem(feedItem);
|
||||
Assert.ok(feedItem.selected, "Should be able to select our item.");
|
||||
|
||||
// Wait for the menu.
|
||||
let list = await waitForCondition(() =>
|
||||
win.document.getAnonymousElementByAttribute(feedItem, "class", "actionsMenu"));
|
||||
info("Got list after item was selected");
|
||||
|
||||
// Find the "Add Live bookmarks option".
|
||||
let chooseItems = list.getElementsByAttribute("action", Ci.nsIHandlerInfo.handleInternally);
|
||||
Assert.equal(chooseItems.length, 1, "Should only be one action to handle internally");
|
||||
|
||||
// Select the option.
|
||||
let cmdEvent = win.document.createEvent("xulcommandevent");
|
||||
cmdEvent.initCommandEvent("command", true, true, win, 0, false, false, false, false, null, 0);
|
||||
chooseItems[0].dispatchEvent(cmdEvent);
|
||||
|
||||
// Check that we display the correct result.
|
||||
list = await waitForCondition(() =>
|
||||
win.document.getAnonymousElementByAttribute(feedItem, "class", "actionsMenu"));
|
||||
info("Got list after item was selected");
|
||||
Assert.ok(list.selectedItem, "Should have a selected item.");
|
||||
Assert.equal(list.selectedItem.getAttribute("action"),
|
||||
Ci.nsIHandlerInfo.handleInternally,
|
||||
"Newly selected item should be the expected one.");
|
||||
});
|
||||
|
||||
// This builds on the previous selectInternalOptionForFeed task.
|
||||
add_task(async function reselectInternalOptionForFeed() {
|
||||
// Now select a different option in the list - use the pdf item as that doesn't
|
||||
// need to load any favicons.
|
||||
let anotherItem = container.querySelector("richlistitem[type='application/pdf']");
|
||||
|
||||
container.selectItem(anotherItem);
|
||||
|
||||
// Wait for the menu so that we don't hit race conditions.
|
||||
await waitForCondition(() =>
|
||||
win.document.getAnonymousElementByAttribute(anotherItem, "class", "actionsMenu"));
|
||||
info("Got list after item was selected");
|
||||
|
||||
// Now select the feed item again, and check what it is displaying.
|
||||
container.selectItem(feedItem);
|
||||
|
||||
let list = await waitForCondition(() =>
|
||||
win.document.getAnonymousElementByAttribute(feedItem, "class", "actionsMenu"));
|
||||
info("Got list after item was selected");
|
||||
|
||||
Assert.ok(list.selectedItem,
|
||||
"Should have a selected item");
|
||||
Assert.equal(list.selectedItem.getAttribute("action"),
|
||||
Ci.nsIHandlerInfo.handleInternally,
|
||||
"Selected item should still be the same as the previously selected item.");
|
||||
});
|
||||
|
||||
add_task(async function sortingCheck() {
|
||||
win = gBrowser.selectedBrowser.contentWindow;
|
||||
|
||||
const handlerView = win.document.getElementById("handlersView");
|
||||
const typeColumn = win.document.getElementById("typeColumn");
|
||||
Assert.ok(typeColumn, "typeColumn is present in handlersView.");
|
||||
|
||||
// Test default sorting
|
||||
assertSortByType("ascending");
|
||||
|
||||
const oldDir = typeColumn.getAttribute("sortDirection");
|
||||
|
||||
|
||||
// Test sorting on the type column
|
||||
typeColumn.click();
|
||||
assertSortByType("descending");
|
||||
Assert.notEqual(oldDir,
|
||||
typeColumn.getAttribute("sortDirection"),
|
||||
"Sort direction should change");
|
||||
|
||||
typeColumn.click();
|
||||
assertSortByType("ascending");
|
||||
|
||||
const actionColumn = win.document.getElementById("actionColumn");
|
||||
Assert.ok(actionColumn, "actionColumn is present in handlersView.");
|
||||
|
||||
// Test sorting on the action column
|
||||
const oldActionDir = actionColumn.getAttribute("sortDirection");
|
||||
actionColumn.click();
|
||||
assertSortByAction("ascending");
|
||||
Assert.notEqual(oldActionDir,
|
||||
actionColumn.getAttribute("sortDirection"),
|
||||
"Sort direction should change");
|
||||
|
||||
actionColumn.click();
|
||||
assertSortByAction("descending");
|
||||
|
||||
function assertSortByAction(order) {
|
||||
Assert.equal(actionColumn.getAttribute("sortDirection"),
|
||||
order,
|
||||
`Sort direction should be ${order}`);
|
||||
let siteItems = handlerView.getElementsByTagName("richlistitem");
|
||||
for (let i = 0; i < siteItems.length - 1; ++i) {
|
||||
let aType = siteItems[i].getAttribute("actionDescription").toLowerCase();
|
||||
let bType = siteItems[i + 1].getAttribute("actionDescription").toLowerCase();
|
||||
let result = 0;
|
||||
if (aType > bType) {
|
||||
result = 1;
|
||||
} else if (bType > aType) {
|
||||
result = -1;
|
||||
}
|
||||
if (order == "ascending") {
|
||||
Assert.lessOrEqual(result, 0, "Should sort applications in the ascending order by action");
|
||||
} else {
|
||||
Assert.greaterOrEqual(result, 0, "Should sort applications in the descending order by action");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function assertSortByType(order) {
|
||||
Assert.equal(typeColumn.getAttribute("sortDirection"),
|
||||
order,
|
||||
`Sort direction should be ${order}`);
|
||||
let siteItems = handlerView.getElementsByTagName("richlistitem");
|
||||
for (let i = 0; i < siteItems.length - 1; ++i) {
|
||||
let aType = siteItems[i].getAttribute("typeDescription").toLowerCase();
|
||||
let bType = siteItems[i + 1].getAttribute("typeDescription").toLowerCase();
|
||||
let result = 0;
|
||||
if (aType > bType) {
|
||||
result = 1;
|
||||
} else if (bType > aType) {
|
||||
result = -1;
|
||||
}
|
||||
if (order == "ascending") {
|
||||
Assert.lessOrEqual(result, 0, "Should sort applications in the ascending order by type");
|
||||
} else {
|
||||
Assert.greaterOrEqual(result, 0, "Should sort applications in the descending order by type");
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
@ -1,110 +0,0 @@
|
||||
Services.prefs.setBoolPref("browser.preferences.instantApply", true);
|
||||
|
||||
registerCleanupFunction(function() {
|
||||
Services.prefs.clearUserPref("browser.preferences.instantApply");
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
let doc = gBrowser.contentDocument;
|
||||
var langGroup = Services.prefs.getComplexValue("font.language.group", Ci.nsIPrefLocalizedString).data
|
||||
is(doc.getElementById("font.language.group").value, langGroup,
|
||||
"Language group should be set correctly.");
|
||||
|
||||
let defaultFontType = Services.prefs.getCharPref("font.default." + langGroup);
|
||||
let fontFamily = Services.prefs.getCharPref("font.name." + defaultFontType + "." + langGroup);
|
||||
let fontFamilyField = doc.getElementById("defaultFont");
|
||||
is(fontFamilyField.value, fontFamily, "Font family should be set correctly.");
|
||||
|
||||
let defaultFontSize = Services.prefs.getIntPref("font.size.variable." + langGroup);
|
||||
let fontSizeField = doc.getElementById("defaultFontSize");
|
||||
is(fontSizeField.value, defaultFontSize, "Font size should be set correctly.");
|
||||
|
||||
let promiseSubDialogLoaded = promiseLoadSubDialog("chrome://browser/content/preferences/fonts.xul");
|
||||
doc.getElementById("advancedFonts").click();
|
||||
let win = await promiseSubDialogLoaded;
|
||||
doc = win.document;
|
||||
|
||||
// Simulate a dumb font backend.
|
||||
win.FontBuilder._enumerator = {
|
||||
_list: ["MockedFont1", "MockedFont2", "MockedFont3"],
|
||||
_defaultFont: null,
|
||||
EnumerateFonts(lang, type, list) {
|
||||
return this._list;
|
||||
},
|
||||
EnumerateAllFonts() {
|
||||
return this._list;
|
||||
},
|
||||
getDefaultFont() { return this._defaultFont; },
|
||||
getStandardFamilyName(name) { return name; },
|
||||
};
|
||||
win.FontBuilder._allFonts = null;
|
||||
win.FontBuilder._langGroupSupported = false;
|
||||
|
||||
let langGroupElement = doc.getElementById("font.language.group");
|
||||
let selectLangsField = doc.getElementById("selectLangs");
|
||||
let serifField = doc.getElementById("serif");
|
||||
let armenian = "x-armn";
|
||||
let western = "x-western";
|
||||
|
||||
langGroupElement.value = armenian;
|
||||
selectLangsField.value = armenian;
|
||||
is(serifField.value, "", "Font family should not be set.");
|
||||
|
||||
let armenianSerifElement = doc.getElementById("font.name.serif.x-armn");
|
||||
|
||||
langGroupElement.value = western;
|
||||
selectLangsField.value = western;
|
||||
|
||||
// Simulate a font backend supporting language-specific enumeration.
|
||||
// NB: FontBuilder has cached the return value from EnumerateAllFonts(),
|
||||
// so _allFonts will always have 3 elements regardless of subsequent
|
||||
// _list changes.
|
||||
win.FontBuilder._enumerator._list = ["MockedFont2"];
|
||||
|
||||
langGroupElement.value = armenian;
|
||||
selectLangsField.value = armenian;
|
||||
is(serifField.value, "", "Font family should still be empty for indicating using 'default' font.");
|
||||
|
||||
langGroupElement.value = western;
|
||||
selectLangsField.value = western;
|
||||
|
||||
// Simulate a system that has no fonts for the specified language.
|
||||
win.FontBuilder._enumerator._list = [];
|
||||
|
||||
langGroupElement.value = armenian;
|
||||
selectLangsField.value = armenian;
|
||||
is(serifField.value, "", "Font family should not be set.");
|
||||
|
||||
// Setting default font to "MockedFont3". Then, when serifField.value is
|
||||
// empty, it should indicate using "MockedFont3" but it shouldn't be saved
|
||||
// to "MockedFont3" in the pref. It should be resolved at runtime.
|
||||
win.FontBuilder._enumerator._list = ["MockedFont1", "MockedFont2", "MockedFont3"];
|
||||
win.FontBuilder._enumerator._defaultFont = "MockedFont3";
|
||||
langGroupElement.value = armenian;
|
||||
selectLangsField.value = armenian;
|
||||
is(serifField.value, "", "Font family should be empty even if there is a default font.");
|
||||
|
||||
armenianSerifElement.value = "MockedFont2";
|
||||
serifField.value = "MockedFont2";
|
||||
is(serifField.value, "MockedFont2", "Font family should be \"MockedFont2\" for now.");
|
||||
|
||||
langGroupElement.value = western;
|
||||
selectLangsField.value = western;
|
||||
is(serifField.value, "", "Font family of other language should not be set.");
|
||||
|
||||
langGroupElement.value = armenian;
|
||||
selectLangsField.value = armenian;
|
||||
is(serifField.value, "MockedFont2", "Font family should not be changed even after switching the language.");
|
||||
|
||||
// If MochedFont2 is removed from the system, the value should be treated
|
||||
// as empty (i.e., 'default' font) after rebuilding the font list.
|
||||
win.FontBuilder._enumerator._list = ["MockedFont1", "MockedFont3"];
|
||||
win.FontBuilder._enumerator._allFonts = ["MockedFont1", "MockedFont3"];
|
||||
serifField.removeAllItems(); // This will cause rebuilding the font list from available fonts.
|
||||
langGroupElement.value = armenian;
|
||||
selectLangsField.value = armenian;
|
||||
is(serifField.value, "", "Font family should become empty due to the font uninstalled.");
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
@ -1,23 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
var originalWindowHeight;
|
||||
registerCleanupFunction(function() {
|
||||
window.resizeTo(window.outerWidth, originalWindowHeight);
|
||||
while (gBrowser.tabs[1])
|
||||
gBrowser.removeTab(gBrowser.tabs[1]);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
originalWindowHeight = window.outerHeight;
|
||||
window.resizeTo(window.outerWidth, 300);
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneSearch", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneSearch", "Search pane was selected");
|
||||
let mainContent = gBrowser.contentDocument.querySelector(".main-content");
|
||||
mainContent.scrollTop = 50;
|
||||
is(mainContent.scrollTop, 50, "main-content should be scrolled 50 pixels");
|
||||
|
||||
gBrowser.contentWindow.gotoPref("paneGeneral");
|
||||
is(mainContent.scrollTop, 0,
|
||||
"Switching to a different category should reset the scroll position");
|
||||
});
|
@ -1,107 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.instantApply", true);
|
||||
|
||||
registerCleanupFunction(function() {
|
||||
Services.prefs.clearUserPref("browser.preferences.instantApply");
|
||||
});
|
||||
|
||||
// Test opening to the differerent panes and subcategories in Preferences
|
||||
add_task(async function() {
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("panePrivacy");
|
||||
is(prefs.selectedPane, "panePrivacy", "Privacy pane was selected");
|
||||
prefs = await openPreferencesViaHash("privacy");
|
||||
is(prefs.selectedPane, "panePrivacy", "Privacy pane is selected when hash is 'privacy'");
|
||||
prefs = await openPreferencesViaOpenPreferencesAPI("nonexistant-category");
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane is selected by default when a nonexistant-category is requested");
|
||||
prefs = await openPreferencesViaHash("nonexistant-category");
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane is selected when hash is a nonexistant-category");
|
||||
prefs = await openPreferencesViaHash();
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane is selected by default");
|
||||
prefs = await openPreferencesViaOpenPreferencesAPI("privacy-reports", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "panePrivacy", "Privacy pane is selected by default");
|
||||
let doc = gBrowser.contentDocument;
|
||||
is(doc.location.hash, "#privacy", "The subcategory should be removed from the URI");
|
||||
ok(doc.querySelector("#locationBarGroup").hidden, "Location Bar prefs should be hidden when only Reports are requested");
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
// Test opening Preferences with subcategory on an existing Preferences tab. See bug 1358475.
|
||||
add_task(async function() {
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("general", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane is selected by default");
|
||||
let doc = gBrowser.contentDocument;
|
||||
is(doc.location.hash, "#general", "The subcategory should be removed from the URI");
|
||||
// The reasons that here just call the `openPreferences` API without the helping function are
|
||||
// - already opened one about:preferences tab up there and
|
||||
// - the goal is to test on the existing tab and
|
||||
// - using `openPreferencesViaOpenPreferencesAPI` would introduce more handling of additional about:blank and unneccessary event
|
||||
openPreferences("privacy-reports");
|
||||
let selectedPane = gBrowser.contentWindow.history.state;
|
||||
is(selectedPane, "panePrivacy", "Privacy pane should be selected");
|
||||
is(doc.location.hash, "#privacy", "The subcategory should be removed from the URI");
|
||||
ok(doc.querySelector("#locationBarGroup").hidden, "Location Bar prefs should be hidden when only Reports are requested");
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
// Test opening to a subcategory displays the correct values for preferences
|
||||
add_task(async function() {
|
||||
// Skip if crash reporting isn't enabled since the checkbox will be missing.
|
||||
if (!AppConstants.MOZ_CRASHREPORTER) {
|
||||
return;
|
||||
}
|
||||
|
||||
await SpecialPowers.pushPrefEnv({
|
||||
set: [["browser.crashReports.unsubmittedCheck.autoSubmit", true]],
|
||||
});
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy-reports", {leaveOpen: true});
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
ok(
|
||||
doc.querySelector("#automaticallySubmitCrashesBox").checked,
|
||||
"Checkbox for automatically submitting crashes should be checked when the pref is true and only Reports are requested"
|
||||
);
|
||||
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
await SpecialPowers.popPrefEnv();
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
// Skip if crash reporting isn't enabled since the checkbox will be missing.
|
||||
if (!AppConstants.MOZ_CRASHREPORTER) {
|
||||
return;
|
||||
}
|
||||
|
||||
await SpecialPowers.pushPrefEnv({
|
||||
set: [["browser.crashReports.unsubmittedCheck.autoSubmit", false]],
|
||||
});
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy-reports", {leaveOpen: true});
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
ok(
|
||||
!doc.querySelector("#automaticallySubmitCrashesBox").checked,
|
||||
"Checkbox for automatically submitting crashes should not be checked when the pref is false only Reports are requested"
|
||||
);
|
||||
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
await SpecialPowers.popPrefEnv();
|
||||
});
|
||||
|
||||
|
||||
function openPreferencesViaHash(aPane) {
|
||||
return new Promise(resolve => {
|
||||
gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, "about:preferences" + (aPane ? "#" + aPane : ""));
|
||||
let newTabBrowser = gBrowser.selectedBrowser;
|
||||
|
||||
newTabBrowser.addEventListener("Initialized", function() {
|
||||
newTabBrowser.contentWindow.addEventListener("load", function() {
|
||||
let win = gBrowser.contentWindow;
|
||||
let selectedPane = win.history.state;
|
||||
gBrowser.removeCurrentTab();
|
||||
resolve({selectedPane});
|
||||
}, {once: true});
|
||||
}, {capture: true, once: true});
|
||||
|
||||
});
|
||||
}
|
@ -1,95 +0,0 @@
|
||||
const ss = Cc["@mozilla.org/browser/sessionstore;1"].getService(Ci.nsISessionStore);
|
||||
|
||||
const {Utils} = Cu.import("resource://gre/modules/sessionstore/Utils.jsm", {});
|
||||
const triggeringPrincipal_base64 = Utils.SERIALIZED_SYSTEMPRINCIPAL;
|
||||
|
||||
add_task(async function() {
|
||||
waitForExplicitFinish();
|
||||
|
||||
const tabURL = getRootDirectory(gTestPath) + "browser_bug1184989_prevent_scrolling_when_preferences_flipped.xul";
|
||||
|
||||
await BrowserTestUtils.withNewTab({ gBrowser, url: tabURL }, async function(browser) {
|
||||
let doc = browser.contentDocument;
|
||||
let container = doc.getElementById("container");
|
||||
|
||||
// Test button
|
||||
let button = doc.getElementById("button");
|
||||
button.focus();
|
||||
EventUtils.synthesizeKey(" ", {});
|
||||
await checkPageScrolling(container, "button");
|
||||
|
||||
// Test checkbox
|
||||
let checkbox = doc.getElementById("checkbox");
|
||||
checkbox.focus();
|
||||
EventUtils.synthesizeKey(" ", {});
|
||||
ok(checkbox.checked, "Checkbox is checked");
|
||||
await checkPageScrolling(container, "checkbox");
|
||||
|
||||
// Test listbox
|
||||
let listbox = doc.getElementById("listbox");
|
||||
let listitem = doc.getElementById("listitem");
|
||||
listbox.focus();
|
||||
EventUtils.synthesizeKey(" ", {});
|
||||
ok(listitem.selected, "Listitem is selected");
|
||||
await checkPageScrolling(container, "listbox");
|
||||
|
||||
// Test radio
|
||||
let radiogroup = doc.getElementById("radiogroup");
|
||||
radiogroup.focus();
|
||||
EventUtils.synthesizeKey(" ", {});
|
||||
await checkPageScrolling(container, "radio");
|
||||
});
|
||||
|
||||
await BrowserTestUtils.withNewTab({ gBrowser, url: "about:preferences#search" }, async function(browser) {
|
||||
let doc = browser.contentDocument;
|
||||
let container = doc.getElementsByClassName("main-content")[0];
|
||||
|
||||
// Test search
|
||||
let engineList = doc.getElementById("engineList");
|
||||
engineList.focus();
|
||||
EventUtils.synthesizeKey(" ", {});
|
||||
is(engineList.view.selection.currentIndex, 0, "Search engineList is selected");
|
||||
EventUtils.synthesizeKey(" ", {});
|
||||
await checkPageScrolling(container, "search engineList");
|
||||
});
|
||||
|
||||
// Test session restore
|
||||
const CRASH_URL = "about:mozilla";
|
||||
const CRASH_FAVICON = "chrome://branding/content/icon32.png";
|
||||
const CRASH_SHENTRY = {url: CRASH_URL};
|
||||
const CRASH_TAB = {entries: [CRASH_SHENTRY], image: CRASH_FAVICON};
|
||||
const CRASH_STATE = {windows: [{tabs: [CRASH_TAB]}]};
|
||||
|
||||
const TAB_URL = "about:sessionrestore";
|
||||
const TAB_FORMDATA = {url: TAB_URL, id: {sessionData: CRASH_STATE}};
|
||||
const TAB_SHENTRY = {url: TAB_URL, triggeringPrincipal_base64};
|
||||
const TAB_STATE = {entries: [TAB_SHENTRY], formdata: TAB_FORMDATA};
|
||||
|
||||
let tab = gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, "about:blank");
|
||||
|
||||
// Fake a post-crash tab
|
||||
ss.setTabState(tab, JSON.stringify(TAB_STATE));
|
||||
|
||||
await BrowserTestUtils.browserLoaded(tab.linkedBrowser);
|
||||
let doc = tab.linkedBrowser.contentDocument;
|
||||
|
||||
// Make body scrollable
|
||||
doc.body.style.height = (doc.body.clientHeight + 100) + "px";
|
||||
|
||||
let tabList = doc.getElementById("tabList");
|
||||
tabList.focus();
|
||||
EventUtils.synthesizeKey(" ", {});
|
||||
await checkPageScrolling(doc.documentElement, "session restore");
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
finish();
|
||||
});
|
||||
|
||||
function checkPageScrolling(container, type) {
|
||||
return new Promise(resolve => {
|
||||
setTimeout(() => {
|
||||
is(container.scrollTop, 0, "Page should not scroll when " + type + " flipped");
|
||||
resolve();
|
||||
}, 0);
|
||||
});
|
||||
}
|
@ -1,33 +0,0 @@
|
||||
<?xml version="1.0"?>
|
||||
<!--
|
||||
XUL Widget Test for Bug 1184989
|
||||
-->
|
||||
<page title="Bug 1184989 Test"
|
||||
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
|
||||
|
||||
<vbox id="container" style="height: 200px; overflow: auto;">
|
||||
<vbox style="height: 500px;">
|
||||
<hbox>
|
||||
<button id="button" label="button" />
|
||||
</hbox>
|
||||
|
||||
<hbox>
|
||||
<checkbox id="checkbox" label="checkbox" />
|
||||
</hbox>
|
||||
|
||||
<hbox style="height: 50px;">
|
||||
<listbox id="listbox">
|
||||
<listitem id="listitem" label="listitem" />
|
||||
<listitem label="listitem" />
|
||||
</listbox>
|
||||
</hbox>
|
||||
|
||||
<hbox>
|
||||
<radiogroup id="radiogroup">
|
||||
<radio id="radio" label="radio" />
|
||||
</radiogroup>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</vbox>
|
||||
|
||||
</page>
|
@ -1,46 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
Components.utils.import("resource://gre/modules/PlacesUtils.jsm");
|
||||
Components.utils.import("resource://gre/modules/NetUtil.jsm");
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
|
||||
// Setup a phony handler to ensure the app pane will be populated.
|
||||
var handler = Cc["@mozilla.org/uriloader/web-handler-app;1"].
|
||||
createInstance(Ci.nsIWebHandlerApp);
|
||||
handler.name = "App pane alive test";
|
||||
handler.uriTemplate = "http://test.mozilla.org/%s";
|
||||
|
||||
var extps = Cc["@mozilla.org/uriloader/external-protocol-service;1"].
|
||||
getService(Ci.nsIExternalProtocolService);
|
||||
var info = extps.getProtocolHandlerInfo("apppanetest");
|
||||
info.possibleApplicationHandlers.appendElement(handler);
|
||||
|
||||
var hserv = Cc["@mozilla.org/uriloader/handler-service;1"].
|
||||
getService(Ci.nsIHandlerService);
|
||||
hserv.store(info);
|
||||
|
||||
openPreferencesViaOpenPreferencesAPI("general", {leaveOpen: true}).then(
|
||||
() => runTest(gBrowser.selectedBrowser.contentWindow)
|
||||
);
|
||||
}
|
||||
|
||||
function runTest(win) {
|
||||
var rbox = win.document.getElementById("handlersView");
|
||||
ok(rbox, "handlersView is present");
|
||||
|
||||
var items = rbox && rbox.getElementsByTagName("richlistitem");
|
||||
ok(items && items.length > 0, "App handler list populated");
|
||||
|
||||
var handlerAdded = false;
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
if (items[i].getAttribute("type") == "apppanetest")
|
||||
handlerAdded = true;
|
||||
}
|
||||
ok(handlerAdded, "apppanetest protocol handler was successfully added");
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
finish();
|
||||
}
|
@ -1,144 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
// Allow all cookies, then actually set up the test
|
||||
SpecialPowers.pushPrefEnv({"set": [["network.cookie.cookieBehavior", 0]]}, initTest);
|
||||
}
|
||||
|
||||
function initTest() {
|
||||
const searchTerm = "example";
|
||||
const dummyTerm = "elpmaxe";
|
||||
|
||||
var cm = Components.classes["@mozilla.org/cookiemanager;1"]
|
||||
.getService(Components.interfaces.nsICookieManager);
|
||||
|
||||
// delete all cookies (might be left over from other tests)
|
||||
cm.removeAll();
|
||||
|
||||
// data for cookies
|
||||
var vals = [[searchTerm + ".com", dummyTerm, dummyTerm], // match
|
||||
[searchTerm + ".org", dummyTerm, dummyTerm], // match
|
||||
[dummyTerm + ".com", searchTerm, dummyTerm], // match
|
||||
[dummyTerm + ".edu", searchTerm + dummyTerm, dummyTerm], // match
|
||||
[dummyTerm + ".net", dummyTerm, searchTerm], // match
|
||||
[dummyTerm + ".org", dummyTerm, searchTerm + dummyTerm], // match
|
||||
[dummyTerm + ".int", dummyTerm, dummyTerm]]; // no match
|
||||
|
||||
// matches must correspond to above data
|
||||
const matches = 6;
|
||||
|
||||
var ios = Components.classes["@mozilla.org/network/io-service;1"]
|
||||
.getService(Components.interfaces.nsIIOService);
|
||||
var cookieSvc = Components.classes["@mozilla.org/cookieService;1"]
|
||||
.getService(Components.interfaces.nsICookieService);
|
||||
var v;
|
||||
// inject cookies
|
||||
for (v in vals) {
|
||||
let [host, name, value] = vals[v];
|
||||
var cookieUri = ios.newURI("http://" + host);
|
||||
cookieSvc.setCookieString(cookieUri, null, name + "=" + value + ";", null);
|
||||
}
|
||||
|
||||
// open cookie manager
|
||||
var cmd = window.openDialog("chrome://browser/content/preferences/cookies.xul",
|
||||
"Browser:Cookies", "", {});
|
||||
|
||||
// when it has loaded, run actual tests
|
||||
cmd.addEventListener("load", function() { executeSoon(function() { runTest(cmd, searchTerm, vals.length, matches); }); });
|
||||
}
|
||||
|
||||
function isDisabled(win, expectation) {
|
||||
var disabled = win.document.getElementById("removeAllCookies").disabled;
|
||||
is(disabled, expectation, "Remove all cookies button has correct state: " + (expectation ? "disabled" : "enabled"));
|
||||
}
|
||||
|
||||
function runTest(win, searchTerm, cookies, matches) {
|
||||
var cm = Components.classes["@mozilla.org/cookiemanager;1"]
|
||||
.getService(Components.interfaces.nsICookieManager);
|
||||
|
||||
|
||||
// number of cookies should match injected cookies
|
||||
var injectedCookies = 0,
|
||||
injectedEnumerator = cm.enumerator;
|
||||
while (injectedEnumerator.hasMoreElements()) {
|
||||
injectedCookies++;
|
||||
injectedEnumerator.getNext();
|
||||
}
|
||||
is(injectedCookies, cookies, "Number of cookies match injected cookies");
|
||||
|
||||
// "delete all cookies" should be enabled
|
||||
isDisabled(win, false);
|
||||
|
||||
// filter cookies and count matches
|
||||
win.gCookiesWindow.setFilter(searchTerm);
|
||||
is(win.gCookiesWindow._view.rowCount, matches, "Correct number of cookies shown after filter is applied");
|
||||
|
||||
// "delete all cookies" should be enabled
|
||||
isDisabled(win, false);
|
||||
|
||||
|
||||
// select first cookie and delete
|
||||
var tree = win.document.getElementById("cookiesList");
|
||||
var deleteButton = win.document.getElementById("removeSelectedCookies");
|
||||
var rect = tree.treeBoxObject.getCoordsForCellItem(0, tree.columns[0], "cell");
|
||||
EventUtils.synthesizeMouse(tree.body, rect.x + rect.width / 2, rect.y + rect.height / 2, {}, win);
|
||||
EventUtils.synthesizeMouseAtCenter(deleteButton, {}, win);
|
||||
|
||||
// count cookies should be matches-1
|
||||
is(win.gCookiesWindow._view.rowCount, matches - 1, "Deleted selected cookie");
|
||||
|
||||
// select two adjacent cells and delete
|
||||
EventUtils.synthesizeMouse(tree.body, rect.x + rect.width / 2, rect.y + rect.height / 2, {}, win);
|
||||
var eventObj = {};
|
||||
if (navigator.platform.indexOf("Mac") >= 0)
|
||||
eventObj.metaKey = true;
|
||||
else
|
||||
eventObj.ctrlKey = true;
|
||||
rect = tree.treeBoxObject.getCoordsForCellItem(1, tree.columns[0], "cell");
|
||||
EventUtils.synthesizeMouse(tree.body, rect.x + rect.width / 2, rect.y + rect.height / 2, eventObj, win);
|
||||
EventUtils.synthesizeMouseAtCenter(deleteButton, {}, win);
|
||||
|
||||
// count cookies should be matches-3
|
||||
is(win.gCookiesWindow._view.rowCount, matches - 3, "Deleted selected two adjacent cookies");
|
||||
|
||||
// "delete all cookies" should be enabled
|
||||
isDisabled(win, false);
|
||||
|
||||
// delete all cookies and count
|
||||
var deleteAllButton = win.document.getElementById("removeAllCookies");
|
||||
EventUtils.synthesizeMouseAtCenter(deleteAllButton, {}, win);
|
||||
is(win.gCookiesWindow._view.rowCount, 0, "Deleted all matching cookies");
|
||||
|
||||
// "delete all cookies" should be disabled
|
||||
isDisabled(win, true);
|
||||
|
||||
// clear filter and count should be cookies-matches
|
||||
win.gCookiesWindow.setFilter("");
|
||||
is(win.gCookiesWindow._view.rowCount, cookies - matches, "Unmatched cookies remain");
|
||||
|
||||
// "delete all cookies" should be enabled
|
||||
isDisabled(win, false);
|
||||
|
||||
// delete all cookies and count should be 0
|
||||
EventUtils.synthesizeMouseAtCenter(deleteAllButton, {}, win);
|
||||
is(win.gCookiesWindow._view.rowCount, 0, "Deleted all cookies");
|
||||
|
||||
// check that datastore is also at 0
|
||||
var remainingCookies = 0,
|
||||
remainingEnumerator = cm.enumerator;
|
||||
while (remainingEnumerator.hasMoreElements()) {
|
||||
remainingCookies++;
|
||||
remainingEnumerator.getNext();
|
||||
}
|
||||
is(remainingCookies, 0, "Zero cookies remain");
|
||||
|
||||
// "delete all cookies" should be disabled
|
||||
isDisabled(win, true);
|
||||
|
||||
// clean up
|
||||
win.close();
|
||||
finish();
|
||||
}
|
||||
|
@ -1,77 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
Components.utils.import("resource://gre/modules/PlacesUtils.jsm");
|
||||
Components.utils.import("resource://gre/modules/NetUtil.jsm");
|
||||
|
||||
const storageManagerDisabled = !SpecialPowers.getBoolPref("browser.storageManager.enabled");
|
||||
const offlineGroupDisabled = !SpecialPowers.getBoolPref("browser.preferences.offlineGroup.enabled");
|
||||
const browserContainersGroupDisabled = !SpecialPowers.getBoolPref("privacy.userContext.ui.enabled");
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
open_preferences(runTest);
|
||||
}
|
||||
|
||||
var gElements;
|
||||
|
||||
function checkElements(expectedPane) {
|
||||
for (let element of gElements) {
|
||||
// keyset and preferences elements fail is_element_visible checks because they are never visible.
|
||||
// special-case the drmGroup item because its visibility depends on pref + OS version
|
||||
if (element.nodeName == "keyset" ||
|
||||
element.nodeName == "preferences" ||
|
||||
element.id === "drmGroup") {
|
||||
continue;
|
||||
}
|
||||
// The siteDataGroup in the Storage Management project is currently only pref-on on Nightly for testing purpose.
|
||||
// During the test and the transition period, we have to check the pref to see if the siteDataGroup
|
||||
// should be hidden always. This would be a bit bothersome, same as the offlineGroup as below.
|
||||
// However, this checking is necessary to make sure we don't leak the siteDataGroup into beta/release build
|
||||
if (element.id == "siteDataGroup" && storageManagerDisabled) {
|
||||
is_element_hidden(element, "Disabled siteDataGroup should be hidden");
|
||||
continue;
|
||||
}
|
||||
// The siteDataGroup in the Storage Management project will replace the offlineGroup eventually,
|
||||
// so during the transition period, we have to check the pref to see if the offlineGroup
|
||||
// should be hidden always. See the bug 1354530 for the details.
|
||||
if (element.id == "offlineGroup" && offlineGroupDisabled) {
|
||||
is_element_hidden(element, "Disabled offlineGroup should be hidden");
|
||||
continue;
|
||||
}
|
||||
// The browserContainersGroup is still only pref-on on Nightly
|
||||
if (element.id == "browserContainersGroup" && browserContainersGroupDisabled) {
|
||||
is_element_hidden(element, "Disabled browserContainersGroup should be hidden");
|
||||
continue;
|
||||
}
|
||||
|
||||
let attributeValue = element.getAttribute("data-category");
|
||||
let suffix = " (id=" + element.id + ")";
|
||||
if (attributeValue == "pane" + expectedPane) {
|
||||
is_element_visible(element, expectedPane + " elements should be visible" + suffix);
|
||||
} else {
|
||||
is_element_hidden(element, "Elements not in " + expectedPane + " should be hidden" + suffix);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function runTest(win) {
|
||||
is(gBrowser.currentURI.spec, "about:preferences", "about:preferences loaded");
|
||||
|
||||
let tab = win.document;
|
||||
gElements = tab.getElementById("mainPrefPane").children;
|
||||
|
||||
let panes = [
|
||||
"General", "Search",
|
||||
"Privacy", "Sync",
|
||||
];
|
||||
|
||||
for (let pane of panes) {
|
||||
win.gotoPref("pane" + pane);
|
||||
checkElements(pane);
|
||||
}
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
win.close();
|
||||
finish();
|
||||
}
|
@ -1,52 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
const { interfaces: Ci, utils: Cu } = Components;
|
||||
Cu.import("resource://gre/modules/PlacesUtils.jsm");
|
||||
Cu.import("resource://gre/modules/NetUtil.jsm");
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
|
||||
// Adding one fake site so that the SiteDataManager would run.
|
||||
// Otherwise, without any site then it would just return so we would end up in not testing SiteDataManager.
|
||||
let principal = Services.scriptSecurityManager.createCodebasePrincipalFromOrigin("https://www.foo.com");
|
||||
Services.perms.addFromPrincipal(principal, "persistent-storage", Ci.nsIPermissionManager.ALLOW_ACTION);
|
||||
registerCleanupFunction(function() {
|
||||
Services.perms.removeFromPrincipal(principal, "persistent-storage");
|
||||
});
|
||||
|
||||
SpecialPowers.pushPrefEnv({set: [
|
||||
["browser.cache.offline.enable", false],
|
||||
["browser.cache.disk.enable", false],
|
||||
["browser.cache.memory.enable", false],
|
||||
["browser.storageManager.enabled", true],
|
||||
["browser.preferences.offlineGroup.enabled", true],
|
||||
["privacy.userContext.ui.enabled", true]
|
||||
]}).then(() => open_preferences(runTest));
|
||||
}
|
||||
|
||||
function runTest(win) {
|
||||
is(gBrowser.currentURI.spec, "about:preferences", "about:preferences loaded");
|
||||
|
||||
let tab = win.document;
|
||||
let elements = tab.getElementById("mainPrefPane").children;
|
||||
|
||||
// Test if privacy pane is opened correctly
|
||||
win.gotoPref("panePrivacy");
|
||||
for (let element of elements) {
|
||||
if (element.nodeName == "preferences") {
|
||||
continue;
|
||||
}
|
||||
let attributeValue = element.getAttribute("data-category");
|
||||
if (attributeValue == "panePrivacy") {
|
||||
is_element_visible(element, `Privacy element of id=${element.id} should be visible`);
|
||||
} else {
|
||||
is_element_hidden(element, `Non-Privacy element of id=${element.id} should be hidden`);
|
||||
}
|
||||
}
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
win.close();
|
||||
finish();
|
||||
}
|
@ -1,101 +0,0 @@
|
||||
var gMimeSvc = Cc["@mozilla.org/mime;1"].getService(Ci.nsIMIMEService);
|
||||
var gHandlerSvc = Cc["@mozilla.org/uriloader/handler-service;1"].getService(Ci.nsIHandlerService);
|
||||
|
||||
SimpleTest.requestCompleteLog();
|
||||
|
||||
function setupFakeHandler() {
|
||||
let info = gMimeSvc.getFromTypeAndExtension("text/plain", "foo.txt");
|
||||
ok(info.possibleLocalHandlers.length, "Should have at least one known handler");
|
||||
let handler = info.possibleLocalHandlers.queryElementAt(0, Ci.nsILocalHandlerApp);
|
||||
|
||||
let infoToModify = gMimeSvc.getFromTypeAndExtension("text/x-test-handler", null);
|
||||
infoToModify.possibleApplicationHandlers.appendElement(handler);
|
||||
|
||||
gHandlerSvc.store(infoToModify);
|
||||
}
|
||||
|
||||
add_task(async function() {
|
||||
setupFakeHandler();
|
||||
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
let win = gBrowser.selectedBrowser.contentWindow;
|
||||
|
||||
let container = win.document.getElementById("handlersView");
|
||||
let ourItem = container.querySelector("richlistitem[type='text/x-test-handler']");
|
||||
ok(ourItem, "handlersView is present");
|
||||
ourItem.scrollIntoView();
|
||||
container.selectItem(ourItem);
|
||||
ok(ourItem.selected, "Should be able to select our item.");
|
||||
|
||||
let list = await waitForCondition(() => win.document.getAnonymousElementByAttribute(ourItem, "class", "actionsMenu"));
|
||||
info("Got list after item was selected");
|
||||
|
||||
let chooseItem = list.firstChild.querySelector(".choose-app-item");
|
||||
let dialogLoadedPromise = promiseLoadSubDialog("chrome://global/content/appPicker.xul");
|
||||
let cmdEvent = win.document.createEvent("xulcommandevent");
|
||||
cmdEvent.initCommandEvent("command", true, true, win, 0, false, false, false, false, null, 0);
|
||||
chooseItem.dispatchEvent(cmdEvent);
|
||||
|
||||
let dialog = await dialogLoadedPromise;
|
||||
info("Dialog loaded");
|
||||
|
||||
let dialogDoc = dialog.document;
|
||||
let dialogList = dialogDoc.getElementById("app-picker-listbox");
|
||||
dialogList.selectItem(dialogList.firstChild);
|
||||
let selectedApp = dialogList.firstChild.handlerApp;
|
||||
dialogDoc.documentElement.acceptDialog();
|
||||
|
||||
// Verify results are correct in mime service:
|
||||
let mimeInfo = gMimeSvc.getFromTypeAndExtension("text/x-test-handler", null);
|
||||
ok(mimeInfo.preferredApplicationHandler.equals(selectedApp), "App should be set as preferred.");
|
||||
|
||||
// Check that we display this result:
|
||||
list = await waitForCondition(() => win.document.getAnonymousElementByAttribute(ourItem, "class", "actionsMenu"));
|
||||
info("Got list after item was selected");
|
||||
ok(list.selectedItem, "Should have a selected item");
|
||||
ok(mimeInfo.preferredApplicationHandler.equals(list.selectedItem.handlerApp),
|
||||
"App should be visible as preferred item.");
|
||||
|
||||
|
||||
// Now try to 'manage' this list:
|
||||
dialogLoadedPromise = promiseLoadSubDialog("chrome://browser/content/preferences/applicationManager.xul");
|
||||
|
||||
let manageItem = list.firstChild.querySelector(".manage-app-item");
|
||||
cmdEvent = win.document.createEvent("xulcommandevent");
|
||||
cmdEvent.initCommandEvent("command", true, true, win, 0, false, false, false, false, null, 0);
|
||||
manageItem.dispatchEvent(cmdEvent);
|
||||
|
||||
dialog = await dialogLoadedPromise;
|
||||
info("Dialog loaded the second time");
|
||||
|
||||
dialogDoc = dialog.document;
|
||||
dialogList = dialogDoc.getElementById("appList");
|
||||
let itemToRemove = dialogList.querySelector('listitem[label="' + selectedApp.name + '"]');
|
||||
dialogList.selectItem(itemToRemove);
|
||||
let itemsBefore = dialogList.children.length;
|
||||
dialogDoc.getElementById("remove").click();
|
||||
ok(!itemToRemove.parentNode, "Item got removed from DOM");
|
||||
is(dialogList.children.length, itemsBefore - 1, "Item got removed");
|
||||
dialogDoc.documentElement.acceptDialog();
|
||||
|
||||
// Verify results are correct in mime service:
|
||||
mimeInfo = gMimeSvc.getFromTypeAndExtension("text/x-test-handler", null);
|
||||
ok(!mimeInfo.preferredApplicationHandler, "App should no longer be set as preferred.");
|
||||
|
||||
// Check that we display this result:
|
||||
list = await waitForCondition(() => win.document.getAnonymousElementByAttribute(ourItem, "class", "actionsMenu"));
|
||||
ok(list.selectedItem, "Should have a selected item");
|
||||
ok(!list.selectedItem.handlerApp,
|
||||
"No app should be visible as preferred item.");
|
||||
|
||||
let tabRemovedPromise = BrowserTestUtils.tabRemoved(gBrowser.selectedTab);
|
||||
gBrowser.removeCurrentTab();
|
||||
await tabRemovedPromise;
|
||||
});
|
||||
|
||||
registerCleanupFunction(function() {
|
||||
let infoToModify = gMimeSvc.getFromTypeAndExtension("text/x-test-handler", null);
|
||||
gHandlerSvc.remove(infoToModify);
|
||||
});
|
||||
|
@ -1,98 +0,0 @@
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* 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/. */
|
||||
|
||||
Components.utils.import("resource://gre/modules/Services.jsm");
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
|
||||
// network.proxy.type needs to be backed up and restored because mochitest
|
||||
// changes this setting from the default
|
||||
let oldNetworkProxyType = Services.prefs.getIntPref("network.proxy.type");
|
||||
registerCleanupFunction(function() {
|
||||
Services.prefs.setIntPref("network.proxy.type", oldNetworkProxyType);
|
||||
Services.prefs.clearUserPref("network.proxy.no_proxies_on");
|
||||
Services.prefs.clearUserPref("browser.preferences.instantApply");
|
||||
});
|
||||
|
||||
let connectionURL = "chrome://browser/content/preferences/connection.xul";
|
||||
|
||||
/*
|
||||
The connection dialog alone won't save onaccept since it uses type="child",
|
||||
so it has to be opened as a sub dialog of the main pref tab.
|
||||
Open the main tab here.
|
||||
*/
|
||||
open_preferences(async function tabOpened(aContentWindow) {
|
||||
is(gBrowser.currentURI.spec, "about:preferences", "about:preferences loaded");
|
||||
let dialog = await openAndLoadSubDialog(connectionURL);
|
||||
let dialogClosingPromise = waitForEvent(dialog.document.documentElement, "dialogclosing");
|
||||
|
||||
ok(dialog, "connection window opened");
|
||||
runConnectionTests(dialog);
|
||||
dialog.document.documentElement.acceptDialog();
|
||||
|
||||
let dialogClosingEvent = await dialogClosingPromise;
|
||||
ok(dialogClosingEvent, "connection window closed");
|
||||
// runConnectionTests will have changed this pref - make sure it was
|
||||
// sanitized correctly when the dialog was accepted
|
||||
is(Services.prefs.getCharPref("network.proxy.no_proxies_on"),
|
||||
".a.com,.b.com,.c.com", "no_proxies_on pref has correct value");
|
||||
gBrowser.removeCurrentTab();
|
||||
finish();
|
||||
});
|
||||
}
|
||||
|
||||
// run a bunch of tests on the window containing connection.xul
|
||||
function runConnectionTests(win) {
|
||||
let doc = win.document;
|
||||
let networkProxyNone = doc.getElementById("networkProxyNone");
|
||||
let networkProxyNonePref = doc.getElementById("network.proxy.no_proxies_on");
|
||||
let networkProxyTypePref = doc.getElementById("network.proxy.type");
|
||||
|
||||
// make sure the networkProxyNone textbox is formatted properly
|
||||
is(networkProxyNone.getAttribute("multiline"), "true",
|
||||
"networkProxyNone textbox is multiline");
|
||||
is(networkProxyNone.getAttribute("rows"), "2",
|
||||
"networkProxyNone textbox has two rows");
|
||||
|
||||
// check if sanitizing the given input for the no_proxies_on pref results in
|
||||
// expected string
|
||||
function testSanitize(input, expected, errorMessage) {
|
||||
networkProxyNonePref.value = input;
|
||||
win.gConnectionsDialog.sanitizeNoProxiesPref();
|
||||
is(networkProxyNonePref.value, expected, errorMessage);
|
||||
}
|
||||
|
||||
// change this pref so proxy exceptions are actually configurable
|
||||
networkProxyTypePref.value = 1;
|
||||
is(networkProxyNone.disabled, false, "networkProxyNone textbox is enabled");
|
||||
|
||||
testSanitize(".a.com", ".a.com",
|
||||
"sanitize doesn't mess up single filter");
|
||||
testSanitize(".a.com, .b.com, .c.com", ".a.com, .b.com, .c.com",
|
||||
"sanitize doesn't mess up multiple comma/space sep filters");
|
||||
testSanitize(".a.com\n.b.com", ".a.com,.b.com",
|
||||
"sanitize turns line break into comma");
|
||||
testSanitize(".a.com,\n.b.com", ".a.com,.b.com",
|
||||
"sanitize doesn't add duplicate comma after comma");
|
||||
testSanitize(".a.com\n,.b.com", ".a.com,.b.com",
|
||||
"sanitize doesn't add duplicate comma before comma");
|
||||
testSanitize(".a.com,\n,.b.com", ".a.com,,.b.com",
|
||||
"sanitize doesn't add duplicate comma surrounded by commas");
|
||||
testSanitize(".a.com, \n.b.com", ".a.com, .b.com",
|
||||
"sanitize doesn't add comma after comma/space");
|
||||
testSanitize(".a.com\n .b.com", ".a.com, .b.com",
|
||||
"sanitize adds comma before space");
|
||||
testSanitize(".a.com\n\n\n;;\n;\n.b.com", ".a.com,.b.com",
|
||||
"sanitize only adds one comma per substring of bad chars");
|
||||
testSanitize(".a.com,,.b.com", ".a.com,,.b.com",
|
||||
"duplicate commas from user are untouched");
|
||||
testSanitize(".a.com\n.b.com\n.c.com,\n.d.com,\n.e.com",
|
||||
".a.com,.b.com,.c.com,.d.com,.e.com",
|
||||
"sanitize replaces things globally");
|
||||
|
||||
// will check that this was sanitized properly after window closes
|
||||
networkProxyNonePref.value = ".a.com;.b.com\n.c.com";
|
||||
}
|
@ -1,124 +0,0 @@
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
Components.utils.import("resource://gre/modules/Services.jsm");
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
const connectionURL = "chrome://browser/content/preferences/connection.xul";
|
||||
let closeable = false;
|
||||
let finalTest = false;
|
||||
|
||||
// The changed preferences need to be backed up and restored because this mochitest
|
||||
// changes them setting from the default
|
||||
let oldNetworkProxyType = Services.prefs.getIntPref("network.proxy.type");
|
||||
registerCleanupFunction(function() {
|
||||
Services.prefs.setIntPref("network.proxy.type", oldNetworkProxyType);
|
||||
Services.prefs.clearUserPref("network.proxy.share_proxy_settings");
|
||||
for (let proxyType of ["http", "ssl", "ftp", "socks"]) {
|
||||
Services.prefs.clearUserPref("network.proxy." + proxyType);
|
||||
Services.prefs.clearUserPref("network.proxy." + proxyType + "_port");
|
||||
if (proxyType == "http") {
|
||||
continue;
|
||||
}
|
||||
Services.prefs.clearUserPref("network.proxy.backup." + proxyType);
|
||||
Services.prefs.clearUserPref("network.proxy.backup." + proxyType + "_port");
|
||||
}
|
||||
});
|
||||
|
||||
/*
|
||||
The connection dialog alone won't save onaccept since it uses type="child",
|
||||
so it has to be opened as a sub dialog of the main pref tab.
|
||||
Open the main tab here.
|
||||
*/
|
||||
open_preferences(async function tabOpened(aContentWindow) {
|
||||
let dialog, dialogClosingPromise;
|
||||
let doc, proxyTypePref, sharePref, httpPref, httpPortPref, ftpPref, ftpPortPref;
|
||||
|
||||
// Convenient function to reset the variables for the new window
|
||||
async function setDoc() {
|
||||
if (closeable) {
|
||||
let dialogClosingEvent = await dialogClosingPromise;
|
||||
ok(dialogClosingEvent, "Connection dialog closed");
|
||||
}
|
||||
|
||||
if (finalTest) {
|
||||
gBrowser.removeCurrentTab();
|
||||
finish();
|
||||
return;
|
||||
}
|
||||
|
||||
dialog = await openAndLoadSubDialog(connectionURL);
|
||||
dialogClosingPromise = waitForEvent(dialog.document.documentElement, "dialogclosing");
|
||||
|
||||
doc = dialog.document;
|
||||
proxyTypePref = doc.getElementById("network.proxy.type");
|
||||
sharePref = doc.getElementById("network.proxy.share_proxy_settings");
|
||||
httpPref = doc.getElementById("network.proxy.http");
|
||||
httpPortPref = doc.getElementById("network.proxy.http_port");
|
||||
ftpPref = doc.getElementById("network.proxy.ftp");
|
||||
ftpPortPref = doc.getElementById("network.proxy.ftp_port");
|
||||
}
|
||||
|
||||
// This batch of tests should not close the dialog
|
||||
await setDoc();
|
||||
|
||||
// Testing HTTP port 0 with share on
|
||||
proxyTypePref.value = 1;
|
||||
sharePref.value = true;
|
||||
httpPref.value = "localhost";
|
||||
httpPortPref.value = 0;
|
||||
doc.documentElement.acceptDialog();
|
||||
|
||||
// Testing HTTP port 0 + FTP port 80 with share off
|
||||
sharePref.value = false;
|
||||
ftpPref.value = "localhost";
|
||||
ftpPortPref.value = 80;
|
||||
doc.documentElement.acceptDialog();
|
||||
|
||||
// Testing HTTP port 80 + FTP port 0 with share off
|
||||
httpPortPref.value = 80;
|
||||
ftpPortPref.value = 0;
|
||||
doc.documentElement.acceptDialog();
|
||||
|
||||
// From now on, the dialog should close since we are giving it legitimate inputs.
|
||||
// The test will timeout if the onbeforeaccept kicks in erroneously.
|
||||
closeable = true;
|
||||
|
||||
// Both ports 80, share on
|
||||
httpPortPref.value = 80;
|
||||
ftpPortPref.value = 80;
|
||||
doc.documentElement.acceptDialog();
|
||||
|
||||
// HTTP 80, FTP 0, with share on
|
||||
await setDoc();
|
||||
proxyTypePref.value = 1;
|
||||
sharePref.value = true;
|
||||
ftpPref.value = "localhost";
|
||||
httpPref.value = "localhost";
|
||||
httpPortPref.value = 80;
|
||||
ftpPortPref.value = 0;
|
||||
doc.documentElement.acceptDialog();
|
||||
|
||||
// HTTP host empty, port 0 with share on
|
||||
await setDoc();
|
||||
proxyTypePref.value = 1;
|
||||
sharePref.value = true;
|
||||
httpPref.value = "";
|
||||
httpPortPref.value = 0;
|
||||
doc.documentElement.acceptDialog();
|
||||
|
||||
// HTTP 0, but in no proxy mode
|
||||
await setDoc();
|
||||
proxyTypePref.value = 0;
|
||||
sharePref.value = true;
|
||||
httpPref.value = "localhost";
|
||||
httpPortPref.value = 0;
|
||||
|
||||
// This is the final test, don't spawn another connection window
|
||||
finalTest = true;
|
||||
doc.documentElement.acceptDialog();
|
||||
await setDoc();
|
||||
});
|
||||
}
|
@ -1,50 +0,0 @@
|
||||
"use strict";
|
||||
|
||||
Components.utils.import("resource://gre/modules/Services.jsm");
|
||||
|
||||
const COOKIES_URL = "chrome://browser/content/preferences/cookies.xul";
|
||||
|
||||
const URI = Services.io.newURI("http://www.example.com");
|
||||
var cookiesDialog;
|
||||
|
||||
add_task(async function openCookiesSubDialog() {
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", {leaveOpen: true});
|
||||
|
||||
let dialogOpened = promiseLoadSubDialog(COOKIES_URL);
|
||||
|
||||
await ContentTask.spawn(gBrowser.selectedBrowser, null, function() {
|
||||
let doc = content.document;
|
||||
let cookiesButton = doc.getElementById("historyRememberCookies");
|
||||
cookiesButton.click();
|
||||
});
|
||||
|
||||
cookiesDialog = await dialogOpened;
|
||||
});
|
||||
|
||||
add_task(async function testDeleteCookie() {
|
||||
let doc = cookiesDialog.document;
|
||||
|
||||
// Add a cookie.
|
||||
Services.cookies.add(URI.host, URI.pathQueryRef, "", "", false, false, true, Date.now());
|
||||
|
||||
let tree = doc.getElementById("cookiesList");
|
||||
Assert.equal(tree.view.rowCount, 1, "Row count should initially be 1");
|
||||
tree.focus();
|
||||
tree.view.selection.select(0);
|
||||
|
||||
if (AppConstants.platform == "macosx") {
|
||||
EventUtils.synthesizeKey("VK_BACK_SPACE", {});
|
||||
} else {
|
||||
EventUtils.synthesizeKey("VK_DELETE", {});
|
||||
}
|
||||
|
||||
await waitForCondition(() => tree.view.rowCount == 0);
|
||||
|
||||
is_element_visible(content.gSubDialog._dialogs[0]._box,
|
||||
"Subdialog is visible after deleting an element");
|
||||
|
||||
});
|
||||
|
||||
add_task(async function removeTab() {
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
@ -1,353 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
requestLongerTimeout(2);
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
requestLongerTimeout(3);
|
||||
testRunner.runTests();
|
||||
}
|
||||
|
||||
var testRunner = {
|
||||
|
||||
tests:
|
||||
[
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "test.com";
|
||||
params.btnAllow.doCommand();
|
||||
is(params.tree.view.rowCount, 1, "added exception shows up in treeview");
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "http://test.com",
|
||||
"origin name should be set correctly");
|
||||
is(params.tree.view.getCellText(0, params.statusCol), params.allowText,
|
||||
"permission text should be set correctly");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "http://test.com", data: "added",
|
||||
capability: Ci.nsIPermissionManager.ALLOW_ACTION }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "test.com";
|
||||
params.btnBlock.doCommand();
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "http://test.com",
|
||||
"origin name should be set correctly");
|
||||
is(params.tree.view.getCellText(0, params.statusCol), params.denyText,
|
||||
"permission should change to deny in UI");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "http://test.com", data: "changed",
|
||||
capability: Ci.nsIPermissionManager.DENY_ACTION }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "test.com";
|
||||
params.btnAllow.doCommand();
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "http://test.com",
|
||||
"origin name should be set correctly");
|
||||
is(params.tree.view.getCellText(0, params.statusCol), params.allowText,
|
||||
"permission should revert back to allow");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "http://test.com", data: "changed",
|
||||
capability: Ci.nsIPermissionManager.ALLOW_ACTION }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "test.com";
|
||||
params.btnRemove.doCommand();
|
||||
is(params.tree.view.rowCount, 0, "exception should be removed");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "http://test.com", data: "deleted" }],
|
||||
},
|
||||
{
|
||||
expectPermObservancesDuringTestFunction: true,
|
||||
test(params) {
|
||||
let uri = params.ioService.newURI("http://test.com");
|
||||
params.pm.add(uri, "popup", Ci.nsIPermissionManager.DENY_ACTION);
|
||||
is(params.tree.view.rowCount, 0, "adding unrelated permission should not change display");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "popup", origin: "http://test.com", data: "added",
|
||||
capability: Ci.nsIPermissionManager.DENY_ACTION }],
|
||||
cleanUp(params) {
|
||||
let uri = params.ioService.newURI("http://test.com");
|
||||
params.pm.remove(uri, "popup");
|
||||
},
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "https://test.com:12345";
|
||||
params.btnAllow.doCommand();
|
||||
is(params.tree.view.rowCount, 1, "added exception shows up in treeview");
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "https://test.com:12345",
|
||||
"origin name should be set correctly");
|
||||
is(params.tree.view.getCellText(0, params.statusCol), params.allowText,
|
||||
"permission text should be set correctly");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "https://test.com:12345", data: "added",
|
||||
capability: Ci.nsIPermissionManager.ALLOW_ACTION }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "https://test.com:12345";
|
||||
params.btnBlock.doCommand();
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "https://test.com:12345",
|
||||
"origin name should be set correctly");
|
||||
is(params.tree.view.getCellText(0, params.statusCol), params.denyText,
|
||||
"permission should change to deny in UI");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "https://test.com:12345", data: "changed",
|
||||
capability: Ci.nsIPermissionManager.DENY_ACTION }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "https://test.com:12345";
|
||||
params.btnAllow.doCommand();
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "https://test.com:12345",
|
||||
"origin name should be set correctly");
|
||||
is(params.tree.view.getCellText(0, params.statusCol), params.allowText,
|
||||
"permission should revert back to allow");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "https://test.com:12345", data: "changed",
|
||||
capability: Ci.nsIPermissionManager.ALLOW_ACTION }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "https://test.com:12345";
|
||||
params.btnRemove.doCommand();
|
||||
is(params.tree.view.rowCount, 0, "exception should be removed");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "https://test.com:12345", data: "deleted" }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "localhost:12345";
|
||||
params.btnAllow.doCommand();
|
||||
is(params.tree.view.rowCount, 1, "added exception shows up in treeview");
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "http://localhost:12345",
|
||||
"origin name should be set correctly");
|
||||
is(params.tree.view.getCellText(0, params.statusCol), params.allowText,
|
||||
"permission text should be set correctly");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "http://localhost:12345", data: "added",
|
||||
capability: Ci.nsIPermissionManager.ALLOW_ACTION }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "localhost:12345";
|
||||
params.btnBlock.doCommand();
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "http://localhost:12345",
|
||||
"origin name should be set correctly");
|
||||
is(params.tree.view.getCellText(0, params.statusCol), params.denyText,
|
||||
"permission should change to deny in UI");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "http://localhost:12345", data: "changed",
|
||||
capability: Ci.nsIPermissionManager.DENY_ACTION }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "localhost:12345";
|
||||
params.btnAllow.doCommand();
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "http://localhost:12345",
|
||||
"origin name should be set correctly");
|
||||
is(params.tree.view.getCellText(0, params.statusCol), params.allowText,
|
||||
"permission should revert back to allow");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "http://localhost:12345", data: "changed",
|
||||
capability: Ci.nsIPermissionManager.ALLOW_ACTION }],
|
||||
},
|
||||
{
|
||||
test(params) {
|
||||
params.url.value = "localhost:12345";
|
||||
params.btnRemove.doCommand();
|
||||
is(params.tree.view.rowCount, 0, "exception should be removed");
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "http://localhost:12345", data: "deleted" }],
|
||||
},
|
||||
{
|
||||
expectPermObservancesDuringTestFunction: true,
|
||||
test(params) {
|
||||
for (let URL of ["http://a", "http://z", "http://b"]) {
|
||||
let URI = params.ioService.newURI(URL);
|
||||
params.pm.add(URI, "cookie", Ci.nsIPermissionManager.ALLOW_ACTION);
|
||||
}
|
||||
|
||||
is(params.tree.view.rowCount, 3, "Three permissions should be present");
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "http://a",
|
||||
"site should be sorted. 'a' should be first");
|
||||
is(params.tree.view.getCellText(1, params.nameCol), "http://b",
|
||||
"site should be sorted. 'b' should be second");
|
||||
is(params.tree.view.getCellText(2, params.nameCol), "http://z",
|
||||
"site should be sorted. 'z' should be third");
|
||||
|
||||
// Sort descending then check results in cleanup since sorting isn't synchronous.
|
||||
EventUtils.synthesizeMouseAtCenter(params.doc.getElementById("siteCol"), {},
|
||||
params.doc.defaultView);
|
||||
params.btnApplyChanges.doCommand();
|
||||
},
|
||||
observances: [{ type: "cookie", origin: "http://a", data: "added",
|
||||
capability: Ci.nsIPermissionManager.ALLOW_ACTION },
|
||||
{ type: "cookie", origin: "http://z", data: "added",
|
||||
capability: Ci.nsIPermissionManager.ALLOW_ACTION },
|
||||
{ type: "cookie", origin: "http://b", data: "added",
|
||||
capability: Ci.nsIPermissionManager.ALLOW_ACTION }],
|
||||
cleanUp(params) {
|
||||
is(params.tree.view.getCellText(0, params.nameCol), "http://z",
|
||||
"site should be sorted. 'z' should be first");
|
||||
is(params.tree.view.getCellText(1, params.nameCol), "http://b",
|
||||
"site should be sorted. 'b' should be second");
|
||||
is(params.tree.view.getCellText(2, params.nameCol), "http://a",
|
||||
"site should be sorted. 'a' should be third");
|
||||
|
||||
for (let URL of ["http://a", "http://z", "http://b"]) {
|
||||
let uri = params.ioService.newURI(URL);
|
||||
params.pm.remove(uri, "cookie");
|
||||
}
|
||||
},
|
||||
},
|
||||
],
|
||||
|
||||
_currentTest: -1,
|
||||
|
||||
runTests() {
|
||||
this._currentTest++;
|
||||
|
||||
info("Running test #" + (this._currentTest + 1) + "\n");
|
||||
let that = this;
|
||||
let p = this.runCurrentTest(this._currentTest + 1);
|
||||
p.then(function() {
|
||||
if (that._currentTest == that.tests.length - 1) {
|
||||
finish();
|
||||
} else {
|
||||
that.runTests();
|
||||
}
|
||||
});
|
||||
},
|
||||
|
||||
runCurrentTest(testNumber) {
|
||||
return new Promise(function(resolve, reject) {
|
||||
|
||||
let helperFunctions = {
|
||||
windowLoad(win) {
|
||||
let doc = win.document;
|
||||
let params = {
|
||||
doc,
|
||||
tree: doc.getElementById("permissionsTree"),
|
||||
nameCol: doc.getElementById("permissionsTree").treeBoxObject.columns.getColumnAt(0),
|
||||
statusCol: doc.getElementById("permissionsTree").treeBoxObject.columns.getColumnAt(1),
|
||||
url: doc.getElementById("url"),
|
||||
btnAllow: doc.getElementById("btnAllow"),
|
||||
btnBlock: doc.getElementById("btnBlock"),
|
||||
btnApplyChanges: doc.getElementById("btnApplyChanges"),
|
||||
btnRemove: doc.getElementById("removePermission"),
|
||||
pm: Cc["@mozilla.org/permissionmanager;1"]
|
||||
.getService(Ci.nsIPermissionManager),
|
||||
ioService: Cc["@mozilla.org/network/io-service;1"]
|
||||
.getService(Ci.nsIIOService),
|
||||
allowText: win.gPermissionManager._getCapabilityString(
|
||||
Ci.nsIPermissionManager.ALLOW_ACTION),
|
||||
denyText: win.gPermissionManager._getCapabilityString(
|
||||
Ci.nsIPermissionManager.DENY_ACTION),
|
||||
allow: Ci.nsIPermissionManager.ALLOW_ACTION,
|
||||
deny: Ci.nsIPermissionManager.DENY_ACTION,
|
||||
};
|
||||
|
||||
let permObserver = {
|
||||
observe(aSubject, aTopic, aData) {
|
||||
if (aTopic != "perm-changed")
|
||||
return;
|
||||
|
||||
if (testRunner.tests[testRunner._currentTest].observances.length == 0) {
|
||||
// Should fail here as we are not expecting a notification, but we don't.
|
||||
// See bug 1063410.
|
||||
return;
|
||||
}
|
||||
|
||||
let permission = aSubject.QueryInterface(Ci.nsIPermission);
|
||||
let expected = testRunner.tests[testRunner._currentTest].observances.shift();
|
||||
|
||||
is(aData, expected.data, "type of message should be the same");
|
||||
for (let prop of ["type", "capability"]) {
|
||||
if (expected[prop])
|
||||
is(permission[prop], expected[prop],
|
||||
"property: \"" + prop + "\" should be equal");
|
||||
}
|
||||
|
||||
if (expected.origin) {
|
||||
is(permission.principal.origin, expected.origin,
|
||||
"property: \"origin\" should be equal");
|
||||
}
|
||||
|
||||
os.removeObserver(permObserver, "perm-changed");
|
||||
|
||||
let testCase = testRunner.tests[testRunner._currentTest];
|
||||
if (!testCase.expectPermObservancesDuringTestFunction) {
|
||||
if (testCase.cleanUp) {
|
||||
testCase.cleanUp(params);
|
||||
}
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
resolve();
|
||||
}
|
||||
},
|
||||
};
|
||||
|
||||
let os = Cc["@mozilla.org/observer-service;1"]
|
||||
.getService(Ci.nsIObserverService);
|
||||
|
||||
os.addObserver(permObserver, "perm-changed");
|
||||
|
||||
if (testRunner._currentTest == 0) {
|
||||
is(params.tree.view.rowCount, 0, "no cookie exceptions");
|
||||
}
|
||||
|
||||
try {
|
||||
let testCase = testRunner.tests[testRunner._currentTest];
|
||||
testCase.test(params);
|
||||
if (testCase.expectPermObservancesDuringTestFunction) {
|
||||
if (testCase.cleanUp) {
|
||||
testCase.cleanUp(params);
|
||||
}
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
resolve();
|
||||
}
|
||||
} catch (ex) {
|
||||
ok(false, "exception while running test #" +
|
||||
testNumber + ": " + ex);
|
||||
}
|
||||
},
|
||||
};
|
||||
|
||||
registerCleanupFunction(function() {
|
||||
Services.prefs.clearUserPref("privacy.history.custom");
|
||||
});
|
||||
|
||||
openPreferencesViaOpenPreferencesAPI("panePrivacy", {leaveOpen: true}).then(function() {
|
||||
let doc = gBrowser.contentDocument;
|
||||
let historyMode = doc.getElementById("historyMode");
|
||||
historyMode.value = "custom";
|
||||
historyMode.doCommand();
|
||||
|
||||
let promiseSubDialogLoaded =
|
||||
promiseLoadSubDialog("chrome://browser/content/preferences/permissions.xul");
|
||||
doc.getElementById("cookieExceptions").doCommand();
|
||||
|
||||
promiseSubDialogLoaded.then(function(win) {
|
||||
helperFunctions.windowLoad(win);
|
||||
});
|
||||
});
|
||||
});
|
||||
},
|
||||
};
|
@ -1,103 +0,0 @@
|
||||
"use strict";
|
||||
|
||||
const CHECK_DEFAULT_INITIAL = Services.prefs.getBoolPref("browser.shell.checkDefaultBrowser");
|
||||
|
||||
add_task(async function clicking_make_default_checks_alwaysCheck_checkbox() {
|
||||
await BrowserTestUtils.openNewForegroundTab(gBrowser, "about:preferences");
|
||||
|
||||
await test_with_mock_shellservice({isDefault: false}, async function() {
|
||||
let setDefaultPane = content.document.getElementById("setDefaultPane");
|
||||
Assert.equal(setDefaultPane.selectedIndex, "0",
|
||||
"The 'make default' pane should be visible when not default");
|
||||
let alwaysCheck = content.document.getElementById("alwaysCheckDefault");
|
||||
Assert.ok(!alwaysCheck.checked, "Always Check is unchecked by default");
|
||||
Assert.ok(!Services.prefs.getBoolPref("browser.shell.checkDefaultBrowser"),
|
||||
"alwaysCheck pref should be false by default in test runs");
|
||||
|
||||
let setDefaultButton = content.document.getElementById("setDefaultButton");
|
||||
setDefaultButton.click();
|
||||
content.window.gMainPane.updateSetDefaultBrowser();
|
||||
|
||||
await ContentTaskUtils.waitForCondition(() => alwaysCheck.checked,
|
||||
"'Always Check' checkbox should get checked after clicking the 'Set Default' button");
|
||||
|
||||
Assert.ok(alwaysCheck.checked,
|
||||
"Clicking 'Make Default' checks the 'Always Check' checkbox");
|
||||
Assert.ok(Services.prefs.getBoolPref("browser.shell.checkDefaultBrowser"),
|
||||
"Checking the checkbox should set the pref to true");
|
||||
Assert.ok(alwaysCheck.disabled,
|
||||
"'Always Check' checkbox is locked with default browser and alwaysCheck=true");
|
||||
Assert.equal(setDefaultPane.selectedIndex, "1",
|
||||
"The 'make default' pane should not be visible when default");
|
||||
Assert.ok(Services.prefs.getBoolPref("browser.shell.checkDefaultBrowser"),
|
||||
"checkDefaultBrowser pref is now enabled");
|
||||
});
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
Services.prefs.clearUserPref("browser.shell.checkDefaultBrowser");
|
||||
});
|
||||
|
||||
add_task(async function clicking_make_default_checks_alwaysCheck_checkbox() {
|
||||
Services.prefs.lockPref("browser.shell.checkDefaultBrowser");
|
||||
await BrowserTestUtils.openNewForegroundTab(gBrowser, "about:preferences");
|
||||
|
||||
await test_with_mock_shellservice({isDefault: false}, async function() {
|
||||
let setDefaultPane = content.document.getElementById("setDefaultPane");
|
||||
Assert.equal(setDefaultPane.selectedIndex, "0",
|
||||
"The 'make default' pane should be visible when not default");
|
||||
let alwaysCheck = content.document.getElementById("alwaysCheckDefault");
|
||||
Assert.ok(alwaysCheck.disabled, "Always Check is disabled when locked");
|
||||
Assert.ok(alwaysCheck.checked,
|
||||
"Always Check is checked because defaultPref is true and pref is locked");
|
||||
Assert.ok(Services.prefs.getBoolPref("browser.shell.checkDefaultBrowser"),
|
||||
"alwaysCheck pref should ship with 'true' by default");
|
||||
|
||||
let setDefaultButton = content.document.getElementById("setDefaultButton");
|
||||
setDefaultButton.click();
|
||||
content.window.gMainPane.updateSetDefaultBrowser();
|
||||
|
||||
await ContentTaskUtils.waitForCondition(() => setDefaultPane.selectedIndex == "1",
|
||||
"Browser is now default");
|
||||
|
||||
Assert.ok(alwaysCheck.checked,
|
||||
"'Always Check' is still checked because it's locked");
|
||||
Assert.ok(alwaysCheck.disabled,
|
||||
"'Always Check is disabled because it's locked");
|
||||
Assert.ok(Services.prefs.getBoolPref("browser.shell.checkDefaultBrowser"),
|
||||
"The pref is locked and so doesn't get changed");
|
||||
});
|
||||
|
||||
Services.prefs.unlockPref("browser.shell.checkDefaultBrowser");
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
||||
|
||||
registerCleanupFunction(function() {
|
||||
Services.prefs.unlockPref("browser.shell.checkDefaultBrowser");
|
||||
Services.prefs.setBoolPref("browser.shell.checkDefaultBrowser", CHECK_DEFAULT_INITIAL);
|
||||
});
|
||||
|
||||
async function test_with_mock_shellservice(options, testFn) {
|
||||
await ContentTask.spawn(gBrowser.selectedBrowser, options, async function(contentOptions) {
|
||||
let doc = content.document;
|
||||
let win = doc.defaultView;
|
||||
win.oldShellService = win.getShellService();
|
||||
let mockShellService = {
|
||||
_isDefault: false,
|
||||
isDefaultBrowser() {
|
||||
return this._isDefault;
|
||||
},
|
||||
setDefaultBrowser() {
|
||||
this._isDefault = true;
|
||||
},
|
||||
};
|
||||
win.getShellService = function() {
|
||||
return mockShellService;
|
||||
}
|
||||
mockShellService._isDefault = contentOptions.isDefault;
|
||||
win.gMainPane.updateSetDefaultBrowser();
|
||||
});
|
||||
|
||||
await ContentTask.spawn(gBrowser.selectedBrowser, null, testFn);
|
||||
|
||||
Services.prefs.setBoolPref("browser.shell.checkDefaultBrowser", CHECK_DEFAULT_INITIAL);
|
||||
}
|
@ -1,62 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
"use strict";
|
||||
|
||||
const FHR_UPLOAD_ENABLED = "datareporting.healthreport.uploadEnabled";
|
||||
|
||||
function runPaneTest(fn) {
|
||||
open_preferences((win) => {
|
||||
let doc = win.document;
|
||||
win.gotoPref("paneAdvanced");
|
||||
let advancedPrefs = doc.getElementById("advancedPrefs");
|
||||
let tab = doc.getElementById("dataChoicesTab");
|
||||
advancedPrefs.selectedTab = tab;
|
||||
fn(win, doc);
|
||||
});
|
||||
}
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
resetPreferences();
|
||||
registerCleanupFunction(resetPreferences);
|
||||
runPaneTest(testBasic);
|
||||
}
|
||||
|
||||
function testBasic(win, doc) {
|
||||
is(Services.prefs.getBoolPref(FHR_UPLOAD_ENABLED), true,
|
||||
"Health Report upload enabled on app first run.");
|
||||
|
||||
let checkbox = doc.getElementById("submitHealthReportBox");
|
||||
ok(checkbox);
|
||||
is(checkbox.checked, true, "Health Report checkbox is checked on app first run.");
|
||||
|
||||
checkbox.checked = false;
|
||||
checkbox.doCommand();
|
||||
is(Services.prefs.getBoolPref(FHR_UPLOAD_ENABLED), false,
|
||||
"Unchecking checkbox opts out of FHR upload.");
|
||||
|
||||
checkbox.checked = true;
|
||||
checkbox.doCommand();
|
||||
is(Services.prefs.getBoolPref(FHR_UPLOAD_ENABLED), true,
|
||||
"Checking checkbox allows FHR upload.");
|
||||
|
||||
win.close();
|
||||
Services.prefs.lockPref(FHR_UPLOAD_ENABLED);
|
||||
runPaneTest(testUploadDisabled);
|
||||
}
|
||||
|
||||
function testUploadDisabled(win, doc) {
|
||||
ok(Services.prefs.prefIsLocked(FHR_UPLOAD_ENABLED), "Upload enabled flag is locked.");
|
||||
let checkbox = doc.getElementById("submitHealthReportBox");
|
||||
is(checkbox.getAttribute("disabled"), "true", "Checkbox is disabled if upload flag is locked.");
|
||||
Services.prefs.unlockPref(FHR_UPLOAD_ENABLED);
|
||||
|
||||
win.close();
|
||||
finish();
|
||||
}
|
||||
|
||||
function resetPreferences() {
|
||||
Services.prefs.clearUserPref(FHR_UPLOAD_ENABLED);
|
||||
}
|
||||
|
@ -1,20 +0,0 @@
|
||||
add_task(async function() {
|
||||
is(gBrowser.currentURI.spec, "about:blank", "Test starts with about:blank open");
|
||||
await BrowserTestUtils.openNewForegroundTab(gBrowser, "about:home");
|
||||
await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
let doc = gBrowser.contentDocument;
|
||||
is(gBrowser.currentURI.spec, "about:preferences#general",
|
||||
"#general should be in the URI for about:preferences");
|
||||
let oldHomepagePref = Services.prefs.getCharPref("browser.startup.homepage");
|
||||
|
||||
let useCurrent = doc.getElementById("useCurrent");
|
||||
useCurrent.click();
|
||||
|
||||
is(gBrowser.tabs.length, 3, "Three tabs should be open");
|
||||
is(Services.prefs.getCharPref("browser.startup.homepage"), "about:blank|about:home",
|
||||
"about:blank and about:home should be the only homepages set");
|
||||
|
||||
Services.prefs.setCharPref("browser.startup.homepage", oldHomepagePref);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
@ -1,44 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
|
||||
registerCleanupFunction(function() {
|
||||
while (gBrowser.tabs[1])
|
||||
gBrowser.removeTab(gBrowser.tabs[1]);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("panePrivacy", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "panePrivacy", "Privacy pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
let notificationsDoNotDisturbBox = doc.getElementById("notificationsDoNotDisturbBox");
|
||||
if (notificationsDoNotDisturbBox.hidden) {
|
||||
todo(false, "Do not disturb is not available on this platform");
|
||||
return;
|
||||
}
|
||||
|
||||
let alertService;
|
||||
try {
|
||||
alertService = Cc["@mozilla.org/alerts-service;1"]
|
||||
.getService(Ci.nsIAlertsService)
|
||||
.QueryInterface(Ci.nsIAlertsDoNotDisturb);
|
||||
} catch (ex) {
|
||||
ok(true, "Do not disturb is not available on this platform: " + ex.message);
|
||||
return;
|
||||
}
|
||||
|
||||
let checkbox = doc.getElementById("notificationsDoNotDisturb");
|
||||
ok(!checkbox.checked, "Checkbox should not be checked by default");
|
||||
ok(!alertService.manualDoNotDisturb, "Do not disturb should be off by default");
|
||||
|
||||
let checkboxChanged = waitForEvent(checkbox, "command")
|
||||
checkbox.click();
|
||||
await checkboxChanged;
|
||||
ok(alertService.manualDoNotDisturb, "Do not disturb should be enabled when checked");
|
||||
|
||||
checkboxChanged = waitForEvent(checkbox, "command")
|
||||
checkbox.click();
|
||||
await checkboxChanged;
|
||||
ok(!alertService.manualDoNotDisturb, "Do not disturb should be disabled when unchecked");
|
||||
});
|
@ -1,73 +0,0 @@
|
||||
"use strict";
|
||||
const PM_URL = "chrome://passwordmgr/content/passwordManager.xul";
|
||||
|
||||
var passwordsDialog;
|
||||
|
||||
add_task(async function test_setup() {
|
||||
let pwmgr = Cc["@mozilla.org/login-manager;1"].
|
||||
getService(Ci.nsILoginManager);
|
||||
pwmgr.removeAllLogins();
|
||||
|
||||
// add login data
|
||||
let nsLoginInfo = new Components.Constructor("@mozilla.org/login-manager/loginInfo;1",
|
||||
Ci.nsILoginInfo, "init");
|
||||
let login = new nsLoginInfo("http://example.com/", "http://example.com/", null,
|
||||
"user", "password", "u1", "p1");
|
||||
pwmgr.addLogin(login);
|
||||
|
||||
registerCleanupFunction(async function() {
|
||||
pwmgr.removeAllLogins();
|
||||
});
|
||||
});
|
||||
|
||||
add_task(async function test_openPasswordSubDialog() {
|
||||
// Undo the save password change.
|
||||
registerCleanupFunction(async function() {
|
||||
await ContentTask.spawn(gBrowser.selectedBrowser, null, function() {
|
||||
let doc = content.document;
|
||||
let savePasswordCheckBox = doc.getElementById("savePasswords");
|
||||
if (savePasswordCheckBox.checked) {
|
||||
savePasswordCheckBox.click();
|
||||
}
|
||||
});
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
||||
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", {leaveOpen: true});
|
||||
|
||||
let dialogOpened = promiseLoadSubDialog(PM_URL);
|
||||
|
||||
await ContentTask.spawn(gBrowser.selectedBrowser, null, function() {
|
||||
let doc = content.document;
|
||||
let savePasswordCheckBox = doc.getElementById("savePasswords");
|
||||
Assert.ok(!savePasswordCheckBox.checked,
|
||||
"Save Password CheckBox should be unchecked by default");
|
||||
savePasswordCheckBox.click();
|
||||
|
||||
let showPasswordsButton = doc.getElementById("showPasswords");
|
||||
showPasswordsButton.click();
|
||||
});
|
||||
|
||||
passwordsDialog = await dialogOpened;
|
||||
});
|
||||
|
||||
add_task(async function test_deletePasswordWithKey() {
|
||||
let doc = passwordsDialog.document;
|
||||
|
||||
let tree = doc.getElementById("signonsTree");
|
||||
Assert.equal(tree.view.rowCount, 1, "Row count should initially be 1");
|
||||
tree.focus();
|
||||
tree.view.selection.select(0);
|
||||
|
||||
if (AppConstants.platform == "macosx") {
|
||||
EventUtils.synthesizeKey("VK_BACK_SPACE", {});
|
||||
} else {
|
||||
EventUtils.synthesizeKey("VK_DELETE", {});
|
||||
}
|
||||
|
||||
await waitForCondition(() => tree.view.rowCount == 0);
|
||||
|
||||
is_element_visible(content.gSubDialog._dialogs[0]._box,
|
||||
"Subdialog is visible after deleting an element");
|
||||
});
|
@ -1,156 +0,0 @@
|
||||
const DEFAULT_HW_ACCEL_PREF = Services.prefs.getDefaultBranch(null).getBoolPref("layers.acceleration.disabled");
|
||||
const DEFAULT_PROCESS_COUNT = Services.prefs.getDefaultBranch(null).getIntPref("dom.ipc.processCount");
|
||||
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [
|
||||
["layers.acceleration.disabled", DEFAULT_HW_ACCEL_PREF],
|
||||
["dom.ipc.processCount", DEFAULT_PROCESS_COUNT],
|
||||
["browser.preferences.defaultPerformanceSettings.enabled", true],
|
||||
]});
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
let useRecommendedPerformanceSettings = doc.querySelector("#useRecommendedPerformanceSettings");
|
||||
|
||||
is(Services.prefs.getBoolPref("browser.preferences.defaultPerformanceSettings.enabled"), true,
|
||||
"pref value should be true before clicking on checkbox");
|
||||
ok(useRecommendedPerformanceSettings.checked, "checkbox should be checked before clicking on checkbox");
|
||||
|
||||
useRecommendedPerformanceSettings.click();
|
||||
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
is(performanceSettings.hidden, false, "performance settings section is shown");
|
||||
|
||||
is(Services.prefs.getBoolPref("browser.preferences.defaultPerformanceSettings.enabled"), false,
|
||||
"pref value should be false after clicking on checkbox");
|
||||
ok(!useRecommendedPerformanceSettings.checked, "checkbox should not be checked after clicking on checkbox");
|
||||
|
||||
let allowHWAccel = doc.querySelector("#allowHWAccel");
|
||||
let allowHWAccelPref = Services.prefs.getBoolPref("layers.acceleration.disabled");
|
||||
is(allowHWAccelPref, DEFAULT_HW_ACCEL_PREF,
|
||||
"pref value should be the default value before clicking on checkbox");
|
||||
is(allowHWAccel.checked, !DEFAULT_HW_ACCEL_PREF, "checkbox should show the invert of the default value");
|
||||
|
||||
let contentProcessCount = doc.querySelector("#contentProcessCount");
|
||||
is(contentProcessCount.disabled, false, "process count control should be enabled");
|
||||
is(Services.prefs.getIntPref("dom.ipc.processCount"), DEFAULT_PROCESS_COUNT, "default pref value should be default value");
|
||||
is(contentProcessCount.selectedItem.value, DEFAULT_PROCESS_COUNT, "selected item should be the default one");
|
||||
|
||||
let contentProcessCountEnabledDescription = doc.querySelector("#contentProcessCountEnabledDescription");
|
||||
is(contentProcessCountEnabledDescription.hidden, false, "process count enabled description should be shown");
|
||||
|
||||
let contentProcessCountDisabledDescription = doc.querySelector("#contentProcessCountDisabledDescription");
|
||||
is(contentProcessCountDisabledDescription.hidden, true, "process count enabled description should be hidden");
|
||||
|
||||
allowHWAccel.click();
|
||||
allowHWAccelPref = Services.prefs.getBoolPref("layers.acceleration.disabled");
|
||||
is(allowHWAccelPref, !DEFAULT_HW_ACCEL_PREF,
|
||||
"pref value should be opposite of the default value after clicking on checkbox");
|
||||
is(allowHWAccel.checked, !allowHWAccelPref, "checkbox should show the invert of the current value");
|
||||
|
||||
contentProcessCount.value = 7;
|
||||
contentProcessCount.doCommand();
|
||||
is(Services.prefs.getIntPref("dom.ipc.processCount"), 7, "pref value should be 7");
|
||||
is(contentProcessCount.selectedItem.value, 7, "selected item should be 7");
|
||||
|
||||
allowHWAccel.click();
|
||||
allowHWAccelPref = Services.prefs.getBoolPref("layers.acceleration.disabled");
|
||||
is(allowHWAccelPref, DEFAULT_HW_ACCEL_PREF,
|
||||
"pref value should be the default value after clicking on checkbox");
|
||||
is(allowHWAccel.checked, !allowHWAccelPref, "checkbox should show the invert of the current value");
|
||||
|
||||
contentProcessCount.value = DEFAULT_PROCESS_COUNT;
|
||||
contentProcessCount.doCommand();
|
||||
is(Services.prefs.getIntPref("dom.ipc.processCount"), DEFAULT_PROCESS_COUNT, "pref value should be default value");
|
||||
is(contentProcessCount.selectedItem.value, DEFAULT_PROCESS_COUNT, "selected item should be default one");
|
||||
|
||||
is(performanceSettings.hidden, false, "performance settings section should be still shown");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
let useRecommendedPerformanceSettings = doc.querySelector("#useRecommendedPerformanceSettings");
|
||||
let allowHWAccel = doc.querySelector("#allowHWAccel");
|
||||
let contentProcessCount = doc.querySelector("#contentProcessCount");
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
|
||||
useRecommendedPerformanceSettings.click();
|
||||
allowHWAccel.click();
|
||||
contentProcessCount.value = 7;
|
||||
contentProcessCount.doCommand();
|
||||
useRecommendedPerformanceSettings.click();
|
||||
|
||||
is(Services.prefs.getBoolPref("browser.preferences.defaultPerformanceSettings.enabled"), true,
|
||||
"pref value should be true before clicking on checkbox");
|
||||
ok(useRecommendedPerformanceSettings.checked, "checkbox should be checked before clicking on checkbox");
|
||||
is(performanceSettings.hidden, true, "performance settings section should be still shown");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
|
||||
is(performanceSettings.hidden, true, "performance settings section should not be shown");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", false);
|
||||
|
||||
is(performanceSettings.hidden, false, "performance settings section should be shown");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
Services.prefs.setIntPref("dom.ipc.processCount", 7);
|
||||
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
is(performanceSettings.hidden, false, "performance settings section should be shown");
|
||||
|
||||
let contentProcessCount = doc.querySelector("#contentProcessCount");
|
||||
is(Services.prefs.getIntPref("dom.ipc.processCount"), 7, "pref value should be 7");
|
||||
is(contentProcessCount.selectedItem.value, 7, "selected item should be 7");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
Services.prefs.setBoolPref("layers.acceleration.disabled", true);
|
||||
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
is(performanceSettings.hidden, false, "performance settings section should be shown");
|
||||
|
||||
let allowHWAccel = doc.querySelector("#allowHWAccel");
|
||||
is(Services.prefs.getBoolPref("layers.acceleration.disabled"), true,
|
||||
"pref value is false");
|
||||
ok(!allowHWAccel.checked, "checkbox should not be checked");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
@ -1,102 +0,0 @@
|
||||
const DEFAULT_HW_ACCEL_PREF = Services.prefs.getDefaultBranch(null).getBoolPref("layers.acceleration.disabled");
|
||||
const DEFAULT_PROCESS_COUNT = Services.prefs.getDefaultBranch(null).getIntPref("dom.ipc.processCount");
|
||||
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [
|
||||
["layers.acceleration.disabled", DEFAULT_HW_ACCEL_PREF],
|
||||
["dom.ipc.processCount", DEFAULT_PROCESS_COUNT],
|
||||
["browser.preferences.defaultPerformanceSettings.enabled", true],
|
||||
]});
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
Services.prefs.clearUserPref("dom.ipc.processCount");
|
||||
Services.prefs.setIntPref("dom.ipc.processCount.web", DEFAULT_PROCESS_COUNT + 1);
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
let useRecommendedPerformanceSettings = doc.querySelector("#useRecommendedPerformanceSettings");
|
||||
|
||||
is(Services.prefs.getBoolPref("browser.preferences.defaultPerformanceSettings.enabled"), true,
|
||||
"pref value should be true before clicking on checkbox");
|
||||
ok(useRecommendedPerformanceSettings.checked, "checkbox should be checked before clicking on checkbox");
|
||||
|
||||
useRecommendedPerformanceSettings.click();
|
||||
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
is(performanceSettings.hidden, false, "performance settings section is shown");
|
||||
|
||||
is(Services.prefs.getBoolPref("browser.preferences.defaultPerformanceSettings.enabled"), false,
|
||||
"pref value should be false after clicking on checkbox");
|
||||
ok(!useRecommendedPerformanceSettings.checked, "checkbox should not be checked after clicking on checkbox");
|
||||
|
||||
let contentProcessCount = doc.querySelector("#contentProcessCount");
|
||||
is(contentProcessCount.disabled, false, "process count control should be enabled");
|
||||
is(Services.prefs.getIntPref("dom.ipc.processCount"), DEFAULT_PROCESS_COUNT + 1, "e10s rollout value should be default value");
|
||||
is(contentProcessCount.selectedItem.value, DEFAULT_PROCESS_COUNT + 1, "selected item should be the default one");
|
||||
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
|
||||
Services.prefs.clearUserPref("dom.ipc.processCount");
|
||||
Services.prefs.clearUserPref("dom.ipc.processCount.web");
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
Services.prefs.clearUserPref("dom.ipc.processCount");
|
||||
Services.prefs.setIntPref("dom.ipc.processCount.web", DEFAULT_PROCESS_COUNT + 1);
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", false);
|
||||
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
is(performanceSettings.hidden, false, "performance settings section is shown");
|
||||
|
||||
let contentProcessCount = doc.querySelector("#contentProcessCount");
|
||||
is(contentProcessCount.disabled, false, "process count control should be enabled");
|
||||
is(Services.prefs.getIntPref("dom.ipc.processCount"), DEFAULT_PROCESS_COUNT, "default value should be the current value");
|
||||
is(contentProcessCount.selectedItem.value, DEFAULT_PROCESS_COUNT, "selected item should be the default one");
|
||||
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
|
||||
Services.prefs.clearUserPref("dom.ipc.processCount");
|
||||
Services.prefs.clearUserPref("dom.ipc.processCount.web");
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
Services.prefs.setIntPref("dom.ipc.processCount", DEFAULT_PROCESS_COUNT + 2);
|
||||
Services.prefs.setIntPref("dom.ipc.processCount.web", DEFAULT_PROCESS_COUNT + 1);
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", false);
|
||||
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
is(performanceSettings.hidden, false, "performance settings section is shown");
|
||||
|
||||
let contentProcessCount = doc.querySelector("#contentProcessCount");
|
||||
is(contentProcessCount.disabled, false, "process count control should be enabled");
|
||||
is(Services.prefs.getIntPref("dom.ipc.processCount"), DEFAULT_PROCESS_COUNT + 2, "process count should be the set value");
|
||||
is(contentProcessCount.selectedItem.value, DEFAULT_PROCESS_COUNT + 2, "selected item should be the set one");
|
||||
|
||||
let useRecommendedPerformanceSettings = doc.querySelector("#useRecommendedPerformanceSettings");
|
||||
useRecommendedPerformanceSettings.click();
|
||||
|
||||
is(Services.prefs.getBoolPref("browser.preferences.defaultPerformanceSettings.enabled"), true,
|
||||
"pref value should be true after clicking on checkbox");
|
||||
is(Services.prefs.getIntPref("dom.ipc.processCount"), DEFAULT_PROCESS_COUNT,
|
||||
"process count should be default value");
|
||||
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
|
||||
Services.prefs.clearUserPref("dom.ipc.processCount");
|
||||
Services.prefs.clearUserPref("dom.ipc.processCount.web");
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
});
|
@ -1,100 +0,0 @@
|
||||
const DEFAULT_HW_ACCEL_PREF = Services.prefs.getDefaultBranch(null).getBoolPref("layers.acceleration.disabled");
|
||||
const DEFAULT_PROCESS_COUNT = Services.prefs.getDefaultBranch(null).getIntPref("dom.ipc.processCount");
|
||||
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [
|
||||
["layers.acceleration.disabled", DEFAULT_HW_ACCEL_PREF],
|
||||
["dom.ipc.processCount", DEFAULT_PROCESS_COUNT],
|
||||
["browser.preferences.defaultPerformanceSettings.enabled", true],
|
||||
]});
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
let useRecommendedPerformanceSettings = doc.querySelector("#useRecommendedPerformanceSettings");
|
||||
|
||||
is(Services.prefs.getBoolPref("browser.preferences.defaultPerformanceSettings.enabled"), true,
|
||||
"pref value should be true before clicking on checkbox");
|
||||
ok(useRecommendedPerformanceSettings.checked, "checkbox should be checked before clicking on checkbox");
|
||||
|
||||
useRecommendedPerformanceSettings.click();
|
||||
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
is(performanceSettings.hidden, false, "performance settings section is shown");
|
||||
|
||||
is(Services.prefs.getBoolPref("browser.preferences.defaultPerformanceSettings.enabled"), false,
|
||||
"pref value should be false after clicking on checkbox");
|
||||
ok(!useRecommendedPerformanceSettings.checked, "checkbox should not be checked after clicking on checkbox");
|
||||
|
||||
let allowHWAccel = doc.querySelector("#allowHWAccel");
|
||||
let allowHWAccelPref = Services.prefs.getBoolPref("layers.acceleration.disabled");
|
||||
is(allowHWAccelPref, DEFAULT_HW_ACCEL_PREF,
|
||||
"pref value should be the default value before clicking on checkbox");
|
||||
is(allowHWAccel.checked, !DEFAULT_HW_ACCEL_PREF, "checkbox should show the invert of the default value");
|
||||
|
||||
let contentProcessCount = doc.querySelector("#contentProcessCount");
|
||||
is(contentProcessCount.disabled, true, "process count control should be disabled");
|
||||
|
||||
let contentProcessCountEnabledDescription = doc.querySelector("#contentProcessCountEnabledDescription");
|
||||
is(contentProcessCountEnabledDescription.hidden, true, "process count enabled description should be hidden");
|
||||
|
||||
let contentProcessCountDisabledDescription = doc.querySelector("#contentProcessCountDisabledDescription");
|
||||
is(contentProcessCountDisabledDescription.hidden, false, "process count enabled description should be shown");
|
||||
|
||||
allowHWAccel.click();
|
||||
allowHWAccelPref = Services.prefs.getBoolPref("layers.acceleration.disabled");
|
||||
is(allowHWAccelPref, !DEFAULT_HW_ACCEL_PREF,
|
||||
"pref value should be opposite of the default value after clicking on checkbox");
|
||||
is(allowHWAccel.checked, !allowHWAccelPref, "checkbox should show the invert of the current value");
|
||||
|
||||
allowHWAccel.click();
|
||||
allowHWAccelPref = Services.prefs.getBoolPref("layers.acceleration.disabled");
|
||||
is(allowHWAccelPref, DEFAULT_HW_ACCEL_PREF,
|
||||
"pref value should be the default value after clicking on checkbox");
|
||||
is(allowHWAccel.checked, !allowHWAccelPref, "checkbox should show the invert of the current value");
|
||||
|
||||
is(performanceSettings.hidden, false, "performance settings section should be still shown");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
|
||||
is(performanceSettings.hidden, true, "performance settings section should not be shown");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", false);
|
||||
|
||||
is(performanceSettings.hidden, false, "performance settings section should be shown");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
Services.prefs.setBoolPref("layers.acceleration.disabled", true);
|
||||
|
||||
let prefs = await openPreferencesViaOpenPreferencesAPI("paneGeneral", {leaveOpen: true});
|
||||
is(prefs.selectedPane, "paneGeneral", "General pane was selected");
|
||||
|
||||
let doc = gBrowser.contentDocument;
|
||||
|
||||
let performanceSettings = doc.querySelector("#performanceSettings");
|
||||
is(performanceSettings.hidden, false, "performance settings section should be shown");
|
||||
|
||||
let allowHWAccel = doc.querySelector("#allowHWAccel");
|
||||
is(Services.prefs.getBoolPref("layers.acceleration.disabled"), true,
|
||||
"pref value is false");
|
||||
ok(!allowHWAccel.checked, "checkbox should not be checked");
|
||||
|
||||
Services.prefs.setBoolPref("browser.preferences.defaultPerformanceSettings.enabled", true);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
@ -1,26 +0,0 @@
|
||||
"use strict";
|
||||
|
||||
const PERMISSIONS_URL = "chrome://browser/content/preferences/permissions.xul";
|
||||
|
||||
add_task(async function urlFieldVisibleForPopupPermissions(finish) {
|
||||
await openPreferencesViaOpenPreferencesAPI("panePrivacy", {leaveOpen: true});
|
||||
let win = gBrowser.selectedBrowser.contentWindow;
|
||||
let doc = win.document;
|
||||
let popupPolicyCheckbox = doc.getElementById("popupPolicy");
|
||||
ok(!popupPolicyCheckbox.checked, "popupPolicyCheckbox should be unchecked by default");
|
||||
popupPolicyCheckbox.click();
|
||||
let popupPolicyButton = doc.getElementById("popupPolicyButton");
|
||||
ok(popupPolicyButton, "popupPolicyButton found");
|
||||
let dialogPromise = promiseLoadSubDialog(PERMISSIONS_URL);
|
||||
popupPolicyButton.click();
|
||||
let dialog = await dialogPromise;
|
||||
ok(dialog, "dialog loaded");
|
||||
|
||||
let urlLabel = dialog.document.getElementById("urlLabel");
|
||||
ok(!urlLabel.hidden, "urlLabel should be visible when one of block/session/allow visible");
|
||||
let url = dialog.document.getElementById("url");
|
||||
ok(!url.hidden, "url should be visible when one of block/session/allow visible");
|
||||
|
||||
popupPolicyCheckbox.click();
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
@ -1,19 +0,0 @@
|
||||
let loader = Cc["@mozilla.org/moz/jssubscript-loader;1"].
|
||||
getService(Ci.mozIJSSubScriptLoader);
|
||||
|
||||
let rootDir = getRootDirectory(gTestPath);
|
||||
let jar = getJar(rootDir);
|
||||
if (jar) {
|
||||
let tmpdir = extractJarToTmp(jar);
|
||||
rootDir = "file://" + tmpdir.path + "/";
|
||||
}
|
||||
/* import-globals-from privacypane_tests_perwindow.js */
|
||||
loader.loadSubScript(rootDir + "privacypane_tests_perwindow.js", this);
|
||||
|
||||
run_test_subset([
|
||||
test_pane_visibility,
|
||||
test_dependent_elements,
|
||||
test_dependent_cookie_elements,
|
||||
test_dependent_clearonclose_elements,
|
||||
test_dependent_prefs,
|
||||
]);
|
@ -1,18 +0,0 @@
|
||||
let loader = Cc["@mozilla.org/moz/jssubscript-loader;1"].
|
||||
getService(Ci.mozIJSSubScriptLoader);
|
||||
let rootDir = getRootDirectory(gTestPath);
|
||||
let jar = getJar(rootDir);
|
||||
if (jar) {
|
||||
let tmpdir = extractJarToTmp(jar);
|
||||
rootDir = "file://" + tmpdir.path + "/";
|
||||
}
|
||||
/* import-globals-from privacypane_tests_perwindow.js */
|
||||
loader.loadSubScript(rootDir + "privacypane_tests_perwindow.js", this);
|
||||
|
||||
run_test_subset([
|
||||
test_custom_retention("rememberHistory", "remember"),
|
||||
test_custom_retention("rememberHistory", "custom"),
|
||||
test_custom_retention("rememberForms", "custom"),
|
||||
test_custom_retention("rememberForms", "custom"),
|
||||
test_historymode_retention("remember", "custom"),
|
||||
]);
|
@ -1,26 +0,0 @@
|
||||
requestLongerTimeout(2);
|
||||
|
||||
let loader = Cc["@mozilla.org/moz/jssubscript-loader;1"].
|
||||
getService(Ci.mozIJSSubScriptLoader);
|
||||
let rootDir = getRootDirectory(gTestPath);
|
||||
let jar = getJar(rootDir);
|
||||
if (jar) {
|
||||
let tmpdir = extractJarToTmp(jar);
|
||||
rootDir = "file://" + tmpdir.path + "/";
|
||||
}
|
||||
/* import-globals-from privacypane_tests_perwindow.js */
|
||||
loader.loadSubScript(rootDir + "privacypane_tests_perwindow.js", this);
|
||||
let runtime = Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsIXULRuntime);
|
||||
|
||||
run_test_subset([
|
||||
test_custom_retention("acceptCookies", "remember"),
|
||||
test_custom_retention("acceptCookies", "custom"),
|
||||
test_custom_retention("acceptThirdPartyMenu", "custom", "visited"),
|
||||
test_custom_retention("acceptThirdPartyMenu", "custom", "always"),
|
||||
test_custom_retention("keepCookiesUntil", "custom", 1),
|
||||
test_custom_retention("keepCookiesUntil", "custom", 2),
|
||||
test_custom_retention("keepCookiesUntil", "custom", 0),
|
||||
test_custom_retention("alwaysClear", "custom"),
|
||||
test_custom_retention("alwaysClear", "custom"),
|
||||
test_historymode_retention("remember", "custom"),
|
||||
]);
|
@ -1,18 +0,0 @@
|
||||
let loader = Cc["@mozilla.org/moz/jssubscript-loader;1"].
|
||||
getService(Ci.mozIJSSubScriptLoader);
|
||||
let rootDir = getRootDirectory(gTestPath);
|
||||
let jar = getJar(rootDir);
|
||||
if (jar) {
|
||||
let tmpdir = extractJarToTmp(jar);
|
||||
rootDir = "file://" + tmpdir.path + "/";
|
||||
}
|
||||
/* import-globals-from privacypane_tests_perwindow.js */
|
||||
loader.loadSubScript(rootDir + "privacypane_tests_perwindow.js", this);
|
||||
|
||||
run_test_subset([
|
||||
test_locbar_suggestion_retention("history", true),
|
||||
test_locbar_suggestion_retention("bookmark", true),
|
||||
test_locbar_suggestion_retention("openpage", false),
|
||||
test_locbar_suggestion_retention("history", true),
|
||||
test_locbar_suggestion_retention("history", false),
|
||||
]);
|
@ -1,27 +0,0 @@
|
||||
let loader = Cc["@mozilla.org/moz/jssubscript-loader;1"].
|
||||
getService(Ci.mozIJSSubScriptLoader);
|
||||
let rootDir = getRootDirectory(gTestPath);
|
||||
let jar = getJar(rootDir);
|
||||
if (jar) {
|
||||
let tmpdir = extractJarToTmp(jar);
|
||||
rootDir = "file://" + tmpdir.path + "/";
|
||||
}
|
||||
/* import-globals-from privacypane_tests_perwindow.js */
|
||||
loader.loadSubScript(rootDir + "privacypane_tests_perwindow.js", this);
|
||||
|
||||
run_test_subset([
|
||||
// history mode should be initialized to remember
|
||||
test_historymode_retention("remember", undefined),
|
||||
|
||||
// history mode should remain remember; toggle acceptCookies checkbox
|
||||
test_custom_retention("acceptCookies", "remember"),
|
||||
|
||||
// history mode should now be custom; set history mode to dontremember
|
||||
test_historymode_retention("dontremember", "custom"),
|
||||
|
||||
// history mode should remain custom; set history mode to remember
|
||||
test_historymode_retention("remember", "custom"),
|
||||
|
||||
// history mode should now be remember
|
||||
test_historymode_retention("remember", "remember"),
|
||||
]);
|
@ -1,64 +0,0 @@
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* 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/. */
|
||||
|
||||
Components.utils.import("resource://gre/modules/Services.jsm");
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
|
||||
// network.proxy.type needs to be backed up and restored because mochitest
|
||||
// changes this setting from the default
|
||||
let oldNetworkProxyType = Services.prefs.getIntPref("network.proxy.type");
|
||||
registerCleanupFunction(function() {
|
||||
Services.prefs.setIntPref("network.proxy.type", oldNetworkProxyType);
|
||||
Services.prefs.clearUserPref("browser.preferences.instantApply");
|
||||
Services.prefs.clearUserPref("network.proxy.share_proxy_settings");
|
||||
for (let proxyType of ["http", "ssl", "ftp", "socks"]) {
|
||||
Services.prefs.clearUserPref("network.proxy." + proxyType);
|
||||
Services.prefs.clearUserPref("network.proxy." + proxyType + "_port");
|
||||
if (proxyType == "http") {
|
||||
continue;
|
||||
}
|
||||
Services.prefs.clearUserPref("network.proxy.backup." + proxyType);
|
||||
Services.prefs.clearUserPref("network.proxy.backup." + proxyType + "_port");
|
||||
}
|
||||
});
|
||||
|
||||
let connectionURL = "chrome://browser/content/preferences/connection.xul";
|
||||
|
||||
// Set a shared proxy and a SOCKS backup
|
||||
Services.prefs.setIntPref("network.proxy.type", 1);
|
||||
Services.prefs.setBoolPref("network.proxy.share_proxy_settings", true);
|
||||
Services.prefs.setCharPref("network.proxy.http", "example.com");
|
||||
Services.prefs.setIntPref("network.proxy.http_port", 1200);
|
||||
Services.prefs.setCharPref("network.proxy.socks", "example.com");
|
||||
Services.prefs.setIntPref("network.proxy.socks_port", 1200);
|
||||
Services.prefs.setCharPref("network.proxy.backup.socks", "127.0.0.1");
|
||||
Services.prefs.setIntPref("network.proxy.backup.socks_port", 9050);
|
||||
|
||||
/*
|
||||
The connection dialog alone won't save onaccept since it uses type="child",
|
||||
so it has to be opened as a sub dialog of the main pref tab.
|
||||
Open the main tab here.
|
||||
*/
|
||||
open_preferences(async function tabOpened(aContentWindow) {
|
||||
is(gBrowser.currentURI.spec, "about:preferences", "about:preferences loaded");
|
||||
let dialog = await openAndLoadSubDialog(connectionURL);
|
||||
let dialogClosingPromise = waitForEvent(dialog.document.documentElement, "dialogclosing");
|
||||
|
||||
ok(dialog, "connection window opened");
|
||||
dialog.document.documentElement.acceptDialog();
|
||||
|
||||
let dialogClosingEvent = await dialogClosingPromise;
|
||||
ok(dialogClosingEvent, "connection window closed");
|
||||
|
||||
// The SOCKS backup should not be replaced by the shared value
|
||||
is(Services.prefs.getCharPref("network.proxy.backup.socks"), "127.0.0.1", "Shared proxy backup shouldn't be replaced");
|
||||
is(Services.prefs.getIntPref("network.proxy.backup.socks_port"), 9050, "Shared proxy port backup shouldn't be replaced");
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
finish();
|
||||
});
|
||||
}
|
@ -1,39 +0,0 @@
|
||||
"use strict";
|
||||
|
||||
function switchToCustomHistoryMode(doc) {
|
||||
// Select the last item in the menulist.
|
||||
let menulist = doc.getElementById("historyMode");
|
||||
menulist.focus();
|
||||
EventUtils.sendKey("UP");
|
||||
}
|
||||
|
||||
function testPrefStateMatchesLockedState() {
|
||||
let win = gBrowser.contentWindow;
|
||||
let doc = win.document;
|
||||
switchToCustomHistoryMode(doc);
|
||||
|
||||
let checkbox = doc.getElementById("alwaysClear");
|
||||
let preference = doc.getElementById("privacy.sanitize.sanitizeOnShutdown");
|
||||
is(checkbox.disabled, preference.locked, "Always Clear checkbox should be enabled when preference is not locked.");
|
||||
|
||||
Services.prefs.clearUserPref("privacy.history.custom");
|
||||
gBrowser.removeCurrentTab();
|
||||
}
|
||||
|
||||
add_task(function setup() {
|
||||
registerCleanupFunction(function resetPreferences() {
|
||||
Services.prefs.unlockPref("privacy.sanitize.sanitizeOnShutdown");
|
||||
Services.prefs.clearUserPref("privacy.history.custom");
|
||||
});
|
||||
});
|
||||
|
||||
add_task(async function test_preference_enabled_when_unlocked() {
|
||||
await openPreferencesViaOpenPreferencesAPI("panePrivacy", {leaveOpen: true});
|
||||
testPrefStateMatchesLockedState();
|
||||
});
|
||||
|
||||
add_task(async function test_preference_disabled_when_locked() {
|
||||
Services.prefs.lockPref("privacy.sanitize.sanitizeOnShutdown");
|
||||
await openPreferencesViaOpenPreferencesAPI("panePrivacy", {leaveOpen: true});
|
||||
testPrefStateMatchesLockedState();
|
||||
});
|
@ -1,43 +0,0 @@
|
||||
var original = Services.prefs.getBoolPref("browser.search.suggest.enabled");
|
||||
|
||||
registerCleanupFunction(() => {
|
||||
Services.prefs.setBoolPref("browser.search.suggest.enabled", original);
|
||||
});
|
||||
|
||||
// Open with suggestions enabled
|
||||
add_task(async function() {
|
||||
Services.prefs.setBoolPref("browser.search.suggest.enabled", true);
|
||||
|
||||
await openPreferencesViaOpenPreferencesAPI("search", { leaveOpen: true });
|
||||
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let urlbarBox = doc.getElementById("urlBarSuggestion");
|
||||
ok(!urlbarBox.disabled, "Checkbox should be enabled");
|
||||
|
||||
Services.prefs.setBoolPref("browser.search.suggest.enabled", false);
|
||||
|
||||
ok(urlbarBox.disabled, "Checkbox should be disabled");
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
||||
|
||||
// Open with suggestions disabled
|
||||
add_task(async function() {
|
||||
Services.prefs.setBoolPref("browser.search.suggest.enabled", false);
|
||||
|
||||
await openPreferencesViaOpenPreferencesAPI("search", { leaveOpen: true });
|
||||
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let urlbarBox = doc.getElementById("urlBarSuggestion");
|
||||
ok(urlbarBox.disabled, "Checkbox should be disabled");
|
||||
|
||||
Services.prefs.setBoolPref("browser.search.suggest.enabled", true);
|
||||
|
||||
ok(!urlbarBox.disabled, "Checkbox should be enabled");
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
||||
|
||||
add_task(async function() {
|
||||
Services.prefs.setBoolPref("browser.search.suggest.enabled", original);
|
||||
});
|
@ -1,424 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
"use strict";
|
||||
|
||||
const { classes: Cc, interfaces: Ci, utils: Cu, results: Cr } = Components;
|
||||
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
/* global sinon */
|
||||
Services.scriptloader.loadSubScript("resource://testing-common/sinon-2.3.2.js");
|
||||
|
||||
const TEST_QUOTA_USAGE_HOST = "example.com";
|
||||
const TEST_QUOTA_USAGE_ORIGIN = "https://" + TEST_QUOTA_USAGE_HOST;
|
||||
const TEST_QUOTA_USAGE_URL = TEST_QUOTA_USAGE_ORIGIN + "/browser/browser/components/preferences/in-content-new/tests/site_data_test.html";
|
||||
const TEST_OFFLINE_HOST = "example.org";
|
||||
const TEST_OFFLINE_ORIGIN = "https://" + TEST_OFFLINE_HOST;
|
||||
const TEST_OFFLINE_URL = TEST_OFFLINE_ORIGIN + "/browser/browser/components/preferences/in-content-new/tests/offline/offline.html";
|
||||
const REMOVE_DIALOG_URL = "chrome://browser/content/preferences/siteDataRemoveSelected.xul";
|
||||
|
||||
const { NetUtil } = Cu.import("resource://gre/modules/NetUtil.jsm", {});
|
||||
const { DownloadUtils } = Cu.import("resource://gre/modules/DownloadUtils.jsm", {});
|
||||
const { SiteDataManager } = Cu.import("resource:///modules/SiteDataManager.jsm", {});
|
||||
const { OfflineAppCacheHelper } = Cu.import("resource:///modules/offlineAppCache.jsm", {});
|
||||
|
||||
const mockOfflineAppCacheHelper = {
|
||||
clear: null,
|
||||
|
||||
originalClear: null,
|
||||
|
||||
register() {
|
||||
this.originalClear = OfflineAppCacheHelper.clear;
|
||||
this.clear = sinon.spy();
|
||||
OfflineAppCacheHelper.clear = this.clear;
|
||||
},
|
||||
|
||||
unregister() {
|
||||
OfflineAppCacheHelper.clear = this.originalClear;
|
||||
}
|
||||
};
|
||||
|
||||
function getPersistentStoragePermStatus(origin) {
|
||||
let uri = NetUtil.newURI(origin);
|
||||
let principal = Services.scriptSecurityManager.createCodebasePrincipal(uri, {});
|
||||
return Services.perms.testExactPermissionFromPrincipal(principal, "persistent-storage");
|
||||
}
|
||||
|
||||
function getQuotaUsage(origin) {
|
||||
return new Promise(resolve => {
|
||||
let uri = NetUtil.newURI(origin);
|
||||
let principal = Services.scriptSecurityManager.createCodebasePrincipal(uri, {});
|
||||
Services.qms.getUsageForPrincipal(principal, request => resolve(request.result.usage));
|
||||
});
|
||||
}
|
||||
|
||||
// XXX: The intermittent bug 1331851
|
||||
// The implementation of nsICacheStorageConsumptionObserver must be passed as weak referenced,
|
||||
// so we must hold this observer here well. If we didn't, there would be a chance that
|
||||
// in Linux debug test run the observer was released before the operation at gecko was completed
|
||||
// (may be because of a relatively quicker GC cycle or a relatively slower operation).
|
||||
// As a result of that, we would never get the cache usage we want so the test would fail from timeout.
|
||||
const cacheUsageGetter = {
|
||||
_promise: null,
|
||||
_resolve: null,
|
||||
get() {
|
||||
if (!this._promise) {
|
||||
this._promise = new Promise(resolve => {
|
||||
this._resolve = resolve;
|
||||
Services.cache2.asyncGetDiskConsumption(this);
|
||||
});
|
||||
}
|
||||
return this._promise;
|
||||
},
|
||||
// nsICacheStorageConsumptionObserver implementations
|
||||
onNetworkCacheDiskConsumption(usage) {
|
||||
cacheUsageGetter._promise = null;
|
||||
cacheUsageGetter._resolve(usage);
|
||||
},
|
||||
QueryInterface: XPCOMUtils.generateQI([
|
||||
Components.interfaces.nsICacheStorageConsumptionObserver,
|
||||
Components.interfaces.nsISupportsWeakReference
|
||||
]),
|
||||
};
|
||||
|
||||
function promiseCookiesCleared() {
|
||||
return TestUtils.topicObserved("cookie-changed", (subj, data) => {
|
||||
return data === "cleared";
|
||||
});
|
||||
}
|
||||
|
||||
registerCleanupFunction(function() {
|
||||
delete window.sinon;
|
||||
mockOfflineAppCacheHelper.unregister();
|
||||
});
|
||||
|
||||
// Test listing site using quota usage or site using appcache
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
|
||||
// Open a test site which would save into appcache
|
||||
await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_OFFLINE_URL);
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
|
||||
// Open a test site which would save into quota manager
|
||||
await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_QUOTA_USAGE_URL);
|
||||
await waitForEvent(gBrowser.selectedBrowser.contentWindow, "test-indexedDB-done");
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
|
||||
let updatedPromise = promiseSiteDataManagerSitesUpdated();
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatedPromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
let dialog = content.gSubDialog._topDialog;
|
||||
let dialogFrame = dialog._frame;
|
||||
let frameDoc = dialogFrame.contentDocument;
|
||||
|
||||
let siteItems = frameDoc.getElementsByTagName("richlistitem");
|
||||
is(siteItems.length, 2, "Should list sites using quota usage or appcache");
|
||||
|
||||
let appcacheSite = frameDoc.querySelector(`richlistitem[host="${TEST_OFFLINE_HOST}"]`);
|
||||
ok(appcacheSite, "Should list site using appcache");
|
||||
|
||||
let qoutaUsageSite = frameDoc.querySelector(`richlistitem[host="${TEST_QUOTA_USAGE_HOST}"]`);
|
||||
ok(qoutaUsageSite, "Should list site using quota usage");
|
||||
|
||||
// Always remember to clean up
|
||||
OfflineAppCacheHelper.clear();
|
||||
await new Promise(resolve => {
|
||||
let principal = Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin(TEST_QUOTA_USAGE_ORIGIN);
|
||||
let request = Services.qms.clearStoragesForPrincipal(principal, null, true);
|
||||
request.callback = resolve;
|
||||
});
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
// Test buttons are disabled and loading message shown while updating sites
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
let updatedPromise = promiseSiteDataManagerSitesUpdated();
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatedPromise;
|
||||
|
||||
let actual = null;
|
||||
let expected = null;
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let clearBtn = doc.getElementById("clearSiteDataButton");
|
||||
let settingsButton = doc.getElementById("siteDataSettings");
|
||||
let prefStrBundle = doc.getElementById("bundlePreferences");
|
||||
let totalSiteDataSizeLabel = doc.getElementById("totalSiteDataSize");
|
||||
is(clearBtn.disabled, false, "Should enable clear button after sites updated");
|
||||
is(settingsButton.disabled, false, "Should enable settings button after sites updated");
|
||||
await SiteDataManager.getTotalUsage()
|
||||
.then(usage => {
|
||||
actual = totalSiteDataSizeLabel.textContent;
|
||||
expected = prefStrBundle.getFormattedString(
|
||||
"totalSiteDataSize", DownloadUtils.convertByteUnits(usage));
|
||||
is(actual, expected, "Should show the right total site data size");
|
||||
});
|
||||
|
||||
Services.obs.notifyObservers(null, "sitedatamanager:updating-sites");
|
||||
is(clearBtn.disabled, true, "Should disable clear button while updating sites");
|
||||
is(settingsButton.disabled, true, "Should disable settings button while updating sites");
|
||||
actual = totalSiteDataSizeLabel.textContent;
|
||||
expected = prefStrBundle.getString("loadingSiteDataSize");
|
||||
is(actual, expected, "Should show the loading message while updating");
|
||||
|
||||
Services.obs.notifyObservers(null, "sitedatamanager:sites-updated");
|
||||
is(clearBtn.disabled, false, "Should enable clear button after sites updated");
|
||||
is(settingsButton.disabled, false, "Should enable settings button after sites updated");
|
||||
await SiteDataManager.getTotalUsage()
|
||||
.then(usage => {
|
||||
actual = totalSiteDataSizeLabel.textContent;
|
||||
expected = prefStrBundle.getFormattedString(
|
||||
"totalSiteDataSize", DownloadUtils.convertByteUnits(usage));
|
||||
is(actual, expected, "Should show the right total site data size");
|
||||
});
|
||||
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
// Test the function of the "Clear All Data" button
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
addPersistentStoragePerm(TEST_QUOTA_USAGE_ORIGIN);
|
||||
|
||||
await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_QUOTA_USAGE_URL);
|
||||
await waitForEvent(gBrowser.selectedBrowser.contentWindow, "test-indexedDB-done");
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
|
||||
// Test the initial states
|
||||
let cacheUsage = await cacheUsageGetter.get();
|
||||
let quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
|
||||
let totalUsage = await SiteDataManager.getTotalUsage();
|
||||
Assert.greater(cacheUsage, 0, "The cache usage should not be 0");
|
||||
Assert.greater(quotaUsage, 0, "The quota usage should not be 0");
|
||||
Assert.greater(totalUsage, 0, "The total usage should not be 0");
|
||||
|
||||
// Test cancelling "Clear All Data"
|
||||
// Click "Clear All Data" button and then cancel
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let cancelPromise = promiseAlertDialogOpen("cancel");
|
||||
let clearBtn = doc.getElementById("clearSiteDataButton");
|
||||
clearBtn.doCommand();
|
||||
await cancelPromise;
|
||||
|
||||
// Test the items are not removed
|
||||
let status = getPersistentStoragePermStatus(TEST_QUOTA_USAGE_ORIGIN);
|
||||
is(status, Ci.nsIPermissionManager.ALLOW_ACTION, "Should not remove permission");
|
||||
|
||||
cacheUsage = await cacheUsageGetter.get();
|
||||
quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
|
||||
totalUsage = await SiteDataManager.getTotalUsage();
|
||||
Assert.greater(cacheUsage, 0, "The cache usage should not be 0");
|
||||
Assert.greater(quotaUsage, 0, "The quota usage should not be 0");
|
||||
Assert.greater(totalUsage, 0, "The total usage should not be 0");
|
||||
// Test cancelling "Clear All Data" ends
|
||||
|
||||
// Test accepting "Clear All Data"
|
||||
// Click "Clear All Data" button and then accept
|
||||
let acceptPromise = promiseAlertDialogOpen("accept");
|
||||
let updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
let cookiesClearedPromise = promiseCookiesCleared();
|
||||
|
||||
mockOfflineAppCacheHelper.register();
|
||||
clearBtn.doCommand();
|
||||
await acceptPromise;
|
||||
await updatePromise;
|
||||
mockOfflineAppCacheHelper.unregister();
|
||||
|
||||
// Test all the items are removed
|
||||
await cookiesClearedPromise;
|
||||
|
||||
ok(mockOfflineAppCacheHelper.clear.calledOnce, "Should clear app cache");
|
||||
|
||||
status = getPersistentStoragePermStatus(TEST_QUOTA_USAGE_ORIGIN);
|
||||
is(status, Ci.nsIPermissionManager.UNKNOWN_ACTION, "Should remove permission");
|
||||
|
||||
cacheUsage = await cacheUsageGetter.get();
|
||||
quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
|
||||
totalUsage = await SiteDataManager.getTotalUsage();
|
||||
is(cacheUsage, 0, "The cache usage should be removed");
|
||||
is(quotaUsage, 0, "The quota usage should be removed");
|
||||
is(totalUsage, 0, "The total usage should be removed");
|
||||
// Test accepting "Clear All Data" ends
|
||||
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
// Test sorting
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
mockSiteDataManager.register(SiteDataManager);
|
||||
mockSiteDataManager.fakeSites = [
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024 * 2,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://books.foo.com"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: 1024 * 3,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://cinema.bar.com"),
|
||||
persisted: true
|
||||
},
|
||||
];
|
||||
|
||||
let updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
|
||||
let dialog = content.gSubDialog._topDialog;
|
||||
let dialogFrame = dialog._frame;
|
||||
let frameDoc = dialogFrame.contentDocument;
|
||||
let hostCol = frameDoc.getElementById("hostCol");
|
||||
let usageCol = frameDoc.getElementById("usageCol");
|
||||
let statusCol = frameDoc.getElementById("statusCol");
|
||||
let sitesList = frameDoc.getElementById("sitesList");
|
||||
|
||||
// Test default sorting
|
||||
assertSortByUsage("descending");
|
||||
|
||||
// Test sorting on the usage column
|
||||
usageCol.click();
|
||||
assertSortByUsage("ascending");
|
||||
usageCol.click();
|
||||
assertSortByUsage("descending");
|
||||
|
||||
// Test sorting on the host column
|
||||
hostCol.click();
|
||||
assertSortByHost("ascending");
|
||||
hostCol.click();
|
||||
assertSortByHost("descending");
|
||||
|
||||
// Test sorting on the permission status column
|
||||
statusCol.click();
|
||||
assertSortByStatus("ascending");
|
||||
statusCol.click();
|
||||
assertSortByStatus("descending");
|
||||
|
||||
mockSiteDataManager.unregister();
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
|
||||
function assertSortByHost(order) {
|
||||
let siteItems = sitesList.getElementsByTagName("richlistitem");
|
||||
for (let i = 0; i < siteItems.length - 1; ++i) {
|
||||
let aHost = siteItems[i].getAttribute("host");
|
||||
let bHost = siteItems[i + 1].getAttribute("host");
|
||||
let result = aHost.localeCompare(bHost);
|
||||
if (order == "ascending") {
|
||||
Assert.lessOrEqual(result, 0, "Should sort sites in the ascending order by host");
|
||||
} else {
|
||||
Assert.greaterOrEqual(result, 0, "Should sort sites in the descending order by host");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function assertSortByStatus(order) {
|
||||
let siteItems = sitesList.getElementsByTagName("richlistitem");
|
||||
for (let i = 0; i < siteItems.length - 1; ++i) {
|
||||
let aHost = siteItems[i].getAttribute("host");
|
||||
let bHost = siteItems[i + 1].getAttribute("host");
|
||||
let a = findSiteByHost(aHost);
|
||||
let b = findSiteByHost(bHost);
|
||||
let result = 0;
|
||||
if (a.persisted && !b.persisted) {
|
||||
result = 1;
|
||||
} else if (!a.persisted && b.persisted) {
|
||||
result = -1;
|
||||
}
|
||||
if (order == "ascending") {
|
||||
Assert.lessOrEqual(result, 0, "Should sort sites in the ascending order by permission status");
|
||||
} else {
|
||||
Assert.greaterOrEqual(result, 0, "Should sort sites in the descending order by permission status");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function assertSortByUsage(order) {
|
||||
let siteItems = sitesList.getElementsByTagName("richlistitem");
|
||||
for (let i = 0; i < siteItems.length - 1; ++i) {
|
||||
let aHost = siteItems[i].getAttribute("host");
|
||||
let bHost = siteItems[i + 1].getAttribute("host");
|
||||
let a = findSiteByHost(aHost);
|
||||
let b = findSiteByHost(bHost);
|
||||
let result = a.usage - b.usage;
|
||||
if (order == "ascending") {
|
||||
Assert.lessOrEqual(result, 0, "Should sort sites in the ascending order by usage");
|
||||
} else {
|
||||
Assert.greaterOrEqual(result, 0, "Should sort sites in the descending order by usage");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function findSiteByHost(host) {
|
||||
return mockSiteDataManager.fakeSites.find(site => site.principal.URI.host == host);
|
||||
}
|
||||
});
|
||||
|
||||
// Test search on the host column
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
mockSiteDataManager.register(SiteDataManager);
|
||||
mockSiteDataManager.fakeSites = [
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://shopping.xyz.com"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://cinema.bar.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://email.bar.com"),
|
||||
persisted: false
|
||||
},
|
||||
];
|
||||
let fakeHosts = mockSiteDataManager.fakeSites.map(site => site.principal.URI.host);
|
||||
|
||||
let updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let frameDoc = content.gSubDialog._topDialog._frame.contentDocument;
|
||||
let searchBox = frameDoc.getElementById("searchBox");
|
||||
|
||||
searchBox.value = "xyz";
|
||||
searchBox.doCommand();
|
||||
assertSitesListed(doc, fakeHosts.filter(host => host.includes("xyz")));
|
||||
|
||||
searchBox.value = "bar";
|
||||
searchBox.doCommand();
|
||||
assertSitesListed(doc, fakeHosts.filter(host => host.includes("bar")));
|
||||
|
||||
searchBox.value = "";
|
||||
searchBox.doCommand();
|
||||
assertSitesListed(doc, fakeHosts);
|
||||
|
||||
mockSiteDataManager.unregister();
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
@ -1,376 +0,0 @@
|
||||
"use strict";
|
||||
const { SiteDataManager } = Cu.import("resource:///modules/SiteDataManager.jsm", {});
|
||||
const REMOVE_DIALOG_URL = "chrome://browser/content/preferences/siteDataRemoveSelected.xul";
|
||||
|
||||
function promiseSettingsDialogClose() {
|
||||
return new Promise(resolve => {
|
||||
let win = gBrowser.selectedBrowser.contentWindow;
|
||||
let dialogOverlay = win.gSubDialog._topDialog._overlay;
|
||||
let dialogWin = win.gSubDialog._topDialog._frame.contentWindow;
|
||||
dialogWin.addEventListener("unload", function unload() {
|
||||
if (dialogWin.document.documentURI === "chrome://browser/content/preferences/siteDataSettings.xul") {
|
||||
isnot(dialogOverlay.style.visibility, "visible", "The Settings dialog should be hidden");
|
||||
resolve();
|
||||
}
|
||||
}, { once: true });
|
||||
});
|
||||
}
|
||||
|
||||
function assertAllSitesNotListed(win) {
|
||||
let frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
let removeBtn = frameDoc.getElementById("removeSelected");
|
||||
let removeAllBtn = frameDoc.getElementById("removeAll");
|
||||
let sitesList = frameDoc.getElementById("sitesList");
|
||||
let sites = sitesList.getElementsByTagName("richlistitem");
|
||||
is(sites.length, 0, "Should not list all sites");
|
||||
is(removeBtn.disabled, true, "Should disable the removeSelected button");
|
||||
is(removeAllBtn.disabled, true, "Should disable the removeAllBtn button");
|
||||
}
|
||||
|
||||
// Test selecting and removing all sites one by one
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
mockSiteDataManager.register(SiteDataManager);
|
||||
mockSiteDataManager.fakeSites = [
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://shopping.xyz.com"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://cinema.bar.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://email.bar.com"),
|
||||
persisted: false
|
||||
},
|
||||
];
|
||||
let fakeHosts = mockSiteDataManager.fakeSites.map(site => site.principal.URI.host);
|
||||
|
||||
let updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
|
||||
let win = gBrowser.selectedBrowser.contentWindow;
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let frameDoc = null;
|
||||
let saveBtn = null;
|
||||
let cancelBtn = null;
|
||||
let settingsDialogClosePromise = null;
|
||||
|
||||
// Test the initial state
|
||||
assertSitesListed(doc, fakeHosts);
|
||||
|
||||
// Test the "Cancel" button
|
||||
settingsDialogClosePromise = promiseSettingsDialogClose();
|
||||
frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
cancelBtn = frameDoc.getElementById("cancel");
|
||||
removeAllSitesOneByOne();
|
||||
assertAllSitesNotListed(win);
|
||||
cancelBtn.doCommand();
|
||||
await settingsDialogClosePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
assertSitesListed(doc, fakeHosts);
|
||||
|
||||
// Test the "Save Changes" button but cancelling save
|
||||
let cancelPromise = promiseAlertDialogOpen("cancel");
|
||||
settingsDialogClosePromise = promiseSettingsDialogClose();
|
||||
frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
saveBtn = frameDoc.getElementById("save");
|
||||
removeAllSitesOneByOne();
|
||||
assertAllSitesNotListed(win);
|
||||
saveBtn.doCommand();
|
||||
await cancelPromise;
|
||||
await settingsDialogClosePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
assertSitesListed(doc, fakeHosts);
|
||||
|
||||
// Test the "Save Changes" button and accepting save
|
||||
let acceptPromise = promiseAlertDialogOpen("accept");
|
||||
settingsDialogClosePromise = promiseSettingsDialogClose();
|
||||
updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
saveBtn = frameDoc.getElementById("save");
|
||||
removeAllSitesOneByOne();
|
||||
assertAllSitesNotListed(win);
|
||||
saveBtn.doCommand();
|
||||
await acceptPromise;
|
||||
await settingsDialogClosePromise;
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
assertAllSitesNotListed(win);
|
||||
|
||||
mockSiteDataManager.unregister();
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
|
||||
function removeAllSitesOneByOne() {
|
||||
frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
let removeBtn = frameDoc.getElementById("removeSelected");
|
||||
let sitesList = frameDoc.getElementById("sitesList");
|
||||
let sites = sitesList.getElementsByTagName("richlistitem");
|
||||
for (let i = sites.length - 1; i >= 0; --i) {
|
||||
sites[i].click();
|
||||
removeBtn.doCommand();
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
// Test selecting and removing partial sites
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
mockSiteDataManager.register(SiteDataManager);
|
||||
mockSiteDataManager.fakeSites = [
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://shopping.xyz.com"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://cinema.bar.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://email.bar.com"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://s3-us-west-2.amazonaws.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://127.0.0.1"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://[0:0:0:0:0:0:0:1]"),
|
||||
persisted: true
|
||||
},
|
||||
];
|
||||
let fakeHosts = mockSiteDataManager.fakeSites.map(site => site.principal.URI.host);
|
||||
|
||||
let updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
|
||||
let win = gBrowser.selectedBrowser.contentWindow;
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let frameDoc = null;
|
||||
let saveBtn = null;
|
||||
let cancelBtn = null;
|
||||
let removeDialogOpenPromise = null;
|
||||
let settingsDialogClosePromise = null;
|
||||
|
||||
// Test the initial state
|
||||
assertSitesListed(doc, fakeHosts);
|
||||
|
||||
// Test the "Cancel" button
|
||||
settingsDialogClosePromise = promiseSettingsDialogClose();
|
||||
frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
cancelBtn = frameDoc.getElementById("cancel");
|
||||
removeSelectedSite(fakeHosts.slice(0, 2));
|
||||
assertSitesListed(doc, fakeHosts.slice(2));
|
||||
cancelBtn.doCommand();
|
||||
await settingsDialogClosePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
assertSitesListed(doc, fakeHosts);
|
||||
|
||||
// Test the "Save Changes" button but canceling save
|
||||
removeDialogOpenPromise = promiseWindowDialogOpen("cancel", REMOVE_DIALOG_URL);
|
||||
settingsDialogClosePromise = promiseSettingsDialogClose();
|
||||
frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
saveBtn = frameDoc.getElementById("save");
|
||||
removeSelectedSite(fakeHosts.slice(0, 2));
|
||||
assertSitesListed(doc, fakeHosts.slice(2));
|
||||
saveBtn.doCommand();
|
||||
await removeDialogOpenPromise;
|
||||
await settingsDialogClosePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
assertSitesListed(doc, fakeHosts);
|
||||
|
||||
// Test the "Save Changes" button and accepting save
|
||||
removeDialogOpenPromise = promiseWindowDialogOpen("accept", REMOVE_DIALOG_URL);
|
||||
settingsDialogClosePromise = promiseSettingsDialogClose();
|
||||
frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
saveBtn = frameDoc.getElementById("save");
|
||||
removeSelectedSite(fakeHosts.slice(0, 2));
|
||||
assertSitesListed(doc, fakeHosts.slice(2));
|
||||
saveBtn.doCommand();
|
||||
await removeDialogOpenPromise;
|
||||
await settingsDialogClosePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
assertSitesListed(doc, fakeHosts.slice(2));
|
||||
|
||||
mockSiteDataManager.unregister();
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
|
||||
function removeSelectedSite(hosts) {
|
||||
frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
let removeBtn = frameDoc.getElementById("removeSelected");
|
||||
let sitesList = frameDoc.getElementById("sitesList");
|
||||
hosts.forEach(host => {
|
||||
let site = sitesList.querySelector(`richlistitem[host="${host}"]`);
|
||||
if (site) {
|
||||
site.click();
|
||||
removeBtn.doCommand();
|
||||
} else {
|
||||
ok(false, `Should not select and remove inexistent site of ${host}`);
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
// Test searching and then removing only visible sites
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
mockSiteDataManager.register(SiteDataManager);
|
||||
mockSiteDataManager.fakeSites = [
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://shopping.xyz.com"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://cinema.bar.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://email.bar.com"),
|
||||
persisted: false
|
||||
},
|
||||
];
|
||||
let fakeHosts = mockSiteDataManager.fakeSites.map(site => site.principal.URI.host);
|
||||
|
||||
let updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
|
||||
// Search "foo" to only list foo.com sites
|
||||
let win = gBrowser.selectedBrowser.contentWindow;
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
let searchBox = frameDoc.getElementById("searchBox");
|
||||
searchBox.value = "xyz";
|
||||
searchBox.doCommand();
|
||||
assertSitesListed(doc, fakeHosts.filter(host => host.includes("xyz")));
|
||||
|
||||
// Test only removing all visible sites listed
|
||||
updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
let acceptRemovePromise = promiseWindowDialogOpen("accept", REMOVE_DIALOG_URL);
|
||||
let settingsDialogClosePromise = promiseSettingsDialogClose();
|
||||
let removeAllBtn = frameDoc.getElementById("removeAll");
|
||||
let saveBtn = frameDoc.getElementById("save");
|
||||
removeAllBtn.doCommand();
|
||||
saveBtn.doCommand();
|
||||
await acceptRemovePromise;
|
||||
await settingsDialogClosePromise;
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
assertSitesListed(doc, fakeHosts.filter(host => !host.includes("xyz")));
|
||||
|
||||
mockSiteDataManager.unregister();
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
// Test dynamically clearing all site data
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
mockSiteDataManager.register(SiteDataManager);
|
||||
mockSiteDataManager.fakeSites = [
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://shopping.xyz.com"),
|
||||
persisted: false
|
||||
},
|
||||
];
|
||||
let fakeHosts = mockSiteDataManager.fakeSites.map(site => site.principal.URI.host);
|
||||
|
||||
// Test the initial state
|
||||
let updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
assertSitesListed(doc, fakeHosts);
|
||||
|
||||
// Add more sites dynamically
|
||||
mockSiteDataManager.fakeSites.push({
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://cinema.bar.com"),
|
||||
persisted: true
|
||||
}, {
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://email.bar.com"),
|
||||
persisted: false
|
||||
});
|
||||
|
||||
// Test clearing all site data dynamically
|
||||
let win = gBrowser.selectedBrowser.contentWindow;
|
||||
let frameDoc = win.gSubDialog._topDialog._frame.contentDocument;
|
||||
updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
let acceptRemovePromise = promiseAlertDialogOpen("accept");
|
||||
let settingsDialogClosePromise = promiseSettingsDialogClose();
|
||||
let removeAllBtn = frameDoc.getElementById("removeAll");
|
||||
let saveBtn = frameDoc.getElementById("save");
|
||||
removeAllBtn.doCommand();
|
||||
saveBtn.doCommand();
|
||||
await acceptRemovePromise;
|
||||
await settingsDialogClosePromise;
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
assertAllSitesNotListed(win);
|
||||
|
||||
mockSiteDataManager.unregister();
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
@ -1,107 +0,0 @@
|
||||
"use strict";
|
||||
const { SiteDataManager } = Cu.import("resource:///modules/SiteDataManager.jsm", {});
|
||||
const { DownloadUtils } = Cu.import("resource://gre/modules/DownloadUtils.jsm", {});
|
||||
|
||||
// Test not displaying sites which store 0 byte and don't have persistent storage.
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
mockSiteDataManager.register(SiteDataManager);
|
||||
mockSiteDataManager.fakeSites = [
|
||||
{
|
||||
usage: 0,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 0,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://shopping.xyz.com"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://cinema.bar.com"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: 1024,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://email.bar.com"),
|
||||
persisted: false
|
||||
},
|
||||
];
|
||||
let fakeHosts = mockSiteDataManager.fakeSites.map(site => site.principal.URI.host);
|
||||
|
||||
let updatePromise = promiseSiteDataManagerSitesUpdated();
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatePromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
assertSitesListed(doc, fakeHosts.filter(host => host != "shopping.xyz.com"));
|
||||
|
||||
mockSiteDataManager.unregister();
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
||||
|
||||
// Test grouping and listing sites across scheme, port and origin attributes by host
|
||||
add_task(async function() {
|
||||
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
|
||||
const quotaUsage = 1024;
|
||||
mockSiteDataManager.register(SiteDataManager);
|
||||
mockSiteDataManager.fakeSites = [
|
||||
{
|
||||
usage: quotaUsage,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com^userContextId=1"),
|
||||
persisted: true
|
||||
},
|
||||
{
|
||||
usage: quotaUsage,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: quotaUsage,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("https://account.xyz.com:123"),
|
||||
persisted: false
|
||||
},
|
||||
{
|
||||
usage: quotaUsage,
|
||||
principal: Services.scriptSecurityManager
|
||||
.createCodebasePrincipalFromOrigin("http://account.xyz.com"),
|
||||
persisted: false
|
||||
},
|
||||
];
|
||||
|
||||
let updatedPromise = promiseSiteDataManagerSitesUpdated();
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
|
||||
await updatedPromise;
|
||||
await openSiteDataSettingsDialog();
|
||||
let win = gBrowser.selectedBrowser.contentWindow;
|
||||
let dialogFrame = win.gSubDialog._topDialog._frame;
|
||||
let frameDoc = dialogFrame.contentDocument;
|
||||
|
||||
let siteItems = frameDoc.getElementsByTagName("richlistitem");
|
||||
is(siteItems.length, 1, "Should group sites across scheme, port and origin attributes");
|
||||
|
||||
let expected = "account.xyz.com";
|
||||
let host = siteItems[0].getAttribute("host");
|
||||
is(host, expected, "Should group and list sites by host");
|
||||
|
||||
let prefStrBundle = frameDoc.getElementById("bundlePreferences");
|
||||
expected = prefStrBundle.getFormattedString("siteUsage",
|
||||
DownloadUtils.convertByteUnits(quotaUsage * mockSiteDataManager.fakeSites.length));
|
||||
let usage = siteItems[0].getAttribute("usage");
|
||||
is(usage, expected, "Should sum up usages across scheme, port and origin attributes");
|
||||
|
||||
expected = prefStrBundle.getString("persistent");
|
||||
let status = siteItems[0].getAttribute("status");
|
||||
is(status, expected, "Should mark persisted status across scheme, port and origin attributes");
|
||||
|
||||
mockSiteDataManager.unregister();
|
||||
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
|
||||
});
|
@ -1,76 +0,0 @@
|
||||
"use strict";
|
||||
const PERMISSIONS_URL = "chrome://browser/content/preferences/permissions.xul";
|
||||
|
||||
var exceptionsDialog;
|
||||
|
||||
add_task(async function openLoginExceptionsSubDialog() {
|
||||
// Undo the save password change.
|
||||
registerCleanupFunction(async function() {
|
||||
await ContentTask.spawn(gBrowser.selectedBrowser, null, function() {
|
||||
let doc = content.document;
|
||||
let savePasswordCheckBox = doc.getElementById("savePasswords");
|
||||
if (savePasswordCheckBox.checked) {
|
||||
savePasswordCheckBox.click();
|
||||
}
|
||||
});
|
||||
|
||||
gBrowser.removeCurrentTab();
|
||||
});
|
||||
|
||||
await openPreferencesViaOpenPreferencesAPI("privacy", {leaveOpen: true});
|
||||
|
||||
let dialogOpened = promiseLoadSubDialog(PERMISSIONS_URL);
|
||||
|
||||
await ContentTask.spawn(gBrowser.selectedBrowser, null, function() {
|
||||
let doc = content.document;
|
||||
let savePasswordCheckBox = doc.getElementById("savePasswords");
|
||||
Assert.ok(!savePasswordCheckBox.checked,
|
||||
"Save Password CheckBox should be unchecked by default");
|
||||
savePasswordCheckBox.click();
|
||||
|
||||
let loginExceptionsButton = doc.getElementById("passwordExceptions");
|
||||
loginExceptionsButton.click();
|
||||
});
|
||||
|
||||
exceptionsDialog = await dialogOpened;
|
||||
});
|
||||
|
||||
add_task(async function addALoginException() {
|
||||
let doc = exceptionsDialog.document;
|
||||
|
||||
let tree = doc.getElementById("permissionsTree");
|
||||
Assert.equal(tree.view.rowCount, 0, "Row count should initially be 0");
|
||||
|
||||
let inputBox = doc.getElementById("url");
|
||||
inputBox.focus();
|
||||
|
||||
EventUtils.sendString("www.example.com", exceptionsDialog);
|
||||
|
||||
let btnBlock = doc.getElementById("btnBlock");
|
||||
btnBlock.click();
|
||||
|
||||
await waitForCondition(() => tree.view.rowCount == 1);
|
||||
|
||||
Assert.equal(tree.view.getCellText(0, tree.treeBoxObject.columns.getColumnAt(0)),
|
||||
"http://www.example.com");
|
||||
});
|
||||
|
||||
add_task(async function deleteALoginException() {
|
||||
let doc = exceptionsDialog.document;
|
||||
|
||||
let tree = doc.getElementById("permissionsTree");
|
||||
Assert.equal(tree.view.rowCount, 1, "Row count should initially be 1");
|
||||
tree.focus();
|
||||
tree.view.selection.select(0);
|
||||
|
||||
if (AppConstants.platform == "macosx") {
|
||||
EventUtils.synthesizeKey("VK_BACK_SPACE", {});
|
||||
} else {
|
||||
EventUtils.synthesizeKey("VK_DELETE", {});
|
||||
}
|
||||
|
||||
await waitForCondition(() => tree.view.rowCount == 0);
|
||||
|
||||
is_element_visible(content.gSubDialog._dialogs[0]._box,
|
||||
"Subdialog is visible after deleting an element");
|
||||
});
|
@ -1,347 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
"use strict";
|
||||
|
||||
/**
|
||||
* Tests for the sub-dialog infrastructure, not for actual sub-dialog functionality.
|
||||
*/
|
||||
|
||||
const gDialogURL = getRootDirectory(gTestPath) + "subdialog.xul";
|
||||
const gDialogURL2 = getRootDirectory(gTestPath) + "subdialog2.xul";
|
||||
|
||||
function open_subdialog_and_test_generic_start_state(browser, domcontentloadedFn, url = gDialogURL) {
|
||||
let domcontentloadedFnStr = domcontentloadedFn ?
|
||||
"(" + domcontentloadedFn.toString() + ")()" :
|
||||
"";
|
||||
return ContentTask.spawn(browser, {url, domcontentloadedFnStr}, async function(args) {
|
||||
let rv = { acceptCount: 0 };
|
||||
let win = content.window;
|
||||
content.gSubDialog.open(args.url, null, rv);
|
||||
let subdialog = content.gSubDialog._topDialog;
|
||||
|
||||
info("waiting for subdialog DOMFrameContentLoaded");
|
||||
await ContentTaskUtils.waitForEvent(win, "DOMFrameContentLoaded", true);
|
||||
let result;
|
||||
if (args.domcontentloadedFnStr) {
|
||||
// eslint-disable-next-line no-eval
|
||||
result = eval(args.domcontentloadedFnStr);
|
||||
}
|
||||
|
||||
info("waiting for subdialog load");
|
||||
await ContentTaskUtils.waitForEvent(subdialog._overlay, "dialogopen");
|
||||
info("subdialog window is loaded");
|
||||
|
||||
let expectedStyleSheetURLs = subdialog._injectedStyleSheets.slice(0);
|
||||
for (let styleSheet of subdialog._frame.contentDocument.styleSheets) {
|
||||
let index = expectedStyleSheetURLs.indexOf(styleSheet.href);
|
||||
if (index >= 0) {
|
||||
expectedStyleSheetURLs.splice(index, 1);
|
||||
}
|
||||
}
|
||||
|
||||
Assert.ok(!!subdialog._frame.contentWindow, "The dialog should be non-null");
|
||||
Assert.notEqual(subdialog._frame.contentWindow.location.toString(), "about:blank",
|
||||
"Subdialog URL should not be about:blank");
|
||||
Assert.equal(win.getComputedStyle(subdialog._overlay).visibility, "visible",
|
||||
"Overlay should be visible");
|
||||
Assert.equal(expectedStyleSheetURLs.length, 0,
|
||||
"No stylesheets that were expected are missing");
|
||||
return result;
|
||||
});
|
||||
}
|
||||
|
||||
async function close_subdialog_and_test_generic_end_state(browser, closingFn, closingButton, acceptCount, options) {
|
||||
let getDialogsCount = () => {
|
||||
return ContentTask.spawn(browser, null, () =>
|
||||
content.window.gSubDialog._dialogs.length);
|
||||
};
|
||||
let getStackChildrenCount = () => {
|
||||
return ContentTask.spawn(browser, null, () =>
|
||||
content.window.gSubDialog._dialogStack.children.length);
|
||||
};
|
||||
let dialogclosingPromise = ContentTask.spawn(browser, {closingButton, acceptCount}, async function(expectations) {
|
||||
let win = content.window;
|
||||
let subdialog = win.gSubDialog._topDialog;
|
||||
let frame = subdialog._frame;
|
||||
info("waiting for dialogclosing");
|
||||
let closingEvent =
|
||||
await ContentTaskUtils.waitForEvent(frame.contentWindow, "dialogclosing");
|
||||
let contentClosingButton = closingEvent.detail.button;
|
||||
let actualAcceptCount = frame.contentWindow.arguments &&
|
||||
frame.contentWindow.arguments[0].acceptCount;
|
||||
|
||||
info("waiting for about:blank load");
|
||||
await ContentTaskUtils.waitForEvent(frame, "load");
|
||||
|
||||
Assert.notEqual(win.getComputedStyle(subdialog._overlay).visibility, "visible",
|
||||
"overlay is not visible");
|
||||
Assert.equal(frame.getAttribute("style"), "", "inline styles should be cleared");
|
||||
Assert.equal(frame.contentWindow.location.href.toString(), "about:blank",
|
||||
"sub-dialog should be unloaded");
|
||||
Assert.equal(contentClosingButton, expectations.closingButton,
|
||||
"closing event should indicate button was '" + expectations.closingButton + "'");
|
||||
Assert.equal(actualAcceptCount, expectations.acceptCount,
|
||||
"should be 1 if accepted, 0 if canceled, undefined if closed w/out button");
|
||||
});
|
||||
let initialDialogsCount = await getDialogsCount();
|
||||
let initialStackChildrenCount = await getStackChildrenCount();
|
||||
if (options && options.runClosingFnOutsideOfContentTask) {
|
||||
await closingFn();
|
||||
} else {
|
||||
ContentTask.spawn(browser, null, closingFn);
|
||||
}
|
||||
|
||||
await dialogclosingPromise;
|
||||
let endDialogsCount = await getDialogsCount();
|
||||
let endStackChildrenCount = await getStackChildrenCount();
|
||||
Assert.equal(initialDialogsCount - 1, endDialogsCount,
|
||||
"dialog count should decrease by 1");
|
||||
Assert.equal(initialStackChildrenCount - 1, endStackChildrenCount,
|
||||
"stack children count should decrease by 1");
|
||||
}
|
||||
|
||||
let tab;
|
||||
|
||||
add_task(async function test_initialize() {
|
||||
tab = await BrowserTestUtils.openNewForegroundTab(gBrowser, "about:preferences");
|
||||
});
|
||||
|
||||
add_task(async function check_titlebar_focus_returnval_titlechanges_accepting() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
|
||||
let domtitlechangedPromise = BrowserTestUtils.waitForEvent(tab.linkedBrowser, "DOMTitleChanged");
|
||||
await ContentTask.spawn(tab.linkedBrowser, null, async function() {
|
||||
let dialog = content.window.gSubDialog._topDialog;
|
||||
let dialogWin = dialog._frame.contentWindow;
|
||||
let dialogTitleElement = dialog._titleElement;
|
||||
Assert.equal(dialogTitleElement.textContent, "Sample sub-dialog",
|
||||
"Title should be correct initially");
|
||||
Assert.equal(dialogWin.document.activeElement.value, "Default text",
|
||||
"Textbox with correct text is focused");
|
||||
dialogWin.document.title = "Updated title";
|
||||
});
|
||||
|
||||
info("waiting for DOMTitleChanged event");
|
||||
await domtitlechangedPromise;
|
||||
|
||||
ContentTask.spawn(tab.linkedBrowser, null, async function() {
|
||||
let dialogTitleElement = content.window.gSubDialog._topDialog._titleElement;
|
||||
Assert.equal(dialogTitleElement.textContent, "Updated title",
|
||||
"subdialog should have updated title");
|
||||
});
|
||||
|
||||
// Accept the dialog
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentDocument.documentElement.acceptDialog(); },
|
||||
"accept", 1);
|
||||
});
|
||||
|
||||
add_task(async function check_canceling_dialog() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
|
||||
info("canceling the dialog");
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentDocument.documentElement.cancelDialog(); },
|
||||
"cancel", 0);
|
||||
});
|
||||
|
||||
add_task(async function check_reopening_dialog() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
info("opening another dialog which will close the first");
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser, "", gDialogURL2);
|
||||
|
||||
ContentTask.spawn(tab.linkedBrowser, null, async function() {
|
||||
let win = content.window;
|
||||
let dialogs = win.gSubDialog._dialogs;
|
||||
let lowerDialog = dialogs[0];
|
||||
let topDialog = dialogs[1];
|
||||
Assert.equal(dialogs.length, 2, "There should be two visible dialogs");
|
||||
Assert.equal(win.getComputedStyle(topDialog._overlay).visibility, "visible",
|
||||
"The top dialog should be visible");
|
||||
Assert.equal(win.getComputedStyle(lowerDialog._overlay).visibility, "visible",
|
||||
"The lower dialog should be visible");
|
||||
Assert.equal(win.getComputedStyle(topDialog._overlay).backgroundColor, "rgba(0, 0, 0, 0.5)",
|
||||
"The top dialog should have a semi-transparent overlay");
|
||||
Assert.equal(win.getComputedStyle(lowerDialog._overlay).backgroundColor, "rgba(0, 0, 0, 0)",
|
||||
"The lower dialog should not have an overlay");
|
||||
});
|
||||
|
||||
info("closing two dialogs");
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentDocument.documentElement.acceptDialog(); },
|
||||
"accept", 1);
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentDocument.documentElement.acceptDialog(); },
|
||||
"accept", 1);
|
||||
});
|
||||
|
||||
add_task(async function check_opening_while_closing() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
info("closing");
|
||||
content.window.gSubDialog._topDialog.close();
|
||||
info("reopening immediately after calling .close()");
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentDocument.documentElement.acceptDialog(); },
|
||||
"accept", 1);
|
||||
|
||||
});
|
||||
|
||||
add_task(async function window_close_on_dialog() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
|
||||
info("canceling the dialog");
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentWindow.window.close(); },
|
||||
null, 0);
|
||||
});
|
||||
|
||||
add_task(async function click_close_button_on_dialog() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
|
||||
info("canceling the dialog");
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { return BrowserTestUtils.synthesizeMouseAtCenter(".dialogClose", {}, tab.linkedBrowser); },
|
||||
null, 0, {runClosingFnOutsideOfContentTask: true});
|
||||
});
|
||||
|
||||
add_task(async function background_click_should_close_dialog() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
|
||||
// Clicking on an inactive part of dialog itself should not close the dialog.
|
||||
// Click the dialog title bar here to make sure nothing happens.
|
||||
info("clicking the dialog title bar");
|
||||
BrowserTestUtils.synthesizeMouseAtCenter(".dialogTitle", {}, tab.linkedBrowser);
|
||||
|
||||
// Close the dialog by clicking on the overlay background. Simulate a click
|
||||
// at point (2,2) instead of (0,0) so we are sure we're clicking on the
|
||||
// overlay background instead of some boundary condition that a real user
|
||||
// would never click.
|
||||
info("clicking the overlay background");
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { return BrowserTestUtils.synthesizeMouseAtPoint(2, 2, {}, tab.linkedBrowser); },
|
||||
null, 0, {runClosingFnOutsideOfContentTask: true});
|
||||
});
|
||||
|
||||
add_task(async function back_navigation_on_subdialog_should_close_dialog() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
|
||||
info("canceling the dialog");
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.goBack(); },
|
||||
null, undefined);
|
||||
});
|
||||
|
||||
add_task(async function back_navigation_on_browser_tab_should_close_dialog() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
|
||||
info("canceling the dialog");
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { tab.linkedBrowser.goBack(); },
|
||||
null, undefined, {runClosingFnOutsideOfContentTask: true});
|
||||
});
|
||||
|
||||
add_task(async function escape_should_close_dialog() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
|
||||
info("canceling the dialog");
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { return BrowserTestUtils.synthesizeKey("VK_ESCAPE", {}, tab.linkedBrowser); },
|
||||
"cancel", 0, {runClosingFnOutsideOfContentTask: true});
|
||||
});
|
||||
|
||||
add_task(async function correct_width_and_height_should_be_used_for_dialog() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser);
|
||||
|
||||
await ContentTask.spawn(tab.linkedBrowser, null, async function() {
|
||||
let frameStyle = content.window.gSubDialog._topDialog._frame.style;
|
||||
Assert.equal(frameStyle.width, "32em",
|
||||
"Width should be set on the frame from the dialog");
|
||||
Assert.equal(frameStyle.height, "5em",
|
||||
"Height should be set on the frame from the dialog");
|
||||
});
|
||||
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentWindow.window.close(); },
|
||||
null, 0);
|
||||
});
|
||||
|
||||
add_task(async function wrapped_text_in_dialog_should_have_expected_scrollHeight() {
|
||||
let oldHeight = await open_subdialog_and_test_generic_start_state(tab.linkedBrowser, function domcontentloadedFn() {
|
||||
let frame = content.window.gSubDialog._topDialog._frame;
|
||||
let doc = frame.contentDocument;
|
||||
let scrollHeight = doc.documentElement.scrollHeight;
|
||||
doc.documentElement.style.removeProperty("height");
|
||||
doc.getElementById("desc").textContent = `
|
||||
Sed ut perspiciatis unde omnis iste natus error sit voluptatem accusantium doloremque
|
||||
laudantium, totam rem aperiam, eaque ipsa quae ab illo inventore veritatis et quasi
|
||||
architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas
|
||||
sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos qui ratione
|
||||
laudantium, totam rem aperiam, eaque ipsa quae ab illo inventore veritatis et quasi
|
||||
architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas
|
||||
sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos qui ratione
|
||||
laudantium, totam rem aperiam, eaque ipsa quae ab illo inventore veritatis et quasi
|
||||
architecto beatae vitae dicta sunt explicabo. Nemo enim ipsam voluptatem quia voluptas
|
||||
sit aspernatur aut odit aut fugit, sed quia consequuntur magni dolores eos qui ratione
|
||||
voluptatem sequi nesciunt.`
|
||||
return scrollHeight;
|
||||
});
|
||||
|
||||
await ContentTask.spawn(tab.linkedBrowser, oldHeight, async function(contentOldHeight) {
|
||||
let frame = content.window.gSubDialog._topDialog._frame;
|
||||
let docEl = frame.contentDocument.documentElement;
|
||||
Assert.equal(frame.style.width, "32em",
|
||||
"Width should be set on the frame from the dialog");
|
||||
Assert.ok(docEl.scrollHeight > contentOldHeight,
|
||||
"Content height increased (from " + contentOldHeight + " to " + docEl.scrollHeight + ").");
|
||||
Assert.equal(frame.style.height, docEl.scrollHeight + "px",
|
||||
"Height on the frame should be higher now");
|
||||
});
|
||||
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentWindow.window.close(); },
|
||||
null, 0);
|
||||
});
|
||||
|
||||
add_task(async function dialog_too_tall_should_get_reduced_in_height() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser, function domcontentloadedFn() {
|
||||
let frame = content.window.gSubDialog._topDialog._frame;
|
||||
frame.contentDocument.documentElement.style.height = "100000px";
|
||||
});
|
||||
|
||||
await ContentTask.spawn(tab.linkedBrowser, null, async function() {
|
||||
let frame = content.window.gSubDialog._topDialog._frame;
|
||||
Assert.equal(frame.style.width, "32em", "Width should be set on the frame from the dialog");
|
||||
Assert.ok(parseInt(frame.style.height, 10) < content.window.innerHeight,
|
||||
"Height on the frame should be smaller than window's innerHeight");
|
||||
});
|
||||
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentWindow.window.close(); },
|
||||
null, 0);
|
||||
});
|
||||
|
||||
add_task(async function scrollWidth_and_scrollHeight_from_subdialog_should_size_the_browser() {
|
||||
await open_subdialog_and_test_generic_start_state(tab.linkedBrowser, function domcontentloadedFn() {
|
||||
let frame = content.window.gSubDialog._topDialog._frame;
|
||||
frame.contentDocument.documentElement.style.removeProperty("height");
|
||||
frame.contentDocument.documentElement.style.removeProperty("width");
|
||||
});
|
||||
|
||||
await ContentTask.spawn(tab.linkedBrowser, null, async function() {
|
||||
let frame = content.window.gSubDialog._topDialog._frame;
|
||||
Assert.ok(frame.style.width.endsWith("px"),
|
||||
"Width (" + frame.style.width + ") should be set to a px value of the scrollWidth from the dialog");
|
||||
Assert.ok(frame.style.height.endsWith("px"),
|
||||
"Height (" + frame.style.height + ") should be set to a px value of the scrollHeight from the dialog");
|
||||
});
|
||||
|
||||
await close_subdialog_and_test_generic_end_state(tab.linkedBrowser,
|
||||
function() { content.window.gSubDialog._topDialog._frame.contentWindow.window.close(); },
|
||||
null, 0);
|
||||
});
|
||||
|
||||
add_task(async function test_shutdown() {
|
||||
gBrowser.removeTab(tab);
|
||||
});
|
@ -1,52 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
"use strict";
|
||||
|
||||
const PREF_TELEMETRY_ENABLED = "toolkit.telemetry.enabled";
|
||||
|
||||
function runPaneTest(fn) {
|
||||
open_preferences((win) => {
|
||||
let doc = win.document;
|
||||
win.gotoPref("paneAdvanced");
|
||||
let advancedPrefs = doc.getElementById("advancedPrefs");
|
||||
let tab = doc.getElementById("dataChoicesTab");
|
||||
advancedPrefs.selectedTab = tab;
|
||||
fn(win, doc);
|
||||
});
|
||||
}
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
resetPreferences();
|
||||
registerCleanupFunction(resetPreferences);
|
||||
runPaneTest(testTelemetryState);
|
||||
}
|
||||
|
||||
function testTelemetryState(win, doc) {
|
||||
let fhrCheckbox = doc.getElementById("submitHealthReportBox");
|
||||
Assert.ok(fhrCheckbox.checked, "Health Report checkbox is checked on app first run.");
|
||||
|
||||
let telmetryCheckbox = doc.getElementById("submitTelemetryBox");
|
||||
Assert.ok(!telmetryCheckbox.disabled,
|
||||
"Telemetry checkbox must be enabled if FHR is checked.");
|
||||
Assert.ok(Services.prefs.getBoolPref(PREF_TELEMETRY_ENABLED),
|
||||
"Telemetry must be enabled if the checkbox is ticked.");
|
||||
|
||||
// Uncheck the FHR checkbox and make sure that Telemetry checkbox gets disabled.
|
||||
fhrCheckbox.click();
|
||||
|
||||
Assert.ok(telmetryCheckbox.disabled,
|
||||
"Telemetry checkbox must be disabled if FHR is unchecked.");
|
||||
Assert.ok(!Services.prefs.getBoolPref(PREF_TELEMETRY_ENABLED),
|
||||
"Telemetry must be disabled if the checkbox is unticked.");
|
||||
|
||||
win.close();
|
||||
finish();
|
||||
}
|
||||
|
||||
function resetPreferences() {
|
||||
Services.prefs.clearUserPref("datareporting.healthreport.uploadEnabled");
|
||||
Services.prefs.clearUserPref(PREF_TELEMETRY_ENABLED);
|
||||
}
|
||||
|
@ -1,287 +0,0 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
Components.utils.import("resource://gre/modules/Promise.jsm");
|
||||
|
||||
// Tests within /browser/components/preferences/in-content-new/tests/
|
||||
// test the "new" preferences organization, after it was reorganized.
|
||||
// Thus, all of these tests should set the "oldOrganization" to false
|
||||
// before running.
|
||||
Services.prefs.setBoolPref("browser.preferences.useOldOrganization", false);
|
||||
registerCleanupFunction(function() {
|
||||
Services.prefs.clearUserPref("browser.preferences.useOldOrganization");
|
||||
});
|
||||
|
||||
const kDefaultWait = 2000;
|
||||
|
||||
function is_hidden(aElement) {
|
||||
var style = aElement.ownerGlobal.getComputedStyle(aElement);
|
||||
if (style.display == "none")
|
||||
return true;
|
||||
if (style.visibility != "visible")
|
||||
return true;
|
||||
|
||||
// Hiding a parent element will hide all its children
|
||||
if (aElement.parentNode != aElement.ownerDocument)
|
||||
return is_hidden(aElement.parentNode);
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
function is_element_visible(aElement, aMsg) {
|
||||
isnot(aElement, null, "Element should not be null, when checking visibility");
|
||||
ok(!is_hidden(aElement), aMsg);
|
||||
}
|
||||
|
||||
function is_element_hidden(aElement, aMsg) {
|
||||
isnot(aElement, null, "Element should not be null, when checking visibility");
|
||||
ok(is_hidden(aElement), aMsg);
|
||||
}
|
||||
|
||||
function open_preferences(aCallback) {
|
||||
gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, "about:preferences");
|
||||
let newTabBrowser = gBrowser.getBrowserForTab(gBrowser.selectedTab);
|
||||
newTabBrowser.addEventListener("Initialized", function() {
|
||||
aCallback(gBrowser.contentWindow);
|
||||
}, {capture: true, once: true});
|
||||
}
|
||||
|
||||
function openAndLoadSubDialog(aURL, aFeatures = null, aParams = null, aClosingCallback = null) {
|
||||
let promise = promiseLoadSubDialog(aURL);
|
||||
content.gSubDialog.open(aURL, aFeatures, aParams, aClosingCallback);
|
||||
return promise;
|
||||
}
|
||||
|
||||
function promiseLoadSubDialog(aURL) {
|
||||
return new Promise((resolve, reject) => {
|
||||
content.gSubDialog._dialogStack.addEventListener("dialogopen", function dialogopen(aEvent) {
|
||||
if (aEvent.detail.dialog._frame.contentWindow.location == "about:blank")
|
||||
return;
|
||||
content.gSubDialog._dialogStack.removeEventListener("dialogopen", dialogopen);
|
||||
|
||||
is(aEvent.detail.dialog._frame.contentWindow.location.toString(), aURL,
|
||||
"Check the proper URL is loaded");
|
||||
|
||||
// Check visibility
|
||||
is_element_visible(aEvent.detail.dialog._overlay, "Overlay is visible");
|
||||
|
||||
// Check that stylesheets were injected
|
||||
let expectedStyleSheetURLs = aEvent.detail.dialog._injectedStyleSheets.slice(0);
|
||||
for (let styleSheet of aEvent.detail.dialog._frame.contentDocument.styleSheets) {
|
||||
let i = expectedStyleSheetURLs.indexOf(styleSheet.href);
|
||||
if (i >= 0) {
|
||||
info("found " + styleSheet.href);
|
||||
expectedStyleSheetURLs.splice(i, 1);
|
||||
}
|
||||
}
|
||||
is(expectedStyleSheetURLs.length, 0, "All expectedStyleSheetURLs should have been found");
|
||||
|
||||
resolve(aEvent.detail.dialog._frame.contentWindow);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Waits a specified number of miliseconds for a specified event to be
|
||||
* fired on a specified element.
|
||||
*
|
||||
* Usage:
|
||||
* let receivedEvent = waitForEvent(element, "eventName");
|
||||
* // Do some processing here that will cause the event to be fired
|
||||
* // ...
|
||||
* // Now yield until the Promise is fulfilled
|
||||
* yield receivedEvent;
|
||||
* if (receivedEvent && !(receivedEvent instanceof Error)) {
|
||||
* receivedEvent.msg == "eventName";
|
||||
* // ...
|
||||
* }
|
||||
*
|
||||
* @param aSubject the element that should receive the event
|
||||
* @param aEventName the event to wait for
|
||||
* @param aTimeoutMs the number of miliseconds to wait before giving up
|
||||
* @returns a Promise that resolves to the received event, or to an Error
|
||||
*/
|
||||
function waitForEvent(aSubject, aEventName, aTimeoutMs, aTarget) {
|
||||
let eventDeferred = Promise.defer();
|
||||
let timeoutMs = aTimeoutMs || kDefaultWait;
|
||||
let stack = new Error().stack;
|
||||
let timerID = setTimeout(function wfe_canceller() {
|
||||
aSubject.removeEventListener(aEventName, listener);
|
||||
eventDeferred.reject(new Error(aEventName + " event timeout at " + stack));
|
||||
}, timeoutMs);
|
||||
|
||||
var listener = function(aEvent) {
|
||||
if (aTarget && aTarget !== aEvent.target)
|
||||
return;
|
||||
|
||||
// stop the timeout clock and resume
|
||||
clearTimeout(timerID);
|
||||
eventDeferred.resolve(aEvent);
|
||||
};
|
||||
|
||||
function cleanup(aEventOrError) {
|
||||
// unhook listener in case of success or failure
|
||||
aSubject.removeEventListener(aEventName, listener);
|
||||
return aEventOrError;
|
||||
}
|
||||
aSubject.addEventListener(aEventName, listener);
|
||||
return eventDeferred.promise.then(cleanup, cleanup);
|
||||
}
|
||||
|
||||
function openPreferencesViaOpenPreferencesAPI(aPane, aOptions) {
|
||||
return new Promise(resolve => {
|
||||
gBrowser.selectedTab = BrowserTestUtils.addTab(gBrowser, "about:blank");
|
||||
openPreferences(aPane);
|
||||
let newTabBrowser = gBrowser.selectedBrowser;
|
||||
|
||||
newTabBrowser.addEventListener("Initialized", function() {
|
||||
newTabBrowser.contentWindow.addEventListener("load", function() {
|
||||
let win = gBrowser.contentWindow;
|
||||
let selectedPane = win.history.state;
|
||||
if (!aOptions || !aOptions.leaveOpen)
|
||||
gBrowser.removeCurrentTab();
|
||||
resolve({selectedPane});
|
||||
}, {once: true});
|
||||
}, {capture: true, once: true});
|
||||
|
||||
});
|
||||
}
|
||||
|
||||
function waitForCondition(aConditionFn, aMaxTries = 50, aCheckInterval = 100) {
|
||||
return new Promise((resolve, reject) => {
|
||||
function tryNow() {
|
||||
tries++;
|
||||
let rv = aConditionFn();
|
||||
if (rv) {
|
||||
resolve(rv);
|
||||
} else if (tries < aMaxTries) {
|
||||
tryAgain();
|
||||
} else {
|
||||
reject("Condition timed out: " + aConditionFn.toSource());
|
||||
}
|
||||
}
|
||||
function tryAgain() {
|
||||
setTimeout(tryNow, aCheckInterval);
|
||||
}
|
||||
let tries = 0;
|
||||
tryAgain();
|
||||
});
|
||||
}
|
||||
|
||||
function promiseWindowDialogOpen(buttonAction, url) {
|
||||
return new Promise(resolve => {
|
||||
Services.ww.registerNotification(function onOpen(subj, topic, data) {
|
||||
if (topic == "domwindowopened" && subj instanceof Ci.nsIDOMWindow) {
|
||||
subj.addEventListener("load", function onLoad() {
|
||||
if (subj.document.documentURI == url) {
|
||||
Services.ww.unregisterNotification(onOpen);
|
||||
let doc = subj.document.documentElement;
|
||||
doc.getButton(buttonAction).click();
|
||||
resolve();
|
||||
}
|
||||
}, {once: true});
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function promiseAlertDialogOpen(buttonAction) {
|
||||
return promiseWindowDialogOpen(buttonAction, "chrome://global/content/commonDialog.xul");
|
||||
}
|
||||
|
||||
function addPersistentStoragePerm(origin) {
|
||||
let uri = NetUtil.newURI(origin);
|
||||
let principal = Services.scriptSecurityManager.createCodebasePrincipal(uri, {});
|
||||
Services.perms.addFromPrincipal(principal, "persistent-storage", Ci.nsIPermissionManager.ALLOW_ACTION);
|
||||
}
|
||||
|
||||
function promiseSiteDataManagerSitesUpdated() {
|
||||
return TestUtils.topicObserved("sitedatamanager:sites-updated", () => true);
|
||||
}
|
||||
|
||||
function openSiteDataSettingsDialog() {
|
||||
let doc = gBrowser.selectedBrowser.contentDocument;
|
||||
let settingsBtn = doc.getElementById("siteDataSettings");
|
||||
let dialogOverlay = content.gSubDialog._preloadDialog._overlay;
|
||||
let dialogLoadPromise = promiseLoadSubDialog("chrome://browser/content/preferences/siteDataSettings.xul");
|
||||
let dialogInitPromise = TestUtils.topicObserved("sitedata-settings-init", () => true);
|
||||
let fullyLoadPromise = Promise.all([ dialogLoadPromise, dialogInitPromise ]).then(() => {
|
||||
is(dialogOverlay.style.visibility, "visible", "The Settings dialog should be visible");
|
||||
});
|
||||
settingsBtn.doCommand();
|
||||
return fullyLoadPromise;
|
||||
}
|
||||
|
||||
function assertSitesListed(doc, hosts) {
|
||||
let frameDoc = content.gSubDialog._topDialog._frame.contentDocument;
|
||||
let removeBtn = frameDoc.getElementById("removeSelected");
|
||||
let removeAllBtn = frameDoc.getElementById("removeAll");
|
||||
let sitesList = frameDoc.getElementById("sitesList");
|
||||
let totalSitesNumber = sitesList.getElementsByTagName("richlistitem").length;
|
||||
is(totalSitesNumber, hosts.length, "Should list the right sites number");
|
||||
hosts.forEach(host => {
|
||||
let site = sitesList.querySelector(`richlistitem[host="${host}"]`);
|
||||
ok(site, `Should list the site of ${host}`);
|
||||
});
|
||||
is(removeBtn.disabled, false, "Should enable the removeSelected button");
|
||||
is(removeAllBtn.disabled, false, "Should enable the removeAllBtn button");
|
||||
}
|
||||
|
||||
async function evaluateSearchResults(keyword, searchReults) {
|
||||
searchReults = Array.isArray(searchReults) ? searchReults : [searchReults];
|
||||
searchReults.push("header-searchResults");
|
||||
|
||||
let searchInput = gBrowser.contentDocument.getElementById("searchInput");
|
||||
searchInput.focus();
|
||||
let searchCompletedPromise = BrowserTestUtils.waitForEvent(
|
||||
gBrowser.contentWindow, "PreferencesSearchCompleted", evt => evt.detail == keyword);
|
||||
EventUtils.sendString(keyword);
|
||||
await searchCompletedPromise;
|
||||
|
||||
let mainPrefTag = gBrowser.contentDocument.getElementById("mainPrefPane");
|
||||
for (let i = 0; i < mainPrefTag.childElementCount; i++) {
|
||||
let child = mainPrefTag.children[i];
|
||||
if (searchReults.includes(child.id)) {
|
||||
is_element_visible(child, "Should be in search results");
|
||||
} else if (child.id) {
|
||||
is_element_hidden(child, "Should not be in search results");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const mockSiteDataManager = {
|
||||
|
||||
_SiteDataManager: null,
|
||||
_originalQMS: null,
|
||||
_originalRemoveQuotaUsage: null,
|
||||
|
||||
getUsage(onUsageResult) {
|
||||
let result = this.fakeSites.map(site => ({
|
||||
origin: site.principal.origin,
|
||||
usage: site.usage,
|
||||
persisted: site.persisted
|
||||
}));
|
||||
onUsageResult({ result });
|
||||
},
|
||||
|
||||
_removeQuotaUsage(site) {
|
||||
var target = site.principals[0].URI.host;
|
||||
this.fakeSites = this.fakeSites.filter(fakeSite => {
|
||||
return fakeSite.principal.URI.host != target;
|
||||
});
|
||||
},
|
||||
|
||||
register(SiteDataManager) {
|
||||
this._SiteDataManager = SiteDataManager;
|
||||
this._originalQMS = this._SiteDataManager._qms;
|
||||
this._SiteDataManager._qms = this;
|
||||
this._originalRemoveQuotaUsage = this._SiteDataManager._removeQuotaUsage;
|
||||
this._SiteDataManager._removeQuotaUsage = this._removeQuotaUsage.bind(this);
|
||||
this.fakeSites = null;
|
||||
},
|
||||
|
||||
unregister() {
|
||||
this._SiteDataManager._qms = this._originalQMS;
|
||||
this._SiteDataManager._removeQuotaUsage = this._originalRemoveQuotaUsage;
|
||||
}
|
||||
};
|
@ -1,3 +0,0 @@
|
||||
CACHE MANIFEST
|
||||
# V1
|
||||
offline.html
|
@ -1,13 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html manifest="manifest.appcache">>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="Cache-Control" content="public" />
|
||||
<meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1, maximum-scale=1">
|
||||
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<h1>Set up offline appcache Test</h1>
|
||||
</body>
|
||||
</html>
|
@ -1,333 +0,0 @@
|
||||
// This file gets imported into the same scope as head.js.
|
||||
/* import-globals-from head.js */
|
||||
|
||||
async function runTestOnPrivacyPrefPane(testFunc) {
|
||||
info("runTestOnPrivacyPrefPane entered");
|
||||
let tab = await BrowserTestUtils.openNewForegroundTab(gBrowser, "about:preferences", true, true);
|
||||
let browser = tab.linkedBrowser;
|
||||
info("loaded about:preferences");
|
||||
browser.contentWindow.gotoPref("panePrivacy");
|
||||
info("viewing privacy pane, executing testFunc");
|
||||
testFunc(browser.contentWindow);
|
||||
await BrowserTestUtils.removeTab(tab);
|
||||
}
|
||||
|
||||
function controlChanged(element) {
|
||||
element.doCommand();
|
||||
}
|
||||
|
||||
// We can only test the panes that don't trigger a preference update
|
||||
function test_pane_visibility(win) {
|
||||
let modes = {
|
||||
"remember": "historyRememberPane",
|
||||
"custom": "historyCustomPane"
|
||||
};
|
||||
|
||||
let historymode = win.document.getElementById("historyMode");
|
||||
ok(historymode, "history mode menulist should exist");
|
||||
let historypane = win.document.getElementById("historyPane");
|
||||
ok(historypane, "history mode pane should exist");
|
||||
|
||||
for (let mode in modes) {
|
||||
historymode.value = mode;
|
||||
controlChanged(historymode);
|
||||
is(historypane.selectedPanel, win.document.getElementById(modes[mode]),
|
||||
"The correct pane should be selected for the " + mode + " mode");
|
||||
is_element_visible(historypane.selectedPanel,
|
||||
"Correct pane should be visible for the " + mode + " mode");
|
||||
}
|
||||
}
|
||||
|
||||
function test_dependent_elements(win) {
|
||||
let historymode = win.document.getElementById("historyMode");
|
||||
ok(historymode, "history mode menulist should exist");
|
||||
let pbautostart = win.document.getElementById("privateBrowsingAutoStart");
|
||||
ok(pbautostart, "the private browsing auto-start checkbox should exist");
|
||||
let controls = [
|
||||
win.document.getElementById("rememberHistory"),
|
||||
win.document.getElementById("rememberForms"),
|
||||
win.document.getElementById("keepUntil"),
|
||||
win.document.getElementById("keepCookiesUntil"),
|
||||
win.document.getElementById("alwaysClear"),
|
||||
];
|
||||
controls.forEach(function(control) {
|
||||
ok(control, "the dependent controls should exist");
|
||||
});
|
||||
let independents = [
|
||||
win.document.getElementById("acceptCookies"),
|
||||
win.document.getElementById("acceptThirdPartyLabel"),
|
||||
win.document.getElementById("acceptThirdPartyMenu")
|
||||
];
|
||||
independents.forEach(function(control) {
|
||||
ok(control, "the independent controls should exist");
|
||||
});
|
||||
let cookieexceptions = win.document.getElementById("cookieExceptions");
|
||||
ok(cookieexceptions, "the cookie exceptions button should exist");
|
||||
let keepuntil = win.document.getElementById("keepCookiesUntil");
|
||||
ok(keepuntil, "the keep cookies until menulist should exist");
|
||||
let alwaysclear = win.document.getElementById("alwaysClear");
|
||||
ok(alwaysclear, "the clear data on close checkbox should exist");
|
||||
let rememberhistory = win.document.getElementById("rememberHistory");
|
||||
ok(rememberhistory, "the remember history checkbox should exist");
|
||||
let rememberforms = win.document.getElementById("rememberForms");
|
||||
ok(rememberforms, "the remember forms checkbox should exist");
|
||||
let alwaysclearsettings = win.document.getElementById("clearDataSettings");
|
||||
ok(alwaysclearsettings, "the clear data settings button should exist");
|
||||
|
||||
function expect_disabled(disabled) {
|
||||
controls.forEach(function(control) {
|
||||
is(control.disabled, disabled,
|
||||
control.getAttribute("id") + " should " + (disabled ? "" : "not ") + "be disabled");
|
||||
});
|
||||
is(keepuntil.value, disabled ? 2 : 0,
|
||||
"the keep cookies until menulist value should be as expected");
|
||||
if (disabled) {
|
||||
ok(!alwaysclear.checked,
|
||||
"the clear data on close checkbox value should be as expected");
|
||||
ok(!rememberhistory.checked,
|
||||
"the remember history checkbox value should be as expected");
|
||||
ok(!rememberforms.checked,
|
||||
"the remember forms checkbox value should be as expected");
|
||||
}
|
||||
}
|
||||
function check_independents(expected) {
|
||||
independents.forEach(function(control) {
|
||||
is(control.disabled, expected,
|
||||
control.getAttribute("id") + " should " + (expected ? "" : "not ") + "be disabled");
|
||||
});
|
||||
|
||||
ok(!cookieexceptions.disabled,
|
||||
"the cookie exceptions button should never be disabled");
|
||||
ok(alwaysclearsettings.disabled,
|
||||
"the clear data settings button should always be disabled");
|
||||
}
|
||||
|
||||
// controls should only change in custom mode
|
||||
historymode.value = "remember";
|
||||
controlChanged(historymode);
|
||||
expect_disabled(false);
|
||||
check_independents(false);
|
||||
|
||||
// setting the mode to custom shouldn't change anything
|
||||
historymode.value = "custom";
|
||||
controlChanged(historymode);
|
||||
expect_disabled(false);
|
||||
check_independents(false);
|
||||
}
|
||||
|
||||
function test_dependent_cookie_elements(win) {
|
||||
let historymode = win.document.getElementById("historyMode");
|
||||
ok(historymode, "history mode menulist should exist");
|
||||
let pbautostart = win.document.getElementById("privateBrowsingAutoStart");
|
||||
ok(pbautostart, "the private browsing auto-start checkbox should exist");
|
||||
let controls = [
|
||||
win.document.getElementById("acceptThirdPartyLabel"),
|
||||
win.document.getElementById("acceptThirdPartyMenu"),
|
||||
win.document.getElementById("keepUntil"),
|
||||
win.document.getElementById("keepCookiesUntil"),
|
||||
];
|
||||
controls.forEach(function(control) {
|
||||
ok(control, "the dependent cookie controls should exist");
|
||||
});
|
||||
let acceptcookies = win.document.getElementById("acceptCookies");
|
||||
ok(acceptcookies, "the accept cookies checkbox should exist");
|
||||
|
||||
function expect_disabled(disabled) {
|
||||
controls.forEach(function(control) {
|
||||
is(control.disabled, disabled,
|
||||
control.getAttribute("id") + " should " + (disabled ? "" : "not ") + "be disabled");
|
||||
});
|
||||
}
|
||||
|
||||
historymode.value = "custom";
|
||||
controlChanged(historymode);
|
||||
pbautostart.checked = false;
|
||||
controlChanged(pbautostart);
|
||||
expect_disabled(false);
|
||||
|
||||
acceptcookies.checked = false;
|
||||
controlChanged(acceptcookies);
|
||||
expect_disabled(true);
|
||||
|
||||
acceptcookies.checked = true;
|
||||
controlChanged(acceptcookies);
|
||||
expect_disabled(false);
|
||||
|
||||
let accessthirdparty = controls.shift();
|
||||
acceptcookies.checked = false;
|
||||
controlChanged(acceptcookies);
|
||||
expect_disabled(true);
|
||||
ok(accessthirdparty.disabled, "access third party button should be disabled");
|
||||
|
||||
pbautostart.checked = false;
|
||||
controlChanged(pbautostart);
|
||||
expect_disabled(true);
|
||||
ok(accessthirdparty.disabled, "access third party button should be disabled");
|
||||
|
||||
acceptcookies.checked = true;
|
||||
controlChanged(acceptcookies);
|
||||
expect_disabled(false);
|
||||
ok(!accessthirdparty.disabled, "access third party button should be enabled");
|
||||
}
|
||||
|
||||
function test_dependent_clearonclose_elements(win) {
|
||||
let historymode = win.document.getElementById("historyMode");
|
||||
ok(historymode, "history mode menulist should exist");
|
||||
let pbautostart = win.document.getElementById("privateBrowsingAutoStart");
|
||||
ok(pbautostart, "the private browsing auto-start checkbox should exist");
|
||||
let alwaysclear = win.document.getElementById("alwaysClear");
|
||||
ok(alwaysclear, "the clear data on close checkbox should exist");
|
||||
let alwaysclearsettings = win.document.getElementById("clearDataSettings");
|
||||
ok(alwaysclearsettings, "the clear data settings button should exist");
|
||||
|
||||
function expect_disabled(disabled) {
|
||||
is(alwaysclearsettings.disabled, disabled,
|
||||
"the clear data settings should " + (disabled ? "" : "not ") + "be disabled");
|
||||
}
|
||||
|
||||
historymode.value = "custom";
|
||||
controlChanged(historymode);
|
||||
pbautostart.checked = false;
|
||||
controlChanged(pbautostart);
|
||||
alwaysclear.checked = false;
|
||||
controlChanged(alwaysclear);
|
||||
expect_disabled(true);
|
||||
|
||||
alwaysclear.checked = true;
|
||||
controlChanged(alwaysclear);
|
||||
expect_disabled(false);
|
||||
|
||||
alwaysclear.checked = false;
|
||||
controlChanged(alwaysclear);
|
||||
expect_disabled(true);
|
||||
}
|
||||
|
||||
function test_dependent_prefs(win) {
|
||||
let historymode = win.document.getElementById("historyMode");
|
||||
ok(historymode, "history mode menulist should exist");
|
||||
let controls = [
|
||||
win.document.getElementById("rememberHistory"),
|
||||
win.document.getElementById("rememberForms"),
|
||||
win.document.getElementById("acceptCookies")
|
||||
];
|
||||
controls.forEach(function(control) {
|
||||
ok(control, "the micro-management controls should exist");
|
||||
});
|
||||
|
||||
let thirdPartyCookieMenu = win.document.getElementById("acceptThirdPartyMenu");
|
||||
ok(thirdPartyCookieMenu, "the third-party cookie control should exist");
|
||||
|
||||
function expect_checked(checked) {
|
||||
controls.forEach(function(control) {
|
||||
is(control.checked, checked,
|
||||
control.getAttribute("id") + " should " + (checked ? "not " : "") + "be checked");
|
||||
});
|
||||
|
||||
is(thirdPartyCookieMenu.value == "always" || thirdPartyCookieMenu.value == "visited", checked, "third-party cookies should " + (checked ? "not " : "") + "be limited");
|
||||
}
|
||||
|
||||
// controls should be checked in remember mode
|
||||
historymode.value = "remember";
|
||||
controlChanged(historymode);
|
||||
expect_checked(true);
|
||||
|
||||
// even if they're unchecked in custom mode
|
||||
historymode.value = "custom";
|
||||
controlChanged(historymode);
|
||||
thirdPartyCookieMenu.value = "never";
|
||||
controlChanged(thirdPartyCookieMenu);
|
||||
controls.forEach(function(control) {
|
||||
control.checked = false;
|
||||
controlChanged(control);
|
||||
});
|
||||
expect_checked(false);
|
||||
historymode.value = "remember";
|
||||
controlChanged(historymode);
|
||||
expect_checked(true);
|
||||
}
|
||||
|
||||
function test_historymode_retention(mode, expect) {
|
||||
return function test_historymode_retention_fn(win) {
|
||||
let historymode = win.document.getElementById("historyMode");
|
||||
ok(historymode, "history mode menulist should exist");
|
||||
|
||||
if ((historymode.value == "remember" && mode == "dontremember") ||
|
||||
(historymode.value == "dontremember" && mode == "remember") ||
|
||||
(historymode.value == "custom" && mode == "dontremember")) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (expect !== undefined) {
|
||||
is(historymode.value, expect,
|
||||
"history mode is expected to remain " + expect);
|
||||
}
|
||||
|
||||
historymode.value = mode;
|
||||
controlChanged(historymode);
|
||||
};
|
||||
}
|
||||
|
||||
function test_custom_retention(controlToChange, expect, valueIncrement) {
|
||||
return function test_custom_retention_fn(win) {
|
||||
let historymode = win.document.getElementById("historyMode");
|
||||
ok(historymode, "history mode menulist should exist");
|
||||
|
||||
if (expect !== undefined) {
|
||||
is(historymode.value, expect,
|
||||
"history mode is expected to remain " + expect);
|
||||
}
|
||||
|
||||
historymode.value = "custom";
|
||||
controlChanged(historymode);
|
||||
|
||||
controlToChange = win.document.getElementById(controlToChange);
|
||||
ok(controlToChange, "the control to change should exist");
|
||||
switch (controlToChange.localName) {
|
||||
case "checkbox":
|
||||
controlToChange.checked = !controlToChange.checked;
|
||||
break;
|
||||
case "textbox":
|
||||
controlToChange.value = parseInt(controlToChange.value) + valueIncrement;
|
||||
break;
|
||||
case "menulist":
|
||||
controlToChange.value = valueIncrement;
|
||||
break;
|
||||
}
|
||||
controlChanged(controlToChange);
|
||||
};
|
||||
}
|
||||
|
||||
function test_locbar_suggestion_retention(suggestion, autocomplete) {
|
||||
return function(win) {
|
||||
let elem = win.document.getElementById(suggestion + "Suggestion");
|
||||
ok(elem, "Suggest " + suggestion + " checkbox should exist.");
|
||||
elem.click();
|
||||
|
||||
is(Services.prefs.getBoolPref("browser.urlbar.autocomplete.enabled"), autocomplete,
|
||||
"browser.urlbar.autocomplete.enabled pref should be " + autocomplete);
|
||||
};
|
||||
}
|
||||
|
||||
const gPrefCache = new Map();
|
||||
|
||||
function cache_preferences(win) {
|
||||
let prefs = win.document.querySelectorAll("#privacyPreferences > preference");
|
||||
for (let pref of prefs)
|
||||
gPrefCache.set(pref.name, pref.value);
|
||||
}
|
||||
|
||||
function reset_preferences(win) {
|
||||
let prefs = win.document.querySelectorAll("#privacyPreferences > preference");
|
||||
for (let pref of prefs)
|
||||
pref.value = gPrefCache.get(pref.name);
|
||||
}
|
||||
|
||||
function run_test_subset(subset) {
|
||||
info("subset: " + Array.from(subset, x => x.name).join(",") + "\n");
|
||||
SpecialPowers.pushPrefEnv({"set": [["browser.preferences.instantApply", true]]});
|
||||
|
||||
let tests = [cache_preferences, ...subset, reset_preferences];
|
||||
for (let test of tests) {
|
||||
add_task(runTestOnPrivacyPrefPane.bind(undefined, test));
|
||||
}
|
||||
}
|
@ -1,29 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="Cache-Control" content="public" />
|
||||
<meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1, maximum-scale=1">
|
||||
|
||||
<title>Site Data Test</title>
|
||||
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<h1>Site Data Test</h1>
|
||||
<script type="text/javascript">
|
||||
let request = indexedDB.open("TestDatabase", 1);
|
||||
request.onupgradeneeded = function(e) {
|
||||
let db = e.target.result;
|
||||
db.createObjectStore("TestStore", { keyPath: "id" });
|
||||
};
|
||||
request.onsuccess = function(e) {
|
||||
let db = e.target.result;
|
||||
let tx = db.transaction("TestStore", "readwrite");
|
||||
let store = tx.objectStore("TestStore");
|
||||
tx.oncomplete = () => window.dispatchEvent(new Event("test-indexedDB-done"));
|
||||
store.put({ id: "test_id", description: "Site Data Test"});
|
||||
}
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
@ -1,27 +0,0 @@
|
||||
<?xml version="1.0"?>
|
||||
|
||||
<!-- Any copyright is dedicated to the Public Domain.
|
||||
- http://creativecommons.org/publicdomain/zero/1.0/ -->
|
||||
|
||||
<?xml-stylesheet href="chrome://global/skin/" type="text/css"?>
|
||||
|
||||
<dialog id="subDialog"
|
||||
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
|
||||
title="Sample sub-dialog" style="width: 32em; height: 5em;"
|
||||
onload="document.getElementById('textbox').focus();"
|
||||
ondialogaccept="acceptSubdialog();">
|
||||
<script>
|
||||
function acceptSubdialog() {
|
||||
window.arguments[0].acceptCount++;
|
||||
}
|
||||
</script>
|
||||
|
||||
<description id="desc">A sample sub-dialog for testing</description>
|
||||
|
||||
<textbox id="textbox" value="Default text" />
|
||||
|
||||
<separator class="thin"/>
|
||||
|
||||
<button oncommand="close();" icon="close" label="Close" />
|
||||
|
||||
</dialog>
|
@ -1,27 +0,0 @@
|
||||
<?xml version="1.0"?>
|
||||
|
||||
<!-- Any copyright is dedicated to the Public Domain.
|
||||
- http://creativecommons.org/publicdomain/zero/1.0/ -->
|
||||
|
||||
<?xml-stylesheet href="chrome://global/skin/" type="text/css"?>
|
||||
|
||||
<dialog id="subDialog"
|
||||
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
|
||||
title="Sample sub-dialog #2" style="width: 32em; height: 5em;"
|
||||
onload="document.getElementById('textbox').focus();"
|
||||
ondialogaccept="acceptSubdialog();">
|
||||
<script>
|
||||
function acceptSubdialog() {
|
||||
window.arguments[0].acceptCount++;
|
||||
}
|
||||
</script>
|
||||
|
||||
<description id="desc">A sample sub-dialog for testing</description>
|
||||
|
||||
<textbox id="textbox" value="Default text" />
|
||||
|
||||
<separator class="thin"/>
|
||||
|
||||
<button oncommand="close();" icon="close" label="Close" />
|
||||
|
||||
</dialog>
|
@ -1,832 +0,0 @@
|
||||
/* 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/. */
|
||||
|
||||
/* import-globals-from preferences.js */
|
||||
|
||||
// Load DownloadUtils module for convertByteUnits
|
||||
Components.utils.import("resource://gre/modules/DownloadUtils.jsm");
|
||||
Components.utils.import("resource://gre/modules/LoadContextInfo.jsm");
|
||||
Components.utils.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "SiteDataManager",
|
||||
"resource:///modules/SiteDataManager.jsm");
|
||||
|
||||
const PREF_UPLOAD_ENABLED = "datareporting.healthreport.uploadEnabled";
|
||||
|
||||
var gAdvancedPane = {
|
||||
_inited: false,
|
||||
|
||||
/**
|
||||
* Brings the appropriate tab to the front and initializes various bits of UI.
|
||||
*/
|
||||
init() {
|
||||
function setEventListener(aId, aEventType, aCallback) {
|
||||
document.getElementById(aId)
|
||||
.addEventListener(aEventType, aCallback.bind(gAdvancedPane));
|
||||
}
|
||||
|
||||
this._inited = true;
|
||||
var advancedPrefs = document.getElementById("advancedPrefs");
|
||||
|
||||
var preference = document.getElementById("browser.preferences.advanced.selectedTabIndex");
|
||||
if (preference.value !== null)
|
||||
advancedPrefs.selectedIndex = preference.value;
|
||||
|
||||
if (AppConstants.MOZ_UPDATER) {
|
||||
let onUnload = () => {
|
||||
window.removeEventListener("unload", onUnload);
|
||||
Services.prefs.removeObserver("app.update.", this);
|
||||
};
|
||||
window.addEventListener("unload", onUnload);
|
||||
Services.prefs.addObserver("app.update.", this);
|
||||
this.updateReadPrefs();
|
||||
}
|
||||
if (AppConstants.MOZ_CRASHREPORTER) {
|
||||
this.initSubmitCrashes();
|
||||
}
|
||||
this.initTelemetry();
|
||||
this.initSubmitHealthReport();
|
||||
this.updateOnScreenKeyboardVisibility();
|
||||
this.updateCacheSizeInputField();
|
||||
this.updateActualCacheSize();
|
||||
|
||||
if (Services.prefs.getBoolPref("browser.storageManager.enabled")) {
|
||||
Services.obs.addObserver(this, "sitedatamanager:sites-updated");
|
||||
Services.obs.addObserver(this, "sitedatamanager:updating-sites");
|
||||
let unload = () => {
|
||||
window.removeEventListener("unload", unload);
|
||||
Services.obs.removeObserver(this, "sitedatamanager:sites-updated");
|
||||
Services.obs.removeObserver(this, "sitedatamanager:updating-sites");
|
||||
};
|
||||
window.addEventListener("unload", unload);
|
||||
SiteDataManager.updateSites();
|
||||
setEventListener("clearSiteDataButton", "command",
|
||||
gAdvancedPane.clearSiteData);
|
||||
setEventListener("siteDataSettings", "command",
|
||||
gAdvancedPane.showSiteDataSettings);
|
||||
|
||||
let url = Services.urlFormatter.formatURLPref("app.support.baseURL") + "storage-permissions";
|
||||
document.getElementById("siteDataLearnMoreLink").setAttribute("href", url);
|
||||
let siteDataGroup = document.getElementById("siteDataGroup");
|
||||
siteDataGroup.hidden = false;
|
||||
}
|
||||
|
||||
setEventListener("layers.acceleration.disabled", "change",
|
||||
gAdvancedPane.updateHardwareAcceleration);
|
||||
setEventListener("advancedPrefs", "select",
|
||||
gAdvancedPane.tabSelectionChanged);
|
||||
setEventListener("submitHealthReportBox", "command",
|
||||
gAdvancedPane.updateSubmitHealthReport);
|
||||
|
||||
setEventListener("connectionSettings", "command",
|
||||
gAdvancedPane.showConnections);
|
||||
setEventListener("clearCacheButton", "command",
|
||||
gAdvancedPane.clearCache);
|
||||
if (AppConstants.MOZ_UPDATER) {
|
||||
setEventListener("updateRadioGroup", "command",
|
||||
gAdvancedPane.updateWritePrefs);
|
||||
setEventListener("showUpdateHistory", "command",
|
||||
gAdvancedPane.showUpdates);
|
||||
}
|
||||
setEventListener("viewCertificatesButton", "command",
|
||||
gAdvancedPane.showCertificates);
|
||||
setEventListener("viewSecurityDevicesButton", "command",
|
||||
gAdvancedPane.showSecurityDevices);
|
||||
setEventListener("cacheSize", "change",
|
||||
gAdvancedPane.updateCacheSizePref);
|
||||
|
||||
if (Services.prefs.getBoolPref("browser.preferences.offlineGroup.enabled")) {
|
||||
this.updateOfflineApps();
|
||||
this.updateActualAppCacheSize();
|
||||
setEventListener("offlineNotifyExceptions", "command",
|
||||
gAdvancedPane.showOfflineExceptions);
|
||||
setEventListener("offlineAppsList", "select",
|
||||
gAdvancedPane.offlineAppSelected);
|
||||
setEventListener("offlineAppsListRemove", "command",
|
||||
gAdvancedPane.removeOfflineApp);
|
||||
setEventListener("clearOfflineAppCacheButton", "command",
|
||||
gAdvancedPane.clearOfflineAppCache);
|
||||
let bundlePrefs = document.getElementById("bundlePreferences");
|
||||
document.getElementById("offlineAppsList")
|
||||
.style.height = bundlePrefs.getString("offlineAppsList.height");
|
||||
let offlineGroup = document.getElementById("offlineGroup");
|
||||
offlineGroup.hidden = false;
|
||||
}
|
||||
|
||||
if (AppConstants.MOZ_WIDGET_GTK) {
|
||||
// GTK tabbox' allow the scroll wheel to change the selected tab,
|
||||
// but we don't want this behavior for the in-content preferences.
|
||||
let tabsElement = document.getElementById("tabsElement");
|
||||
tabsElement.addEventListener("DOMMouseScroll", event => {
|
||||
event.stopPropagation();
|
||||
}, true);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Stores the identity of the current tab in preferences so that the selected
|
||||
* tab can be persisted between openings of the preferences window.
|
||||
*/
|
||||
tabSelectionChanged() {
|
||||
if (!this._inited)
|
||||
return;
|
||||
var advancedPrefs = document.getElementById("advancedPrefs");
|
||||
var preference = document.getElementById("browser.preferences.advanced.selectedTabIndex");
|
||||
|
||||
// tabSelectionChanged gets called twice due to the selectedIndex being set
|
||||
// by both the selectedItem and selectedPanel callstacks. This guard is used
|
||||
// to prevent double-counting in Telemetry.
|
||||
if (preference.valueFromPreferences != advancedPrefs.selectedIndex) {
|
||||
Services.telemetry
|
||||
.getHistogramById("FX_PREFERENCES_CATEGORY_OPENED")
|
||||
.add(telemetryBucketForCategory("advanced"));
|
||||
}
|
||||
|
||||
preference.valueFromPreferences = advancedPrefs.selectedIndex;
|
||||
},
|
||||
|
||||
// GENERAL TAB
|
||||
|
||||
/*
|
||||
* Preferences:
|
||||
*
|
||||
* accessibility.browsewithcaret
|
||||
* - true enables keyboard navigation and selection within web pages using a
|
||||
* visible caret, false uses normal keyboard navigation with no caret
|
||||
* accessibility.typeaheadfind
|
||||
* - when set to true, typing outside text areas and input boxes will
|
||||
* automatically start searching for what's typed within the current
|
||||
* document; when set to false, no search action happens
|
||||
* ui.osk.enabled
|
||||
* - when set to true, subject to other conditions, we may sometimes invoke
|
||||
* an on-screen keyboard when a text input is focused.
|
||||
* (Currently Windows-only, and depending on prefs, may be Windows-8-only)
|
||||
* general.autoScroll
|
||||
* - when set to true, clicking the scroll wheel on the mouse activates a
|
||||
* mouse mode where moving the mouse down scrolls the document downward with
|
||||
* speed correlated with the distance of the cursor from the original
|
||||
* position at which the click occurred (and likewise with movement upward);
|
||||
* if false, this behavior is disabled
|
||||
* general.smoothScroll
|
||||
* - set to true to enable finer page scrolling than line-by-line on page-up,
|
||||
* page-down, and other such page movements
|
||||
* layout.spellcheckDefault
|
||||
* - an integer:
|
||||
* 0 disables spellchecking
|
||||
* 1 enables spellchecking, but only for multiline text fields
|
||||
* 2 enables spellchecking for all text fields
|
||||
*/
|
||||
|
||||
/**
|
||||
* Stores the original value of the spellchecking preference to enable proper
|
||||
* restoration if unchanged (since we're mapping a tristate onto a checkbox).
|
||||
*/
|
||||
_storedSpellCheck: 0,
|
||||
|
||||
/**
|
||||
* Returns true if any spellchecking is enabled and false otherwise, caching
|
||||
* the current value to enable proper pref restoration if the checkbox is
|
||||
* never changed.
|
||||
*/
|
||||
readCheckSpelling() {
|
||||
var pref = document.getElementById("layout.spellcheckDefault");
|
||||
this._storedSpellCheck = pref.value;
|
||||
|
||||
return (pref.value != 0);
|
||||
},
|
||||
|
||||
/**
|
||||
* Returns the value of the spellchecking preference represented by UI,
|
||||
* preserving the preference's "hidden" value if the preference is
|
||||
* unchanged and represents a value not strictly allowed in UI.
|
||||
*/
|
||||
writeCheckSpelling() {
|
||||
var checkbox = document.getElementById("checkSpelling");
|
||||
if (checkbox.checked) {
|
||||
if (this._storedSpellCheck == 2) {
|
||||
return 2;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
},
|
||||
|
||||
/**
|
||||
* readEnableOCSP is used by the preferences UI to determine whether or not
|
||||
* the checkbox for OCSP fetching should be checked (it returns true if it
|
||||
* should be checked and false otherwise). The about:config preference
|
||||
* "security.OCSP.enabled" is an integer rather than a boolean, so it can't be
|
||||
* directly mapped from {true,false} to {checked,unchecked}. The possible
|
||||
* values for "security.OCSP.enabled" are:
|
||||
* 0: fetching is disabled
|
||||
* 1: fetch for all certificates
|
||||
* 2: fetch only for EV certificates
|
||||
* Hence, if "security.OCSP.enabled" is non-zero, the checkbox should be
|
||||
* checked. Otherwise, it should be unchecked.
|
||||
*/
|
||||
readEnableOCSP() {
|
||||
var preference = document.getElementById("security.OCSP.enabled");
|
||||
// This is the case if the preference is the default value.
|
||||
if (preference.value === undefined) {
|
||||
return true;
|
||||
}
|
||||
return preference.value != 0;
|
||||
},
|
||||
|
||||
/**
|
||||
* writeEnableOCSP is used by the preferences UI to map the checked/unchecked
|
||||
* state of the OCSP fetching checkbox to the value that the preference
|
||||
* "security.OCSP.enabled" should be set to (it returns that value). See the
|
||||
* readEnableOCSP documentation for more background. We unfortunately don't
|
||||
* have enough information to map from {true,false} to all possible values for
|
||||
* "security.OCSP.enabled", but a reasonable alternative is to map from
|
||||
* {true,false} to {<the default value>,0}. That is, if the box is checked,
|
||||
* "security.OCSP.enabled" will be set to whatever default it should be, given
|
||||
* the platform and channel. If the box is unchecked, the preference will be
|
||||
* set to 0. Obviously this won't work if the default is 0, so we will have to
|
||||
* revisit this if we ever set it to 0.
|
||||
*/
|
||||
writeEnableOCSP() {
|
||||
var checkbox = document.getElementById("enableOCSP");
|
||||
var defaults = Services.prefs.getDefaultBranch(null);
|
||||
var defaultValue = defaults.getIntPref("security.OCSP.enabled");
|
||||
return checkbox.checked ? defaultValue : 0;
|
||||
},
|
||||
|
||||
updateHardwareAcceleration() {
|
||||
// Placeholder for restart
|
||||
},
|
||||
|
||||
// DATA CHOICES TAB
|
||||
|
||||
/**
|
||||
* Set up or hide the Learn More links for various data collection options
|
||||
*/
|
||||
_setupLearnMoreLink(pref, element) {
|
||||
// set up the Learn More link with the correct URL
|
||||
let url = Services.prefs.getCharPref(pref);
|
||||
let el = document.getElementById(element);
|
||||
|
||||
if (url) {
|
||||
el.setAttribute("href", url);
|
||||
} else {
|
||||
el.setAttribute("hidden", "true");
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
initSubmitCrashes() {
|
||||
this._setupLearnMoreLink("toolkit.crashreporter.infoURL",
|
||||
"crashReporterLearnMore");
|
||||
},
|
||||
|
||||
/**
|
||||
* The preference/checkbox is configured in XUL.
|
||||
*
|
||||
* In all cases, set up the Learn More link sanely.
|
||||
*/
|
||||
initTelemetry() {
|
||||
this._setupLearnMoreLink("toolkit.telemetry.infoURL", "telemetryLearnMore");
|
||||
// If we're not sending any Telemetry, disable the telemetry upload checkbox as well.
|
||||
if (!AppConstants.MOZ_TELEMETRY_REPORTING) {
|
||||
document.getElementById("submitTelemetryBox").setAttribute("disabled", "true");
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Set the status of the telemetry controls based on the input argument.
|
||||
* @param {Boolean} aEnabled False disables the controls, true enables them.
|
||||
*/
|
||||
setTelemetrySectionEnabled(aEnabled) {
|
||||
// If FHR is disabled, additional data sharing should be disabled as well.
|
||||
let disabled = !aEnabled;
|
||||
document.getElementById("submitTelemetryBox").disabled = disabled;
|
||||
if (disabled) {
|
||||
// If we disable FHR, untick the telemetry checkbox.
|
||||
Services.prefs.setBoolPref("toolkit.telemetry.enabled", false);
|
||||
}
|
||||
document.getElementById("telemetryDataDesc").disabled = disabled;
|
||||
},
|
||||
|
||||
/**
|
||||
* Initialize the health report service reference and checkbox.
|
||||
*/
|
||||
initSubmitHealthReport() {
|
||||
this._setupLearnMoreLink("datareporting.healthreport.infoURL", "FHRLearnMore");
|
||||
|
||||
let checkbox = document.getElementById("submitHealthReportBox");
|
||||
|
||||
// Telemetry is only sending data if MOZ_TELEMETRY_REPORTING is defined.
|
||||
// We still want to display the preferences panel if that's not the case, but
|
||||
// we want it to be disabled and unchecked.
|
||||
if (Services.prefs.prefIsLocked(PREF_UPLOAD_ENABLED) ||
|
||||
!AppConstants.MOZ_TELEMETRY_REPORTING) {
|
||||
checkbox.setAttribute("disabled", "true");
|
||||
return;
|
||||
}
|
||||
|
||||
checkbox.checked = Services.prefs.getBoolPref(PREF_UPLOAD_ENABLED) &&
|
||||
AppConstants.MOZ_TELEMETRY_REPORTING;
|
||||
this.setTelemetrySectionEnabled(checkbox.checked);
|
||||
},
|
||||
|
||||
/**
|
||||
* Update the health report preference with state from checkbox.
|
||||
*/
|
||||
updateSubmitHealthReport() {
|
||||
let checkbox = document.getElementById("submitHealthReportBox");
|
||||
Services.prefs.setBoolPref(PREF_UPLOAD_ENABLED, checkbox.checked);
|
||||
this.setTelemetrySectionEnabled(checkbox.checked);
|
||||
},
|
||||
|
||||
updateOnScreenKeyboardVisibility() {
|
||||
if (AppConstants.platform == "win") {
|
||||
let minVersion = Services.prefs.getBoolPref("ui.osk.require_win10") ? 10 : 6.2;
|
||||
if (Services.vc.compare(Services.sysinfo.getProperty("version"), minVersion) >= 0) {
|
||||
document.getElementById("useOnScreenKeyboard").hidden = false;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
// NETWORK TAB
|
||||
|
||||
/*
|
||||
* Preferences:
|
||||
*
|
||||
* browser.cache.disk.capacity
|
||||
* - the size of the browser cache in KB
|
||||
* - Only used if browser.cache.disk.smart_size.enabled is disabled
|
||||
*/
|
||||
|
||||
/**
|
||||
* Displays a dialog in which proxy settings may be changed.
|
||||
*/
|
||||
showConnections() {
|
||||
gSubDialog.open("chrome://browser/content/preferences/connection.xul");
|
||||
},
|
||||
|
||||
showSiteDataSettings() {
|
||||
gSubDialog.open("chrome://browser/content/preferences/siteDataSettings.xul");
|
||||
},
|
||||
|
||||
toggleSiteData(shouldShow) {
|
||||
let clearButton = document.getElementById("clearSiteDataButton");
|
||||
let settingsButton = document.getElementById("siteDataSettings");
|
||||
clearButton.disabled = !shouldShow;
|
||||
settingsButton.disabled = !shouldShow;
|
||||
},
|
||||
|
||||
updateTotalDataSizeLabel(usage) {
|
||||
let prefStrBundle = document.getElementById("bundlePreferences");
|
||||
let totalSiteDataSizeLabel = document.getElementById("totalSiteDataSize");
|
||||
if (usage < 0) {
|
||||
totalSiteDataSizeLabel.textContent = prefStrBundle.getString("loadingSiteDataSize");
|
||||
} else {
|
||||
let size = DownloadUtils.convertByteUnits(usage);
|
||||
totalSiteDataSizeLabel.textContent = prefStrBundle.getFormattedString("totalSiteDataSize", size);
|
||||
}
|
||||
},
|
||||
|
||||
// Retrieves the amount of space currently used by disk cache
|
||||
updateActualCacheSize() {
|
||||
var actualSizeLabel = document.getElementById("actualDiskCacheSize");
|
||||
var prefStrBundle = document.getElementById("bundlePreferences");
|
||||
|
||||
// Needs to root the observer since cache service keeps only a weak reference.
|
||||
this.observer = {
|
||||
onNetworkCacheDiskConsumption(consumption) {
|
||||
var size = DownloadUtils.convertByteUnits(consumption);
|
||||
// The XBL binding for the string bundle may have been destroyed if
|
||||
// the page was closed before this callback was executed.
|
||||
if (!prefStrBundle.getFormattedString) {
|
||||
return;
|
||||
}
|
||||
actualSizeLabel.value = prefStrBundle.getFormattedString("actualDiskCacheSize", size);
|
||||
},
|
||||
|
||||
QueryInterface: XPCOMUtils.generateQI([
|
||||
Components.interfaces.nsICacheStorageConsumptionObserver,
|
||||
Components.interfaces.nsISupportsWeakReference
|
||||
])
|
||||
};
|
||||
|
||||
actualSizeLabel.value = prefStrBundle.getString("actualDiskCacheSizeCalculated");
|
||||
|
||||
try {
|
||||
var cacheService =
|
||||
Components.classes["@mozilla.org/netwerk/cache-storage-service;1"]
|
||||
.getService(Components.interfaces.nsICacheStorageService);
|
||||
cacheService.asyncGetDiskConsumption(this.observer);
|
||||
} catch (e) {}
|
||||
},
|
||||
|
||||
updateCacheSizeUI(smartSizeEnabled) {
|
||||
document.getElementById("useCacheBefore").disabled = smartSizeEnabled;
|
||||
document.getElementById("cacheSize").disabled = smartSizeEnabled;
|
||||
document.getElementById("useCacheAfter").disabled = smartSizeEnabled;
|
||||
},
|
||||
|
||||
readSmartSizeEnabled() {
|
||||
// The smart_size.enabled preference element is inverted="true", so its
|
||||
// value is the opposite of the actual pref value
|
||||
var disabled = document.getElementById("browser.cache.disk.smart_size.enabled").value;
|
||||
this.updateCacheSizeUI(!disabled);
|
||||
},
|
||||
|
||||
/**
|
||||
* Converts the cache size from units of KB to units of MB and stores it in
|
||||
* the textbox element.
|
||||
*/
|
||||
updateCacheSizeInputField() {
|
||||
let cacheSizeElem = document.getElementById("cacheSize");
|
||||
let cachePref = document.getElementById("browser.cache.disk.capacity");
|
||||
cacheSizeElem.value = cachePref.value / 1024;
|
||||
if (cachePref.locked)
|
||||
cacheSizeElem.disabled = true;
|
||||
},
|
||||
|
||||
/**
|
||||
* Updates the cache size preference once user enters a new value.
|
||||
* We intentionally do not set preference="browser.cache.disk.capacity"
|
||||
* onto the textbox directly, as that would update the pref at each keypress
|
||||
* not only after the final value is entered.
|
||||
*/
|
||||
updateCacheSizePref() {
|
||||
let cacheSizeElem = document.getElementById("cacheSize");
|
||||
let cachePref = document.getElementById("browser.cache.disk.capacity");
|
||||
// Converts the cache size as specified in UI (in MB) to KB.
|
||||
let intValue = parseInt(cacheSizeElem.value, 10);
|
||||
cachePref.value = isNaN(intValue) ? 0 : intValue * 1024;
|
||||
},
|
||||
|
||||
/**
|
||||
* Clears the cache.
|
||||
*/
|
||||
clearCache() {
|
||||
try {
|
||||
var cache = Components.classes["@mozilla.org/netwerk/cache-storage-service;1"]
|
||||
.getService(Components.interfaces.nsICacheStorageService);
|
||||
cache.clear();
|
||||
} catch (ex) {}
|
||||
this.updateActualCacheSize();
|
||||
},
|
||||
|
||||
clearSiteData() {
|
||||
let flags =
|
||||
Services.prompt.BUTTON_TITLE_IS_STRING * Services.prompt.BUTTON_POS_0 +
|
||||
Services.prompt.BUTTON_TITLE_CANCEL * Services.prompt.BUTTON_POS_1 +
|
||||
Services.prompt.BUTTON_POS_0_DEFAULT;
|
||||
let prefStrBundle = document.getElementById("bundlePreferences");
|
||||
let title = prefStrBundle.getString("clearSiteDataPromptTitle");
|
||||
let text = prefStrBundle.getString("clearSiteDataPromptText");
|
||||
let btn0Label = prefStrBundle.getString("clearSiteDataNow");
|
||||
|
||||
let result = Services.prompt.confirmEx(
|
||||
window, title, text, flags, btn0Label, null, null, null, {});
|
||||
if (result == 0) {
|
||||
SiteDataManager.removeAll();
|
||||
}
|
||||
},
|
||||
|
||||
// Methods for Offline Apps(Appcache)
|
||||
|
||||
/**
|
||||
* Clears the application cache.
|
||||
*/
|
||||
clearOfflineAppCache() {
|
||||
Components.utils.import("resource:///modules/offlineAppCache.jsm");
|
||||
OfflineAppCacheHelper.clear();
|
||||
|
||||
this.updateActualAppCacheSize();
|
||||
this.updateOfflineApps();
|
||||
},
|
||||
|
||||
// Retrieves the amount of space currently used by offline cache
|
||||
updateActualAppCacheSize() {
|
||||
var visitor = {
|
||||
onCacheStorageInfo(aEntryCount, aConsumption, aCapacity, aDiskDirectory) {
|
||||
var actualSizeLabel = document.getElementById("actualAppCacheSize");
|
||||
var sizeStrings = DownloadUtils.convertByteUnits(aConsumption);
|
||||
var prefStrBundle = document.getElementById("bundlePreferences");
|
||||
// The XBL binding for the string bundle may have been destroyed if
|
||||
// the page was closed before this callback was executed.
|
||||
if (!prefStrBundle.getFormattedString) {
|
||||
return;
|
||||
}
|
||||
var sizeStr = prefStrBundle.getFormattedString("actualAppCacheSize", sizeStrings);
|
||||
actualSizeLabel.value = sizeStr;
|
||||
}
|
||||
};
|
||||
|
||||
try {
|
||||
var cacheService =
|
||||
Components.classes["@mozilla.org/netwerk/cache-storage-service;1"]
|
||||
.getService(Components.interfaces.nsICacheStorageService);
|
||||
var storage = cacheService.appCacheStorage(LoadContextInfo.default, null);
|
||||
storage.asyncVisitStorage(visitor, false);
|
||||
} catch (e) {}
|
||||
},
|
||||
|
||||
readOfflineNotify() {
|
||||
var pref = document.getElementById("browser.offline-apps.notify");
|
||||
var button = document.getElementById("offlineNotifyExceptions");
|
||||
button.disabled = !pref.value;
|
||||
return pref.value;
|
||||
},
|
||||
|
||||
showOfflineExceptions() {
|
||||
var bundlePreferences = document.getElementById("bundlePreferences");
|
||||
var params = { blockVisible: false,
|
||||
sessionVisible: false,
|
||||
allowVisible: false,
|
||||
prefilledHost: "",
|
||||
permissionType: "offline-app",
|
||||
manageCapability: Components.interfaces.nsIPermissionManager.DENY_ACTION,
|
||||
windowTitle: bundlePreferences.getString("offlinepermissionstitle"),
|
||||
introText: bundlePreferences.getString("offlinepermissionstext") };
|
||||
gSubDialog.open("chrome://browser/content/preferences/permissions.xul",
|
||||
null, params);
|
||||
},
|
||||
|
||||
// XXX: duplicated in browser.js
|
||||
_getOfflineAppUsage(perm, groups) {
|
||||
let cacheService = Cc["@mozilla.org/network/application-cache-service;1"].
|
||||
getService(Ci.nsIApplicationCacheService);
|
||||
if (!groups) {
|
||||
try {
|
||||
groups = cacheService.getGroups();
|
||||
} catch (ex) {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
let usage = 0;
|
||||
for (let group of groups) {
|
||||
let uri = Services.io.newURI(group);
|
||||
if (perm.matchesURI(uri, true)) {
|
||||
let cache = cacheService.getActiveCache(group);
|
||||
usage += cache.usage;
|
||||
}
|
||||
}
|
||||
|
||||
return usage;
|
||||
},
|
||||
|
||||
/**
|
||||
* Updates the list of offline applications
|
||||
*/
|
||||
updateOfflineApps() {
|
||||
var pm = Components.classes["@mozilla.org/permissionmanager;1"]
|
||||
.getService(Components.interfaces.nsIPermissionManager);
|
||||
|
||||
var list = document.getElementById("offlineAppsList");
|
||||
while (list.firstChild) {
|
||||
list.firstChild.remove();
|
||||
}
|
||||
|
||||
var groups;
|
||||
try {
|
||||
var cacheService = Components.classes["@mozilla.org/network/application-cache-service;1"].
|
||||
getService(Components.interfaces.nsIApplicationCacheService);
|
||||
groups = cacheService.getGroups();
|
||||
} catch (e) {
|
||||
return;
|
||||
}
|
||||
|
||||
var bundle = document.getElementById("bundlePreferences");
|
||||
|
||||
var enumerator = pm.enumerator;
|
||||
while (enumerator.hasMoreElements()) {
|
||||
var perm = enumerator.getNext().QueryInterface(Components.interfaces.nsIPermission);
|
||||
if (perm.type == "offline-app" &&
|
||||
perm.capability != Components.interfaces.nsIPermissionManager.DEFAULT_ACTION &&
|
||||
perm.capability != Components.interfaces.nsIPermissionManager.DENY_ACTION) {
|
||||
var row = document.createElement("listitem");
|
||||
row.id = "";
|
||||
row.className = "offlineapp";
|
||||
row.setAttribute("origin", perm.principal.origin);
|
||||
var converted = DownloadUtils.
|
||||
convertByteUnits(this._getOfflineAppUsage(perm, groups));
|
||||
row.setAttribute("usage",
|
||||
bundle.getFormattedString("offlineAppUsage",
|
||||
converted));
|
||||
list.appendChild(row);
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
offlineAppSelected() {
|
||||
var removeButton = document.getElementById("offlineAppsListRemove");
|
||||
var list = document.getElementById("offlineAppsList");
|
||||
if (list.selectedItem) {
|
||||
removeButton.setAttribute("disabled", "false");
|
||||
} else {
|
||||
removeButton.setAttribute("disabled", "true");
|
||||
}
|
||||
},
|
||||
|
||||
removeOfflineApp() {
|
||||
var list = document.getElementById("offlineAppsList");
|
||||
var item = list.selectedItem;
|
||||
var origin = item.getAttribute("origin");
|
||||
var principal = Services.scriptSecurityManager.createCodebasePrincipalFromOrigin(origin);
|
||||
|
||||
var prompts = Components.classes["@mozilla.org/embedcomp/prompt-service;1"]
|
||||
.getService(Components.interfaces.nsIPromptService);
|
||||
var flags = prompts.BUTTON_TITLE_IS_STRING * prompts.BUTTON_POS_0 +
|
||||
prompts.BUTTON_TITLE_CANCEL * prompts.BUTTON_POS_1;
|
||||
|
||||
var bundle = document.getElementById("bundlePreferences");
|
||||
var title = bundle.getString("offlineAppRemoveTitle");
|
||||
var prompt = bundle.getFormattedString("offlineAppRemovePrompt", [principal.URI.prePath]);
|
||||
var confirm = bundle.getString("offlineAppRemoveConfirm");
|
||||
var result = prompts.confirmEx(window, title, prompt, flags, confirm,
|
||||
null, null, null, {});
|
||||
if (result != 0)
|
||||
return;
|
||||
|
||||
// get the permission
|
||||
var pm = Components.classes["@mozilla.org/permissionmanager;1"]
|
||||
.getService(Components.interfaces.nsIPermissionManager);
|
||||
var perm = pm.getPermissionObject(principal, "offline-app", true);
|
||||
if (perm) {
|
||||
// clear offline cache entries
|
||||
try {
|
||||
var cacheService = Components.classes["@mozilla.org/network/application-cache-service;1"].
|
||||
getService(Components.interfaces.nsIApplicationCacheService);
|
||||
var groups = cacheService.getGroups();
|
||||
for (var i = 0; i < groups.length; i++) {
|
||||
var uri = Services.io.newURI(groups[i]);
|
||||
if (perm.matchesURI(uri, true)) {
|
||||
var cache = cacheService.getActiveCache(groups[i]);
|
||||
cache.discard();
|
||||
}
|
||||
}
|
||||
} catch (e) {}
|
||||
|
||||
pm.removePermission(perm);
|
||||
}
|
||||
list.removeChild(item);
|
||||
gAdvancedPane.offlineAppSelected();
|
||||
this.updateActualAppCacheSize();
|
||||
},
|
||||
// Methods for Offline Apps(Appcache) end
|
||||
|
||||
// UPDATE TAB
|
||||
|
||||
/*
|
||||
* Preferences:
|
||||
*
|
||||
* app.update.enabled
|
||||
* - true if updates to the application are enabled, false otherwise
|
||||
* app.update.auto
|
||||
* - true if updates should be automatically downloaded and installed and
|
||||
* false if the user should be asked what he wants to do when an update is
|
||||
* available
|
||||
* extensions.update.enabled
|
||||
* - true if updates to extensions and themes are enabled, false otherwise
|
||||
* browser.search.update
|
||||
* - true if updates to search engines are enabled, false otherwise
|
||||
*/
|
||||
|
||||
/**
|
||||
* Selects the item of the radiogroup based on the pref values and locked
|
||||
* states.
|
||||
*
|
||||
* UI state matrix for update preference conditions
|
||||
*
|
||||
* UI Components: Preferences
|
||||
* Radiogroup i = app.update.enabled
|
||||
* ii = app.update.auto
|
||||
*
|
||||
* Disabled states:
|
||||
* Element pref value locked disabled
|
||||
* radiogroup i t/f f false
|
||||
* i t/f *t* *true*
|
||||
* ii t/f f false
|
||||
* ii t/f *t* *true*
|
||||
*/
|
||||
updateReadPrefs() {
|
||||
if (AppConstants.MOZ_UPDATER) {
|
||||
var enabledPref = document.getElementById("app.update.enabled");
|
||||
var autoPref = document.getElementById("app.update.auto");
|
||||
var radiogroup = document.getElementById("updateRadioGroup");
|
||||
|
||||
if (!enabledPref.value) // Don't care for autoPref.value in this case.
|
||||
radiogroup.value = "manual"; // 3. Never check for updates.
|
||||
else if (autoPref.value) // enabledPref.value && autoPref.value
|
||||
radiogroup.value = "auto"; // 1. Automatically install updates
|
||||
else // enabledPref.value && !autoPref.value
|
||||
radiogroup.value = "checkOnly"; // 2. Check, but let me choose
|
||||
|
||||
var canCheck = Components.classes["@mozilla.org/updates/update-service;1"].
|
||||
getService(Components.interfaces.nsIApplicationUpdateService).
|
||||
canCheckForUpdates;
|
||||
// canCheck is false if the enabledPref is false and locked,
|
||||
// or the binary platform or OS version is not known.
|
||||
// A locked pref is sufficient to disable the radiogroup.
|
||||
radiogroup.disabled = !canCheck || enabledPref.locked || autoPref.locked;
|
||||
|
||||
if (AppConstants.MOZ_MAINTENANCE_SERVICE) {
|
||||
// Check to see if the maintenance service is installed.
|
||||
// If it is don't show the preference at all.
|
||||
var installed;
|
||||
try {
|
||||
var wrk = Components.classes["@mozilla.org/windows-registry-key;1"]
|
||||
.createInstance(Components.interfaces.nsIWindowsRegKey);
|
||||
wrk.open(wrk.ROOT_KEY_LOCAL_MACHINE,
|
||||
"SOFTWARE\\Mozilla\\MaintenanceService",
|
||||
wrk.ACCESS_READ | wrk.WOW64_64);
|
||||
installed = wrk.readIntValue("Installed");
|
||||
wrk.close();
|
||||
} catch (e) {
|
||||
}
|
||||
if (installed != 1) {
|
||||
document.getElementById("useService").hidden = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Sets the pref values based on the selected item of the radiogroup.
|
||||
*/
|
||||
updateWritePrefs() {
|
||||
if (AppConstants.MOZ_UPDATER) {
|
||||
var enabledPref = document.getElementById("app.update.enabled");
|
||||
var autoPref = document.getElementById("app.update.auto");
|
||||
var radiogroup = document.getElementById("updateRadioGroup");
|
||||
switch (radiogroup.value) {
|
||||
case "auto": // 1. Automatically install updates for Desktop only
|
||||
enabledPref.value = true;
|
||||
autoPref.value = true;
|
||||
break;
|
||||
case "checkOnly": // 2. Check, but let me choose
|
||||
enabledPref.value = true;
|
||||
autoPref.value = false;
|
||||
break;
|
||||
case "manual": // 3. Never check for updates.
|
||||
enabledPref.value = false;
|
||||
autoPref.value = false;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Displays the history of installed updates.
|
||||
*/
|
||||
showUpdates() {
|
||||
gSubDialog.open("chrome://mozapps/content/update/history.xul");
|
||||
},
|
||||
|
||||
// ENCRYPTION TAB
|
||||
|
||||
/*
|
||||
* Preferences:
|
||||
*
|
||||
* security.default_personal_cert
|
||||
* - a string:
|
||||
* "Select Automatically" select a certificate automatically when a site
|
||||
* requests one
|
||||
* "Ask Every Time" present a dialog to the user so he can select
|
||||
* the certificate to use on a site which
|
||||
* requests one
|
||||
*/
|
||||
|
||||
/**
|
||||
* Displays the user's certificates and associated options.
|
||||
*/
|
||||
showCertificates() {
|
||||
gSubDialog.open("chrome://pippki/content/certManager.xul");
|
||||
},
|
||||
|
||||
/**
|
||||
* Displays a dialog from which the user can manage his security devices.
|
||||
*/
|
||||
showSecurityDevices() {
|
||||
gSubDialog.open("chrome://pippki/content/device_manager.xul");
|
||||
},
|
||||
|
||||
observe(aSubject, aTopic, aData) {
|
||||
switch (aTopic) {
|
||||
case "nsPref:changed":
|
||||
this.updateReadPrefs();
|
||||
break;
|
||||
|
||||
case "sitedatamanager:updating-sites":
|
||||
// While updating, we want to disable this section and display loading message until updated
|
||||
this.toggleSiteData(false);
|
||||
this.updateTotalDataSizeLabel(-1);
|
||||
break;
|
||||
|
||||
case "sitedatamanager:sites-updated":
|
||||
this.toggleSiteData(true);
|
||||
SiteDataManager.getTotalUsage()
|
||||
.then(this.updateTotalDataSizeLabel.bind(this));
|
||||
break;
|
||||
}
|
||||
},
|
||||
};
|
@ -1,421 +0,0 @@
|
||||
# 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/.
|
||||
|
||||
<!-- Advanced panel -->
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content/advanced.js"/>
|
||||
|
||||
<preferences id="advancedPreferences" hidden="true" data-category="paneAdvanced">
|
||||
<preference id="browser.preferences.advanced.selectedTabIndex"
|
||||
name="browser.preferences.advanced.selectedTabIndex"
|
||||
type="int"/>
|
||||
|
||||
<!-- General tab -->
|
||||
<preference id="accessibility.browsewithcaret"
|
||||
name="accessibility.browsewithcaret"
|
||||
type="bool"/>
|
||||
<preference id="accessibility.typeaheadfind"
|
||||
name="accessibility.typeaheadfind"
|
||||
type="bool"/>
|
||||
<preference id="accessibility.blockautorefresh"
|
||||
name="accessibility.blockautorefresh"
|
||||
type="bool"/>
|
||||
#ifdef XP_WIN
|
||||
<preference id="ui.osk.enabled"
|
||||
name="ui.osk.enabled"
|
||||
type="bool"/>
|
||||
#endif
|
||||
|
||||
<preference id="general.autoScroll"
|
||||
name="general.autoScroll"
|
||||
type="bool"/>
|
||||
<preference id="general.smoothScroll"
|
||||
name="general.smoothScroll"
|
||||
type="bool"/>
|
||||
<preference id="layout.spellcheckDefault"
|
||||
name="layout.spellcheckDefault"
|
||||
type="int"/>
|
||||
<preference id="toolkit.telemetry.enabled"
|
||||
name="toolkit.telemetry.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Data Choices tab -->
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
<preference id="browser.crashReports.unsubmittedCheck.autoSubmit"
|
||||
name="browser.crashReports.unsubmittedCheck.autoSubmit"
|
||||
type="bool"/>
|
||||
#endif
|
||||
|
||||
<!-- Network tab -->
|
||||
<preference id="browser.cache.disk.capacity"
|
||||
name="browser.cache.disk.capacity"
|
||||
type="int"/>
|
||||
<preference id="browser.offline-apps.notify"
|
||||
name="browser.offline-apps.notify"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.cache.disk.smart_size.enabled"
|
||||
name="browser.cache.disk.smart_size.enabled"
|
||||
inverted="true"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Update tab -->
|
||||
#ifdef MOZ_UPDATER
|
||||
<preference id="app.update.enabled"
|
||||
name="app.update.enabled"
|
||||
type="bool"/>
|
||||
<preference id="app.update.auto"
|
||||
name="app.update.auto"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="app.update.disable_button.showUpdateHistory"
|
||||
name="app.update.disable_button.showUpdateHistory"
|
||||
type="bool"/>
|
||||
|
||||
#ifdef MOZ_MAINTENANCE_SERVICE
|
||||
<preference id="app.update.service.enabled"
|
||||
name="app.update.service.enabled"
|
||||
type="bool"/>
|
||||
#endif
|
||||
#endif
|
||||
|
||||
<preference id="browser.search.update"
|
||||
name="browser.search.update"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Certificates tab -->
|
||||
<preference id="security.default_personal_cert"
|
||||
name="security.default_personal_cert"
|
||||
type="string"/>
|
||||
|
||||
<preference id="security.disable_button.openCertManager"
|
||||
name="security.disable_button.openCertManager"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="security.disable_button.openDeviceManager"
|
||||
name="security.disable_button.openDeviceManager"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="security.OCSP.enabled"
|
||||
name="security.OCSP.enabled"
|
||||
type="int"/>
|
||||
</preferences>
|
||||
|
||||
#ifdef HAVE_SHELL_SERVICE
|
||||
<stringbundle id="bundleShell" src="chrome://browser/locale/shellservice.properties"/>
|
||||
<stringbundle id="bundleBrand" src="chrome://branding/locale/brand.properties"/>
|
||||
#endif
|
||||
<stringbundle id="bundlePreferences" src="chrome://browser/locale/preferences-old/preferences.properties"/>
|
||||
|
||||
<hbox id="header-advanced"
|
||||
class="header"
|
||||
hidden="true"
|
||||
data-category="paneAdvanced">
|
||||
<label class="header-name" flex="1">&paneAdvanced.title;</label>
|
||||
<html:a class="help-button" target="_blank" aria-label="&helpButton.label;"></html:a>
|
||||
</hbox>
|
||||
|
||||
<tabbox id="advancedPrefs"
|
||||
handleCtrlTab="false"
|
||||
handleCtrlPageUpDown="false"
|
||||
flex="1"
|
||||
data-category="paneAdvanced"
|
||||
hidden="true">
|
||||
|
||||
<tabs id="tabsElement">
|
||||
<tab id="generalTab" label="&generalTab.label;"/>
|
||||
#ifdef MOZ_DATA_REPORTING
|
||||
<tab id="dataChoicesTab" label="&dataChoicesTab.label;"/>
|
||||
#endif
|
||||
<tab id="networkTab" label="&networkTab.label;"/>
|
||||
<tab id="updateTab" label="&updateTab.label;"/>
|
||||
<tab id="encryptionTab" label="&certificateTab.label;"/>
|
||||
</tabs>
|
||||
|
||||
<tabpanels flex="1">
|
||||
|
||||
<!-- General -->
|
||||
<tabpanel id="generalPanel" orient="vertical">
|
||||
<!-- Accessibility -->
|
||||
<groupbox id="accessibilityGroup" align="start">
|
||||
<caption><label>&accessibility.label;</label></caption>
|
||||
|
||||
#ifdef XP_WIN
|
||||
<checkbox id="useOnScreenKeyboard"
|
||||
hidden="true"
|
||||
label="&useOnScreenKeyboard.label;"
|
||||
accesskey="&useOnScreenKeyboard.accesskey;"
|
||||
preference="ui.osk.enabled"/>
|
||||
#endif
|
||||
<checkbox id="useCursorNavigation"
|
||||
label="&useCursorNavigation.label;"
|
||||
accesskey="&useCursorNavigation.accesskey;"
|
||||
preference="accessibility.browsewithcaret"/>
|
||||
<checkbox id="searchStartTyping"
|
||||
label="&searchOnStartTyping.label;"
|
||||
accesskey="&searchOnStartTyping.accesskey;"
|
||||
preference="accessibility.typeaheadfind"/>
|
||||
<checkbox id="blockAutoRefresh"
|
||||
label="&blockAutoReload.label;"
|
||||
accesskey="&blockAutoReload.accesskey;"
|
||||
preference="accessibility.blockautorefresh"/>
|
||||
</groupbox>
|
||||
<!-- Browsing -->
|
||||
<groupbox id="browsingGroup" align="start">
|
||||
<caption><label>&browsing.label;</label></caption>
|
||||
|
||||
<checkbox id="useAutoScroll"
|
||||
label="&useAutoScroll.label;"
|
||||
accesskey="&useAutoScroll.accesskey;"
|
||||
preference="general.autoScroll"/>
|
||||
<checkbox id="useSmoothScrolling"
|
||||
label="&useSmoothScrolling.label;"
|
||||
accesskey="&useSmoothScrolling.accesskey;"
|
||||
preference="general.smoothScroll"/>
|
||||
<checkbox id="checkSpelling"
|
||||
label="&checkUserSpelling.label;"
|
||||
accesskey="&checkUserSpelling.accesskey;"
|
||||
onsyncfrompreference="return gAdvancedPane.readCheckSpelling();"
|
||||
onsynctopreference="return gAdvancedPane.writeCheckSpelling();"
|
||||
preference="layout.spellcheckDefault"/>
|
||||
</groupbox>
|
||||
</tabpanel>
|
||||
#ifdef MOZ_DATA_REPORTING
|
||||
<!-- Data Choices -->
|
||||
<tabpanel id="dataChoicesPanel" orient="vertical">
|
||||
#ifdef MOZ_TELEMETRY_REPORTING
|
||||
<description>&healthReportingDisabled.label;</description>
|
||||
<separator class="thin"/>
|
||||
#endif
|
||||
<groupbox>
|
||||
<caption>
|
||||
<checkbox id="submitHealthReportBox" label="&enableHealthReport.label;"
|
||||
accesskey="&enableHealthReport.accesskey;"/>
|
||||
</caption>
|
||||
<vbox>
|
||||
<hbox class="indent" flex="1">
|
||||
<label flex="1">&healthReportDesc.label;</label>
|
||||
<label id="FHRLearnMore" flex="1"
|
||||
class="learnMore text-link">&healthReportLearnMore.label;</label>
|
||||
</hbox>
|
||||
<hbox class="indent">
|
||||
<groupbox flex="1">
|
||||
<caption>
|
||||
<checkbox id="submitTelemetryBox" preference="toolkit.telemetry.enabled"
|
||||
label="&enableTelemetryData.label;"
|
||||
accesskey="&enableTelemetryData.accesskey;"/>
|
||||
</caption>
|
||||
<hbox class="indent" flex="1">
|
||||
<label id="telemetryDataDesc" flex="1">&telemetryDesc.label;</label>
|
||||
<label id="telemetryLearnMore" flex="1"
|
||||
class="learnMore text-link">&telemetryLearnMore.label;</label>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
<groupbox>
|
||||
<caption>
|
||||
<checkbox id="automaticallySubmitCrashesBox"
|
||||
preference="browser.crashReports.unsubmittedCheck.autoSubmit"
|
||||
label="&alwaysSubmitCrashReports.label;"
|
||||
accesskey="&alwaysSubmitCrashReports.accesskey;"/>
|
||||
</caption>
|
||||
<hbox class="indent" flex="1">
|
||||
<label flex="1">&crashReporterDesc2.label;</label>
|
||||
<label id="crashReporterLearnMore" flex="1"
|
||||
class="learnMore text-link">&crashReporterLearnMore.label;</label>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
#endif
|
||||
</tabpanel>
|
||||
#endif
|
||||
|
||||
<!-- Network -->
|
||||
<tabpanel id="networkPanel" orient="vertical">
|
||||
|
||||
<!-- Connection -->
|
||||
<groupbox id="connectionGroup">
|
||||
<caption><label>&connection.label;</label></caption>
|
||||
|
||||
<hbox align="center">
|
||||
<description flex="1" control="connectionSettings">&connectionDesc.label;</description>
|
||||
<button id="connectionSettings" icon="network" label="&connectionSettings.label;"
|
||||
accesskey="&connectionSettings.accesskey;"/>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Cache -->
|
||||
<groupbox id="cacheGroup">
|
||||
<caption><label>&httpCache.label;</label></caption>
|
||||
|
||||
<hbox align="center">
|
||||
<label id="actualDiskCacheSize" flex="1"/>
|
||||
<button id="clearCacheButton" icon="clear"
|
||||
label="&clearCacheNow.label;" accesskey="&clearCacheNow.accesskey;"/>
|
||||
</hbox>
|
||||
<hbox>
|
||||
<checkbox preference="browser.cache.disk.smart_size.enabled"
|
||||
id="allowSmartSize"
|
||||
onsyncfrompreference="return gAdvancedPane.readSmartSizeEnabled();"
|
||||
label="&overrideSmartCacheSize.label;"
|
||||
accesskey="&overrideSmartCacheSize.accesskey;"/>
|
||||
</hbox>
|
||||
<hbox align="center" class="indent">
|
||||
<label id="useCacheBefore" control="cacheSize"
|
||||
accesskey="&limitCacheSizeBefore.accesskey;">
|
||||
&limitCacheSizeBefore.label;
|
||||
</label>
|
||||
<textbox id="cacheSize" type="number" size="4" max="1024"
|
||||
aria-labelledby="useCacheBefore cacheSize useCacheAfter"/>
|
||||
<label id="useCacheAfter" flex="1">&limitCacheSizeAfter.label;</label>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Offline apps -->
|
||||
<groupbox id="offlineGroup" hidden="true">
|
||||
<caption><label>&offlineStorage2.label;</label></caption>
|
||||
|
||||
<hbox align="center">
|
||||
<label id="actualAppCacheSize" flex="1"/>
|
||||
<button id="clearOfflineAppCacheButton" icon="clear"
|
||||
label="&clearOfflineAppCacheNow.label;" accesskey="&clearOfflineAppCacheNow.accesskey;"/>
|
||||
</hbox>
|
||||
<hbox align="center">
|
||||
<checkbox id="offlineNotify"
|
||||
label="&offlineStorageNotify.label;" accesskey="&offlineStorageNotify.accesskey;"
|
||||
preference="browser.offline-apps.notify"
|
||||
onsyncfrompreference="return gAdvancedPane.readOfflineNotify();"/>
|
||||
<spacer flex="1"/>
|
||||
<button id="offlineNotifyExceptions"
|
||||
label="&offlineStorageNotifyExceptions.label;"
|
||||
accesskey="&offlineStorageNotifyExceptions.accesskey;"/>
|
||||
</hbox>
|
||||
<hbox>
|
||||
<vbox flex="1">
|
||||
<label id="offlineAppsListLabel">&offlineAppsList2.label;</label>
|
||||
<listbox id="offlineAppsList"
|
||||
flex="1"
|
||||
aria-labelledby="offlineAppsListLabel">
|
||||
</listbox>
|
||||
</vbox>
|
||||
<vbox pack="end">
|
||||
<button id="offlineAppsListRemove"
|
||||
disabled="true"
|
||||
label="&offlineAppsListRemove.label;"
|
||||
accesskey="&offlineAppsListRemove.accesskey;"/>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Site Data -->
|
||||
<groupbox id="siteDataGroup" hidden="true">
|
||||
<caption><label>&siteData.label;</label></caption>
|
||||
|
||||
<hbox align="baseline">
|
||||
<label id="totalSiteDataSize"></label>
|
||||
<label id="siteDataLearnMoreLink" class="learnMore text-link" value="&siteDataLearnMoreLink.label;"></label>
|
||||
<spacer flex="1" />
|
||||
<button id="clearSiteDataButton" icon="clear"
|
||||
label="&clearSiteData.label;" accesskey="&clearSiteData.accesskey;"/>
|
||||
</hbox>
|
||||
<vbox align="end">
|
||||
<button id="siteDataSettings"
|
||||
label="&siteDataSettings.label;"
|
||||
accesskey="&siteDataSettings.accesskey;"/>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
</tabpanel>
|
||||
|
||||
<!-- Update -->
|
||||
<tabpanel id="updatePanel" orient="vertical">
|
||||
#ifdef MOZ_UPDATER
|
||||
<groupbox id="updateApp" align="start">
|
||||
<caption><label>&updateApplication.label;</label></caption>
|
||||
<radiogroup id="updateRadioGroup" align="start">
|
||||
<radio id="autoDesktop"
|
||||
value="auto"
|
||||
label="&updateAuto1.label;"
|
||||
accesskey="&updateAuto1.accesskey;"/>
|
||||
<radio value="checkOnly"
|
||||
label="&updateCheckChoose.label;"
|
||||
accesskey="&updateCheckChoose.accesskey;"/>
|
||||
<radio value="manual"
|
||||
label="&updateManual.label;"
|
||||
accesskey="&updateManual.accesskey;"/>
|
||||
</radiogroup>
|
||||
<separator class="thin"/>
|
||||
<hbox>
|
||||
<button id="showUpdateHistory"
|
||||
label="&updateHistory.label;"
|
||||
accesskey="&updateHistory.accesskey;"
|
||||
preference="app.update.disable_button.showUpdateHistory"/>
|
||||
</hbox>
|
||||
|
||||
#ifdef MOZ_MAINTENANCE_SERVICE
|
||||
<checkbox id="useService"
|
||||
label="&useService.label;"
|
||||
accesskey="&useService.accesskey;"
|
||||
preference="app.update.service.enabled"/>
|
||||
#endif
|
||||
</groupbox>
|
||||
#endif
|
||||
<groupbox id="updateOthers" align="start">
|
||||
<caption><label>&autoUpdateOthers.label;</label></caption>
|
||||
<checkbox id="enableSearchUpdate"
|
||||
label="&enableSearchUpdate.label;"
|
||||
accesskey="&enableSearchUpdate.accesskey;"
|
||||
preference="browser.search.update"/>
|
||||
</groupbox>
|
||||
</tabpanel>
|
||||
|
||||
<!-- Certificates -->
|
||||
<tabpanel id="encryptionPanel" orient="vertical">
|
||||
<groupbox id="certSelection" align="start">
|
||||
<caption><label>&certPersonal.label;</label></caption>
|
||||
<description id="CertSelectionDesc" control="certSelection">&certPersonal.description;</description>
|
||||
|
||||
<!--
|
||||
The values on these radio buttons may look like l12y issues, but
|
||||
they're not - this preference uses *those strings* as its values.
|
||||
I KID YOU NOT.
|
||||
-->
|
||||
<radiogroup id="certSelection"
|
||||
preftype="string"
|
||||
preference="security.default_personal_cert"
|
||||
aria-labelledby="CertSelectionDesc">
|
||||
<radio label="&selectCerts.auto;"
|
||||
accesskey="&selectCerts.auto.accesskey;"
|
||||
value="Select Automatically"/>
|
||||
<radio label="&selectCerts.ask;"
|
||||
accesskey="&selectCerts.ask.accesskey;"
|
||||
value="Ask Every Time"/>
|
||||
</radiogroup>
|
||||
</groupbox>
|
||||
<separator/>
|
||||
<checkbox id="enableOCSP"
|
||||
label="&enableOCSP.label;"
|
||||
accesskey="&enableOCSP.accesskey;"
|
||||
onsyncfrompreference="return gAdvancedPane.readEnableOCSP();"
|
||||
onsynctopreference="return gAdvancedPane.writeEnableOCSP();"
|
||||
preference="security.OCSP.enabled"/>
|
||||
<separator/>
|
||||
<hbox>
|
||||
<button id="viewCertificatesButton"
|
||||
flex="1"
|
||||
label="&viewCerts.label;"
|
||||
accesskey="&viewCerts.accesskey;"
|
||||
preference="security.disable_button.openCertManager"/>
|
||||
<button id="viewSecurityDevicesButton"
|
||||
flex="1"
|
||||
label="&viewSecurityDevices.label;"
|
||||
accesskey="&viewSecurityDevices.accesskey;"
|
||||
preference="security.disable_button.openDeviceManager"/>
|
||||
<hbox flex="10"/>
|
||||
</hbox>
|
||||
</tabpanel>
|
||||
</tabpanels>
|
||||
</tabbox>
|
File diff suppressed because it is too large
Load Diff
@ -1,88 +0,0 @@
|
||||
# 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/.
|
||||
|
||||
<!-- Applications panel -->
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content/applications.js"/>
|
||||
|
||||
<preferences id="feedsPreferences" hidden="true" data-category="paneApplications">
|
||||
<preference id="browser.feeds.handler"
|
||||
name="browser.feeds.handler"
|
||||
type="string"/>
|
||||
<preference id="browser.feeds.handler.default"
|
||||
name="browser.feeds.handler.default"
|
||||
type="string"/>
|
||||
<preference id="browser.feeds.handlers.application"
|
||||
name="browser.feeds.handlers.application"
|
||||
type="file"/>
|
||||
<preference id="browser.feeds.handlers.webservice"
|
||||
name="browser.feeds.handlers.webservice"
|
||||
type="string"/>
|
||||
|
||||
<preference id="browser.videoFeeds.handler"
|
||||
name="browser.videoFeeds.handler"
|
||||
type="string"/>
|
||||
<preference id="browser.videoFeeds.handler.default"
|
||||
name="browser.videoFeeds.handler.default"
|
||||
type="string"/>
|
||||
<preference id="browser.videoFeeds.handlers.application"
|
||||
name="browser.videoFeeds.handlers.application"
|
||||
type="file"/>
|
||||
<preference id="browser.videoFeeds.handlers.webservice"
|
||||
name="browser.videoFeeds.handlers.webservice"
|
||||
type="string"/>
|
||||
|
||||
<preference id="browser.audioFeeds.handler"
|
||||
name="browser.audioFeeds.handler"
|
||||
type="string"/>
|
||||
<preference id="browser.audioFeeds.handler.default"
|
||||
name="browser.audioFeeds.handler.default"
|
||||
type="string"/>
|
||||
<preference id="browser.audioFeeds.handlers.application"
|
||||
name="browser.audioFeeds.handlers.application"
|
||||
type="file"/>
|
||||
<preference id="browser.audioFeeds.handlers.webservice"
|
||||
name="browser.audioFeeds.handlers.webservice"
|
||||
type="string"/>
|
||||
|
||||
<preference id="pref.downloads.disable_button.edit_actions"
|
||||
name="pref.downloads.disable_button.edit_actions"
|
||||
type="bool"/>
|
||||
</preferences>
|
||||
|
||||
<hbox id="header-applications"
|
||||
class="header"
|
||||
hidden="true"
|
||||
data-category="paneApplications">
|
||||
<label class="header-name" flex="1">&paneApplications.title;</label>
|
||||
<html:a class="help-button" target="_blank" aria-label="&helpButton.label;"></html:a>
|
||||
</hbox>
|
||||
|
||||
<vbox id="applicationsContent"
|
||||
data-category="paneApplications"
|
||||
hidden="true"
|
||||
flex="1">
|
||||
<hbox>
|
||||
<textbox id="filter" flex="1"
|
||||
type="search"
|
||||
placeholder="&filter.emptytext;"
|
||||
aria-controls="handlersView"/>
|
||||
</hbox>
|
||||
|
||||
<separator class="thin"/>
|
||||
|
||||
<richlistbox id="handlersView" orient="vertical" persist="lastSelectedType"
|
||||
preference="pref.downloads.disable_button.edit_actions"
|
||||
flex="1">
|
||||
<listheader equalsize="always">
|
||||
<treecol id="typeColumn" label="&typeColumn.label;" value="type"
|
||||
accesskey="&typeColumn.accesskey;" persist="sortDirection"
|
||||
flex="1" sortDirection="ascending"/>
|
||||
<treecol id="actionColumn" label="&actionColumn2.label;" value="action"
|
||||
accesskey="&actionColumn2.accesskey;" persist="sortDirection"
|
||||
flex="1"/>
|
||||
</listheader>
|
||||
</richlistbox>
|
||||
</vbox>
|
@ -7,7 +7,7 @@
|
||||
Components.utils.import("resource://gre/modules/AppConstants.jsm");
|
||||
Components.utils.import("resource://gre/modules/ContextualIdentityService.jsm");
|
||||
|
||||
const containersBundle = Services.strings.createBundle("chrome://browser/locale/preferences-old/containers.properties");
|
||||
const containersBundle = Services.strings.createBundle("chrome://browser/locale/preferences/containers.properties");
|
||||
|
||||
const defaultContainerIcon = "fingerprint";
|
||||
const defaultContainerColor = "blue";
|
||||
@ -18,7 +18,7 @@ let gContainersPane = {
|
||||
this._list = document.getElementById("containersView");
|
||||
|
||||
document.getElementById("backContainersLink").addEventListener("click", function() {
|
||||
gotoPref("privacy");
|
||||
gotoPref("general");
|
||||
});
|
||||
|
||||
this._rebuildView();
|
||||
|
@ -18,7 +18,7 @@
|
||||
<hbox hidden="true"
|
||||
class="container-header-links"
|
||||
data-category="paneContainers">
|
||||
<label class="text-link" id="backContainersLink" value="&backLink.label;" />
|
||||
<label class="text-link" id="backContainersLink">&backLink2.label;</label>
|
||||
</hbox>
|
||||
|
||||
<hbox id="header-containers"
|
||||
@ -26,12 +26,11 @@
|
||||
hidden="true"
|
||||
data-category="paneContainers">
|
||||
<label class="header-name" flex="1">&paneContainers.title;</label>
|
||||
<button class="help-button"
|
||||
aria-label="&helpButton.label;"/>
|
||||
</hbox>
|
||||
|
||||
<!-- Containers -->
|
||||
<groupbox id="browserContainersGroup" data-category="paneContainers" hidden="true">
|
||||
<groupbox id="browserContainersGroupPane" data-category="paneContainers" hidden="true"
|
||||
data-hidden-from-search="true" data-subpanel="true">
|
||||
<vbox id="browserContainersbox">
|
||||
|
||||
<richlistbox id="containersView" orient="vertical" persist="lastSelectedType"
|
||||
|
@ -1,279 +0,0 @@
|
||||
/* 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/. */
|
||||
|
||||
/* import-globals-from preferences.js */
|
||||
/* import-globals-from ../../../../toolkit/mozapps/preferences/fontbuilder.js */
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "AlertsServiceDND", function() {
|
||||
try {
|
||||
let alertsService = Cc["@mozilla.org/alerts-service;1"]
|
||||
.getService(Ci.nsIAlertsService)
|
||||
.QueryInterface(Ci.nsIAlertsDoNotDisturb);
|
||||
// This will throw if manualDoNotDisturb isn't implemented.
|
||||
alertsService.manualDoNotDisturb;
|
||||
return alertsService;
|
||||
} catch (ex) {
|
||||
return undefined;
|
||||
}
|
||||
});
|
||||
|
||||
var gContentPane = {
|
||||
init() {
|
||||
function setEventListener(aId, aEventType, aCallback) {
|
||||
document.getElementById(aId)
|
||||
.addEventListener(aEventType, aCallback.bind(gContentPane));
|
||||
}
|
||||
|
||||
// Initializes the fonts dropdowns displayed in this pane.
|
||||
this._rebuildFonts();
|
||||
|
||||
// Show translation preferences if we may:
|
||||
const prefName = "browser.translation.ui.show";
|
||||
if (Services.prefs.getBoolPref(prefName)) {
|
||||
let row = document.getElementById("translationBox");
|
||||
row.removeAttribute("hidden");
|
||||
// Showing attribution only for Bing Translator.
|
||||
Components.utils.import("resource:///modules/translation/Translation.jsm");
|
||||
if (Translation.translationEngine == "bing") {
|
||||
document.getElementById("bingAttribution").removeAttribute("hidden");
|
||||
}
|
||||
}
|
||||
|
||||
if (AlertsServiceDND) {
|
||||
let notificationsDoNotDisturbRow =
|
||||
document.getElementById("notificationsDoNotDisturbRow");
|
||||
notificationsDoNotDisturbRow.removeAttribute("hidden");
|
||||
if (AlertsServiceDND.manualDoNotDisturb) {
|
||||
let notificationsDoNotDisturb =
|
||||
document.getElementById("notificationsDoNotDisturb");
|
||||
notificationsDoNotDisturb.setAttribute("checked", true);
|
||||
}
|
||||
}
|
||||
|
||||
setEventListener("font.language.group", "change",
|
||||
gContentPane._rebuildFonts);
|
||||
setEventListener("notificationsPolicyButton", "command",
|
||||
gContentPane.showNotificationExceptions);
|
||||
setEventListener("popupPolicyButton", "command",
|
||||
gContentPane.showPopupExceptions);
|
||||
setEventListener("advancedFonts", "command",
|
||||
gContentPane.configureFonts);
|
||||
setEventListener("colors", "command",
|
||||
gContentPane.configureColors);
|
||||
setEventListener("chooseLanguage", "command",
|
||||
gContentPane.showLanguages);
|
||||
setEventListener("translationAttributionImage", "click",
|
||||
gContentPane.openTranslationProviderAttribution);
|
||||
setEventListener("translateButton", "command",
|
||||
gContentPane.showTranslationExceptions);
|
||||
setEventListener("notificationsDoNotDisturb", "command",
|
||||
gContentPane.toggleDoNotDisturbNotifications);
|
||||
|
||||
let notificationInfoURL =
|
||||
Services.urlFormatter.formatURLPref("app.support.baseURL") + "push";
|
||||
document.getElementById("notificationsPolicyLearnMore").setAttribute("href",
|
||||
notificationInfoURL);
|
||||
|
||||
let drmInfoURL =
|
||||
Services.urlFormatter.formatURLPref("app.support.baseURL") + "drm-content";
|
||||
document.getElementById("playDRMContentLink").setAttribute("href", drmInfoURL);
|
||||
let emeUIEnabled = Services.prefs.getBoolPref("browser.eme.ui.enabled");
|
||||
// Force-disable/hide on WinXP:
|
||||
if (navigator.platform.toLowerCase().startsWith("win")) {
|
||||
emeUIEnabled = emeUIEnabled && parseFloat(Services.sysinfo.get("version")) >= 6;
|
||||
}
|
||||
if (!emeUIEnabled) {
|
||||
// Don't want to rely on .hidden for the toplevel groupbox because
|
||||
// of the pane hiding/showing code potentially interfering:
|
||||
document.getElementById("drmGroup").setAttribute("style", "display: none !important");
|
||||
}
|
||||
},
|
||||
|
||||
// UTILITY FUNCTIONS
|
||||
|
||||
/**
|
||||
* Utility function to enable/disable the button specified by aButtonID based
|
||||
* on the value of the Boolean preference specified by aPreferenceID.
|
||||
*/
|
||||
updateButtons(aButtonID, aPreferenceID) {
|
||||
var button = document.getElementById(aButtonID);
|
||||
var preference = document.getElementById(aPreferenceID);
|
||||
button.disabled = preference.value != true;
|
||||
return undefined;
|
||||
},
|
||||
|
||||
// BEGIN UI CODE
|
||||
|
||||
/*
|
||||
* Preferences:
|
||||
*
|
||||
* dom.disable_open_during_load
|
||||
* - true if popups are blocked by default, false otherwise
|
||||
*/
|
||||
|
||||
// NOTIFICATIONS
|
||||
|
||||
/**
|
||||
* Displays the notifications exceptions dialog where specific site notification
|
||||
* preferences can be set.
|
||||
*/
|
||||
showNotificationExceptions() {
|
||||
let bundlePreferences = document.getElementById("bundlePreferences");
|
||||
let params = { permissionType: "desktop-notification" };
|
||||
params.windowTitle = bundlePreferences.getString("notificationspermissionstitle");
|
||||
params.introText = bundlePreferences.getString("notificationspermissionstext4");
|
||||
|
||||
gSubDialog.open("chrome://browser/content/preferences/permissions.xul",
|
||||
"resizable=yes", params);
|
||||
|
||||
try {
|
||||
Services.telemetry
|
||||
.getHistogramById("WEB_NOTIFICATION_EXCEPTIONS_OPENED").add();
|
||||
} catch (e) {}
|
||||
},
|
||||
|
||||
|
||||
// POP-UPS
|
||||
|
||||
/**
|
||||
* Displays the popup exceptions dialog where specific site popup preferences
|
||||
* can be set.
|
||||
*/
|
||||
showPopupExceptions() {
|
||||
var bundlePreferences = document.getElementById("bundlePreferences");
|
||||
var params = { blockVisible: false, sessionVisible: false, allowVisible: true,
|
||||
prefilledHost: "", permissionType: "popup" }
|
||||
params.windowTitle = bundlePreferences.getString("popuppermissionstitle2");
|
||||
params.introText = bundlePreferences.getString("popuppermissionstext");
|
||||
|
||||
gSubDialog.open("chrome://browser/content/preferences/permissions.xul",
|
||||
"resizable=yes", params);
|
||||
},
|
||||
|
||||
// FONTS
|
||||
|
||||
/**
|
||||
* Populates the default font list in UI.
|
||||
*/
|
||||
_rebuildFonts() {
|
||||
var preferences = document.getElementById("contentPreferences");
|
||||
// Ensure preferences are "visible" to ensure bindings work.
|
||||
preferences.hidden = false;
|
||||
// Force flush:
|
||||
preferences.clientHeight;
|
||||
var langGroupPref = document.getElementById("font.language.group");
|
||||
this._selectDefaultLanguageGroup(langGroupPref.value,
|
||||
this._readDefaultFontTypeForLanguage(langGroupPref.value) == "serif");
|
||||
},
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
_selectDefaultLanguageGroup(aLanguageGroup, aIsSerif) {
|
||||
const kFontNameFmtSerif = "font.name.serif.%LANG%";
|
||||
const kFontNameFmtSansSerif = "font.name.sans-serif.%LANG%";
|
||||
const kFontNameListFmtSerif = "font.name-list.serif.%LANG%";
|
||||
const kFontNameListFmtSansSerif = "font.name-list.sans-serif.%LANG%";
|
||||
const kFontSizeFmtVariable = "font.size.variable.%LANG%";
|
||||
|
||||
var preferences = document.getElementById("contentPreferences");
|
||||
var prefs = [{ format: aIsSerif ? kFontNameFmtSerif : kFontNameFmtSansSerif,
|
||||
type: "fontname",
|
||||
element: "defaultFont",
|
||||
fonttype: aIsSerif ? "serif" : "sans-serif" },
|
||||
{ format: aIsSerif ? kFontNameListFmtSerif : kFontNameListFmtSansSerif,
|
||||
type: "unichar",
|
||||
element: null,
|
||||
fonttype: aIsSerif ? "serif" : "sans-serif" },
|
||||
{ format: kFontSizeFmtVariable,
|
||||
type: "int",
|
||||
element: "defaultFontSize",
|
||||
fonttype: null }];
|
||||
for (var i = 0; i < prefs.length; ++i) {
|
||||
var preference = document.getElementById(prefs[i].format.replace(/%LANG%/, aLanguageGroup));
|
||||
if (!preference) {
|
||||
preference = document.createElement("preference");
|
||||
var name = prefs[i].format.replace(/%LANG%/, aLanguageGroup);
|
||||
preference.id = name;
|
||||
preference.setAttribute("name", name);
|
||||
preference.setAttribute("type", prefs[i].type);
|
||||
preferences.appendChild(preference);
|
||||
}
|
||||
|
||||
if (!prefs[i].element)
|
||||
continue;
|
||||
|
||||
var element = document.getElementById(prefs[i].element);
|
||||
if (element) {
|
||||
element.setAttribute("preference", preference.id);
|
||||
|
||||
if (prefs[i].fonttype)
|
||||
FontBuilder.buildFontList(aLanguageGroup, prefs[i].fonttype, element);
|
||||
|
||||
preference.setElementValue(element);
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Returns the type of the current default font for the language denoted by
|
||||
* aLanguageGroup.
|
||||
*/
|
||||
_readDefaultFontTypeForLanguage(aLanguageGroup) {
|
||||
const kDefaultFontType = "font.default.%LANG%";
|
||||
var defaultFontTypePref = kDefaultFontType.replace(/%LANG%/, aLanguageGroup);
|
||||
var preference = document.getElementById(defaultFontTypePref);
|
||||
if (!preference) {
|
||||
preference = document.createElement("preference");
|
||||
preference.id = defaultFontTypePref;
|
||||
preference.setAttribute("name", defaultFontTypePref);
|
||||
preference.setAttribute("type", "string");
|
||||
preference.setAttribute("onchange", "gContentPane._rebuildFonts();");
|
||||
document.getElementById("contentPreferences").appendChild(preference);
|
||||
}
|
||||
return preference.value;
|
||||
},
|
||||
|
||||
/**
|
||||
* Displays the fonts dialog, where web page font names and sizes can be
|
||||
* configured.
|
||||
*/
|
||||
configureFonts() {
|
||||
gSubDialog.open("chrome://browser/content/preferences/fonts.xul", "resizable=no");
|
||||
},
|
||||
|
||||
/**
|
||||
* Displays the colors dialog, where default web page/link/etc. colors can be
|
||||
* configured.
|
||||
*/
|
||||
configureColors() {
|
||||
gSubDialog.open("chrome://browser/content/preferences/colors.xul", "resizable=no");
|
||||
},
|
||||
|
||||
// LANGUAGES
|
||||
|
||||
/**
|
||||
* Shows a dialog in which the preferred language for web content may be set.
|
||||
*/
|
||||
showLanguages() {
|
||||
gSubDialog.open("chrome://browser/content/preferences/languages.xul");
|
||||
},
|
||||
|
||||
/**
|
||||
* Displays the translation exceptions dialog where specific site and language
|
||||
* translation preferences can be set.
|
||||
*/
|
||||
showTranslationExceptions() {
|
||||
gSubDialog.open("chrome://browser/content/preferences/translation.xul");
|
||||
},
|
||||
|
||||
openTranslationProviderAttribution() {
|
||||
Components.utils.import("resource:///modules/translation/Translation.jsm");
|
||||
Translation.openProviderAttribution();
|
||||
},
|
||||
|
||||
toggleDoNotDisturbNotifications(event) {
|
||||
AlertsServiceDND.manualDoNotDisturb = event.target.checked;
|
||||
},
|
||||
};
|
@ -1,207 +0,0 @@
|
||||
# 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/.
|
||||
|
||||
<!-- Content panel -->
|
||||
|
||||
<preferences id="contentPreferences" hidden="true" data-category="paneContent">
|
||||
|
||||
<!-- DRM content -->
|
||||
<preference id="media.eme.enabled"
|
||||
name="media.eme.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Popups -->
|
||||
<preference id="dom.disable_open_during_load"
|
||||
name="dom.disable_open_during_load"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Fonts -->
|
||||
<preference id="font.language.group"
|
||||
name="font.language.group"
|
||||
type="wstring"/>
|
||||
|
||||
<!-- Languages -->
|
||||
<preference id="browser.translation.detectLanguage"
|
||||
name="browser.translation.detectLanguage"
|
||||
type="bool"/>
|
||||
</preferences>
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://mozapps/content/preferences/fontbuilder.js"/>
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content/content.js"/>
|
||||
|
||||
<hbox id="header-content"
|
||||
class="header"
|
||||
hidden="true"
|
||||
data-category="paneContent">
|
||||
<label class="header-name" flex="1">&paneContent.title;</label>
|
||||
<html:a class="help-button" target="_blank" aria-label="&helpButton.label;"></html:a>
|
||||
</hbox>
|
||||
|
||||
<groupbox id="drmGroup" data-category="paneContent" hidden="true">
|
||||
<caption><label>&drmContent.label;</label></caption>
|
||||
<grid id="contentGrid2">
|
||||
<columns>
|
||||
<column flex="1"/>
|
||||
<column/>
|
||||
</columns>
|
||||
<rows id="contentRows-2">
|
||||
<row id="playDRMContentRow">
|
||||
<hbox align="center">
|
||||
<checkbox id="playDRMContent" preference="media.eme.enabled"
|
||||
label="&playDRMContent.label;" accesskey="&playDRMContent.accesskey;"/>
|
||||
<label id="playDRMContentLink" class="learnMore text-link" value="&playDRMContent.learnMore.label;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
</rows>
|
||||
</grid>
|
||||
</groupbox>
|
||||
|
||||
<groupbox id="notificationsGroup" data-category="paneContent" hidden="true">
|
||||
<caption><label>¬ificationsPolicy.label;</label></caption>
|
||||
<grid>
|
||||
<columns>
|
||||
<column flex="1"/>
|
||||
<column/>
|
||||
</columns>
|
||||
<rows>
|
||||
<row id="notificationsPolicyRow" align="center">
|
||||
<hbox align="start">
|
||||
<label id="notificationsPolicy">¬ificationsPolicyDesc4.label;</label>
|
||||
<label id="notificationsPolicyLearnMore"
|
||||
class="learnMore text-link"
|
||||
value="¬ificationsPolicyLearnMore.label;"/>
|
||||
</hbox>
|
||||
<hbox pack="end">
|
||||
<button id="notificationsPolicyButton" label="¬ificationsPolicyButton.label;"
|
||||
accesskey="¬ificationsPolicyButton.accesskey;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
<row id="notificationsDoNotDisturbRow" hidden="true">
|
||||
<vbox align="start">
|
||||
<checkbox id="notificationsDoNotDisturb" label="¬ificationsDoNotDisturb.label;"
|
||||
accesskey="¬ificationsDoNotDisturb.accesskey;"/>
|
||||
<label id="notificationsDoNotDisturbDetails"
|
||||
class="indent"
|
||||
value="¬ificationsDoNotDisturbDetails.value;"/>
|
||||
</vbox>
|
||||
</row>
|
||||
</rows>
|
||||
</grid>
|
||||
</groupbox>
|
||||
|
||||
<groupbox id="miscGroup" data-category="paneContent" hidden="true">
|
||||
<caption><label>&popups.label;</label></caption>
|
||||
<grid id="contentGrid">
|
||||
<columns>
|
||||
<column flex="1"/>
|
||||
<column/>
|
||||
</columns>
|
||||
<rows id="contentRows-1">
|
||||
<row id="popupPolicyRow">
|
||||
<vbox align="start">
|
||||
<checkbox id="popupPolicy" preference="dom.disable_open_during_load"
|
||||
label="&blockPopups.label;" accesskey="&blockPopups.accesskey;"
|
||||
onsyncfrompreference="return gContentPane.updateButtons('popupPolicyButton',
|
||||
'dom.disable_open_during_load');"/>
|
||||
</vbox>
|
||||
<hbox pack="end">
|
||||
<button id="popupPolicyButton" label="&popupExceptions.label;"
|
||||
accesskey="&popupExceptions.accesskey;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
</rows>
|
||||
</grid>
|
||||
</groupbox>
|
||||
|
||||
<!-- Fonts and Colors -->
|
||||
<groupbox id="fontsGroup" data-category="paneContent" hidden="true">
|
||||
<caption><label>&fontsAndColors.label;</label></caption>
|
||||
|
||||
<grid id="fontsGrid">
|
||||
<columns>
|
||||
<column flex="1"/>
|
||||
<column/>
|
||||
</columns>
|
||||
<rows id="fontsRows">
|
||||
<row id="fontRow">
|
||||
<hbox align="center">
|
||||
<label control="defaultFont" accesskey="&defaultFont.accesskey;">&defaultFont.label;</label>
|
||||
<menulist id="defaultFont" delayprefsave="true" onsyncfrompreference="return FontBuilder.readFontSelection(this);"/>
|
||||
<label id="defaultFontSizeLabel" control="defaultFontSize" accesskey="&defaultSize.accesskey;">&defaultSize.label;</label>
|
||||
<menulist id="defaultFontSize" delayprefsave="true">
|
||||
<menupopup>
|
||||
<menuitem value="9" label="9"/>
|
||||
<menuitem value="10" label="10"/>
|
||||
<menuitem value="11" label="11"/>
|
||||
<menuitem value="12" label="12"/>
|
||||
<menuitem value="13" label="13"/>
|
||||
<menuitem value="14" label="14"/>
|
||||
<menuitem value="15" label="15"/>
|
||||
<menuitem value="16" label="16"/>
|
||||
<menuitem value="17" label="17"/>
|
||||
<menuitem value="18" label="18"/>
|
||||
<menuitem value="20" label="20"/>
|
||||
<menuitem value="22" label="22"/>
|
||||
<menuitem value="24" label="24"/>
|
||||
<menuitem value="26" label="26"/>
|
||||
<menuitem value="28" label="28"/>
|
||||
<menuitem value="30" label="30"/>
|
||||
<menuitem value="32" label="32"/>
|
||||
<menuitem value="34" label="34"/>
|
||||
<menuitem value="36" label="36"/>
|
||||
<menuitem value="40" label="40"/>
|
||||
<menuitem value="44" label="44"/>
|
||||
<menuitem value="48" label="48"/>
|
||||
<menuitem value="56" label="56"/>
|
||||
<menuitem value="64" label="64"/>
|
||||
<menuitem value="72" label="72"/>
|
||||
</menupopup>
|
||||
</menulist>
|
||||
</hbox>
|
||||
<button id="advancedFonts" icon="select-font"
|
||||
label="&advancedFonts.label;"
|
||||
accesskey="&advancedFonts.accesskey;"/>
|
||||
</row>
|
||||
<row id="colorsRow">
|
||||
<hbox/>
|
||||
<button id="colors" icon="select-color"
|
||||
label="&colors.label;"
|
||||
accesskey="&colors.accesskey;"/>
|
||||
</row>
|
||||
</rows>
|
||||
</grid>
|
||||
</groupbox>
|
||||
|
||||
<!-- Languages -->
|
||||
<groupbox id="languagesGroup" data-category="paneContent" hidden="true">
|
||||
<caption><label>&languages.label;</label></caption>
|
||||
|
||||
<hbox id="languagesBox" align="center">
|
||||
<description flex="1" control="chooseLanguage">&chooseLanguage.label;</description>
|
||||
<button id="chooseLanguage"
|
||||
label="&chooseButton.label;"
|
||||
accesskey="&chooseButton.accesskey;"/>
|
||||
</hbox>
|
||||
|
||||
<hbox id="translationBox" hidden="true">
|
||||
<hbox align="center" flex="1">
|
||||
<checkbox id="translate" preference="browser.translation.detectLanguage"
|
||||
label="&translateWebPages.label;." accesskey="&translateWebPages.accesskey;"
|
||||
onsyncfrompreference="return gContentPane.updateButtons('translateButton',
|
||||
'browser.translation.detectLanguage');"/>
|
||||
<hbox id="bingAttribution" hidden="true">
|
||||
<label>&translation.options.attribution.beforeLogo;</label>
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<image id="translationAttributionImage" aria-label="Microsoft Translator"
|
||||
src="chrome://browser/content/microsoft-translator-attribution.png"/>
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label>&translation.options.attribution.afterLogo;</label>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<button id="translateButton" label="&translateExceptions.label;"
|
||||
accesskey="&translateExceptions.accesskey;"/>
|
||||
</hbox>
|
||||
</groupbox>
|
@ -8,11 +8,8 @@ browser.jar:
|
||||
content/browser/preferences/in-content/subdialogs.js
|
||||
|
||||
content/browser/preferences/in-content/main.js
|
||||
content/browser/preferences/in-content/search.js
|
||||
content/browser/preferences/in-content/privacy.js
|
||||
content/browser/preferences/in-content/containers.js
|
||||
content/browser/preferences/in-content/advanced.js
|
||||
content/browser/preferences/in-content/applications.js
|
||||
content/browser/preferences/in-content/content.js
|
||||
content/browser/preferences/in-content/sync.js
|
||||
content/browser/preferences/in-content/security.js
|
||||
content/browser/preferences/in-content/search.js
|
||||
content/browser/preferences/in-content/findInPage.js
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -7,6 +7,13 @@
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content/main.js"/>
|
||||
|
||||
#ifdef MOZ_UPDATER
|
||||
<script type="application/javascript" src="chrome://browser/content/aboutDialog-appUpdater.js"/>
|
||||
#endif
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://mozapps/content/preferences/fontbuilder.js"/>
|
||||
|
||||
<stringbundle id="bundlePreferences" src="chrome://browser/locale/preferences.properties"/>
|
||||
|
||||
<preferences id="mainPreferences" hidden="true" data-category="paneGeneral">
|
||||
@ -111,6 +118,64 @@
|
||||
name="browser.ctrlTab.previews"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Fonts -->
|
||||
<preference id="font.language.group"
|
||||
name="font.language.group"
|
||||
type="wstring"/>
|
||||
|
||||
<!-- Languages -->
|
||||
<preference id="browser.translation.detectLanguage"
|
||||
name="browser.translation.detectLanguage"
|
||||
type="bool"/>
|
||||
|
||||
<!-- General tab -->
|
||||
|
||||
<!-- Accessibility
|
||||
* accessibility.browsewithcaret
|
||||
- true enables keyboard navigation and selection within web pages using a
|
||||
visible caret, false uses normal keyboard navigation with no caret
|
||||
* accessibility.typeaheadfind
|
||||
- when set to true, typing outside text areas and input boxes will
|
||||
automatically start searching for what's typed within the current
|
||||
document; when set to false, no search action happens -->
|
||||
<preference id="accessibility.browsewithcaret"
|
||||
name="accessibility.browsewithcaret"
|
||||
type="bool"/>
|
||||
<preference id="accessibility.typeaheadfind"
|
||||
name="accessibility.typeaheadfind"
|
||||
type="bool"/>
|
||||
<preference id="accessibility.blockautorefresh"
|
||||
name="accessibility.blockautorefresh"
|
||||
type="bool"/>
|
||||
#ifdef XP_WIN
|
||||
<preference id="ui.osk.enabled"
|
||||
name="ui.osk.enabled"
|
||||
type="bool"/>
|
||||
#endif
|
||||
<!-- Browsing
|
||||
* general.autoScroll
|
||||
- when set to true, clicking the scroll wheel on the mouse activates a
|
||||
mouse mode where moving the mouse down scrolls the document downward with
|
||||
speed correlated with the distance of the cursor from the original
|
||||
position at which the click occurred (and likewise with movement upward);
|
||||
if false, this behavior is disabled
|
||||
* general.smoothScroll
|
||||
- set to true to enable finer page scrolling than line-by-line on page-up,
|
||||
page-down, and other such page movements -->
|
||||
<preference id="general.autoScroll"
|
||||
name="general.autoScroll"
|
||||
type="bool"/>
|
||||
<preference id="general.smoothScroll"
|
||||
name="general.smoothScroll"
|
||||
type="bool"/>
|
||||
<preference id="layout.spellcheckDefault"
|
||||
name="layout.spellcheckDefault"
|
||||
type="int"/>
|
||||
|
||||
<preference id="toolkit.telemetry.enabled"
|
||||
name="toolkit.telemetry.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.preferences.defaultPerformanceSettings.enabled"
|
||||
name="browser.preferences.defaultPerformanceSettings.enabled"
|
||||
type="bool"/>
|
||||
@ -127,14 +192,90 @@
|
||||
name="layers.acceleration.disabled"
|
||||
type="bool"
|
||||
inverted="true"/>
|
||||
|
||||
<!-- Files and Applications -->
|
||||
<preference id="browser.feeds.handler"
|
||||
name="browser.feeds.handler"
|
||||
type="string"/>
|
||||
<preference id="browser.feeds.handler.default"
|
||||
name="browser.feeds.handler.default"
|
||||
type="string"/>
|
||||
<preference id="browser.feeds.handlers.application"
|
||||
name="browser.feeds.handlers.application"
|
||||
type="file"/>
|
||||
<preference id="browser.feeds.handlers.webservice"
|
||||
name="browser.feeds.handlers.webservice"
|
||||
type="string"/>
|
||||
|
||||
<preference id="browser.videoFeeds.handler"
|
||||
name="browser.videoFeeds.handler"
|
||||
type="string"/>
|
||||
<preference id="browser.videoFeeds.handler.default"
|
||||
name="browser.videoFeeds.handler.default"
|
||||
type="string"/>
|
||||
<preference id="browser.videoFeeds.handlers.application"
|
||||
name="browser.videoFeeds.handlers.application"
|
||||
type="file"/>
|
||||
<preference id="browser.videoFeeds.handlers.webservice"
|
||||
name="browser.videoFeeds.handlers.webservice"
|
||||
type="string"/>
|
||||
|
||||
<preference id="browser.audioFeeds.handler"
|
||||
name="browser.audioFeeds.handler"
|
||||
type="string"/>
|
||||
<preference id="browser.audioFeeds.handler.default"
|
||||
name="browser.audioFeeds.handler.default"
|
||||
type="string"/>
|
||||
<preference id="browser.audioFeeds.handlers.application"
|
||||
name="browser.audioFeeds.handlers.application"
|
||||
type="file"/>
|
||||
<preference id="browser.audioFeeds.handlers.webservice"
|
||||
name="browser.audioFeeds.handlers.webservice"
|
||||
type="string"/>
|
||||
|
||||
<preference id="pref.downloads.disable_button.edit_actions"
|
||||
name="pref.downloads.disable_button.edit_actions"
|
||||
type="bool"/>
|
||||
|
||||
<!-- DRM content -->
|
||||
<preference id="media.eme.enabled"
|
||||
name="media.eme.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Update -->
|
||||
<preference id="browser.preferences.advanced.selectedTabIndex"
|
||||
name="browser.preferences.advanced.selectedTabIndex"
|
||||
type="int"/>
|
||||
|
||||
#ifdef MOZ_UPDATER
|
||||
<preference id="app.update.enabled"
|
||||
name="app.update.enabled"
|
||||
type="bool"/>
|
||||
<preference id="app.update.auto"
|
||||
name="app.update.auto"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="app.update.disable_button.showUpdateHistory"
|
||||
name="app.update.disable_button.showUpdateHistory"
|
||||
type="bool"/>
|
||||
|
||||
#ifdef MOZ_MAINTENANCE_SERVICE
|
||||
<preference id="app.update.service.enabled"
|
||||
name="app.update.service.enabled"
|
||||
type="bool"/>
|
||||
#endif
|
||||
#endif
|
||||
|
||||
<preference id="browser.search.update"
|
||||
name="browser.search.update"
|
||||
type="bool"/>
|
||||
</preferences>
|
||||
|
||||
<hbox id="header-general"
|
||||
class="header"
|
||||
<hbox id="generalCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneGeneral">
|
||||
<label class="header-name" flex="1">&paneGeneral.title;</label>
|
||||
<html:a class="help-button" target="_blank" aria-label="&helpButton.label;"></html:a>
|
||||
</hbox>
|
||||
|
||||
<!-- Startup -->
|
||||
@ -164,139 +305,88 @@
|
||||
|
||||
#ifdef HAVE_SHELL_SERVICE
|
||||
<vbox id="defaultBrowserBox">
|
||||
<hbox align="center">
|
||||
<checkbox id="alwaysCheckDefault" preference="browser.shell.checkDefaultBrowser"
|
||||
label="&alwaysCheckDefault2.label;" accesskey="&alwaysCheckDefault2.accesskey;"/>
|
||||
</hbox>
|
||||
<checkbox id="alwaysCheckDefault" preference="browser.shell.checkDefaultBrowser"
|
||||
label="&alwaysCheckDefault2.label;" accesskey="&alwaysCheckDefault2.accesskey;"/>
|
||||
<deck id="setDefaultPane">
|
||||
<hbox align="center" class="indent">
|
||||
<image class="face-sad"/>
|
||||
<label id="isNotDefaultLabel" flex="1">&isNotDefault.label;</label>
|
||||
<button id="setDefaultButton"
|
||||
label="&setAsMyDefaultBrowser2.label;" accesskey="&setAsMyDefaultBrowser2.accesskey;"
|
||||
class="accessory-button"
|
||||
label="&setAsMyDefaultBrowser3.label;" accesskey="&setAsMyDefaultBrowser3.accesskey;"
|
||||
preference="pref.general.disable_button.default_browser"/>
|
||||
</hbox>
|
||||
<hbox align="center" class="indent">
|
||||
<image class="face-smile"/>
|
||||
<label id="isDefaultLabel" flex="1">&isDefault.label;</label>
|
||||
</hbox>
|
||||
</deck>
|
||||
<separator class="thin"/>
|
||||
</vbox>
|
||||
#endif
|
||||
|
||||
<html:table id="startupTable">
|
||||
<html:tr>
|
||||
<html:td class="label-cell">
|
||||
<label accesskey="&startupPage.accesskey;"
|
||||
control="browserStartupPage">&startupPage.label;</label>
|
||||
</html:td>
|
||||
<html:td class="content-cell">
|
||||
<menulist id="browserStartupPage"
|
||||
class="content-cell-item"
|
||||
preference="browser.startup.page">
|
||||
<menupopup>
|
||||
<menuitem label="&startupUserHomePage.label;"
|
||||
value="1"
|
||||
id="browserStartupHomePage"/>
|
||||
<menuitem label="&startupBlankPage.label;"
|
||||
value="0"
|
||||
id="browserStartupBlank"/>
|
||||
<menuitem label="&startupPrevSession.label;"
|
||||
value="3"
|
||||
id="browserStartupLastSession"/>
|
||||
</menupopup>
|
||||
</menulist>
|
||||
</html:td>
|
||||
</html:tr>
|
||||
<html:tr>
|
||||
<html:td class="label-cell">
|
||||
<label accesskey="&homepage.accesskey;"
|
||||
control="browserHomePage">&homepage.label;</label>
|
||||
</html:td>
|
||||
<html:td class="content-cell">
|
||||
<textbox id="browserHomePage"
|
||||
class="padded uri-element content-cell-item"
|
||||
type="autocomplete"
|
||||
autocompletesearch="unifiedcomplete"
|
||||
onsyncfrompreference="return gMainPane.syncFromHomePref();"
|
||||
onsynctopreference="return gMainPane.syncToHomePref(this.value);"
|
||||
placeholder="&abouthome.pageTitle;"
|
||||
preference="browser.startup.homepage"/>
|
||||
</html:td>
|
||||
</html:tr>
|
||||
<html:tr>
|
||||
<html:td class="label-cell" />
|
||||
<html:td class="content-cell homepage-buttons">
|
||||
<button id="useCurrent"
|
||||
class="content-cell-item"
|
||||
label=""
|
||||
accesskey="&useCurrentPage.accesskey;"
|
||||
label1="&useCurrentPage.label;"
|
||||
label2="&useMultiple.label;"
|
||||
preference="pref.browser.homepage.disable_button.current_page"/>
|
||||
<button id="useBookmark"
|
||||
class="content-cell-item"
|
||||
label="&chooseBookmark.label;"
|
||||
accesskey="&chooseBookmark.accesskey;"
|
||||
preference="pref.browser.homepage.disable_button.bookmark_page"/>
|
||||
<button id="restoreDefaultHomePage"
|
||||
class="content-cell-item"
|
||||
label="&restoreDefault.label;"
|
||||
accesskey="&restoreDefault.accesskey;"
|
||||
preference="pref.browser.homepage.disable_button.restore_default"/>
|
||||
</html:td>
|
||||
</html:tr>
|
||||
</html:table>
|
||||
<vbox id="startupPageBox">
|
||||
<label accesskey="&startupPage2.accesskey;"
|
||||
control="browserStartupPage">&startupPage2.label;</label>
|
||||
<radiogroup id="browserStartupPage"
|
||||
preference="browser.startup.page">
|
||||
<radio label="&startupUserHomePage.label;"
|
||||
value="1"
|
||||
id="browserStartupHomePage"/>
|
||||
<radio label="&startupBlankPage.label;"
|
||||
value="0"
|
||||
id="browserStartupBlank"/>
|
||||
<radio label="&startupPrevSession.label;"
|
||||
value="3"
|
||||
id="browserStartupLastSession"/>
|
||||
</radiogroup>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Downloads -->
|
||||
<groupbox id="downloadsGroup"
|
||||
<!-- Home Page -->
|
||||
<groupbox id="homepageGroup"
|
||||
data-category="paneGeneral"
|
||||
hidden="true">
|
||||
<caption><label>&downloads.label;</label></caption>
|
||||
<caption><label>&homepage2.label;</label></caption>
|
||||
|
||||
<radiogroup id="saveWhere"
|
||||
preference="browser.download.useDownloadDir"
|
||||
onsyncfrompreference="return gMainPane.readUseDownloadDir();">
|
||||
<hbox id="saveToRow">
|
||||
<radio id="saveTo"
|
||||
value="true"
|
||||
label="&saveTo.label;"
|
||||
accesskey="&saveTo.accesskey;"
|
||||
aria-labelledby="saveTo downloadFolder"/>
|
||||
<filefield id="downloadFolder"
|
||||
flex="1"
|
||||
preference="browser.download.folderList"
|
||||
preference-editable="true"
|
||||
aria-labelledby="saveTo"
|
||||
onsyncfrompreference="return gMainPane.displayDownloadDirPref();"/>
|
||||
<button id="chooseFolder"
|
||||
#ifdef XP_MACOSX
|
||||
accesskey="&chooseFolderMac.accesskey;"
|
||||
label="&chooseFolderMac.label;"
|
||||
#else
|
||||
accesskey="&chooseFolderWin.accesskey;"
|
||||
label="&chooseFolderWin.label;"
|
||||
#endif
|
||||
/>
|
||||
</hbox>
|
||||
<hbox>
|
||||
<!-- Additional radio button added to support CloudStorage - Bug 1357171 -->
|
||||
<radio id="saveToCloud"
|
||||
value="true"
|
||||
hidden="true"/>
|
||||
</hbox>
|
||||
<hbox>
|
||||
<radio id="alwaysAsk"
|
||||
value="false"
|
||||
label="&alwaysAskWhere.label;"
|
||||
accesskey="&alwaysAskWhere.accesskey;"/>
|
||||
</hbox>
|
||||
</radiogroup>
|
||||
<vbox>
|
||||
<textbox id="browserHomePage"
|
||||
class="uri-element"
|
||||
type="autocomplete"
|
||||
autocompletesearch="unifiedcomplete"
|
||||
onsyncfrompreference="return gMainPane.syncFromHomePref();"
|
||||
onsynctopreference="return gMainPane.syncToHomePref(this.value);"
|
||||
placeholder="&abouthome.pageTitle;"
|
||||
preference="browser.startup.homepage"/>
|
||||
</vbox>
|
||||
|
||||
<hbox class="homepage-buttons">
|
||||
<button id="useCurrent"
|
||||
flex="1"
|
||||
class="homepage-button"
|
||||
label=""
|
||||
accesskey="&useCurrentPage.accesskey;"
|
||||
label1="&useCurrentPage.label;"
|
||||
label2="&useMultiple.label;"
|
||||
preference="pref.browser.homepage.disable_button.current_page"/>
|
||||
<button id="useBookmark"
|
||||
flex="1"
|
||||
class="homepage-button"
|
||||
label="&chooseBookmark.label;"
|
||||
accesskey="&chooseBookmark.accesskey;"
|
||||
preference="pref.browser.homepage.disable_button.bookmark_page"
|
||||
searchkeywords="&selectBookmark.title; &selectBookmark.label;"/>
|
||||
<button id="restoreDefaultHomePage"
|
||||
flex="1"
|
||||
class="homepage-button"
|
||||
label="&restoreDefault.label;"
|
||||
accesskey="&restoreDefault.accesskey;"
|
||||
preference="pref.browser.homepage.disable_button.restore_default"/>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Tab preferences -->
|
||||
<groupbox data-category="paneGeneral"
|
||||
hidden="true" align="start">
|
||||
hidden="true">
|
||||
<caption><label>&tabsGroup.label;</label></caption>
|
||||
|
||||
<checkbox id="ctrlTabRecentlyUsedOrder" label="&ctrlTabRecentlyUsedOrder.label;"
|
||||
@ -326,20 +416,501 @@
|
||||
accesskey="&showTabsInTaskbar.accesskey;"
|
||||
preference="browser.taskbar.previews.enable"/>
|
||||
#endif
|
||||
|
||||
<hbox id="browserContainersbox" hidden="true" align="center">
|
||||
<checkbox id="browserContainersCheckbox"
|
||||
label="&browserContainersEnabled.label;"
|
||||
accesskey="&browserContainersEnabled.accesskey;"
|
||||
preference="privacy.userContext.enabled"
|
||||
onsyncfrompreference="return gPrivacyPane.readBrowserContainersCheckbox();"/>
|
||||
<label id="browserContainersLearnMore" class="learnMore text-link">
|
||||
&browserContainersLearnMore.label;
|
||||
</label>
|
||||
<spacer flex="1"/>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="browserContainersSettings"
|
||||
class="accessory-button"
|
||||
label="&browserContainersSettings.label;"
|
||||
accesskey="&browserContainersSettings.accesskey;"
|
||||
searchkeywords="&addButton.label;
|
||||
&preferencesButton.label;
|
||||
&removeButton.label;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<hbox id="languageAndAppearanceCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneGeneral">
|
||||
<label class="header-name" flex="1">&languageAndAppearance.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Fonts and Colors -->
|
||||
<groupbox id="fontsGroup" data-category="paneGeneral" hidden="true">
|
||||
<caption><label>&fontsAndColors.label;</label></caption>
|
||||
|
||||
<vbox>
|
||||
<hbox id="fontSettings">
|
||||
<hbox align="center" flex="1">
|
||||
<label control="defaultFont" accesskey="&defaultFont2.accesskey;">&defaultFont2.label;</label>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox flex="1">
|
||||
<menulist id="defaultFont" flex="1" delayprefsave="true" onsyncfrompreference="return FontBuilder.readFontSelection(this);"/>
|
||||
</hbox>
|
||||
<label id="defaultFontSizeLabel" control="defaultFontSize" accesskey="&defaultSize2.accesskey;">&defaultSize2.label;</label>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<menulist id="defaultFontSize" delayprefsave="true">
|
||||
<menupopup>
|
||||
<menuitem value="9" label="9"/>
|
||||
<menuitem value="10" label="10"/>
|
||||
<menuitem value="11" label="11"/>
|
||||
<menuitem value="12" label="12"/>
|
||||
<menuitem value="13" label="13"/>
|
||||
<menuitem value="14" label="14"/>
|
||||
<menuitem value="15" label="15"/>
|
||||
<menuitem value="16" label="16"/>
|
||||
<menuitem value="17" label="17"/>
|
||||
<menuitem value="18" label="18"/>
|
||||
<menuitem value="20" label="20"/>
|
||||
<menuitem value="22" label="22"/>
|
||||
<menuitem value="24" label="24"/>
|
||||
<menuitem value="26" label="26"/>
|
||||
<menuitem value="28" label="28"/>
|
||||
<menuitem value="30" label="30"/>
|
||||
<menuitem value="32" label="32"/>
|
||||
<menuitem value="34" label="34"/>
|
||||
<menuitem value="36" label="36"/>
|
||||
<menuitem value="40" label="40"/>
|
||||
<menuitem value="44" label="44"/>
|
||||
<menuitem value="48" label="48"/>
|
||||
<menuitem value="56" label="56"/>
|
||||
<menuitem value="64" label="64"/>
|
||||
<menuitem value="72" label="72"/>
|
||||
</menupopup>
|
||||
</menulist>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<spacer flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="advancedFonts"
|
||||
class="accessory-button"
|
||||
icon="select-font"
|
||||
label="&advancedFonts.label;"
|
||||
accesskey="&advancedFonts.accesskey;"
|
||||
searchkeywords="&fontsDialog.title;
|
||||
&fonts.label;
|
||||
&size2.label;
|
||||
&proportional2.label;
|
||||
&serif2.label;
|
||||
&sans-serif2.label;
|
||||
&monospace2.label;
|
||||
&font.langGroup.latin;
|
||||
&font.langGroup.japanese;
|
||||
&font.langGroup.trad-chinese;
|
||||
&font.langGroup.simpl-chinese;
|
||||
&font.langGroup.trad-chinese-hk;
|
||||
&font.langGroup.korean;
|
||||
&font.langGroup.cyrillic;
|
||||
&font.langGroup.el;
|
||||
&font.langGroup.other;
|
||||
&font.langGroup.thai;
|
||||
&font.langGroup.hebrew;
|
||||
&font.langGroup.arabic;
|
||||
&font.langGroup.devanagari;
|
||||
&font.langGroup.tamil;
|
||||
&font.langGroup.armenian;
|
||||
&font.langGroup.bengali;
|
||||
&font.langGroup.canadian;
|
||||
&font.langGroup.ethiopic;
|
||||
&font.langGroup.georgian;
|
||||
&font.langGroup.gujarati;
|
||||
&font.langGroup.gurmukhi;
|
||||
&font.langGroup.khmer;
|
||||
&font.langGroup.malayalam;
|
||||
&font.langGroup.math;
|
||||
&font.langGroup.odia;
|
||||
&font.langGroup.telugu;
|
||||
&font.langGroup.kannada;
|
||||
&font.langGroup.sinhala;
|
||||
&font.langGroup.tibetan;
|
||||
&minSize2.label;
|
||||
&minSize.none;
|
||||
&useDefaultFontSerif.label;
|
||||
&useDefaultFontSansSerif.label;
|
||||
&allowPagesToUseOwn.label;
|
||||
&languages.customize.Fallback2.grouplabel;
|
||||
&languages.customize.Fallback3.label;
|
||||
&languages.customize.Fallback2.desc;
|
||||
&languages.customize.Fallback.auto;
|
||||
&languages.customize.Fallback.arabic;
|
||||
&languages.customize.Fallback.baltic;
|
||||
&languages.customize.Fallback.ceiso;
|
||||
&languages.customize.Fallback.cewindows;
|
||||
&languages.customize.Fallback.simplified;
|
||||
&languages.customize.Fallback.traditional;
|
||||
&languages.customize.Fallback.cyrillic;
|
||||
&languages.customize.Fallback.greek;
|
||||
&languages.customize.Fallback.hebrew;
|
||||
&languages.customize.Fallback.japanese;
|
||||
&languages.customize.Fallback.korean;
|
||||
&languages.customize.Fallback.thai;
|
||||
&languages.customize.Fallback.turkish;
|
||||
&languages.customize.Fallback.vietnamese;
|
||||
&languages.customize.Fallback.other;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<hbox id="colorsSettings">
|
||||
<spacer flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="colors"
|
||||
class="accessory-button"
|
||||
icon="select-color"
|
||||
label="&colors.label;"
|
||||
accesskey="&colors.accesskey;"
|
||||
searchkeywords="&overrideDefaultPageColors.label;
|
||||
&overrideDefaultPageColors.always.label;
|
||||
&overrideDefaultPageColors.auto.label;
|
||||
&overrideDefaultPageColors.never.label;
|
||||
&color;
|
||||
&textColor2.label;
|
||||
&backgroundColor2.label;
|
||||
&useSystemColors.label;
|
||||
&underlineLinks.label;
|
||||
&linkColor2.label;
|
||||
&visitedLinkColor2.label;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Languages -->
|
||||
<groupbox id="languagesGroup" data-category="paneGeneral" hidden="true">
|
||||
<caption><label>&language2.label;</label></caption>
|
||||
|
||||
<hbox id="languagesBox" align="center">
|
||||
<description flex="1" control="chooseLanguage">&chooseLanguage.label;</description>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="chooseLanguage"
|
||||
class="accessory-button"
|
||||
label="&chooseButton.label;"
|
||||
accesskey="&chooseButton.accesskey;"
|
||||
searchkeywords="&languages.customize.Header;
|
||||
&languages.customize2.description;
|
||||
&languages.customize.moveUp.label;
|
||||
&languages.customize.moveDown.label;
|
||||
&languages.customize.deleteButton.label;
|
||||
&languages.customize.selectLanguage.label;
|
||||
&languages.customize.addButton.label;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
|
||||
<hbox id="translationBox" hidden="true">
|
||||
<hbox align="center" flex="1">
|
||||
<checkbox id="translate" preference="browser.translation.detectLanguage"
|
||||
label="&translateWebPages.label;." accesskey="&translateWebPages.accesskey;"
|
||||
onsyncfrompreference="return gMainPane.updateButtons('translateButton',
|
||||
'browser.translation.detectLanguage');"/>
|
||||
<hbox id="bingAttribution" hidden="true">
|
||||
<label>&translation.options.attribution.beforeLogo;</label>
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<image id="translationAttributionImage" aria-label="Microsoft Translator"
|
||||
src="chrome://browser/content/microsoft-translator-attribution.png"/>
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label>&translation.options.attribution.afterLogo;</label>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<button id="translateButton"
|
||||
class="accessory-button"
|
||||
label="&translateExceptions.label;"
|
||||
accesskey="&translateExceptions.accesskey;"/>
|
||||
</hbox>
|
||||
<checkbox id="checkSpelling"
|
||||
label="&checkUserSpelling.label;"
|
||||
accesskey="&checkUserSpelling.accesskey;"
|
||||
onsyncfrompreference="return gMainPane.readCheckSpelling();"
|
||||
onsynctopreference="return gMainPane.writeCheckSpelling();"
|
||||
preference="layout.spellcheckDefault"/>
|
||||
</groupbox>
|
||||
|
||||
<!-- Files and Applications -->
|
||||
<hbox id="filesAndApplicationsCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneGeneral">
|
||||
<label class="header-name" flex="1">&filesAndApplications.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!--Downloads-->
|
||||
<groupbox id="downloadsGroup" data-category="paneGeneral" hidden="true">
|
||||
<caption><label>&downloads.label;</label></caption>
|
||||
|
||||
<radiogroup id="saveWhere"
|
||||
preference="browser.download.useDownloadDir"
|
||||
onsyncfrompreference="return gMainPane.readUseDownloadDir();">
|
||||
<hbox id="saveToRow">
|
||||
<radio id="saveTo"
|
||||
value="true"
|
||||
label="&saveTo.label;"
|
||||
accesskey="&saveTo.accesskey;"
|
||||
aria-labelledby="saveTo downloadFolder"/>
|
||||
<filefield id="downloadFolder"
|
||||
flex="1"
|
||||
preference="browser.download.folderList"
|
||||
preference-editable="true"
|
||||
aria-labelledby="saveTo"
|
||||
onsyncfrompreference="return gMainPane.displayDownloadDirPref();"/>
|
||||
<button id="chooseFolder"
|
||||
#ifdef XP_MACOSX
|
||||
accesskey="&chooseFolderMac.accesskey;"
|
||||
label="&chooseFolderMac.label;"
|
||||
#else
|
||||
accesskey="&chooseFolderWin.accesskey;"
|
||||
label="&chooseFolderWin.label;"
|
||||
#endif
|
||||
/>
|
||||
</hbox>
|
||||
<!-- Additional radio button added to support CloudStorage - Bug 1357171 -->
|
||||
<radio id="saveToCloud"
|
||||
value="true"
|
||||
hidden="true"/>
|
||||
<radio id="alwaysAsk"
|
||||
value="false"
|
||||
label="&alwaysAskWhere.label;"
|
||||
accesskey="&alwaysAskWhere.accesskey;"/>
|
||||
</radiogroup>
|
||||
</groupbox>
|
||||
|
||||
<groupbox id="applicationsGroup" data-category="paneGeneral" hidden="true">
|
||||
<caption><label>&applications.label;</label></caption>
|
||||
<description>&applications.description;</description>
|
||||
<textbox id="filter" flex="1"
|
||||
type="search"
|
||||
placeholder="&filter2.emptytext;"
|
||||
aria-controls="handlersView"/>
|
||||
|
||||
<richlistbox id="handlersView" orient="vertical" persist="lastSelectedType"
|
||||
preference="pref.downloads.disable_button.edit_actions"
|
||||
flex="1">
|
||||
<listheader equalsize="always">
|
||||
<treecol id="typeColumn" label="&typeColumn.label;" value="type"
|
||||
accesskey="&typeColumn.accesskey;" persist="sortDirection"
|
||||
flex="1" sortDirection="ascending"/>
|
||||
<treecol id="actionColumn" label="&actionColumn2.label;" value="action"
|
||||
accesskey="&actionColumn2.accesskey;" persist="sortDirection"
|
||||
flex="1"/>
|
||||
</listheader>
|
||||
</richlistbox>
|
||||
</groupbox>
|
||||
|
||||
|
||||
<!-- DRM Content -->
|
||||
<groupbox id="drmGroup" data-category="paneGeneral" data-subcategory="drm" hidden="true">
|
||||
<caption><label>&drmContent2.label;</label></caption>
|
||||
<grid id="contentGrid2">
|
||||
<columns>
|
||||
<column flex="1"/>
|
||||
<column/>
|
||||
</columns>
|
||||
<rows id="contentRows-2">
|
||||
<row id="playDRMContentRow">
|
||||
<hbox align="center">
|
||||
<checkbox id="playDRMContent" preference="media.eme.enabled"
|
||||
label="&playDRMContent2.label;" accesskey="&playDRMContent2.accesskey;"/>
|
||||
<label id="playDRMContentLink" class="learnMore text-link">
|
||||
&playDRMContent.learnMore.label;
|
||||
</label>
|
||||
</hbox>
|
||||
</row>
|
||||
</rows>
|
||||
</grid>
|
||||
</groupbox>
|
||||
|
||||
#ifdef HAVE_SHELL_SERVICE
|
||||
<stringbundle id="bundleShell" src="chrome://browser/locale/shellservice.properties"/>
|
||||
<stringbundle id="bundleBrand" src="chrome://branding/locale/brand.properties"/>
|
||||
#endif
|
||||
|
||||
<hbox id="updatesCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneGeneral">
|
||||
<label class="header-name" flex="1">&updateApplication.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Update -->
|
||||
<groupbox id="updateApp" data-category="paneGeneral" hidden="true">
|
||||
<caption class="search-header" hidden="true"><label>&updateApplication.label;</label></caption>
|
||||
|
||||
<label>&updateApplicationDescription.label;</label>
|
||||
<hbox align="start">
|
||||
<vbox flex="1">
|
||||
<description>
|
||||
&updateApplication.version.pre;<label id="version"/>&updateApplication.version.post;
|
||||
<label id="releasenotes" class="learnMore text-link" hidden="true">&releaseNotes.link;</label>
|
||||
</description>
|
||||
<description id="distribution" class="text-blurb" hidden="true"/>
|
||||
<description id="distributionId" class="text-blurb" hidden="true"/>
|
||||
</vbox>
|
||||
#ifdef MOZ_UPDATER
|
||||
<spacer flex="1"/>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<vbox>
|
||||
<button id="showUpdateHistory"
|
||||
class="accessory-button"
|
||||
label="&updateHistory2.label;"
|
||||
accesskey="&updateHistory2.accesskey;"
|
||||
preference="app.update.disable_button.showUpdateHistory"
|
||||
searchkeywords="&history.title; &history2.intro;"/>
|
||||
</vbox>
|
||||
#endif
|
||||
</hbox>
|
||||
#ifdef MOZ_UPDATER
|
||||
<vbox id="updateBox">
|
||||
<deck id="updateDeck" orient="vertical">
|
||||
<hbox id="checkForUpdates" align="start">
|
||||
<spacer flex="1"/>
|
||||
<button id="checkForUpdatesButton"
|
||||
label="&update.checkForUpdatesButton.label;"
|
||||
accesskey="&update.checkForUpdatesButton.accesskey;"
|
||||
oncommand="gAppUpdater.checkForUpdates();"/>
|
||||
</hbox>
|
||||
<hbox id="downloadAndInstall" align="start">
|
||||
<spacer flex="1"/>
|
||||
<button id="downloadAndInstallButton"
|
||||
oncommand="gAppUpdater.startDownload();"/>
|
||||
<!-- label and accesskey will be filled by JS -->
|
||||
</hbox>
|
||||
<hbox id="apply" align="start">
|
||||
<spacer flex="1"/>
|
||||
<button id="updateButton"
|
||||
label="&update.updateButton.label3;"
|
||||
accesskey="&update.updateButton.accesskey;"
|
||||
oncommand="gAppUpdater.buttonRestartAfterDownload();"/>
|
||||
</hbox>
|
||||
<hbox id="checkingForUpdates" align="start">
|
||||
<image class="update-throbber"/><label>&update.checkingForUpdates;</label>
|
||||
<spacer flex="1"/>
|
||||
<button label="&update.checkForUpdatesButton.label;"
|
||||
accesskey="&update.checkForUpdatesButton.accesskey;"
|
||||
disabled="true"/>
|
||||
</hbox>
|
||||
<hbox id="downloading" align="start">
|
||||
<image class="update-throbber"/><label>&update.downloading.start;</label><label id="downloadStatus"/><label>&update.downloading.end;</label>
|
||||
</hbox>
|
||||
<hbox id="applying" align="start">
|
||||
<image class="update-throbber"/><label>&update.applying;</label>
|
||||
</hbox>
|
||||
<hbox id="downloadFailed" align="start">
|
||||
<label>&update.failed.start;</label><label id="failedLink" class="text-link">&update.failed.linkText;</label><label>&update.failed.end;</label>
|
||||
<spacer flex="1"/>
|
||||
<button label="&update.checkForUpdatesButton.label;"
|
||||
accesskey="&update.checkForUpdatesButton.accesskey;"
|
||||
oncommand="gAppUpdater.checkForUpdates();"/>
|
||||
</hbox>
|
||||
<hbox id="adminDisabled" align="start">
|
||||
<label>&update.adminDisabled;</label>
|
||||
<spacer flex="1"/>
|
||||
<button label="&update.checkForUpdatesButton.label;"
|
||||
accesskey="&update.checkForUpdatesButton.accesskey;"
|
||||
disabled="true"/>
|
||||
</hbox>
|
||||
<hbox id="noUpdatesFound" align="start">
|
||||
<image class="face-smile"/>
|
||||
<label>&update.noUpdatesFound;</label>
|
||||
<spacer flex="1"/>
|
||||
<button label="&update.checkForUpdatesButton.label;"
|
||||
accesskey="&update.checkForUpdatesButton.accesskey;"
|
||||
oncommand="gAppUpdater.checkForUpdates();"/>
|
||||
</hbox>
|
||||
<hbox id="otherInstanceHandlingUpdates" align="start">
|
||||
<label>&update.otherInstanceHandlingUpdates;</label>
|
||||
<spacer flex="1"/>
|
||||
<button label="&update.checkForUpdatesButton.label;"
|
||||
accesskey="&update.checkForUpdatesButton.accesskey;"
|
||||
disabled="true"/>
|
||||
</hbox>
|
||||
<hbox id="manualUpdate" align="start">
|
||||
<image class="face-sad"/>
|
||||
<description flex="1">
|
||||
<label>&update.manual.start;</label><label id="manualLink" class="text-link"/><label>&update.manual.end;</label>
|
||||
</description>
|
||||
<spacer flex="1"/>
|
||||
<button label="&update.checkForUpdatesButton.label;"
|
||||
accesskey="&update.checkForUpdatesButton.accesskey;"
|
||||
disabled="true"/>
|
||||
</hbox>
|
||||
<hbox id="unsupportedSystem" align="start">
|
||||
<description flex="1">
|
||||
<label>&update.unsupported.start;</label><label id="unsupportedLink" class="learnMore text-link">&update.unsupported.linkText;</label><label>&update.unsupported.end;</label>
|
||||
</description>
|
||||
<spacer flex="1"/>
|
||||
<button label="&update.checkForUpdatesButton.label;"
|
||||
accesskey="&update.checkForUpdatesButton.accesskey;"
|
||||
disabled="true"/>
|
||||
</hbox>
|
||||
<hbox id="restarting" align="start">
|
||||
<image class="update-throbber"/><label>&update.restarting;</label>
|
||||
<spacer flex="1"/>
|
||||
<button label="&update.updateButton.label3;"
|
||||
accesskey="&update.updateButton.accesskey;"
|
||||
disabled="true"/>
|
||||
</hbox>
|
||||
</deck>
|
||||
</vbox>
|
||||
#endif
|
||||
|
||||
#ifdef MOZ_UPDATER
|
||||
<description>&updateApplication.description;</description>
|
||||
<radiogroup id="updateRadioGroup">
|
||||
<radio id="autoDesktop"
|
||||
value="auto"
|
||||
label="&updateAuto3.label;"
|
||||
accesskey="&updateAuto3.accesskey;"/>
|
||||
<radio value="checkOnly"
|
||||
label="&updateCheckChoose2.label;"
|
||||
accesskey="&updateCheckChoose2.accesskey;"/>
|
||||
<radio value="manual"
|
||||
label="&updateManual2.label;"
|
||||
accesskey="&updateManual2.accesskey;"/>
|
||||
</radiogroup>
|
||||
#ifdef MOZ_MAINTENANCE_SERVICE
|
||||
<checkbox id="useService"
|
||||
label="&useService.label;"
|
||||
accesskey="&useService.accesskey;"
|
||||
preference="app.update.service.enabled"/>
|
||||
#endif
|
||||
#endif
|
||||
<checkbox id="enableSearchUpdate"
|
||||
label="&enableSearchUpdate2.label;"
|
||||
accesskey="&enableSearchUpdate2.accesskey;"
|
||||
preference="browser.search.update"/>
|
||||
</groupbox>
|
||||
|
||||
<hbox id="performanceCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneGeneral">
|
||||
<label class="header-name" flex="1">&performance.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Performance -->
|
||||
<groupbox id="performanceGroup" data-category="paneGeneral" hidden="true">
|
||||
<caption><label>&performance.label;</label></caption>
|
||||
<caption class="search-header" hidden="true"><label>&performance.label;</label></caption>
|
||||
|
||||
<hbox align="center">
|
||||
<checkbox id="useRecommendedPerformanceSettings"
|
||||
label="&useRecommendedPerformanceSettings.label;"
|
||||
accesskey="&useRecommendedPerformanceSettings.accesskey;"
|
||||
label="&useRecommendedPerformanceSettings2.label;"
|
||||
accesskey="&useRecommendedPerformanceSettings2.accesskey;"
|
||||
preference="browser.preferences.defaultPerformanceSettings.enabled"/>
|
||||
<label id="performanceSettingsLearnMore" class="learnMore text-link">&performanceSettingsLearnMore.label;</label>
|
||||
</hbox>
|
||||
<description class="indent">&useRecommendedPerformanceSettings.description;</description>
|
||||
<description class="indent">&useRecommendedPerformanceSettings2.description;</description>
|
||||
|
||||
<vbox id="performanceSettings" class="indent" hidden="true">
|
||||
<checkbox id="allowHWAccel"
|
||||
@ -364,3 +935,83 @@
|
||||
<description id="contentProcessCountDisabledDescription">&limitContentProcessOption.disabledDescription;<label class="text-link" href="https://wiki.mozilla.org/Electrolysis">&limitContentProcessOption.disabledDescriptionLink;</label></description>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<hbox id="browsingCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneGeneral">
|
||||
<label class="header-name" flex="1">&browsing.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Browsing -->
|
||||
<groupbox id="browsingGroup" data-category="paneGeneral" hidden="true">
|
||||
<caption class="search-header" hidden="true"><label>&browsing.label;</label></caption>
|
||||
|
||||
<checkbox id="useAutoScroll"
|
||||
label="&useAutoScroll.label;"
|
||||
accesskey="&useAutoScroll.accesskey;"
|
||||
preference="general.autoScroll"/>
|
||||
<checkbox id="useSmoothScrolling"
|
||||
label="&useSmoothScrolling.label;"
|
||||
accesskey="&useSmoothScrolling.accesskey;"
|
||||
preference="general.smoothScroll"/>
|
||||
|
||||
#ifdef XP_WIN
|
||||
<checkbox id="useOnScreenKeyboard"
|
||||
hidden="true"
|
||||
label="&useOnScreenKeyboard.label;"
|
||||
accesskey="&useOnScreenKeyboard.accesskey;"
|
||||
preference="ui.osk.enabled"/>
|
||||
#endif
|
||||
<checkbox id="useCursorNavigation"
|
||||
label="&useCursorNavigation.label;"
|
||||
accesskey="&useCursorNavigation.accesskey;"
|
||||
preference="accessibility.browsewithcaret"/>
|
||||
<checkbox id="searchStartTyping"
|
||||
label="&searchOnStartTyping.label;"
|
||||
accesskey="&searchOnStartTyping.accesskey;"
|
||||
preference="accessibility.typeaheadfind"/>
|
||||
</groupbox>
|
||||
|
||||
<hbox id="networkProxyCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneGeneral">
|
||||
<label class="header-name" flex="1">&networkProxy.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Network Proxy-->
|
||||
<groupbox id="connectionGroup" data-category="paneGeneral" hidden="true">
|
||||
<caption class="search-header" hidden="true"><label>&networkProxy.label;</label></caption>
|
||||
|
||||
<hbox align="center">
|
||||
<description flex="1" control="connectionSettings">&connectionDesc.label;</description>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="connectionSettings"
|
||||
class="accessory-button"
|
||||
icon="network"
|
||||
label="&connectionSettings.label;"
|
||||
accesskey="&connectionSettings.accesskey;"
|
||||
searchkeywords="&connectionsDialog.title;
|
||||
&noProxyTypeRadio.label;
|
||||
&WPADTypeRadio.label;
|
||||
&systemTypeRadio.label;
|
||||
&manualTypeRadio2.label;
|
||||
&http2.label;
|
||||
&ssl2.label;
|
||||
&ftp2.label;
|
||||
&port2.label;
|
||||
&socks2.label;
|
||||
&socks4.label;
|
||||
&socks5.label;
|
||||
&noproxy2.label;
|
||||
&noproxyExplain.label;
|
||||
&shareproxy.label;
|
||||
&autoTypeRadio2.label;
|
||||
&reload.label;
|
||||
&autologinproxy.label;
|
||||
&socksRemoteDNS.label2;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
@ -4,15 +4,12 @@
|
||||
|
||||
// Import globals from the files imported by the .xul files.
|
||||
/* import-globals-from subdialogs.js */
|
||||
/* import-globals-from advanced.js */
|
||||
/* import-globals-from main.js */
|
||||
/* import-globals-from search.js */
|
||||
/* import-globals-from containers.js */
|
||||
/* import-globals-from content.js */
|
||||
/* import-globals-from privacy.js */
|
||||
/* import-globals-from applications.js */
|
||||
/* import-globals-from security.js */
|
||||
/* import-globals-from sync.js */
|
||||
/* import-globals-from findInPage.js */
|
||||
/* import-globals-from ../../../base/content/utilityOverlay.js */
|
||||
|
||||
"use strict";
|
||||
@ -60,11 +57,9 @@ function init_all() {
|
||||
register_module("paneSearch", gSearchPane);
|
||||
register_module("panePrivacy", gPrivacyPane);
|
||||
register_module("paneContainers", gContainersPane);
|
||||
register_module("paneAdvanced", gAdvancedPane);
|
||||
register_module("paneApplications", gApplicationsPane);
|
||||
register_module("paneContent", gContentPane);
|
||||
register_module("paneSync", gSyncPane);
|
||||
register_module("paneSecurity", gSecurityPane);
|
||||
register_module("paneSearchResults", gSearchResultsPane);
|
||||
gSearchResultsPane.init();
|
||||
|
||||
let categories = document.getElementById("categories");
|
||||
categories.addEventListener("select", event => gotoPref(event.target.value));
|
||||
@ -83,23 +78,14 @@ function init_all() {
|
||||
|
||||
init_dynamic_padding();
|
||||
|
||||
var initFinished = new CustomEvent("Initialized", {
|
||||
let helpButton = document.querySelector(".help-button");
|
||||
let helpUrl = Services.urlFormatter.formatURLPref("app.support.baseURL") + "preferences";
|
||||
helpButton.setAttribute("href", helpUrl);
|
||||
|
||||
document.dispatchEvent(new CustomEvent("Initialized", {
|
||||
"bubbles": true,
|
||||
"cancelable": true
|
||||
});
|
||||
document.dispatchEvent(initFinished);
|
||||
|
||||
categories = categories.querySelectorAll("richlistitem.category");
|
||||
for (let category of categories) {
|
||||
let name = internalPrefCategoryNameToFriendlyName(category.value);
|
||||
let helpSelector = `#header-${name} > .help-button`;
|
||||
let helpButton = document.querySelector(helpSelector);
|
||||
helpButton.setAttribute("href", getHelpLinkURL(category.getAttribute("helpTopic")));
|
||||
}
|
||||
|
||||
// Wait until initialization of all preferences are complete before
|
||||
// notifying observers that the UI is now ready.
|
||||
Services.obs.notifyObservers(window, "advanced-pane-loaded");
|
||||
}));
|
||||
}
|
||||
|
||||
// Make the space above the categories list shrink on low window heights
|
||||
@ -107,11 +93,25 @@ function init_dynamic_padding() {
|
||||
let categories = document.getElementById("categories");
|
||||
let catPadding = Number.parseInt(getComputedStyle(categories)
|
||||
.getPropertyValue("padding-top"));
|
||||
let fullHeight = categories.lastElementChild.getBoundingClientRect().bottom;
|
||||
let helpButton = document.querySelector(".help-button");
|
||||
let helpButtonCS = getComputedStyle(helpButton);
|
||||
let helpHeight = Number.parseInt(helpButtonCS.height);
|
||||
let helpBottom = Number.parseInt(helpButtonCS.bottom);
|
||||
// Reduce the padding to account for less space, but due
|
||||
// to bug 1357841, the status panel will overlap the link.
|
||||
const reducedHelpButtonBottomFactor = .75;
|
||||
let reducedHelpButtonBottom = helpBottom * reducedHelpButtonBottomFactor;
|
||||
let fullHelpHeight = helpHeight + reducedHelpButtonBottom;
|
||||
let fullHeight = categories.lastElementChild.getBoundingClientRect().bottom +
|
||||
fullHelpHeight;
|
||||
let mediaRule = `
|
||||
@media (max-height: ${fullHeight}px) {
|
||||
#categories {
|
||||
padding-top: calc(100vh - ${fullHeight - catPadding}px);
|
||||
padding-bottom: ${fullHelpHeight}px;
|
||||
}
|
||||
.help-button {
|
||||
bottom: ${reducedHelpButtonBottom / 2}px;
|
||||
}
|
||||
}
|
||||
`;
|
||||
@ -122,30 +122,15 @@ function init_dynamic_padding() {
|
||||
}
|
||||
|
||||
function telemetryBucketForCategory(category) {
|
||||
category = category.toLowerCase();
|
||||
switch (category) {
|
||||
case "containers":
|
||||
case "general":
|
||||
case "search":
|
||||
case "content":
|
||||
case "applications":
|
||||
case "privacy":
|
||||
case "security":
|
||||
case "search":
|
||||
case "sync":
|
||||
case "searchresults":
|
||||
return category;
|
||||
case "advanced":
|
||||
let advancedPaneTabs = document.getElementById("advancedPrefs");
|
||||
switch (advancedPaneTabs.selectedTab.id) {
|
||||
case "generalTab":
|
||||
return "advancedGeneral";
|
||||
case "dataChoicesTab":
|
||||
return "advancedDataChoices";
|
||||
case "networkTab":
|
||||
return "advancedNetwork";
|
||||
case "updateTab":
|
||||
return "advancedUpdates";
|
||||
case "encryptionTab":
|
||||
return "advancedCerts";
|
||||
}
|
||||
// fall-through for unknown.
|
||||
default:
|
||||
return "unknown";
|
||||
}
|
||||
@ -157,19 +142,44 @@ function onHashChange() {
|
||||
|
||||
function gotoPref(aCategory) {
|
||||
let categories = document.getElementById("categories");
|
||||
const kDefaultCategoryInternalName = categories.firstElementChild.value;
|
||||
const kDefaultCategoryInternalName = "paneGeneral";
|
||||
const kDefaultCategory = "general";
|
||||
let hash = document.location.hash;
|
||||
|
||||
let category = aCategory || hash.substr(1) || kDefaultCategoryInternalName;
|
||||
let breakIndex = category.indexOf("-");
|
||||
// Subcategories allow for selecting smaller sections of the preferences
|
||||
// until proper search support is enabled (bug 1353954).
|
||||
let subcategory = breakIndex != -1 && category.substring(breakIndex + 1);
|
||||
if (subcategory) {
|
||||
category = category.substring(0, breakIndex);
|
||||
}
|
||||
category = friendlyPrefCategoryNameToInternalName(category);
|
||||
if (category != "paneSearchResults") {
|
||||
gSearchResultsPane.searchInput.value = "";
|
||||
gSearchResultsPane.getFindSelection(window).removeAllRanges();
|
||||
gSearchResultsPane.removeAllSearchTooltips();
|
||||
gSearchResultsPane.removeAllSearchMenuitemIndicators();
|
||||
} else if (!gSearchResultsPane.searchInput.value) {
|
||||
// Something tried to send us to the search results pane without
|
||||
// a query string. Default to the General pane instead.
|
||||
category = kDefaultCategoryInternalName;
|
||||
document.location.hash = kDefaultCategory;
|
||||
gSearchResultsPane.query = null;
|
||||
}
|
||||
|
||||
// Updating the hash (below) or changing the selected category
|
||||
// will re-enter gotoPref.
|
||||
if (gLastHash == category)
|
||||
if (gLastHash == category && !subcategory)
|
||||
return;
|
||||
let item = categories.querySelector(".category[value=" + category + "]");
|
||||
if (!item) {
|
||||
category = kDefaultCategoryInternalName;
|
||||
|
||||
let item;
|
||||
if (category != "paneSearchResults") {
|
||||
item = categories.querySelector(".category[value=" + category + "]");
|
||||
if (!item) {
|
||||
category = kDefaultCategoryInternalName;
|
||||
item = categories.querySelector(".category[value=" + category + "]");
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
@ -180,29 +190,53 @@ function gotoPref(aCategory) {
|
||||
}
|
||||
|
||||
let friendlyName = internalPrefCategoryNameToFriendlyName(category);
|
||||
if (gLastHash || category != kDefaultCategoryInternalName) {
|
||||
if (gLastHash || category != kDefaultCategoryInternalName || subcategory) {
|
||||
document.location.hash = friendlyName;
|
||||
}
|
||||
// Need to set the gLastHash before setting categories.selectedItem since
|
||||
// the categories 'select' event will re-enter the gotoPref codepath.
|
||||
gLastHash = category;
|
||||
categories.selectedItem = item;
|
||||
if (item) {
|
||||
categories.selectedItem = item;
|
||||
} else {
|
||||
categories.clearSelection();
|
||||
}
|
||||
window.history.replaceState(category, document.title);
|
||||
search(category, "data-category");
|
||||
search(category, "data-category", subcategory, "data-subcategory");
|
||||
|
||||
let mainContent = document.querySelector(".main-content");
|
||||
mainContent.scrollTop = 0;
|
||||
|
||||
Services.telemetry
|
||||
.getHistogramById("FX_PREFERENCES_CATEGORY_OPENED")
|
||||
.getHistogramById("FX_PREFERENCES_CATEGORY_OPENED_V2")
|
||||
.add(telemetryBucketForCategory(friendlyName));
|
||||
}
|
||||
|
||||
function search(aQuery, aAttribute) {
|
||||
function search(aQuery, aAttribute, aSubquery, aSubAttribute) {
|
||||
let mainPrefPane = document.getElementById("mainPrefPane");
|
||||
let elements = mainPrefPane.children;
|
||||
for (let element of elements) {
|
||||
let attributeValue = element.getAttribute(aAttribute);
|
||||
element.hidden = (attributeValue != aQuery);
|
||||
// If the "data-hidden-from-search" is "true", the
|
||||
// element will not get considered during search. This
|
||||
// should only be used when an element is still under
|
||||
// development and should not be shown for any reason.
|
||||
if (element.getAttribute("data-hidden-from-search") != "true" ||
|
||||
element.getAttribute("data-subpanel") == "true") {
|
||||
let attributeValue = element.getAttribute(aAttribute);
|
||||
if (attributeValue == aQuery) {
|
||||
if (!element.classList.contains("header") &&
|
||||
element.localName !== "preferences" &&
|
||||
aSubquery && aSubAttribute) {
|
||||
let subAttributeValue = element.getAttribute(aSubAttribute);
|
||||
element.hidden = subAttributeValue != aSubquery;
|
||||
} else {
|
||||
element.hidden = false;
|
||||
}
|
||||
} else {
|
||||
element.hidden = true;
|
||||
}
|
||||
}
|
||||
element.classList.remove("visually-hidden");
|
||||
}
|
||||
|
||||
let keysets = mainPrefPane.getElementsByTagName("keyset");
|
||||
@ -311,3 +345,14 @@ function confirmRestartPrompt(aRestartToEnable, aDefaultButtonIndex,
|
||||
}
|
||||
return buttonIndex;
|
||||
}
|
||||
|
||||
// This function is used to append search keywords found
|
||||
// in the related subdialog to the button that will activate the subdialog.
|
||||
function appendSearchKeywords(aId, keywords) {
|
||||
let element = document.getElementById(aId);
|
||||
let searchKeywords = element.getAttribute("searchkeywords");
|
||||
if (searchKeywords) {
|
||||
keywords.push(searchKeywords);
|
||||
}
|
||||
element.setAttribute("searchkeywords", keywords.join(" "));
|
||||
}
|
||||
|
@ -14,32 +14,59 @@
|
||||
<?xml-stylesheet href="chrome://browser/skin/preferences/applications.css"?>
|
||||
<?xml-stylesheet href="chrome://browser/skin/preferences/in-content/search.css"?>
|
||||
<?xml-stylesheet href="chrome://browser/skin/preferences/in-content/containers.css"?>
|
||||
<?xml-stylesheet href="chrome://browser/skin/preferences/in-content/privacy.css"?>
|
||||
|
||||
<!DOCTYPE page [
|
||||
<!ENTITY % brandDTD SYSTEM "chrome://branding/locale/brand.dtd">
|
||||
<!ENTITY % globalPreferencesDTD SYSTEM "chrome://global/locale/preferences.dtd">
|
||||
<!ENTITY % preferencesDTD SYSTEM
|
||||
"chrome://browser/locale/preferences-old/preferences.dtd">
|
||||
<!ENTITY % privacyDTD SYSTEM "chrome://browser/locale/preferences-old/privacy.dtd">
|
||||
<!ENTITY % tabsDTD SYSTEM "chrome://browser/locale/preferences-old/tabs.dtd">
|
||||
<!ENTITY % searchDTD SYSTEM "chrome://browser/locale/preferences-old/search.dtd">
|
||||
"chrome://browser/locale/preferences/preferences.dtd">
|
||||
<!ENTITY % selectBookmarkDTD SYSTEM
|
||||
"chrome://browser/locale/preferences/selectBookmark.dtd">
|
||||
<!ENTITY % languagesDTD SYSTEM "chrome://browser/locale/preferences/languages.dtd">
|
||||
<!ENTITY % fontDTD SYSTEM "chrome://browser/locale/preferences/fonts.dtd">
|
||||
<!ENTITY % colorsDTD SYSTEM "chrome://browser/locale/preferences/colors.dtd">
|
||||
<!ENTITY % permissionsDTD SYSTEM "chrome://browser/locale/preferences/permissions.dtd">
|
||||
<!ENTITY % passwordManagerDTD SYSTEM "chrome://passwordmgr/locale/passwordManager.dtd">
|
||||
<!ENTITY % historyDTD SYSTEM "chrome://mozapps/locale/update/history.dtd">
|
||||
<!ENTITY % certManagerDTD SYSTEM "chrome://pippki/locale/certManager.dtd">
|
||||
<!ENTITY % deviceManangerDTD SYSTEM "chrome://pippki/locale/deviceManager.dtd">
|
||||
<!ENTITY % connectionDTD SYSTEM "chrome://browser/locale/preferences/connection.dtd">
|
||||
<!ENTITY % siteDataSettingsDTD SYSTEM
|
||||
"chrome://browser/locale/preferences/siteDataSettings.dtd" >
|
||||
<!ENTITY % privacyDTD SYSTEM "chrome://browser/locale/preferences/privacy.dtd">
|
||||
<!ENTITY % tabsDTD SYSTEM "chrome://browser/locale/preferences/tabs.dtd">
|
||||
<!ENTITY % searchDTD SYSTEM "chrome://browser/locale/preferences/search.dtd">
|
||||
<!ENTITY % syncBrandDTD SYSTEM "chrome://browser/locale/syncBrand.dtd">
|
||||
<!ENTITY % syncDTD SYSTEM "chrome://browser/locale/preferences-old/sync.dtd">
|
||||
<!ENTITY % syncDTD SYSTEM "chrome://browser/locale/preferences/sync.dtd">
|
||||
<!ENTITY % securityDTD SYSTEM
|
||||
"chrome://browser/locale/preferences-old/security.dtd">
|
||||
"chrome://browser/locale/preferences/security.dtd">
|
||||
<!ENTITY % containersDTD SYSTEM
|
||||
"chrome://browser/locale/preferences-old/containers.dtd">
|
||||
"chrome://browser/locale/preferences/containers.dtd">
|
||||
<!ENTITY % sanitizeDTD SYSTEM "chrome://browser/locale/sanitize.dtd">
|
||||
<!ENTITY % mainDTD SYSTEM "chrome://browser/locale/preferences-old/main.dtd">
|
||||
<!ENTITY % mainDTD SYSTEM "chrome://browser/locale/preferences/main.dtd">
|
||||
<!ENTITY % aboutHomeDTD SYSTEM "chrome://browser/locale/aboutHome.dtd">
|
||||
<!ENTITY % contentDTD SYSTEM "chrome://browser/locale/preferences-old/content.dtd">
|
||||
<!ENTITY % contentDTD SYSTEM "chrome://browser/locale/preferences/content.dtd">
|
||||
<!ENTITY % applicationsDTD SYSTEM
|
||||
"chrome://browser/locale/preferences-old/applications.dtd">
|
||||
"chrome://browser/locale/preferences/applications.dtd">
|
||||
<!ENTITY % advancedDTD SYSTEM
|
||||
"chrome://browser/locale/preferences-old/advanced.dtd">
|
||||
"chrome://browser/locale/preferences/advanced.dtd">
|
||||
<!ENTITY % aboutDialogDTD SYSTEM "chrome://browser/locale/aboutDialog.dtd" >
|
||||
%aboutDialogDTD;
|
||||
%brandDTD;
|
||||
%globalPreferencesDTD;
|
||||
%preferencesDTD;
|
||||
%selectBookmarkDTD;
|
||||
%languagesDTD;
|
||||
%fontDTD;
|
||||
%colorsDTD;
|
||||
%permissionsDTD;
|
||||
%passwordManagerDTD;
|
||||
%historyDTD;
|
||||
%certManagerDTD;
|
||||
%deviceManangerDTD;
|
||||
%connectionDTD;
|
||||
%siteDataSettingsDTD;
|
||||
%privacyDTD;
|
||||
%tabsDTD;
|
||||
%searchDTD;
|
||||
@ -75,12 +102,17 @@
|
||||
src="chrome://browser/content/utilityOverlay.js"/>
|
||||
<script type="application/javascript"
|
||||
src="chrome://browser/content/preferences/in-content/preferences.js"/>
|
||||
<script src="chrome://browser/content/preferences/in-content/findInPage.js"/>
|
||||
<script src="chrome://browser/content/preferences/in-content/subdialogs.js"/>
|
||||
|
||||
<stringbundle id="bundleBrand"
|
||||
src="chrome://branding/locale/brand.properties"/>
|
||||
<stringbundle id="bundlePreferences"
|
||||
src="chrome://browser/locale/preferences-old/preferences.properties"/>
|
||||
src="chrome://browser/locale/preferences/preferences.properties"/>
|
||||
<stringbundle id="pkiBundle"
|
||||
src="chrome://pippki/locale/pippki.properties"/>
|
||||
<stringbundle id="browserBundle"
|
||||
src="chrome://browser/locale/browser.properties"/>
|
||||
|
||||
<stringbundleset id="appManagerBundleset">
|
||||
<stringbundle id="appManagerBundle"
|
||||
@ -112,94 +144,54 @@
|
||||
<label class="category-name" flex="1">&paneSearch.title;</label>
|
||||
</richlistitem>
|
||||
|
||||
<richlistitem id="category-content"
|
||||
class="category"
|
||||
value="paneContent"
|
||||
helpTopic="prefs-content"
|
||||
tooltiptext="&paneContent.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&paneContent.title;</label>
|
||||
</richlistitem>
|
||||
|
||||
<richlistitem id="category-application"
|
||||
class="category"
|
||||
value="paneApplications"
|
||||
helpTopic="prefs-applications"
|
||||
tooltiptext="&paneApplications.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&paneApplications.title;</label>
|
||||
</richlistitem>
|
||||
|
||||
<richlistitem id="category-privacy"
|
||||
class="category"
|
||||
value="panePrivacy"
|
||||
helpTopic="prefs-privacy"
|
||||
tooltiptext="&panePrivacy.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&panePrivacy.title;</label>
|
||||
</richlistitem>
|
||||
|
||||
<richlistitem id="category-containers"
|
||||
class="category"
|
||||
value="paneContainers"
|
||||
helpTopic="prefs-containers"
|
||||
hidden="true"/>
|
||||
|
||||
<richlistitem id="category-security"
|
||||
<richlistitem id="category-privacy"
|
||||
class="category"
|
||||
value="paneSecurity"
|
||||
helpTopic="prefs-security"
|
||||
tooltiptext="&paneSecurity.title;"
|
||||
value="panePrivacy"
|
||||
helpTopic="prefs-privacy"
|
||||
tooltiptext="&panePrivacySecurity.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&paneSecurity.title;</label>
|
||||
<label class="category-name" flex="1">&panePrivacySecurity.title;</label>
|
||||
</richlistitem>
|
||||
|
||||
<richlistitem id="category-sync"
|
||||
class="category"
|
||||
value="paneSync"
|
||||
helpTopic="prefs-weave"
|
||||
tooltiptext="&paneSync.title;"
|
||||
tooltiptext="&paneSync1.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&paneSync.title;</label>
|
||||
</richlistitem>
|
||||
|
||||
<richlistitem id="category-advanced"
|
||||
class="category"
|
||||
value="paneAdvanced"
|
||||
helpTopic="prefs-advanced-general"
|
||||
tooltiptext="&paneAdvanced.title;"
|
||||
align="center">
|
||||
<image class="category-icon"/>
|
||||
<label class="category-name" flex="1">&paneAdvanced.title;</label>
|
||||
<label class="category-name" flex="1">&paneSync1.title;</label>
|
||||
</richlistitem>
|
||||
</richlistbox>
|
||||
|
||||
<keyset>
|
||||
<!-- Disable the findbar because it doesn't work properly.
|
||||
Remove this keyset once bug 1094240 ("disablefastfind" attribute
|
||||
broken in e10s mode) is fixed. -->
|
||||
<key key="&focusSearch1.key;" modifiers="accel" id="focusSearch1" oncommand=";"/>
|
||||
<key key="&focusSearch1.key;" modifiers="accel" id="focusSearch1" oncommand="gSearchResultsPane.searchInput.focus();"/>
|
||||
</keyset>
|
||||
|
||||
<vbox class="main-content" flex="1">
|
||||
<prefpane id="mainPrefPane">
|
||||
<html:a class="help-button" target="_blank" aria-label="&helpButton2.label;">&helpButton2.label;</html:a>
|
||||
|
||||
<vbox class="main-content" flex="1" align="start">
|
||||
<vbox class="pane-container">
|
||||
<hbox class="search-container" pack="end">
|
||||
<textbox type="search" id="searchInput" hidden="true" clickSelectsAll="true"/>
|
||||
</hbox>
|
||||
<prefpane id="mainPrefPane">
|
||||
#include searchResults.xul
|
||||
#include main.xul
|
||||
#include search.xul
|
||||
#include privacy.xul
|
||||
#include containers.xul
|
||||
#include advanced.xul
|
||||
#include applications.xul
|
||||
#include content.xul
|
||||
#include security.xul
|
||||
#include sync.xul
|
||||
</prefpane>
|
||||
</prefpane>
|
||||
</vbox>
|
||||
</vbox>
|
||||
|
||||
</hbox>
|
||||
|
||||
<stack id="dialogStack" hidden="true"/>
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -76,71 +76,153 @@
|
||||
<preference id="browser.privatebrowsing.autostart"
|
||||
name="browser.privatebrowsing.autostart"
|
||||
type="bool"/>
|
||||
<!-- Do not track -->
|
||||
<preference id="privacy.donottrackheader.enabled"
|
||||
name="privacy.donottrackheader.enabled"
|
||||
type="bool"/>
|
||||
<!-- Popups -->
|
||||
<preference id="dom.disable_open_during_load"
|
||||
name="dom.disable_open_during_load"
|
||||
type="bool"/>
|
||||
<!-- Passwords -->
|
||||
<preference id="signon.rememberSignons" name="signon.rememberSignons" type="bool"/>
|
||||
|
||||
<!-- XXX buttons -->
|
||||
<preference id="pref.privacy.disable_button.view_passwords"
|
||||
name="pref.privacy.disable_button.view_passwords"
|
||||
type="bool"/>
|
||||
<preference id="pref.privacy.disable_button.view_passwords_exceptions"
|
||||
name="pref.privacy.disable_button.view_passwords_exceptions"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Certificates tab
|
||||
* security.default_personal_cert
|
||||
- a string:
|
||||
"Select Automatically" select a certificate automatically when a site
|
||||
requests one
|
||||
"Ask Every Time" present a dialog to the user so he can select
|
||||
the certificate to use on a site which
|
||||
requests one -->
|
||||
<preference id="security.default_personal_cert"
|
||||
name="security.default_personal_cert"
|
||||
type="string"/>
|
||||
|
||||
<preference id="security.disable_button.openCertManager"
|
||||
name="security.disable_button.openCertManager"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="security.disable_button.openDeviceManager"
|
||||
name="security.disable_button.openDeviceManager"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="security.OCSP.enabled"
|
||||
name="security.OCSP.enabled"
|
||||
type="int"/>
|
||||
|
||||
<!-- Add-ons, malware, phishing -->
|
||||
<preference id="xpinstall.whitelist.required"
|
||||
name="xpinstall.whitelist.required"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.safebrowsing.malware.enabled"
|
||||
name="browser.safebrowsing.malware.enabled"
|
||||
type="bool"/>
|
||||
<preference id="browser.safebrowsing.phishing.enabled"
|
||||
name="browser.safebrowsing.phishing.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.safebrowsing.downloads.enabled"
|
||||
name="browser.safebrowsing.downloads.enabled"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="urlclassifier.malwareTable"
|
||||
name="urlclassifier.malwareTable"
|
||||
type="string"/>
|
||||
|
||||
<preference id="browser.safebrowsing.downloads.remote.block_potentially_unwanted"
|
||||
name="browser.safebrowsing.downloads.remote.block_potentially_unwanted"
|
||||
type="bool"/>
|
||||
<preference id="browser.safebrowsing.downloads.remote.block_uncommon"
|
||||
name="browser.safebrowsing.downloads.remote.block_uncommon"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Network tab -->
|
||||
<preference id="browser.cache.disk.capacity"
|
||||
name="browser.cache.disk.capacity"
|
||||
type="int"/>
|
||||
<preference id="browser.offline-apps.notify"
|
||||
name="browser.offline-apps.notify"
|
||||
type="bool"/>
|
||||
|
||||
<preference id="browser.cache.disk.smart_size.enabled"
|
||||
name="browser.cache.disk.smart_size.enabled"
|
||||
inverted="true"
|
||||
type="bool"/>
|
||||
|
||||
<!-- Data Choices tab -->
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
<preference id="browser.crashReports.unsubmittedCheck.autoSubmit"
|
||||
name="browser.crashReports.unsubmittedCheck.autoSubmit"
|
||||
type="bool"/>
|
||||
#endif
|
||||
|
||||
</preferences>
|
||||
|
||||
<hbox id="header-privacy"
|
||||
class="header"
|
||||
<stringbundle id="bundlePreferences" src="chrome://browser/locale/preferences/preferences.properties"/>
|
||||
<stringbundle id="signonBundle" src="chrome://passwordmgr/locale/passwordmgr.properties"/>
|
||||
|
||||
<hbox id="browserPrivacyCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="panePrivacy">
|
||||
<label class="header-name" flex="1">&panePrivacy.title;</label>
|
||||
<html:a class="help-button" target="_blank" aria-label="&helpButton.label;"></html:a>
|
||||
<label class="header-name" flex="1">&browserPrivacy.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Tracking -->
|
||||
<groupbox id="trackingGroup" data-category="panePrivacy" hidden="true">
|
||||
<vbox id="trackingprotectionbox" hidden="true">
|
||||
<hbox align="start">
|
||||
<vbox>
|
||||
<caption><label>&trackingProtectionHeader.label;
|
||||
<label id="trackingProtectionLearnMore" class="learnMore text-link"
|
||||
value="&trackingProtectionLearnMore.label;"/>
|
||||
</label></caption>
|
||||
<radiogroup id="trackingProtectionRadioGroup">
|
||||
<radio value="always"
|
||||
label="&trackingProtectionAlways.label;"
|
||||
accesskey="&trackingProtectionAlways.accesskey;"/>
|
||||
<radio value="private"
|
||||
label="&trackingProtectionPrivate.label;"
|
||||
accesskey="&trackingProtectionPrivate.accesskey;"/>
|
||||
<radio value="never"
|
||||
label="&trackingProtectionNever.label;"
|
||||
accesskey="&trackingProtectionNever.accesskey;"/>
|
||||
</radiogroup>
|
||||
</vbox>
|
||||
<spacer flex="1" />
|
||||
<vbox>
|
||||
<button id="trackingProtectionExceptions"
|
||||
label="&trackingProtectionExceptions.label;"
|
||||
accesskey="&trackingProtectionExceptions.accesskey;"
|
||||
preference="pref.privacy.disable_button.tracking_protection_exceptions"/>
|
||||
<button id="changeBlockList"
|
||||
label="&changeBlockList.label;"
|
||||
accesskey="&changeBlockList.accesskey;"
|
||||
preference="pref.privacy.disable_button.change_blocklist"/>
|
||||
</vbox>
|
||||
<!-- Passwords -->
|
||||
<groupbox id="passwordsGroup" orient="vertical" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&formsAndPasswords.label;</label></caption>
|
||||
|
||||
<vbox id="passwordSettings">
|
||||
<hbox id="savePasswordsBox">
|
||||
<checkbox id="savePasswords"
|
||||
label="&rememberLogins2.label;" accesskey="&rememberLogins2.accesskey;"
|
||||
preference="signon.rememberSignons"
|
||||
onsyncfrompreference="return gPrivacyPane.readSavePasswords();"
|
||||
flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="passwordExceptions"
|
||||
class="accessory-button"
|
||||
label="&passwordExceptions.label;"
|
||||
accesskey="&passwordExceptions.accesskey;"
|
||||
preference="pref.privacy.disable_button.view_passwords_exceptions"
|
||||
searchkeywords="&address2.label;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<hbox id="showPasswordBox" pack="end">
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="showPasswords"
|
||||
class="accessory-button"
|
||||
label="&savedLogins.label;" accesskey="&savedLogins.accesskey;"
|
||||
preference="pref.privacy.disable_button.view_passwords"
|
||||
searchkeywords="&savedLogins.title;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
</vbox>
|
||||
<vbox id="trackingprotectionpbmbox">
|
||||
<caption><label>&tracking.label;</label></caption>
|
||||
<hbox align="center">
|
||||
<checkbox id="trackingProtectionPBM"
|
||||
preference="privacy.trackingprotection.pbmode.enabled"
|
||||
accesskey="&trackingProtectionPBM5.accesskey;"
|
||||
label="&trackingProtectionPBM5.label;"/>
|
||||
<label id="trackingProtectionPBMLearnMore"
|
||||
class="learnMore text-link"
|
||||
value="&trackingProtectionPBMLearnMore.label;"/>
|
||||
<spacer flex="1" />
|
||||
<button id="changeBlockListPBM"
|
||||
label="&changeBlockList.label;" accesskey="&changeBlockList.accesskey;"
|
||||
preference="pref.privacy.disable_button.change_blocklist"/>
|
||||
<hbox id="masterPasswordRow">
|
||||
<checkbox id="useMasterPassword"
|
||||
label="&useMasterPassword.label;"
|
||||
accesskey="&useMasterPassword.accesskey;"
|
||||
flex="1"/>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="changeMasterPassword"
|
||||
class="accessory-button"
|
||||
label="&changeMasterPassword.label;"
|
||||
accesskey="&changeMasterPassword.accesskey;"/>
|
||||
</hbox>
|
||||
</vbox>
|
||||
<vbox>
|
||||
<description>&doNotTrack.pre.label;<label
|
||||
class="text-link" id="doNotTrackSettings"
|
||||
>&doNotTrack.settings.label;</label>&doNotTrack.post.label;</description>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- History -->
|
||||
@ -149,15 +231,40 @@
|
||||
<hbox align="center">
|
||||
<label id="historyModeLabel"
|
||||
control="historyMode"
|
||||
accesskey="&historyHeader.pre.accesskey;">&historyHeader.pre.label;
|
||||
accesskey="&historyHeader2.pre.accesskey;">&historyHeader2.pre.label;
|
||||
</label>
|
||||
<menulist id="historyMode">
|
||||
<menupopup>
|
||||
<menuitem label="&historyHeader.remember.label;" value="remember"/>
|
||||
<menuitem label="&historyHeader.dontremember.label;" value="dontremember"/>
|
||||
<menuitem label="&historyHeader.custom.label;" value="custom"/>
|
||||
</menupopup>
|
||||
</menulist>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<menulist id="historyMode">
|
||||
<menupopup>
|
||||
<menuitem label="&historyHeader.remember.label;" value="remember" searchkeywords="&rememberDescription.label;
|
||||
&rememberActions.pre.label;
|
||||
&rememberActions.clearHistory.label;
|
||||
&rememberActions.middle.label;
|
||||
&rememberActions.removeCookies.label;
|
||||
&rememberActions.post.label;"/>
|
||||
<menuitem label="&historyHeader.dontremember.label;" value="dontremember" searchkeywords="&dontrememberDescription.label;
|
||||
&dontrememberActions.pre.label;
|
||||
&dontrememberActions.clearHistory.label;
|
||||
&dontrememberActions.post.label;"/>
|
||||
<menuitem label="&historyHeader.custom.label;" value="custom" searchkeywords="&privateBrowsingPermanent2.label;
|
||||
&rememberHistory2.label;
|
||||
&rememberSearchForm.label;
|
||||
&acceptCookies2.label;
|
||||
&cookieExceptions.label;
|
||||
&acceptThirdParty2.pre.label;
|
||||
&acceptThirdParty.always.label;
|
||||
&acceptThirdParty.visited.label;
|
||||
&acceptThirdParty.never.label;
|
||||
&keepUntil2.label;
|
||||
&expire.label;
|
||||
&close.label;
|
||||
&showCookies.label;
|
||||
&clearOnClose.label;
|
||||
&clearOnCloseSettings.label;"/>
|
||||
</menupopup>
|
||||
</menulist>
|
||||
</hbox>
|
||||
<label>&historyHeader.post.label;</label>
|
||||
</hbox>
|
||||
<deck id="historyPane">
|
||||
@ -188,31 +295,28 @@
|
||||
<vbox id="historyCustomPane">
|
||||
<separator class="thin"/>
|
||||
<vbox>
|
||||
<vbox align="start">
|
||||
<checkbox id="privateBrowsingAutoStart"
|
||||
label="&privateBrowsingPermanent2.label;"
|
||||
accesskey="&privateBrowsingPermanent2.accesskey;"
|
||||
preference="browser.privatebrowsing.autostart"/>
|
||||
</vbox>
|
||||
<checkbox id="privateBrowsingAutoStart"
|
||||
label="&privateBrowsingPermanent2.label;"
|
||||
accesskey="&privateBrowsingPermanent2.accesskey;"
|
||||
preference="browser.privatebrowsing.autostart"/>
|
||||
<vbox class="indent">
|
||||
<vbox align="start">
|
||||
<checkbox id="rememberHistory"
|
||||
label="&rememberHistory2.label;"
|
||||
accesskey="&rememberHistory2.accesskey;"
|
||||
preference="places.history.enabled"/>
|
||||
<checkbox id="rememberForms"
|
||||
label="&rememberSearchForm.label;"
|
||||
accesskey="&rememberSearchForm.accesskey;"
|
||||
preference="browser.formfill.enable"/>
|
||||
</vbox>
|
||||
<checkbox id="rememberHistory"
|
||||
label="&rememberHistory2.label;"
|
||||
accesskey="&rememberHistory2.accesskey;"
|
||||
preference="places.history.enabled"/>
|
||||
<checkbox id="rememberForms"
|
||||
label="&rememberSearchForm.label;"
|
||||
accesskey="&rememberSearchForm.accesskey;"
|
||||
preference="browser.formfill.enable"/>
|
||||
<hbox id="cookiesBox">
|
||||
<checkbox id="acceptCookies" label="&acceptCookies2.label;"
|
||||
preference="network.cookie.cookieBehavior"
|
||||
accesskey="&acceptCookies2.accesskey;"
|
||||
onsyncfrompreference="return gPrivacyPane.readAcceptCookies();"
|
||||
onsynctopreference="return gPrivacyPane.writeAcceptCookies();"/>
|
||||
<spacer flex="1" />
|
||||
onsynctopreference="return gPrivacyPane.writeAcceptCookies();"
|
||||
flex="1" />
|
||||
<button id="cookieExceptions"
|
||||
class="accessory-button"
|
||||
label="&cookieExceptions.label;" accesskey="&cookieExceptions.accesskey;"
|
||||
preference="pref.privacy.disable_button.cookie_exceptions"/>
|
||||
</hbox>
|
||||
@ -220,7 +324,7 @@
|
||||
class="indent"
|
||||
align="center">
|
||||
<label id="acceptThirdPartyLabel" control="acceptThirdPartyMenu"
|
||||
accesskey="&acceptThirdParty.pre.accesskey;">&acceptThirdParty.pre.label;</label>
|
||||
accesskey="&acceptThirdParty2.pre.accesskey;">&acceptThirdParty2.pre.label;</label>
|
||||
<menulist id="acceptThirdPartyMenu" preference="network.cookie.cookieBehavior"
|
||||
onsyncfrompreference="return gPrivacyPane.readAcceptThirdPartyCookies();"
|
||||
onsynctopreference="return gPrivacyPane.writeAcceptThirdPartyCookies();">
|
||||
@ -236,7 +340,7 @@
|
||||
align="center">
|
||||
<label id="keepUntil"
|
||||
control="keepCookiesUntil"
|
||||
accesskey="&keepUntil.accesskey;">&keepUntil.label;</label>
|
||||
accesskey="&keepUntil2.accesskey;">&keepUntil2.label;</label>
|
||||
<menulist id="keepCookiesUntil"
|
||||
preference="network.cookie.lifetimePolicy">
|
||||
<menupopup>
|
||||
@ -246,6 +350,7 @@
|
||||
</menulist>
|
||||
<spacer flex="1"/>
|
||||
<button id="showCookiesButton"
|
||||
class="accessory-button"
|
||||
label="&showCookies.label;" accesskey="&showCookies.accesskey;"
|
||||
preference="pref.privacy.disable_button.view_cookies"/>
|
||||
</hbox>
|
||||
@ -254,9 +359,11 @@
|
||||
<checkbox id="alwaysClear"
|
||||
preference="privacy.sanitize.sanitizeOnShutdown"
|
||||
label="&clearOnClose.label;"
|
||||
accesskey="&clearOnClose.accesskey;"/>
|
||||
<spacer flex="1"/>
|
||||
<button id="clearDataSettings" label="&clearOnCloseSettings.label;"
|
||||
accesskey="&clearOnClose.accesskey;"
|
||||
flex="1" />
|
||||
<button id="clearDataSettings"
|
||||
class="accessory-button"
|
||||
label="&clearOnCloseSettings.label;"
|
||||
accesskey="&clearOnCloseSettings.accesskey;"/>
|
||||
</hbox>
|
||||
</vbox>
|
||||
@ -265,14 +372,14 @@
|
||||
</deck>
|
||||
</groupbox>
|
||||
|
||||
<!-- Location Bar -->
|
||||
<!-- Address Bar -->
|
||||
<groupbox id="locationBarGroup"
|
||||
data-category="panePrivacy"
|
||||
hidden="true">
|
||||
<caption><label>&locationBar.label;</label></caption>
|
||||
<label id="locationBarSuggestionLabel">&locbar.suggest.label;</label>
|
||||
<checkbox id="historySuggestion" label="&locbar.history.label;"
|
||||
accesskey="&locbar.history.accesskey;"
|
||||
<caption><label>&addressBar.label;</label></caption>
|
||||
<label id="locationBarSuggestionLabel">&addressBar.suggest.label;</label>
|
||||
<checkbox id="historySuggestion" label="&locbar.history2.label;"
|
||||
accesskey="&locbar.history2.accesskey;"
|
||||
preference="browser.urlbar.suggest.history"/>
|
||||
<checkbox id="bookmarkSuggestion" label="&locbar.bookmarks.label;"
|
||||
accesskey="&locbar.bookmarks.accesskey;"
|
||||
@ -281,26 +388,475 @@
|
||||
accesskey="&locbar.openpage.accesskey;"
|
||||
preference="browser.urlbar.suggest.openpage"/>
|
||||
<label class="text-link" onclick="gotoPref('search')">
|
||||
&suggestionSettings.label;
|
||||
&suggestionSettings2.label;
|
||||
</label>
|
||||
</groupbox>
|
||||
|
||||
<!-- Containers -->
|
||||
<groupbox id="browserContainersGroup" data-category="panePrivacy" hidden="true">
|
||||
<vbox id="browserContainersbox" hidden="true">
|
||||
<caption><label>&browserContainersHeader.label;</label></caption>
|
||||
<hbox align="center">
|
||||
<checkbox id="browserContainersCheckbox"
|
||||
label="&browserContainersEnabled.label;"
|
||||
accesskey="&browserContainersEnabled.accesskey;"
|
||||
preference="privacy.userContext.enabled"
|
||||
onsyncfrompreference="return gPrivacyPane.readBrowserContainersCheckbox();"/>
|
||||
<label id="browserContainersLearnMore" class="learnMore text-link"
|
||||
value="&browserContainersLearnMore.label;"/>
|
||||
<!-- Cache -->
|
||||
<groupbox id="cacheGroup" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&httpCache.label;</label></caption>
|
||||
|
||||
<hbox align="center">
|
||||
<label id="actualDiskCacheSize" flex="1"/>
|
||||
<button id="clearCacheButton"
|
||||
class="accessory-button"
|
||||
icon="clear"
|
||||
label="&clearCacheNow.label;" accesskey="&clearCacheNow.accesskey;"/>
|
||||
</hbox>
|
||||
<checkbox preference="browser.cache.disk.smart_size.enabled"
|
||||
id="allowSmartSize"
|
||||
onsyncfrompreference="return gPrivacyPane.readSmartSizeEnabled();"
|
||||
label="&overrideSmartCacheSize.label;"
|
||||
accesskey="&overrideSmartCacheSize.accesskey;"/>
|
||||
<hbox align="center" class="indent">
|
||||
<label id="useCacheBefore" control="cacheSize"
|
||||
accesskey="&limitCacheSizeBefore.accesskey;">
|
||||
&limitCacheSizeBefore.label;
|
||||
</label>
|
||||
<textbox id="cacheSize" type="number" size="4" max="1024"
|
||||
aria-labelledby="useCacheBefore cacheSize useCacheAfter"/>
|
||||
<label id="useCacheAfter" flex="1">&limitCacheSizeAfter.label;</label>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Site Data -->
|
||||
<groupbox id="siteDataGroup" hidden="true" data-category="panePrivacy" data-hidden-from-search="true">
|
||||
<caption><label>&siteData.label;</label></caption>
|
||||
|
||||
<hbox align="baseline">
|
||||
<vbox flex="1">
|
||||
<description flex="1">
|
||||
<label id="totalSiteDataSize"></label>
|
||||
<label id="siteDataLearnMoreLink" class="learnMore text-link">&siteDataLearnMoreLink.label;</label>
|
||||
</description>
|
||||
</vbox>
|
||||
<vbox align="end">
|
||||
<button id="siteDataSettings"
|
||||
class="accessory-button"
|
||||
label="&siteDataSettings.label;"
|
||||
accesskey="&siteDataSettings.accesskey;"
|
||||
searchkeywords="&window.title;
|
||||
&hostCol.label;
|
||||
&statusCol.label;
|
||||
&usageCol.label;"/>
|
||||
<button id="clearSiteDataButton"
|
||||
class="accessory-button"
|
||||
icon="clear"
|
||||
label="&clearSiteData.label;" accesskey="&clearSiteData.accesskey;"/>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Tracking -->
|
||||
<groupbox id="trackingGroup" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&trackingProtectionHeader2.label;</label></caption>
|
||||
<vbox>
|
||||
<hbox align="start">
|
||||
<vbox flex="1">
|
||||
<description>
|
||||
&trackingProtection2.description;
|
||||
</description>
|
||||
</vbox>
|
||||
<spacer flex="1"/>
|
||||
<button id="browserContainersSettings"
|
||||
label="&browserContainersSettings.label;"
|
||||
accesskey="&browserContainersSettings.accesskey;"/>
|
||||
</hbox>
|
||||
<hbox>
|
||||
<vbox id="trackingProtectionBox" flex="1" hidden="true">
|
||||
<description id="trackingProtectionDesc"
|
||||
control="trackingProtectionRadioGroup">
|
||||
&trackingProtection2.radioGroupLabel;
|
||||
<label id="trackingProtectionLearnMore" class="learnMore text-link">&trackingProtectionLearnMore.label;</label>
|
||||
</description>
|
||||
<radiogroup id="trackingProtectionRadioGroup" aria-labelledby="trackingProtectionDesc">
|
||||
<radio value="always"
|
||||
label="&trackingProtectionAlways.label;"
|
||||
accesskey="&trackingProtectionAlways.accesskey;"/>
|
||||
<radio value="private"
|
||||
label="&trackingProtectionPrivate.label;"
|
||||
accesskey="&trackingProtectionPrivate.accesskey;"/>
|
||||
<radio value="never"
|
||||
label="&trackingProtectionNever.label;"
|
||||
accesskey="&trackingProtectionNever.accesskey;"/>
|
||||
</radiogroup>
|
||||
</vbox>
|
||||
<vbox id="trackingProtectionPBMBox" flex="1">
|
||||
<hbox align="center">
|
||||
<checkbox id="trackingProtectionPBM"
|
||||
preference="privacy.trackingprotection.pbmode.enabled"
|
||||
accesskey="&trackingProtectionPBM6.accesskey;"/>
|
||||
<label flex="1">&trackingProtectionPBM6.label;<label id="trackingProtectionPBMLearnMore"
|
||||
class="learnMore text-link">&trackingProtectionPBMLearnMore.label;</label>
|
||||
</label>
|
||||
</hbox>
|
||||
</vbox>
|
||||
<vbox id="trackingProtectionAdvancedSettings">
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="trackingProtectionExceptions"
|
||||
class="accessory-button"
|
||||
flex="1"
|
||||
hidden="true"
|
||||
label="&trackingProtectionExceptions.label;"
|
||||
accesskey="&trackingProtectionExceptions.accesskey;"
|
||||
preference="pref.privacy.disable_button.tracking_protection_exceptions"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="changeBlockList"
|
||||
class="accessory-button"
|
||||
flex="1"
|
||||
label="&changeBlockList2.label;"
|
||||
accesskey="&changeBlockList2.accesskey;"
|
||||
preference="pref.privacy.disable_button.change_blocklist"
|
||||
searchkeywords="&button.cancel.label; &button.ok.label;"/>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
<vbox id="doNotTrackLearnMoreBox">
|
||||
<label>&doNotTrack.description;<label
|
||||
class="learnMore text-link" href="https://www.mozilla.org/dnt"
|
||||
>&doNotTrack.learnMore.label;</label></label>
|
||||
<radiogroup id="doNotTrackRadioGroup" aria-labelledby="doNotTrackDesc" preference="privacy.donottrackheader.enabled">
|
||||
<radio value="false" label="&doNotTrack.default.label;"/>
|
||||
<radio value="true" label="&doNotTrack.always.label;"/>
|
||||
</radiogroup>
|
||||
</vbox>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<hbox id="permissionsCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="panePrivacy">
|
||||
<label class="header-name" flex="1">&permissions.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Permissions -->
|
||||
<groupbox id="permissionsGroup" data-category="panePrivacy" hidden="true">
|
||||
<caption class="search-header" hidden="true"><label>&permissions.label;</label></caption>
|
||||
|
||||
<grid>
|
||||
<columns>
|
||||
<column flex="1"/>
|
||||
<column/>
|
||||
</columns>
|
||||
<rows>
|
||||
<row id="locationSettingsRow" align="center">
|
||||
<description flex="1">
|
||||
<image class="geo-icon permission-icon" />
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label id="locationPermissionsLabel">&locationPermissions.label;</label>
|
||||
</description>
|
||||
<hbox pack="end">
|
||||
<button id="locationSettingsButton"
|
||||
class="accessory-button"
|
||||
label="&locationSettingsButton.label;"
|
||||
accesskey="&locationSettingsButton.accesskey;"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
|
||||
<row id="cameraSettingsRow" align="center">
|
||||
<description flex="1">
|
||||
<image class="camera-icon permission-icon" />
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label id="cameraPermissionsLabel">&cameraPermissions.label;</label>
|
||||
</description>
|
||||
<hbox pack="end">
|
||||
<button id="cameraSettingsButton"
|
||||
class="accessory-button"
|
||||
label="&cameraSettingsButton.label;"
|
||||
accesskey="&cameraSettingsButton.accesskey;"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
|
||||
<row id="microphoneSettingsRow" align="center">
|
||||
<description flex="1">
|
||||
<image class="microphone-icon permission-icon" />
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label id="microphonePermissionsLabel">µphonePermissions.label;</label>
|
||||
</description>
|
||||
<hbox pack="end">
|
||||
<button id="microphoneSettingsButton"
|
||||
class="accessory-button"
|
||||
label="µphoneSettingsButton.label;"
|
||||
accesskey="µphoneSettingsButton.accesskey;"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
|
||||
<row id="notificationSettingsRow" align="center">
|
||||
<description flex="1">
|
||||
<image class="desktop-notification-icon permission-icon" />
|
||||
<separator orient="vertical" class="thin"/>
|
||||
<label id="notificationPermissionsLabel">¬ificationPermissions.label;</label>
|
||||
<label id="notificationPermissionsLearnMore"
|
||||
class="learnMore text-link">¬ificationPermissionsLearnMore.label;</label>
|
||||
</description>
|
||||
<hbox pack="end">
|
||||
<button id="notificationSettingsButton"
|
||||
class="accessory-button"
|
||||
label="¬ificationSettingsButton.label;"
|
||||
accesskey="¬ificationSettingsButton.accesskey;"
|
||||
searchkeywords="&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</row>
|
||||
</rows>
|
||||
</grid>
|
||||
|
||||
<separator flex="1"/>
|
||||
|
||||
<vbox id="notificationsDoNotDisturbBox" hidden="true">
|
||||
<checkbox id="notificationsDoNotDisturb" label="¬ificationsDoNotDisturb.label;"
|
||||
accesskey="¬ificationsDoNotDisturb.accesskey;"/>
|
||||
<label id="notificationsDoNotDisturbDetails"
|
||||
class="indent">¬ificationsDoNotDisturbDetails.value;</label>
|
||||
</vbox>
|
||||
|
||||
<hbox align="start">
|
||||
<checkbox id="popupPolicy" preference="dom.disable_open_during_load"
|
||||
label="&blockPopups.label;" accesskey="&blockPopups.accesskey;"
|
||||
onsyncfrompreference="return gPrivacyPane.updateButtons('popupPolicyButton',
|
||||
'dom.disable_open_during_load');"
|
||||
flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="popupPolicyButton"
|
||||
class="accessory-button"
|
||||
label="&popupExceptions.label;"
|
||||
accesskey="&popupExceptions.accesskey;"
|
||||
searchkeywords="&address2.label; &button.cancel.label; &button.ok.label;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
|
||||
<hbox id="addonInstallBox">
|
||||
<checkbox id="warnAddonInstall"
|
||||
label="&warnOnAddonInstall2.label;"
|
||||
accesskey="&warnOnAddonInstall2.accesskey;"
|
||||
preference="xpinstall.whitelist.required"
|
||||
onsyncfrompreference="return gPrivacyPane.readWarnAddonInstall();"
|
||||
flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="addonExceptions"
|
||||
class="accessory-button"
|
||||
label="&addonExceptions.label;"
|
||||
accesskey="&addonExceptions.accesskey;"
|
||||
searchkeywords="&address2.label;
|
||||
&allow.label;
|
||||
&removepermission2.label;
|
||||
&removeallpermissions2.label;
|
||||
&button.cancel.label;
|
||||
&button.ok.label;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
|
||||
<vbox id="a11yPermissionsBox">
|
||||
<description flex="1">
|
||||
<checkbox id="a11yPrivacyCheckbox" label="&a11yPrivacy.checkbox.label;"
|
||||
accesskey="&a11yPrivacy.checkbox.accesskey;"
|
||||
oncommand="return gPrivacyPane.updateA11yPrefs(this.checked)"/>
|
||||
<label id="a11yLearnMoreLink" class="learnMore text-link"
|
||||
value="&a11yPrivacy.learnmore.label;"></label>
|
||||
</description>
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<hbox id="dataCollectionCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="panePrivacy"
|
||||
data-subcategory="reports">
|
||||
<label class="header-name" flex="1">&dataCollection.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- Firefox Data Collection and Use -->
|
||||
#ifdef MOZ_DATA_REPORTING
|
||||
<groupbox id="dataCollectionGroup" data-category="panePrivacy" data-subcategory="reports" hidden="true">
|
||||
<caption class="search-header" hidden="true"><label>&dataCollection.label;</label></caption>
|
||||
|
||||
<vbox>
|
||||
<description>
|
||||
&dataCollectionDesc.label;<label id="dataCollectionPrivacyNotice" class="learnMore text-link">&dataCollectionPrivacyNotice.label;</label>
|
||||
</description>
|
||||
<description flex="1">
|
||||
<checkbox id="submitHealthReportBox" label="&enableHealthReport1.label;"
|
||||
accesskey="&enableHealthReport1.accesskey;"/>
|
||||
<label id="FHRLearnMore"
|
||||
class="learnMore text-link">&healthReportLearnMore.label;</label>
|
||||
</description>
|
||||
#ifndef MOZ_TELEMETRY_REPORTING
|
||||
<description id="TelemetryDisabledDesc" class="indent" control="telemetryGroup">&healthReportingDisabled.label;</description>
|
||||
#endif
|
||||
</vbox>
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
<hbox align="center">
|
||||
<checkbox id="automaticallySubmitCrashesBox"
|
||||
preference="browser.crashReports.unsubmittedCheck.autoSubmit"
|
||||
label="&alwaysSubmitCrashReports1.label;"
|
||||
accesskey="&alwaysSubmitCrashReports1.accesskey;"/>
|
||||
<label id="crashReporterLearnMore"
|
||||
class="learnMore text-link">&crashReporterLearnMore.label;</label>
|
||||
</hbox>
|
||||
#endif
|
||||
</groupbox>
|
||||
#endif
|
||||
|
||||
<hbox id="securityCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="panePrivacy">
|
||||
<label class="header-name" flex="1">&security.label;</label>
|
||||
</hbox>
|
||||
|
||||
<!-- addons, forgery (phishing) UI Security -->
|
||||
<groupbox id="addonsPhishingGroup" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&phishingProtection.label;</label></caption>
|
||||
<checkbox id="enableSafeBrowsing"
|
||||
label="&enableSafeBrowsing.label;"
|
||||
accesskey="&enableSafeBrowsing.accesskey;" />
|
||||
<vbox class="indent">
|
||||
<checkbox id="blockDownloads"
|
||||
label="&blockDownloads.label;"
|
||||
accesskey="&blockDownloads.accesskey;" />
|
||||
<checkbox id="blockUncommonUnwanted"
|
||||
label="&blockUncommonAndUnwanted.label;"
|
||||
accesskey="&blockUncommonAndUnwanted.accesskey;" />
|
||||
</vbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Certificates -->
|
||||
<groupbox id="certSelection" data-category="panePrivacy" hidden="true">
|
||||
<caption><label>&certificateTab.label;</label></caption>
|
||||
<description id="CertSelectionDesc" control="certSelection">&certPersonal2.description;</description>
|
||||
|
||||
<!--
|
||||
The values on these radio buttons may look like l10n issues, but
|
||||
they're not - this preference uses *those strings* as its values.
|
||||
I KID YOU NOT.
|
||||
-->
|
||||
<radiogroup id="certSelection"
|
||||
preftype="string"
|
||||
preference="security.default_personal_cert"
|
||||
aria-labelledby="CertSelectionDesc">
|
||||
<radio label="&selectCerts.auto;"
|
||||
accesskey="&selectCerts.auto.accesskey;"
|
||||
value="Select Automatically"/>
|
||||
<radio label="&selectCerts.ask;"
|
||||
accesskey="&selectCerts.ask.accesskey;"
|
||||
value="Ask Every Time"/>
|
||||
</radiogroup>
|
||||
<hbox align="start">
|
||||
<checkbox id="enableOCSP"
|
||||
label="&enableOCSP.label;"
|
||||
accesskey="&enableOCSP.accesskey;"
|
||||
onsyncfrompreference="return gPrivacyPane.readEnableOCSP();"
|
||||
onsynctopreference="return gPrivacyPane.writeEnableOCSP();"
|
||||
preference="security.OCSP.enabled"
|
||||
flex="1" />
|
||||
<vbox>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox pack="end">
|
||||
<button id="viewCertificatesButton"
|
||||
class="accessory-button"
|
||||
label="&viewCerts2.label;"
|
||||
accesskey="&viewCerts2.accesskey;"
|
||||
preference="security.disable_button.openCertManager"
|
||||
searchkeywords="&certmgr.tab.mine;
|
||||
&certmgr.tab.others2;
|
||||
&certmgr.tab.websites3;
|
||||
&certmgr.tab.ca;
|
||||
&certmgr.tab.orphan2;
|
||||
&certmgr.mine2;
|
||||
&certmgr.others2;
|
||||
&certmgr.websites3;
|
||||
&certmgr.cas2;
|
||||
&certmgr.orphans2;
|
||||
&certmgr.certname;
|
||||
&certmgr.tokenname;
|
||||
&certmgr.view2.label;
|
||||
&certmgr.export.label;
|
||||
&certmgr.delete2.label;"/>
|
||||
</hbox>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox pack="end">
|
||||
<button id="viewSecurityDevicesButton"
|
||||
class="accessory-button"
|
||||
label="&viewSecurityDevices2.label;"
|
||||
accesskey="&viewSecurityDevices2.accesskey;"
|
||||
preference="security.disable_button.openDeviceManager"
|
||||
searchkeywords="&devmgr.title;
|
||||
&devmgr.devlist.label;
|
||||
&devmgr.details.title;
|
||||
&devmgr.details.title2;
|
||||
&devmgr.button.login.label;
|
||||
&devmgr.button.logout.label;
|
||||
&devmgr.button.changepw.label;
|
||||
&devmgr.button.load.label;
|
||||
&devmgr.button.unload.label;"/>
|
||||
</hbox>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
||||
<!-- Offline apps -->
|
||||
<groupbox id="offlineGroup" data-category="panePrivacy" hidden="true" data-hidden-from-search="true">
|
||||
<caption><label>&offlineStorage2.label;</label></caption>
|
||||
|
||||
<hbox align="center">
|
||||
<label id="actualAppCacheSize" flex="1"/>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="clearOfflineAppCacheButton"
|
||||
class="accessory-button"
|
||||
icon="clear"
|
||||
label="&clearOfflineAppCacheNow.label;" accesskey="&clearOfflineAppCacheNow.accesskey;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<hbox align="center">
|
||||
<checkbox id="offlineNotify"
|
||||
label="&offlineStorageNotify.label;" accesskey="&offlineStorageNotify.accesskey;"
|
||||
preference="browser.offline-apps.notify"
|
||||
onsyncfrompreference="return gPrivacyPane.readOfflineNotify();"
|
||||
flex="1" />
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<button id="offlineNotifyExceptions"
|
||||
class="accessory-button"
|
||||
label="&offlineStorageNotifyExceptions.label;"
|
||||
accesskey="&offlineStorageNotifyExceptions.accesskey;"/>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<hbox>
|
||||
<vbox flex="1">
|
||||
<label id="offlineAppsListLabel">&offlineAppsList3.label;</label>
|
||||
<listbox id="offlineAppsList"
|
||||
flex="1"
|
||||
aria-labelledby="offlineAppsListLabel">
|
||||
</listbox>
|
||||
</vbox>
|
||||
<vbox pack="end">
|
||||
<button id="offlineAppsListRemove"
|
||||
class="accessory-button"
|
||||
disabled="true"
|
||||
label="&offlineAppsListRemove.label;"
|
||||
accesskey="&offlineAppsListRemove.accesskey;"/>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
@ -19,28 +19,32 @@
|
||||
|
||||
<stringbundle id="engineManagerBundle" src="chrome://browser/locale/engineManager.properties"/>
|
||||
|
||||
<hbox id="header-search"
|
||||
class="header"
|
||||
<hbox id="searchCategory"
|
||||
class="subcategory"
|
||||
hidden="true"
|
||||
data-category="paneSearch">
|
||||
<label class="header-name" flex="1">&paneSearch.title;</label>
|
||||
<html:a class="help-button" target="_blank" aria-label="&helpButton.label;"></html:a>
|
||||
</hbox>
|
||||
|
||||
<!-- Default Search Engine -->
|
||||
<groupbox id="defaultEngineGroup" align="start" data-category="paneSearch">
|
||||
<caption label="&defaultSearchEngine.label;"/>
|
||||
<label>&chooseYourDefaultSearchEngine.label;</label>
|
||||
<menulist id="defaultEngine">
|
||||
<menupopup/>
|
||||
</menulist>
|
||||
<groupbox id="defaultEngineGroup" data-category="paneSearch">
|
||||
<caption><label>&defaultSearchEngine.label;</label></caption>
|
||||
<description>&chooseYourDefaultSearchEngine2.label;</description>
|
||||
<hbox>
|
||||
<!-- Please don't remove the wrapping hbox/vbox/box for these elements. It's used to properly compute the search tooltip position. -->
|
||||
<hbox>
|
||||
<menulist id="defaultEngine">
|
||||
<menupopup/>
|
||||
</menulist>
|
||||
</hbox>
|
||||
</hbox>
|
||||
<checkbox id="suggestionsInSearchFieldsCheckbox"
|
||||
label="&provideSearchSuggestions.label;"
|
||||
accesskey="&provideSearchSuggestions.accesskey;"
|
||||
preference="browser.search.suggest.enabled"/>
|
||||
<vbox class="indent">
|
||||
<checkbox id="urlBarSuggestion" label="&showURLBarSuggestions.label;"
|
||||
accesskey="&showURLBarSuggestions.accesskey;"
|
||||
<checkbox id="urlBarSuggestion" label="&showURLBarSuggestions2.label;"
|
||||
accesskey="&showURLBarSuggestions2.accesskey;"
|
||||
preference="browser.urlbar.suggest.searches"/>
|
||||
<hbox id="urlBarSuggestionPermanentPBLabel"
|
||||
align="center" class="indent">
|
||||
@ -50,8 +54,8 @@
|
||||
</groupbox>
|
||||
|
||||
<groupbox id="oneClickSearchProvidersGroup" data-category="paneSearch">
|
||||
<caption label="&oneClickSearchEngines.label;"/>
|
||||
<label>&chooseWhichOneToDisplay.label;</label>
|
||||
<caption><label>&oneClickSearchEngines.label;</label></caption>
|
||||
<description>&chooseWhichOneToDisplay2.label;</description>
|
||||
|
||||
<tree id="engineList" flex="1" rows="8" hidecolumnpicker="true" editable="true"
|
||||
seltype="single">
|
||||
@ -77,10 +81,7 @@
|
||||
disabled="true"
|
||||
/>
|
||||
</hbox>
|
||||
|
||||
<separator class="thin"/>
|
||||
|
||||
<hbox id="addEnginesBox" pack="start">
|
||||
<label id="addEngines" class="text-link" value="&addMoreSearchEngines.label;"/>
|
||||
<label id="addEngines" class="text-link">&findMoreSearchEngines.label;</label>
|
||||
</hbox>
|
||||
</groupbox>
|
||||
|
@ -1,299 +0,0 @@
|
||||
/* 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/. */
|
||||
|
||||
/* import-globals-from preferences.js */
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "LoginHelper",
|
||||
"resource://gre/modules/LoginHelper.jsm");
|
||||
|
||||
Components.utils.import("resource://gre/modules/PrivateBrowsingUtils.jsm");
|
||||
|
||||
var gSecurityPane = {
|
||||
_pane: null,
|
||||
|
||||
/**
|
||||
* Initializes master password UI.
|
||||
*/
|
||||
init() {
|
||||
function setEventListener(aId, aEventType, aCallback) {
|
||||
document.getElementById(aId)
|
||||
.addEventListener(aEventType, aCallback.bind(gSecurityPane));
|
||||
}
|
||||
|
||||
this._pane = document.getElementById("paneSecurity");
|
||||
this._initMasterPasswordUI();
|
||||
this._initSafeBrowsing();
|
||||
|
||||
setEventListener("addonExceptions", "command",
|
||||
gSecurityPane.showAddonExceptions);
|
||||
setEventListener("passwordExceptions", "command",
|
||||
gSecurityPane.showPasswordExceptions);
|
||||
setEventListener("useMasterPassword", "command",
|
||||
gSecurityPane.updateMasterPasswordButton);
|
||||
setEventListener("changeMasterPassword", "command",
|
||||
gSecurityPane.changeMasterPassword);
|
||||
setEventListener("showPasswords", "command",
|
||||
gSecurityPane.showPasswords);
|
||||
},
|
||||
|
||||
// ADD-ONS
|
||||
|
||||
/*
|
||||
* Preferences:
|
||||
*
|
||||
* xpinstall.whitelist.required
|
||||
* - true if a site must be added to a site whitelist before extensions
|
||||
* provided by the site may be installed from it, false if the extension
|
||||
* may be directly installed after a confirmation dialog
|
||||
*/
|
||||
|
||||
/**
|
||||
* Enables/disables the add-ons Exceptions button depending on whether
|
||||
* or not add-on installation warnings are displayed.
|
||||
*/
|
||||
readWarnAddonInstall() {
|
||||
var warn = document.getElementById("xpinstall.whitelist.required");
|
||||
var exceptions = document.getElementById("addonExceptions");
|
||||
|
||||
exceptions.disabled = !warn.value;
|
||||
|
||||
// don't override the preference value
|
||||
return undefined;
|
||||
},
|
||||
|
||||
/**
|
||||
* Displays the exceptions lists for add-on installation warnings.
|
||||
*/
|
||||
showAddonExceptions() {
|
||||
var bundlePrefs = document.getElementById("bundlePreferences");
|
||||
|
||||
var params = this._addonParams;
|
||||
if (!params.windowTitle || !params.introText) {
|
||||
params.windowTitle = bundlePrefs.getString("addons_permissions_title2");
|
||||
params.introText = bundlePrefs.getString("addonspermissionstext");
|
||||
}
|
||||
|
||||
gSubDialog.open("chrome://browser/content/preferences/permissions.xul",
|
||||
null, params);
|
||||
},
|
||||
|
||||
/**
|
||||
* Parameters for the add-on install permissions dialog.
|
||||
*/
|
||||
_addonParams:
|
||||
{
|
||||
blockVisible: false,
|
||||
sessionVisible: false,
|
||||
allowVisible: true,
|
||||
prefilledHost: "",
|
||||
permissionType: "install"
|
||||
},
|
||||
|
||||
// PASSWORDS
|
||||
|
||||
/*
|
||||
* Preferences:
|
||||
*
|
||||
* signon.rememberSignons
|
||||
* - true if passwords are remembered, false otherwise
|
||||
*/
|
||||
|
||||
/**
|
||||
* Enables/disables the Exceptions button used to configure sites where
|
||||
* passwords are never saved. When browser is set to start in Private
|
||||
* Browsing mode, the "Remember passwords" UI is useless, so we disable it.
|
||||
*/
|
||||
readSavePasswords() {
|
||||
var pref = document.getElementById("signon.rememberSignons");
|
||||
var excepts = document.getElementById("passwordExceptions");
|
||||
|
||||
if (PrivateBrowsingUtils.permanentPrivateBrowsing) {
|
||||
document.getElementById("savePasswords").disabled = true;
|
||||
excepts.disabled = true;
|
||||
return false;
|
||||
}
|
||||
excepts.disabled = !pref.value;
|
||||
// don't override pref value in UI
|
||||
return undefined;
|
||||
},
|
||||
|
||||
/**
|
||||
* Displays a dialog in which the user can view and modify the list of sites
|
||||
* where passwords are never saved.
|
||||
*/
|
||||
showPasswordExceptions() {
|
||||
var bundlePrefs = document.getElementById("bundlePreferences");
|
||||
var params = {
|
||||
blockVisible: true,
|
||||
sessionVisible: false,
|
||||
allowVisible: false,
|
||||
hideStatusColumn: true,
|
||||
prefilledHost: "",
|
||||
permissionType: "login-saving",
|
||||
windowTitle: bundlePrefs.getString("savedLoginsExceptions_title"),
|
||||
introText: bundlePrefs.getString("savedLoginsExceptions_desc2")
|
||||
};
|
||||
|
||||
gSubDialog.open("chrome://browser/content/preferences/permissions.xul",
|
||||
null, params);
|
||||
},
|
||||
|
||||
/**
|
||||
* Initializes master password UI: the "use master password" checkbox, selects
|
||||
* the master password button to show, and enables/disables it as necessary.
|
||||
* The master password is controlled by various bits of NSS functionality, so
|
||||
* the UI for it can't be controlled by the normal preference bindings.
|
||||
*/
|
||||
_initMasterPasswordUI() {
|
||||
var noMP = !LoginHelper.isMasterPasswordSet();
|
||||
|
||||
var button = document.getElementById("changeMasterPassword");
|
||||
button.disabled = noMP;
|
||||
|
||||
var checkbox = document.getElementById("useMasterPassword");
|
||||
checkbox.checked = !noMP;
|
||||
},
|
||||
|
||||
_initSafeBrowsing() {
|
||||
let enableSafeBrowsing = document.getElementById("enableSafeBrowsing");
|
||||
let blockDownloads = document.getElementById("blockDownloads");
|
||||
let blockUncommonUnwanted = document.getElementById("blockUncommonUnwanted");
|
||||
|
||||
let safeBrowsingPhishingPref = document.getElementById("browser.safebrowsing.phishing.enabled");
|
||||
let safeBrowsingMalwarePref = document.getElementById("browser.safebrowsing.malware.enabled");
|
||||
|
||||
let blockDownloadsPref = document.getElementById("browser.safebrowsing.downloads.enabled");
|
||||
let malwareTable = document.getElementById("urlclassifier.malwareTable");
|
||||
|
||||
let blockUnwantedPref = document.getElementById("browser.safebrowsing.downloads.remote.block_potentially_unwanted");
|
||||
let blockUncommonPref = document.getElementById("browser.safebrowsing.downloads.remote.block_uncommon");
|
||||
|
||||
enableSafeBrowsing.addEventListener("command", function() {
|
||||
safeBrowsingPhishingPref.value = enableSafeBrowsing.checked;
|
||||
safeBrowsingMalwarePref.value = enableSafeBrowsing.checked;
|
||||
|
||||
if (enableSafeBrowsing.checked) {
|
||||
blockDownloads.removeAttribute("disabled");
|
||||
if (blockDownloads.checked) {
|
||||
blockUncommonUnwanted.removeAttribute("disabled");
|
||||
}
|
||||
} else {
|
||||
blockDownloads.setAttribute("disabled", "true");
|
||||
blockUncommonUnwanted.setAttribute("disabled", "true");
|
||||
}
|
||||
});
|
||||
|
||||
blockDownloads.addEventListener("command", function() {
|
||||
blockDownloadsPref.value = blockDownloads.checked;
|
||||
if (blockDownloads.checked) {
|
||||
blockUncommonUnwanted.removeAttribute("disabled");
|
||||
} else {
|
||||
blockUncommonUnwanted.setAttribute("disabled", "true");
|
||||
}
|
||||
});
|
||||
|
||||
blockUncommonUnwanted.addEventListener("command", function() {
|
||||
blockUnwantedPref.value = blockUncommonUnwanted.checked;
|
||||
blockUncommonPref.value = blockUncommonUnwanted.checked;
|
||||
|
||||
let malware = malwareTable.value
|
||||
.split(",")
|
||||
.filter(x => x !== "goog-unwanted-proto" &&
|
||||
x !== "goog-unwanted-shavar" &&
|
||||
x !== "test-unwanted-simple");
|
||||
|
||||
if (blockUncommonUnwanted.checked) {
|
||||
if (malware.indexOf("goog-malware-shavar") != -1) {
|
||||
malware.push("goog-unwanted-shavar");
|
||||
} else {
|
||||
malware.push("goog-unwanted-proto");
|
||||
}
|
||||
|
||||
malware.push("test-unwanted-simple");
|
||||
}
|
||||
|
||||
// sort alphabetically to keep the pref consistent
|
||||
malware.sort();
|
||||
|
||||
malwareTable.value = malware.join(",");
|
||||
});
|
||||
|
||||
// set initial values
|
||||
|
||||
enableSafeBrowsing.checked = safeBrowsingPhishingPref.value && safeBrowsingMalwarePref.value;
|
||||
if (!enableSafeBrowsing.checked) {
|
||||
blockDownloads.setAttribute("disabled", "true");
|
||||
blockUncommonUnwanted.setAttribute("disabled", "true");
|
||||
}
|
||||
|
||||
blockDownloads.checked = blockDownloadsPref.value;
|
||||
if (!blockDownloadsPref.value) {
|
||||
blockUncommonUnwanted.setAttribute("disabled", "true");
|
||||
}
|
||||
|
||||
blockUncommonUnwanted.checked = blockUnwantedPref.value && blockUncommonPref.value;
|
||||
},
|
||||
|
||||
/**
|
||||
* Enables/disables the master password button depending on the state of the
|
||||
* "use master password" checkbox, and prompts for master password removal if
|
||||
* one is set.
|
||||
*/
|
||||
updateMasterPasswordButton() {
|
||||
var checkbox = document.getElementById("useMasterPassword");
|
||||
var button = document.getElementById("changeMasterPassword");
|
||||
button.disabled = !checkbox.checked;
|
||||
|
||||
// unchecking the checkbox should try to immediately remove the master
|
||||
// password, because it's impossible to non-destructively remove the master
|
||||
// password used to encrypt all the passwords without providing it (by
|
||||
// design), and it would be extremely odd to pop up that dialog when the
|
||||
// user closes the prefwindow and saves his settings
|
||||
if (!checkbox.checked)
|
||||
this._removeMasterPassword();
|
||||
else
|
||||
this.changeMasterPassword();
|
||||
|
||||
this._initMasterPasswordUI();
|
||||
},
|
||||
|
||||
/**
|
||||
* Displays the "remove master password" dialog to allow the user to remove
|
||||
* the current master password. When the dialog is dismissed, master password
|
||||
* UI is automatically updated.
|
||||
*/
|
||||
_removeMasterPassword() {
|
||||
var secmodDB = Cc["@mozilla.org/security/pkcs11moduledb;1"].
|
||||
getService(Ci.nsIPKCS11ModuleDB);
|
||||
if (secmodDB.isFIPSEnabled) {
|
||||
var promptService = Cc["@mozilla.org/embedcomp/prompt-service;1"].
|
||||
getService(Ci.nsIPromptService);
|
||||
var bundle = document.getElementById("bundlePreferences");
|
||||
promptService.alert(window,
|
||||
bundle.getString("pw_change_failed_title"),
|
||||
bundle.getString("pw_change2empty_in_fips_mode"));
|
||||
this._initMasterPasswordUI();
|
||||
} else {
|
||||
gSubDialog.open("chrome://mozapps/content/preferences/removemp.xul",
|
||||
null, null, this._initMasterPasswordUI.bind(this));
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Displays a dialog in which the master password may be changed.
|
||||
*/
|
||||
changeMasterPassword() {
|
||||
gSubDialog.open("chrome://mozapps/content/preferences/changemp.xul",
|
||||
"resizable=no", null, this._initMasterPasswordUI.bind(this));
|
||||
},
|
||||
|
||||
/**
|
||||
* Shows the sites where the user has saved passwords and the associated login
|
||||
* information.
|
||||
*/
|
||||
showPasswords() {
|
||||
gSubDialog.open("chrome://passwordmgr/content/passwordManager.xul");
|
||||
}
|
||||
|
||||
};
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user