I am in the process of developing a modal that needs to be centered on my page and expand organically, but only up to a specific width and height limit.
Using flexbox, I have successfully centered this modal (.modal
) on the page.
Within the modal, there is another flexbox (.modal-content
) containing a body (.modal-content__body
) and a footer (.modal-content__footer
). I aim for the body to expand until the entire .modal
reaches the defined max-height
, at which point the .modal-content__body
should start scrolling vertically.
The HTML structure is as follows:
.modal-container // Takes up the full screen
.modal // Centered box with max-width and max-height limits
.modal-content // Content inside the modal
.modal-content__body // Content that may grow dynamically
.modal-content__footer
I am encountering an issue where the content within .modal-content
overflows. It does not adhere to the height restrictions set by its parent element (.modal
) and continues to expand to accommodate more content.
If I merge the .modal
and .modal-content
without the additional div layer, everything functions as intended. However, due to constraints imposed by using a framework (Angular), altering the structure of HTML elements is not feasible.
(NOTE: Applying
max-height: -webkit-fill-available;
to .modal-content
resolves the issue, but this property's compatibility issues prevent its use)
Below is a code snippet illustrating the problem:
/* Centers the child */
.modal-container {
display: flex;
align-items: center;
justify-content: center;
}
/* The central box that should naturally grow
whilst remaining constrained */
.modal,
.modal-content--merged-with-modal {
width: 30rem;
max-width: calc(50vw - 3rem);
max-height: calc(100vh - 3rem);
/* Styling details irrelevant to the problem */
background: rgba(255, 255, 255, 0.6);
border-radius: 3px;
line-height: 1.5rem;
}
.modal-content {
display: flex;
flex-direction: column;
min-height: 0;
}
.modal-content__body {
flex: 1;
min-height: 0;
overflow-y: scroll;
/* Styling details irrelevant to the problem */
padding: 0.75rem;
background: rgba(0, 0, 255, 0.1);
}
.modal-content__footer {
/* Styling details irrelevant to the problem */
border-top: 1px solid silver;
background: rgba(0, 255, 0, 0.1);
padding: 0.75rem;
}
/* Irrelevant styling given to highlight the issue */
html {
font-family: arial, sans-serif;
font-size: 16px;
}
main {
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
display: flex;
}
section {
flex: 1;
background: rgba(255, 0, 0, 0.1);
}
<main>
<section class="modal-container">
<div class="modal-content modal-content--merged-with-modal">
<div class="modal-content__body">
<code>BODY // </code> srollable<br>
<br> Container resizes as expected when<br> the container height is reduced.<br>
<br> In this case, the modal is the same<br> element, as the flexbox handling<br> the body and the footer.<br> .
<br> .
<br> .
<br> .
<br> .
<br> .
<br>
</div>
<div class="modal-content__footer">
<code>FOOTER // </code> Works
</div>
</div>
</section>
<section class="modal-container">
<div class="modal">
<div class="modal-content">
<div class="modal-content__body">
<code>BODY // </code> simply grows<br>
<br> Container overflows if<br> container height is reduced.<br>
<br> In this case, modal <strong>contains</strong><br> flexbox managing<br> body and footer.<br>.
<br> .
<br> .
<br> .
<br> .
<br> .
<br> .
<br>
</div>
<div class="modal-content__footer">
<code>FOOTER // </code> Doesn't work
</div>
</div>
</div>
</section>
</main>