[css] How to put scroll bar only for modal-body?

I have the following element:

<div class="modal" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true"> 
    <div class="modal-dialog" style="overflow-y: scroll; max-height:85%;  margin-top: 50px; margin-bottom:50px;" > 
        <div class="modal-content"> 
            <div class="modal-header"> 
                <h3 class="modal-title"></h3> 
            </div> 
            <div class="modal-body"></div> 
            <div class="modal-footer"></div> 
        </div> 
    </div> 
</div> 

It shows modal dialog something like this, basically, it puts scroll bar around entire modal-dialog and not modal-body that contains the content I am trying to display.

The image looks something like this:

enter image description here

How do I get a scroll bar around modal-body only?

I have tried assigning style="overflow-y: scroll; max-height:85%; margin-top: 50px; margin-bottom:50px;" to modal-body but it didn't work.

This question is related to css twitter-bootstrap

The answer is


If you're only supporting IE 9 or higher, you can use this CSS that will smoothly scale to the size of the window. You may need to tweak the "200px" though, depending on the height of your header or footer.

.modal-body{
    max-height: calc(100vh - 200px);
    overflow-y: auto;
}

A simple js solution to set modal height proportional to body's height :

$(document).ready(function () {
    $('head').append('<style type="text/css">.modal .modal-body {max-height: ' + ($('body').height() * .8) + 'px;overflow-y: auto;}.modal-open .modal{overflow-y: hidden !important;}</style>');
});

body's height has to be 100% :

html, body {
    height: 100%;
    min-height: 100%;
}

I set modal body height to 80% of body, this can be of course customized.

Hope it helps.


Or simpler you can put between your tags first, then to the css class.

<div style="height: 35px;overflow-y: auto;"> Some text o othre div scroll </div>

#scroll-wrap {
    max-height: 50vh;
    overflow-y: auto;
}

Using max-height with vh as the unit on the modal-body or a wrapper div inside of the modal-body. This will resize the height of modal-body or the wrapping div(in this example) automatically when a user resize the window.

vh is length unit representing 1% of the viewport size for viewport height.

Browser compatibility chart for vh unit.

Example: https://jsfiddle.net/q3xwr53f/


Adding on to Carlos Calla's great answer.

The height of .modal-body must be set, BUT you can use media queries to make sure it's appropriate for the screen size.

.modal-body{
    height: 250px;
    overflow-y: auto;
}

@media (min-height: 500px) {
    .modal-body { height: 400px; }
}

@media (min-height: 800px) {
    .modal-body { height: 600px; }
}

What worked for me is setting the height to 100% the having the overflow on auto hope this will help

   <div style="height: 100%;overflow-y: auto;"> Some text o othre div scroll </div>

Optional: If you don't want the modal to exceed the window height and use a scrollbar in the .modal-body, you can use this responsive solution. See a working demo here: http://codepen.io/dimbslmh/full/mKfCc/

function setModalMaxHeight(element) {
  this.$element     = $(element);
  this.$content     = this.$element.find('.modal-content');
  var borderWidth   = this.$content.outerHeight() - this.$content.innerHeight();
  var dialogMargin  = $(window).width() > 767 ? 60 : 20;
  var contentHeight = $(window).height() - (dialogMargin + borderWidth);
  var headerHeight  = this.$element.find('.modal-header').outerHeight() || 0;
  var footerHeight  = this.$element.find('.modal-footer').outerHeight() || 0;
  var maxHeight     = contentHeight - (headerHeight + footerHeight);

  this.$content.css({
      'overflow': 'hidden'
  });

  this.$element
    .find('.modal-body').css({
      'max-height': maxHeight,
      'overflow-y': 'auto'
  });
}

$('.modal').on('show.bs.modal', function() {
  $(this).show();
  setModalMaxHeight(this);
});

$(window).resize(function() {
  if ($('.modal.in').length != 0) {
    setModalMaxHeight($('.modal.in'));
  }
});

Problem solved with combine solution @carlos calla and @jonathan marston.

    /* Important part */
