The issue is the stacking context here, but if you move the element, it's no longer tied to its parent position as it scrolls.
The future CSS Anchor Positioning API can fix this, but it has limited support as of today. There is a polyfill available though.
Anchor Positioning Demo:
.fixedScrollable {
height: 300px;
width: 200px;
padding: 10px;
background-color: lightblue;
overflow: auto;
}
.container1 {
background-color: lightslategrey;
height: 500px;
padding: 10px;
padding-top: 100px;
}
.container2 {
position: relative;
background-color: pink;
height: 50px;
/* define the anchor name */
anchor-name: --dropdown-anchor;
}
.dropdown {
background-color: blue;
height: min-content;
width: 100px;
position: absolute;
/* reset all positioning */
inset: 0;
/* override margin defaults */
margin: initial;
/* position on anchor */
top: anchor(bottom);
left: anchor(right);
position-anchor: --dropdown-anchor;
}
<!-- Add polyfill (normally in document <head>) -->
<script type="module">
if (!("anchorName" in document.documentElement.style)) {
import("https://unpkg.com/@oddbird/css-anchor-positioning");
}
</script>
<div class="fixedScrollable">
<div class="container1">
<!-- <div class="dropdown">Dropdown menu</div> -->
<div class="container2"></div>
</div>
</div>
<!--
Move the dropdown outside of the stacking context
that is causing the clipping
-->
<div class="dropdown">Dropdown menu</div>
While this works, it means that the hierarchy of your html is lost and it introduces some potentially big accessibility issues.
Instead of moving the element out of the stacking context by changing its source order, you could take advantage of the browser top layer by utilizing either a <dialog> element or popover attribute. Assuming that the element you called your "dropdown" is dismissible anyway, the Popover API makes it easy to create a menu that can be opened and closed with potentially no JS at all as shown in the demo below.
Anchor Positioning + Popover Demo:
.fixedScrollable {
height: 300px;
width: 200px;
padding: 10px;
background-color: lightblue;
overflow: auto;
}
.container1 {
background-color: lightslategrey;
height: 500px;
padding: 10px;
padding-top: 100px;
}
.container2 {
position: relative;
background-color: pink;
height: 50px;
anchor-name: --dropdown-anchor;
}
.dropdown {
background-color: blue;
height: min-content;
width: 100px;
position: absolute;
/* reset all positioning */
inset: 0;
/* override margin defaults */
margin: initial;
/* position on anchor */
top: anchor(bottom);
left: anchor(right);
position-anchor: --dropdown-anchor;
}
.dropdown:popover-open {
/* styles to be applied to the
dropdown in the open state
(great for transitions and
animations)
*/
}
<script type="module">
if (!("anchorName" in document.documentElement.style)) {
import("https://unpkg.com/@oddbird/css-anchor-positioning");
}
</script>
<div class="fixedScrollable">
<div class="container1">
<button class="container2" popovertarget="dropdown">
click to display dropdown
</button>
<div popover class="dropdown" id="dropdown">
Dropdown menu
</div>
</div>
</div>