Bug 1053434 - Add listeners for devedition prefs in browser.js and stub CSS files;r=Gijs
authorBrian Grinstead <bgrinstead@mozilla.com>
Wed, 08 Oct 2014 16:05:46 -0500
changeset 209683 98daafd906a9f7bd01d9ca71a8a433b56587e237
parent 209682 c98a31227412b993cdcacd8dcc8282f106c5f5f3
child 209684 d864cbdfee340e43ac06f570c093662e3dcff9cc
push id1
push userroot
push dateMon, 20 Oct 2014 17:29:22 +0000
reviewersGijs
bugs1053434
milestone35.0a1
Bug 1053434 - Add listeners for devedition prefs in browser.js and stub CSS files;r=Gijs
browser/app/profile/firefox.js
browser/base/content/browser-devedition.js
browser/base/content/browser.js
browser/base/content/test/general/browser.ini
browser/base/content/test/general/browser_devedition.js
browser/themes/linux/devedition.css
browser/themes/linux/jar.mn
browser/themes/osx/devedition.css
browser/themes/osx/jar.mn
browser/themes/shared/devedition.inc.css
browser/themes/windows/devedition-aero.css
browser/themes/windows/devedition.css
browser/themes/windows/jar.mn
--- a/browser/app/profile/firefox.js
+++ b/browser/app/profile/firefox.js
@@ -1287,16 +1287,19 @@ pref("services.sync.prefs.sync.security.
 pref("services.sync.prefs.sync.security.default_personal_cert", true);
 pref("services.sync.prefs.sync.security.tls.version.min", true);
 pref("services.sync.prefs.sync.security.tls.version.max", true);
 pref("services.sync.prefs.sync.signon.rememberSignons", true);
 pref("services.sync.prefs.sync.spellchecker.dictionary", true);
 pref("services.sync.prefs.sync.xpinstall.whitelist.required", true);
 #endif
 
+// Developer edition preferences
+pref("browser.devedition.theme.enabled", false);
+
 // Disable the error console
 pref("devtools.errorconsole.enabled", false);
 
 // Developer toolbar and GCLI preferences
 pref("devtools.toolbar.enabled", true);
 pref("devtools.toolbar.visible", false);
 pref("devtools.commands.dir", "");
 
new file mode 100644
--- /dev/null
+++ b/browser/base/content/browser-devedition.js
@@ -0,0 +1,85 @@
+# 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/.
+
+/**
+ * Listeners for the DevEdition theme.  This adds an extra stylesheet
+ * to browser.xul if a pref is set and no other themes are applied.
+ */
+let DevEdition = {
+  _prefName: "browser.devedition.theme.enabled",
+  _themePrefName: "general.skins.selectedSkin",
+  _lwThemePrefName: "lightweightThemes.isThemeSelected",
+  _devtoolsThemePrefName: "devtools.theme",
+
+  styleSheetLocation: "chrome://browser/skin/devedition.css",
+  styleSheet: null,
+
+  init: function () {
+    this._updateDevtoolsThemeAttribute();
+    this._updateStyleSheet();
+
+    // Listen for changes to all prefs except for complete themes.
+    // No need for this since changing a complete theme requires a
+    // restart.
+    Services.prefs.addObserver(this._lwThemePrefName, this, false);
+    Services.prefs.addObserver(this._prefName, this, false);
+    Services.prefs.addObserver(this._devtoolsThemePrefName, this, false);
+  },
+
+  observe: function (subject, topic, data) {
+    if (topic == "nsPref:changed") {
+      if (data == this._devtoolsThemePrefName) {
+        this._updateDevtoolsThemeAttribute();
+      } else {
+        this._updateStyleSheet();
+      }
+    }
+  },
+
+  _updateDevtoolsThemeAttribute: function() {
+    // Set an attribute on root element to make it possible
+    // to change colors based on the selected devtools theme.
+    document.documentElement.setAttribute("devtoolstheme",
+      Services.prefs.getCharPref(this._devtoolsThemePrefName));
+  },
+
+  _updateStyleSheet: function() {
+    // Only try to apply the dev edition theme if it is preffered
+    // on and there are no other themes applied.
+    let lightweightThemeSelected = false;
+    try {
+      lightweightThemeSelected = Services.prefs.getBoolPref(this._lwThemePrefName);
+    } catch(e) {}
+
+    let defaultThemeSelected = false;
+    try {
+       defaultThemeSelected = Services.prefs.getCharPref(this._themePrefName) == "classic/1.0";
+    } catch(e) {}
+
+    let deveditionThemeEnabled = Services.prefs.getBoolPref(this._prefName) &&
+      !lightweightThemeSelected && defaultThemeSelected;
+
+    if (deveditionThemeEnabled && !this.styleSheet) {
+      let styleSheetAttr = `href="${this.styleSheetLocation}" type="text/css"`;
+      let styleSheet = this.styleSheet = document.createProcessingInstruction(
+        'xml-stylesheet', styleSheetAttr);
+      this.styleSheet.addEventListener("load", function onLoad() {
+        styleSheet.removeEventListener("load", onLoad);
+        ToolbarIconColor.inferFromText();
+      });
+      document.insertBefore(this.styleSheet, document.documentElement);
+    } else if (!deveditionThemeEnabled && this.styleSheet) {
+      this.styleSheet.remove();
+      this.styleSheet = null;
+      ToolbarIconColor.inferFromText();
+    }
+  },
+
+  uninit: function () {
+    Services.prefs.removeObserver(this._lwThemePrefName, this);
+    Services.prefs.removeObserver(this._prefName, this);
+    Services.prefs.removeObserver(this._devtoolsThemePrefName, this);
+    this.styleSheet = null;
+  }
+};
--- a/browser/base/content/browser.js
+++ b/browser/base/content/browser.js
@@ -194,16 +194,17 @@ let gInitialPages = [
   "about:home",
   "about:privatebrowsing",
   "about:welcomeback",
   "about:sessionrestore"
 ];
 
 #include browser-addons.js
 #include browser-customization.js
+#include browser-devedition.js
 #include browser-feeds.js
 #include browser-fullScreen.js
 #include browser-fullZoom.js
 #include browser-loop.js
 #include browser-places.js
 #include browser-plugins.js
 #include browser-safebrowsing.js
 #include browser-social.js
@@ -829,16 +830,17 @@ var gBrowserInit = {
     // These routines add message listeners. They must run before
     // loading the frame script to ensure that we don't miss any
     // message sent between when the frame script is loaded and when
     // the listener is registered.
     DOMLinkHandler.init();
     gPageStyleMenu.init();
     LanguageDetectionListener.init();
     BrowserOnClick.init();
+    DevEdition.init();
 
     let mm = window.getGroupMessageManager("browsers");
     mm.loadFrameScript("chrome://browser/content/content.js", true);
 
     // initialize observers and listeners
     // and give C++ access to gBrowser
     XULBrowserWindow.init();
     window.QueryInterface(Ci.nsIInterfaceRequestor)
@@ -1386,16 +1388,18 @@ var gBrowserInit = {
     BookmarkingUI.uninit();
 
     TabsInTitlebar.uninit();
 
     ToolbarIconColor.uninit();
 
     BrowserOnClick.uninit();
 
+    DevEdition.uninit();
+
     var enumerator = Services.wm.getEnumerator(null);
     enumerator.getNext();
     if (!enumerator.hasMoreElements()) {
       document.persist("sidebar-box", "sidebarcommand");
       document.persist("sidebar-box", "width");
       document.persist("sidebar-box", "src");
       document.persist("sidebar-title", "value");
     }
--- a/browser/base/content/test/general/browser.ini
+++ b/browser/base/content/test/general/browser.ini
@@ -304,16 +304,17 @@ skip-if = e10s
 [browser_contextSearchTabPosition.js]
 skip-if = os == "mac" || e10s # bug 967013, bug 926729
 [browser_ctrlTab.js]
 skip-if = e10s # Bug ????? - thumbnail captures need e10s love (tabPreviews_capture fails with Argument 1 of CanvasRenderingContext2D.drawWindow does not implement interface Window.)
 [browser_customize_popupNotification.js]
 skip-if = e10s
 [browser_datareporting_notification.js]
 run-if = datareporting
+[browser_devedition.js]
 [browser_devices_get_user_media.js]
 skip-if = buildapp == 'mulet' || (os == "linux" && debug) || e10s # linux: bug 976544; e10s: Bug 973001 - appears user media notifications only happen in the child and don't make their way to the parent?
 [browser_devices_get_user_media_about_urls.js]
 skip-if = e10s # Bug 973001 - appears user media notifications only happen in the child and don't make their way to the parent?
 [browser_discovery.js]
 skip-if = e10s # Bug 918663 - DOMLinkAdded events don't make their way to chrome
 [browser_duplicateIDs.js]
 [browser_drag.js]
new file mode 100644
--- /dev/null
+++ b/browser/base/content/test/general/browser_devedition.js
@@ -0,0 +1,66 @@
+/*
+ * Testing changes for Developer Edition theme.
+ * A special stylesheet should be added to the browser.xul document
+ * when browser.devedition.theme.enabled is set to true and no themes
+ * are applied.
+ */
+
+const PREF_DEVEDITION_THEME = "browser.devedition.theme.enabled";
+const PREF_THEME = "general.skins.selectedSkin";
+const PREF_LWTHEME = "lightweightThemes.isThemeSelected";
+const PREF_DEVTOOLS_THEME = "devtools.theme";
+
+registerCleanupFunction(() => {
+  // Set preferences back to their original values
+  Services.prefs.clearUserPref(PREF_DEVEDITION_THEME);
+  Services.prefs.clearUserPref(PREF_THEME);
+  Services.prefs.clearUserPref(PREF_LWTHEME);
+  Services.prefs.clearUserPref(PREF_DEVTOOLS_THEME);
+});
+
+function test() {
+  waitForExplicitFinish();
+  startTests();
+}
+
+function startTests() {
+  ok (!DevEdition.styleSheet, "There is no devedition style sheet by default.");
+
+  info ("Setting browser.devedition.theme.enabled to true.");
+  Services.prefs.setBoolPref(PREF_DEVEDITION_THEME, true);
+  ok (DevEdition.styleSheet, "There is a devedition stylesheet when no themes are applied and pref is set.");
+
+  info ("Adding a lightweight theme.");
+  Services.prefs.setBoolPref(PREF_LWTHEME, true);
+  ok (!DevEdition.styleSheet, "The devedition stylesheet has been removed when a lightweight theme is applied.");
+
+  info ("Removing a lightweight theme.");
+  Services.prefs.setBoolPref(PREF_LWTHEME, false);
+  ok (DevEdition.styleSheet, "The devedition stylesheet has been added when a lightweight theme is removed.");
+
+  // There are no listeners for the complete theme pref since applying the theme
+  // requires a restart.
+  info ("Setting general.skins.selectedSkin to a custom string.");
+  Services.prefs.setCharPref(PREF_THEME, "custom-theme");
+  ok (DevEdition.styleSheet, "The devedition stylesheet is still here when a complete theme is added.");
+
+  info ("Resetting general.skins.selectedSkin to default value.");
+  Services.prefs.clearUserPref(PREF_THEME);
+  ok (DevEdition.styleSheet, "The devedition stylesheet is still here when a complete theme is removed.");
+
+  info ("Setting browser.devedition.theme.enabled to false.");
+  Services.prefs.setBoolPref(PREF_DEVEDITION_THEME, false);
+  ok (!DevEdition.styleSheet, "The devedition stylesheet has been removed.");
+
+  info ("Checking :root attributes based on devtools theme.");
+  is (document.documentElement.getAttribute("devtoolstheme"), "light",
+    "The documentElement has an attribute based on devtools theme.");
+  Services.prefs.setCharPref(PREF_DEVTOOLS_THEME, "dark");
+  is (document.documentElement.getAttribute("devtoolstheme"), "dark",
+    "The documentElement has an attribute based on devtools theme.");
+  Services.prefs.setCharPref(PREF_DEVTOOLS_THEME, "light");
+  is (document.documentElement.getAttribute("devtoolstheme"), "light",
+    "The documentElement has an attribute based on devtools theme.");
+
+  finish();
+}
new file mode 100644
--- /dev/null
+++ b/browser/themes/linux/devedition.css
@@ -0,0 +1,5 @@
+% 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/.
+
+%include ../shared/devedition.inc.css
--- a/browser/themes/linux/jar.mn
+++ b/browser/themes/linux/jar.mn
@@ -17,16 +17,17 @@ browser.jar:
   skin/classic/browser/aboutNetError_info.svg                   (../shared/aboutNetError_info.svg)
   skin/classic/browser/aboutSocialError.css
 #ifdef MOZ_SERVICES_SYNC
   skin/classic/browser/aboutSyncTabs.css
 #endif
   skin/classic/browser/aboutTabCrashed.css
   skin/classic/browser/actionicon-tab.png
 * skin/classic/browser/browser.css
+* skin/classic/browser/devedition.css
 * skin/classic/browser/browser-lightweightTheme.css
   skin/classic/browser/click-to-play-warning-stripes.png
 * skin/classic/browser/content-contextmenu.svg
 * skin/classic/browser/engineManager.css
   skin/classic/browser/fullscreen-darknoise.png
   skin/classic/browser/Geolocation-16.png
   skin/classic/browser/Geolocation-64.png
   skin/classic/browser/identity.png
new file mode 100644
--- /dev/null
+++ b/browser/themes/osx/devedition.css
@@ -0,0 +1,5 @@
+% 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/.
+
+%include ../shared/devedition.inc.css
--- a/browser/themes/osx/jar.mn
+++ b/browser/themes/osx/jar.mn
@@ -17,16 +17,17 @@ browser.jar:
   skin/classic/browser/aboutSocialError.css
 #ifdef MOZ_SERVICES_SYNC
   skin/classic/browser/aboutSyncTabs.css
 #endif
   skin/classic/browser/aboutTabCrashed.css
   skin/classic/browser/actionicon-tab.png
   skin/classic/browser/actionicon-tab@2x.png
 * skin/classic/browser/browser.css                          (browser.css)
+* skin/classic/browser/devedition.css
 * skin/classic/browser/browser-lightweightTheme.css
   skin/classic/browser/click-to-play-warning-stripes.png
 * skin/classic/browser/content-contextmenu.svg
 * skin/classic/browser/engineManager.css                    (engineManager.css)
   skin/classic/browser/fullscreen-darknoise.png
   skin/classic/browser/Geolocation-16.png
   skin/classic/browser/Geolocation-16@2x.png
   skin/classic/browser/Geolocation-64.png
new file mode 100644
--- /dev/null
+++ b/browser/themes/shared/devedition.inc.css
@@ -0,0 +1,3 @@
+% 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/.
new file mode 100644
--- /dev/null
+++ b/browser/themes/windows/devedition-aero.css
@@ -0,0 +1,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/.
+
+%define WINDOWS_AERO
+%include devedition.css
+%undef WINDOWS_AERO
new file mode 100644
--- /dev/null
+++ b/browser/themes/windows/devedition.css
@@ -0,0 +1,5 @@
+% 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/.
+
+%include ../shared/devedition.inc.css
--- a/browser/themes/windows/jar.mn
+++ b/browser/themes/windows/jar.mn
@@ -19,16 +19,17 @@ browser.jar:
         skin/classic/browser/aboutNetError_info.svg                  (../shared/aboutNetError_info.svg)
         skin/classic/browser/aboutSocialError.css
 #ifdef MOZ_SERVICES_SYNC
         skin/classic/browser/aboutSyncTabs.css
 #endif
         skin/classic/browser/aboutTabCrashed.css
         skin/classic/browser/actionicon-tab.png
 *       skin/classic/browser/browser.css
+*       skin/classic/browser/devedition.css
 *       skin/classic/browser/browser-lightweightTheme.css
         skin/classic/browser/click-to-play-warning-stripes.png
 *       skin/classic/browser/content-contextmenu.svg
 *       skin/classic/browser/engineManager.css
         skin/classic/browser/fullscreen-darknoise.png
         skin/classic/browser/Geolocation-16.png
         skin/classic/browser/Geolocation-64.png
         skin/classic/browser/Info.png
@@ -441,16 +442,17 @@ browser.jar:
         skin/classic/aero/browser/aboutSocialError.css
 #ifdef MOZ_SERVICES_SYNC
         skin/classic/aero/browser/aboutSyncTabs.css
 #endif
         skin/classic/aero/browser/aboutTabCrashed.css
         skin/classic/aero/browser/aboutWelcomeBack.css               (../shared/aboutWelcomeBack.css)
         skin/classic/aero/browser/actionicon-tab.png
 *       skin/classic/aero/browser/browser.css                        (browser-aero.css)
+*       skin/classic/aero/browser/devedition.css                     (devedition-aero.css)
 *       skin/classic/aero/browser/browser-lightweightTheme.css
         skin/classic/aero/browser/click-to-play-warning-stripes.png
 *       skin/classic/aero/browser/content-contextmenu.svg
 *       skin/classic/aero/browser/engineManager.css
         skin/classic/aero/browser/fullscreen-darknoise.png
         skin/classic/aero/browser/Geolocation-16.png
         skin/classic/aero/browser/Geolocation-64.png
         skin/classic/aero/browser/Info.png                           (Info-aero.png)