.modal-dialog{
    overflow-y: initial !important
}
.modal-body{
    max-height: calc(100vh - 200px);
    overflow-y: auto;
}

In latest bootstrap version there is a class to make modal body scrollable.

.modal-dialog-scrollable to .modal-dialog.

Bootstrap modal link for modal body scrollable content

<!-- Scrollable modal -->
<div class="modal-dialog modal-dialog-scrollable">
  ...
</div>

For Bootstrap versions >= 4.3

Bootstrap 4.3 added new built-in scroll feature to modals. This makes only the modal-body content scroll if the size of the content would otherwise make the page scroll. To use it, just add the class modal-dialog-scrollable to the same div that has the modal-dialog class.

Here is an example:

_x000D_
_x000D_
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>_x000D_
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.bundle.min.js"></script>_x000D_
<link href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" rel="stylesheet"/>_x000D_
<!-- Button trigger modal -->_x000D_
<button type="button" class="btn btn-primary" data-toggle="modal" data-target="#exampleModalScrollable">_x000D_
  Launch demo modal_x000D_
</button>_x000D_
_x000D_
<!-- Modal -->_x000D_
<div class="modal fade" id="exampleModalScrollable" tabindex="-1" role="dialog" aria-labelledby="exampleModalScrollableTitle" aria-hidden="true">_x000D_
  <div class="modal-dialog modal-dialog-scrollable" role="document">_x000D_
    <div class="modal-content">_x000D_
      <div class="modal-header">_x000D_
        <h5 class="modal-title" id="exampleModalScrollableTitle">Modal title</h5>_x000D_
        <button type="button" class="close" data-dismiss="modal" aria-label="Close">_x000D_
          <span aria-hidden="true">&times;</span>_x000D_
        </button>_x000D_
      </div>_x000D_
      <div class="modal-body">_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
        the<br>quick<br>brown<br>fox<br>_x000D_
      </div>_x000D_
      <div class="modal-footer">_x000D_
        <button type="button" class="btn btn-secondary" data-dismiss="modal">Close</button>_x000D_
        <button type="button" class="btn btn-primary">Save changes</button>_x000D_
      </div>_x000D_
    </div>_x000D_
  </div>_x000D_
</div>
_x000D_
_x000D_
_x000D_


In your modal body you have to set a height, it can be % vh or calc:

modal-body {
    height: 80vh;
    overflow-x: auto;
}

or

modal-body {
    height: calc(100vh - 5em);
    overflow-x: auto;
}

In my case look like: enter image description here


I know this is an old topic but this may help someone else.

I was able to make the body scroll by making the modal-dialog element position fixed. And since I would never know the exact height of the browser window, I took the information I was sure about, the height of the header and the footer. I was then able to make the modal-body element's top and bottom margins match those heights. This then produced the result I was looking for. I threw together a fiddle to show my work.

also, if you want a full screen dialog just un-comment the width:auto; inside the .modal-dialog.full-screen section.

https://jsfiddle.net/lot224/znrktLej/

And here is the css that I used to modify the bootstrap dialog.

.modal-dialog.full-screen {
    position:fixed;
    //width:auto;  // uncomment to make the width based on the left/right attributes.
    margin:auto;                        
    left:0px;
    right:0px;
    top:0px;
    bottom:0px;
}

.modal-dialog.full-screen .modal-content {
      position:absolute;
      left:10px;
      right:10px;
      top:10px;
      bottom:10px;
}

.modal-dialog.full-screen .modal-content .modal-header {
        height:55px;  // adjust as needed.
}

.modal-dialog.full-screen .modal-content .modal-body {
        overflow-y: auto;
          position: absolute;
          top: 0;
          bottom: 0;
        left:0;
        right:0;
          margin-top: 55px; // .modal-header height
          margin-bottom: 80px;  // .modal-footer height
}

.modal-dialog.full-screen .modal-content .modal-footer {
        height:80px;  // adjust as needed.
        position:absolute;
        bottom:0;
        left:0;
        right:0;
}