Bug 1350670 - Extend the MutationObserver to cover attributes in case the page sets styles through style, class, ID or other attributes. r=mossop, a=gchang
authorJared Wein <jwein@mozilla.com>
Wed, 29 Mar 2017 12:47:13 -0400
changeset 395659 c3c509c0b9710393913ffb699d347334090acc31
parent 395658 a2f248438fc21abf4005ac6b4bf82019aa19fdb3
child 395660 e99180e4d04608f53182e8d55e981ae3a3d27050
push id1468
push userasasaki@mozilla.com
push dateMon, 05 Jun 2017 19:31:07 +0000
treeherdermozilla-release@0641fc6ee9d1 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmossop, gchang
bugs1350670
milestone54.0a2
Bug 1350670 - Extend the MutationObserver to cover attributes in case the page sets styles through style, class, ID or other attributes. r=mossop, a=gchang MozReview-Commit-ID: 3tYjbqH9zYb
browser/base/content/test/forms/browser_selectpopup_colors.js
toolkit/modules/SelectContentHelper.jsm
--- a/browser/base/content/test/forms/browser_selectpopup_colors.js
+++ b/browser/base/content/test/forms/browser_selectpopup_colors.js
@@ -115,16 +115,26 @@ const SELECT_STYLE_OF_OPTION_IS_BASED_ON
   "  select:focus { background-color: #3a96dd; }" +
   "  select:focus option { background-color: #fff; }" +
   "</style></head>" +
   "<body><select id='one'>" +
   '  <option>{"color": "rgb(0, 0, 0)", "backgroundColor": "rgb(255, 255, 255)"}</option>' +
   '  <option selected="true">{"end": "true"}</option>' +
   "</select></body></html>";
 
+const SELECT_STYLE_OF_OPTION_CHANGES_AFTER_FOCUS_EVENT =
+  "<html><body><select id='one'>" +
+  '  <option>{"color": "rgb(255, 0, 0)", "backgroundColor": "rgba(0, 0, 0, 0)"}</option>' +
+  '  <option selected="true">{"end": "true"}</option>' +
+  "</select></body><scr" +
+  "ipt>" +
+  "  var select = document.getElementById('one');" +
+  "  select.addEventListener('focus', () => select.style.color = 'red');" +
+  "</script></html>";
+
 function getSystemColor(color) {
   // Need to convert system color to RGB color.
   let textarea = document.createElementNS("http://www.w3.org/1999/xhtml", "textarea");
   textarea.style.color = color;
   return getComputedStyle(textarea).color;
 }
 
 function testOptionColors(index, item, menulist) {
@@ -164,16 +174,25 @@ function* testSelectColors(select, itemC
 
   let menulist = document.getElementById("ContentSelectDropdown");
   let selectPopup = menulist.menupopup;
 
   let popupShownPromise = BrowserTestUtils.waitForEvent(selectPopup, "popupshown");
   yield BrowserTestUtils.synthesizeMouseAtCenter("#one", { type: "mousedown" }, gBrowser.selectedBrowser);
   yield popupShownPromise;
 
+  if (options.waitForComputedStyle) {
+    let property = options.waitForComputedStyle.property;
+    let value = options.waitForComputedStyle.value;
+    yield BrowserTestUtils.waitForCondition(() => {
+      info(`<select> has ${property}: ${getComputedStyle(selectPopup)[property]}`);
+      return getComputedStyle(selectPopup)[property] == value;
+    }, `Waiting for <select> to have ${property}: ${value}`);
+  }
+
   is(selectPopup.parentNode.itemCount, itemCount, "Correct number of items");
   let child = selectPopup.firstChild;
   let idx = 1;
 
   if (!options.skipSelectColorTest) {
     is(getComputedStyle(selectPopup).color, options.selectColor,
       "popup has expected foreground color");
 
@@ -330,8 +349,19 @@ add_task(function* test_bgcolor_on_selec
 add_task(function* test_style_of_options_is_dependent_on_focus_of_select() {
   let options = {
     selectColor: "rgb(0, 0, 0)",
     selectBgColor: "rgb(58, 150, 221)"
   };
 
   yield testSelectColors(SELECT_STYLE_OF_OPTION_IS_BASED_ON_FOCUS_OF_SELECT, 2, options);
 });
+
+add_task(function* test_style_of_options_is_dependent_on_focus_of_select() {
+  let options = {
+    skipSelectColorTest: true,
+    waitForComputedStyle: {
+      property: "color",
+      value: "rgb(255, 0, 0)"
+    }
+  };
+  yield testSelectColors(SELECT_STYLE_OF_OPTION_CHANGES_AFTER_FOCUS_EVENT, 2, options);
+});
--- a/toolkit/modules/SelectContentHelper.jsm
+++ b/toolkit/modules/SelectContentHelper.jsm
@@ -65,17 +65,17 @@ this.SelectContentHelper.prototype = {
     this.element.addEventListener("blur", this, { mozSystemGroup: true });
     let MutationObserver = this.element.ownerGlobal.MutationObserver;
     this.mut = new MutationObserver(mutations => {
       // Something changed the <select> while it was open, so
       // we'll poke a DeferredTask to update the parent sometime
       // in the very near future.
       this._updateTimer.arm();
     });
-    this.mut.observe(this.element, {childList: true, subtree: true});
+    this.mut.observe(this.element, {childList: true, subtree: true, attributes: true});
   },
 
   uninit() {
     this.element.openInParentProcess = false;
     this.global.removeMessageListener("Forms:SelectDropDownItem", this);
     this.global.removeMessageListener("Forms:DismissedDropDown", this);
     this.global.removeMessageListener("Forms:MouseOver", this);
     this.global.removeMessageListener("Forms:MouseOut", this);