Cotten
Cotten

Reputation: 9077

maxHeight on parent and overflow-y: scroll on one of its children

It is possible to set maxHeight on a parent and have one specific child (1) take up as mush space as is available and (2) have overflow-y: scroll set on that child?

<div style="max-height: 200px">
  <div>Header that I don't want to specify any height on</div>
  <div style="max-height: auto; overflow-y: scroll">
    <div>Item no 1 in long list>
    <div>Item no 2 in long list>
    ...
  </div>
</div>

The code above and max-height: auto does not work. The closest I've come is to only have ONE child and set its max-height to inherit like so:

<div style="max-height: 200px">
  <div style="max-height: inherit; overflow-y: scroll">
    <div>Item no 1 in long list>
    <div>Item no 2 in long list>
    ...
  </div>
</div>

Which works but if I have 2 children and max-height: inherit on one of them, the total height will be too much.

Upvotes: 4

Views: 5530

Answers (2)

designcise
designcise

Reputation: 4362

Set the height property on the parent, and the max-height on the child element, like this:

<div>
  <div>Header that I don't want to specify any height on</div>
  <div style="height: 200px; background: pink;">
    <div style="max-height: 100%; overflow-y: scroll; background: yellow;">
      <div>Item no 1 in long list</div>
      <div>Item no 2 in long list</div>
    </div>
  </div>
</div>

When there are enough elements to span, as in the example, 200px on screen the child element will become scrollable, like so:

<div>
  <div>Header that I don't want to specify any height on</div>
  <div style="height: 200px; background: pink;">
    <div style="max-height: 100%; overflow-y: scroll; background: yellow;">
      <div>Item no 1 in long list</div>
      <div>Item no 2 in long list</div>
      <div>Item no 1 in long list</div>
      <div>Item no 2 in long list</div>
      <div>Item no 2 in long list</div>
      <div>Item no 1 in long list</div>
      <div>Item no 2 in long list</div>
      <div>Item no 2 in long list</div>
      <div>Item no 1 in long list</div>
      <div>Item no 2 in long list</div>
      <div>Item no 2 in long list</div>
      <div>Item no 1 in long list</div>
      <div>Item no 2 in long list</div>
    </div>
  </div>
</div>

Upvotes: 0

Paul
Paul

Reputation: 9022

You can use the flexbox option.

.container {
  display: flex;
  max-height: 100px;
  flex-direction: column;
  border: 1px solid red;
}
.header {
  background: #eee;
}

.container > div {
  flex: 0 0 auto;
}
.container > div.content {
  flex: 0 1 auto;
  overflow: auto;
}
<div class="container">
  <div class="header">Header without specific height. Always stays at top of .container, even if it is so long it uses up two lines.</div>
  <div class="content">
    <div>Item no 1 in long list</div>
    <div>Item no 2 in long list</div>
    <div>Item no 3 in long list</div>
    <div>Item no 4 in long list</div>
    <div>Item no 5 in long list</div>
    <div>Item no 6 in long list</div>
    <div>Item no 7 in long list</div>
    <div>Item no 8 in long list</div>
    <div>Item no 9 in long list</div>
    <div>Item no 10 in long list</div>
    <div>Item no 11 in long list</div>
    <div>Item no 12 in long list</div>
  </div>
</div>

By setting the container to flex display and giving it a max-height, the child elements will only use this max-height in total. By setting flex-grow to 1 (second argument in flex property), the content div will take up as much space as possible, while the header only uses as much space as necessary.

Upvotes: 11

Related Questions