Bug 1425088 - (Part 2) Change the dropdown frame to a top-level absolute frame when content-select is enabled. draft
authorKuoE0 <kuoe0.tw@gmail.com>
Wed, 13 Dec 2017 17:59:29 -0600
changeset 717470 351ef273f5df10268a205587d002f782572bfff9
parent 717469 1e6e0303e9903f7c00494503ec6a940694713cf7
child 717471 ecd0f9dd4923c6d456a13ecac746a58808324af9
push id94690
push userbmo:kuoe0@mozilla.com
push dateTue, 09 Jan 2018 02:16:54 +0000
bugs1425088
milestone59.0a1
Bug 1425088 - (Part 2) Change the dropdown frame to a top-level absolute frame when content-select is enabled. MozReview-Commit-ID: E77XdiELqhm
layout/base/nsCSSFrameConstructor.cpp
layout/style/res/forms.css
--- a/layout/base/nsCSSFrameConstructor.cpp
+++ b/layout/base/nsCSSFrameConstructor.cpp
@@ -102,16 +102,17 @@
 #include "nsPageFrame.h"
 #include "nsSimplePageSequenceFrame.h"
 #include "nsTableWrapperFrame.h"
 #include "nsIScrollableFrame.h"
 #include "nsBackdropFrame.h"
 #include "nsTransitionManager.h"
 #include "DetailsFrame.h"
 #include "nsThemeConstants.h"
+#include "mozilla/Preferences.h"
 
 #ifdef MOZ_XUL
 #include "nsIRootBox.h"
 #endif
 #ifdef ACCESSIBILITY
 #include "nsAccessibilityService.h"
 #endif
 
@@ -129,16 +130,17 @@
 #include "ActiveLayerTracker.h"
 #include "nsIPresShellInlines.h"
 
 using namespace mozilla;
 using namespace mozilla::dom;
 
 // An alias for convenience.
 static const nsIFrame::ChildListID kPrincipalList = nsIFrame::kPrincipalList;
+static const char* kPrefSelectPopupInContent = "dom.select_popup_in_content.enabled";
 
 nsIFrame*
 NS_NewHTMLCanvasFrame (nsIPresShell* aPresShell, nsStyleContext* aContext);
 
 nsIFrame*
 NS_NewHTMLVideoFrame (nsIPresShell* aPresShell, nsStyleContext* aContext);
 
 nsContainerFrame*
@@ -3229,18 +3231,21 @@ nsCSSFrameConstructor::ConstructSelectFr
     // Notify the listbox that it is being used as a dropdown list.
     nsIListControlFrame * listControlFrame = do_QueryFrame(listFrame);
     if (listControlFrame) {
       listControlFrame->SetComboboxFrame(comboboxFrame);
     }
     // Notify combobox that it should use the listbox as it's popup
     comboboxFrame->SetDropDown(listFrame);
 
-    NS_ASSERTION(!listFrame->IsAbsPosContainingBlock(),
-                 "Ended up with positioned dropdown list somehow.");
+    if (!Preferences::GetBool(kPrefSelectPopupInContent)) {
+      // TODO(kuoe0) Remove this assertion when content-select is shipped.
+      NS_ASSERTION(!listFrame->IsAbsPosContainingBlock(),
+                   "Ended up with positioned dropdown list somehow.");
+    }
     NS_ASSERTION(!listFrame->IsFloating(),
                  "Ended up with floating dropdown list somehow.");
 
     // Initialize the scroll frame positioned. Note that it is NOT
     // initialized as absolutely positioned.
     nsContainerFrame* scrolledFrame =
       NS_NewSelectsAreaFrame(mPresShell, styleContext, flags);
 
--- a/layout/style/res/forms.css
+++ b/layout/style/res/forms.css
@@ -417,16 +417,23 @@ optgroup:before {
    * to make sure that our inline-start border+padding matches the inline-start
    * border+padding of a combobox so that our scrollbar will line up
    * with the dropmarker.  So set our inline-start border to 2px.
    */
   border: 1px outset black !important;
   border-inline-start-width: 2px ! important;
 }
 
+@supports -moz-bool-pref("dom.select_popup_in_content.enabled") {
+  select::-moz-dropdown-list {
+    -moz-top-layer: top !important;
+    position: absolute !important;
+  }
+}
+
 input:disabled,
 textarea:disabled,
 option:disabled,
 optgroup:disabled,
 select:disabled:disabled /* Need the pseudo-class twice to have the specificity
                             be at least the same as select[size][multiple] above */
 {
   -moz-user-input: disabled;