From af93db294b8670dabefbe481603a74e02c84dc0a Mon Sep 17 00:00:00 2001
From: Johann-S <johann.servoire@gmail.com>
Date: Sun, 4 Jun 2017 17:56:51 +0200
Subject: [PATCH] Reset Popper.js styles for Dropdowns in navbar

---
 js/src/dropdown.js | 67 +++++++++++++++++++++++++++++++++++-----------
 scss/_navbar.scss  | 23 +++++++++++++---
 2 files changed, 70 insertions(+), 20 deletions(-)

diff --git a/js/src/dropdown.js b/js/src/dropdown.js
index 4ed0210a54..9a4beae63a 100644
--- a/js/src/dropdown.js
+++ b/js/src/dropdown.js
@@ -96,10 +96,11 @@ const Dropdown = (($) => {
   class Dropdown {
 
     constructor(element, config) {
-      this._element = element
-      this._popper  = null
-      this._config = this._getConfig(config)
-      this._menu = this._getMenuElement()
+      this._element  = element
+      this._popper   = null
+      this._config   = this._getConfig(config)
+      this._menu     = this._getMenuElement()
+      this._inNavbar = this._detectNavbar()
 
       this._addEventListeners()
     }
@@ -153,17 +154,7 @@ const Dropdown = (($) => {
           element = parent
         }
       }
-      this._popper = new Popper(element, this._menu, {
-        placement : this._getPlacement(),
-        modifiers : {
-          offset : {
-            offset : this._config.offset
-          },
-          flip : {
-            enabled : this._config.flip
-          }
-        }
-      })
+      this._popper = new Popper(element, this._menu, this._getPopperConfig())
 
       // if this is a touch-enabled device we add extra
       // empty mouseover listeners to the body's immediate children;
@@ -253,10 +244,54 @@ const Dropdown = (($) => {
       } else if ($(this._menu).hasClass(ClassName.MENURIGHT)) {
         placement = AttachmentMap.BOTTOMEND
       }
-
       return placement
     }
 
+    _detectNavbar() {
+      return $(this._element).closest('.navbar').length > 0
+    }
+
+    _navbarPositioning() {
+      const $parentNavbar = $(this._element).closest('.navbar')
+      if ($(this._menu).hasClass(ClassName.MENURIGHT)) {
+        if (!$parentNavbar.hasClass('navbar-expand')) {
+          return {
+            position: 'static',
+            transform: '',
+            float: 'none'
+          }
+        }
+      }
+
+      return {}
+    }
+
+    _getPopperConfig() {
+      const popperConfig = {
+        placement : this._getPlacement(),
+        modifiers : {
+          offset : {
+            offset : this._config.offset
+          },
+          flip : {
+            enabled : this._config.flip
+          }
+        }
+      }
+
+      if (this._inNavbar) {
+        popperConfig.modifiers.AfterApplyStyle = {
+          enabled: true,
+          order: 901, // ApplyStyle order + 1
+          fn: () => {
+            // reset Popper styles
+            $(this._menu).attr('style', '')
+          }
+        }
+      }
+      return popperConfig
+    }
+
     // static
 
     static _jQueryInterface(config) {
diff --git a/scss/_navbar.scss b/scss/_navbar.scss
index 59cc52d9a1..1803a82b43 100644
--- a/scss/_navbar.scss
+++ b/scss/_navbar.scss
@@ -77,9 +77,8 @@
   }
 
   .dropdown-menu {
-    position: static !important;
+    position: static;
     float: none;
-    transform: unset !important;
   }
 }
 
@@ -142,6 +141,13 @@
 
     &#{$infix} {
       @include media-breakpoint-down($breakpoint) {
+        .navbar-nav {
+          .dropdown-menu {
+            position: static;
+            float: none;
+          }
+        }
+
         > .container,
         > .container-fluid {
           padding-right: 0;
@@ -158,8 +164,17 @@
           flex-direction: row;
 
           .dropdown-menu {
-            position: absolute !important;
-            top: 100% !important;
+            position: absolute;
+          }
+
+          .dropdown-menu-right {
+            right: 0;
+            left: auto; // Reset the default from `.dropdown-menu`
+          }
+
+          .dropdown-menu-left {
+            right: auto;
+            left: 0;
           }
 
           .nav-link {
-- 
GitLab