Reputation: 1018
I have a problem similar to this . But the solutions there does not work for my issue. And that discussion has been closed for further suggestions. Unfortunately I can't show my code exactly as it is on jsfiddle. However the issue is something like this. When trying to expand the dropdown inside first panel section, the dropdown hidden behind other elements. I've spent hours trying different suggestions concerning "stacking context", "position", and "z-index". I would really appreciate if anyone could point me to any resources that could help.
<div class="btn-group">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown"> <span data-bind="label">Select One</span> <span class="caret"></span>
</button>
<ul class="dropdown-menu" role="menu">
<li><a href="#">Item 1</a>
</li>
<li><a href="#">Another item</a>
</li>
<li><a href="#">This is a longer item that will not fit properly</a>
</li>
</ul>
</div>
Upvotes: 13
Views: 40902
Reputation: 1659
Maybe this will help someone, I spent hours on this:
And for me this issue was from this style on a parent div:
backdrop-filter: blur(50px);
Just had to remove it to get the dropdown-menu not being hidden over some elements of the page!
Upvotes: 0
Reputation: 38
Add an additional class on your HTML and use the below codepen reference code.
check here: https://codepen.io/qpqinc/pen/yLyPVMJ
<div class="dropdown">
<button class="btn btn-default dropdown-toggle" type="button" id="dropdownMenu1" data-toggle="dropdown" aria-haspopup="true" aria-expanded="true">
Dropdown
<span class="caret"></span>
</button>
<ul class="dropdown-menu" aria-labelledby="dropdownMenu1">
<li><a href="#">Item 1</a></li>
<li><a href="#">Item 2</a></li>
<li><a href="#">Item 3</a></li>
<li><a href="#">Item 4</a></li>
<li><a href="#">Item 5</a></li>
<li><a href="#">Item 6</a></li>
<li><a href="#">Item 7</a></li>
<li><a href="#">Item 8</a></li>
<li><a href="#">Item 9</a></li>
<li><a href="#">Item 10</a></li>
</ul>
</div>
$(function() {
//add BT DD show event
$(".dropdown").on("show.bs.dropdown", function() {
var $btnDropDown = $(this).find(".dropdown-toggle");
var $listHolder = $(this).find(".dropdown-menu");
//reset position property for DD container
$(this).css("position", "static");
$listHolder.css({
"top": ($btnDropDown.offset().top + $btnDropDown.outerHeight(true)) + "px",
"left": $btnDropDown.offset().left + "px"
});
$listHolder.data("open", true);
});
//add BT DD hide event
$(".dropdown").on("hidden.bs.dropdown", function() {
var $listHolder = $(this).find(".dropdown-menu");
$listHolder.data("open", false);
});
//add on scroll for table holder
$(".ak-holder").scroll(function() {
var $ddHolder = $(this).find(".dropdown")
var $btnDropDown = $(this).find(".dropdown-toggle");
var $listHolder = $(this).find(".dropdown-menu");
if ($listHolder.data("open")) {
$listHolder.css({
"top": ($btnDropDown.offset().top + $btnDropDown.outerHeight(true)) + "px",
"left": $btnDropDown.offset().left + "px"
});
$ddHolder.toggleClass("open", ($btnDropDown.offset().left > $(this).offset().left))
}
})
});
Upvotes: 0
Reputation: 1210
Modification of Jonathan's answer above, which was a huge help, but I modified it to place the menu back at it's source row, which allows custom jQuery to function properly (because the menu still exists at its initial parent element hierarchy. My use case was a jQuery DataTable with frozen columns. We had a bootstrap 4 "Action" dropdown-menu embedded in a cell of that table. The menu was appearing behind the hidden columns. This function allowed it be copied and pasted above the fixed columns where users can actually interact with it.
function BringActionMenuToForeground() {
var dropdownMenu;
/// When you show the menu, remove it from its current row and place it right back. This puts it on top of the DOM.
$(window).on('show.bs.dropdown', function (e) {
/// grab the menu
dropdownMenu = $(e.target).find('.dropdown-menu');
/// get the row where the menu appers.
var menuRow = $(dropdownMenu).closest("tr");
/// detach it and append it right back to the row from which it was taken.
$(menuRow).append(dropdownMenu.detach());
/// grab the new offset position
var eOffset = $(e.target).offset();
/// make sure to place it where it would normally go (this could be improved)
dropdownMenu.css({
'display': 'block',
'top': eOffset.top + $(e.target).outerHeight(),
'left': eOffset.left
});
});
/// and when you hide it, reattach the drop down, and hide it normally
$(window).on('hide.bs.dropdown', function (e) {
$(e.target).append(dropdownMenu.detach());
dropdownMenu.hide();
});
}
Upvotes: 0
Reputation: 570
You need to add only:
.panel.panel-default{
overflow: inherit !important;
}
Upvotes: -1
Reputation: 1156
You have two options. You can make the container's overflow expand to fit the content by setting 'overflow: auto' to the parent's css.
.panel-body { /* parent container of the menu */
overflow:auto;
}
Or you could do something functionally with JavaScript to handle the menu placement. This option is a little bit 'hacky' and would require further improvements. You would need to improve it to handle multiple menus open at once on the same page, and you would need to improve how it selects the menu. You might also want to add scroll support to move the menu with its target element unless that's not an issue. Here's the fiddle:
(function() {
// hold onto the drop down menu
var dropdownMenu;
// and when you show it, move it to the body
$(window).on('show.bs.dropdown', function(e) {
// grab the menu
dropdownMenu = $(e.target).find('.dropdown-menu');
// detach it and append it to the body
$('body').append(dropdownMenu.detach());
// grab the new offset position
var eOffset = $(e.target).offset();
// make sure to place it where it would normally go (this could be improved)
dropdownMenu.css({
'display': 'block',
'top': eOffset.top + $(e.target).outerHeight(),
'left': eOffset.left
});
});
// and when you hide it, reattach the drop down, and hide it normally
$(window).on('hide.bs.dropdown', function(e) {
$(e.target).append(dropdownMenu.detach());
dropdownMenu.hide();
});
})();
There is probably a better way to do this, but the concept is to move the menu from the confines of the parent element to the body. When you're relying on the html data-attributes to setup the menu, you'll have trouble doing this, but that is where the second solution I reference becomes useful.
Sadly I would have suggested looking into the 'Via Javascript' options that bootstrap provides, but apparently they don't have the option to set the target append element. It would have been nice to have an option to append the menu on to whichever element you want like most of their other items: Bootstrap Docs
EDIT
As @Andrea Pizzirani mentioned, you could try removing the css for the menu absolute positioning, but I wouldn't recommend it! That will mess up all other instances of the menu unless you add other css to restrict scope of the change. Also, if you want the menu positioned under the button, you'll have to redo CSS that bootstrap already had in place.
Still, if it works, and you're not worried about messing up all other menus, it may be the solution you were looking for. Heres a fiddle demonstrating the solution:
dropdown-menu {}
EDIT I finally found where I originally found this solution. Gotta give credit where credit is due!
Upvotes: 25
Reputation: 53
Try to remove position: absolute; from:
dropdown-menu {}
and place the menu under the button by css.
Upvotes: 1