flex child is growing out of parent

HtmlCssFlexbox

Html Problem Overview


How to force the green boxes to be contained in the red one without setting a static height value and no absolute position?

I want to shrink the content to fit into the parent.

The content (video in this case) is allowed to shrink and scrollbars are allowed.

.my-box {
  height: 300px;
  width: 600px;
  background: red;
  padding: 5px;
}
.content-box {
  background: blue;
}
.col {
  display: flex;
  flex-direction: column;
  justify-content: space-between
}
.box-shrink {
  flex: 0 1 auto;
  background: green;
  padding: 5px;
  margin: 5px;
}
.box-grow {
  flex: 1 0 auto;
  background: green;
  padding: 5px;
  margin: 5px;
}
video {
  max-height: 100%;
  max-width: 100%;
  margin: auto;
  display: block;
}

<div class="my-box col">
  <div class="box-shrink">
    small sized static content
  </div>
  <div class="content-box box-grow">
    <video controls>
      <source src="http://techslides.com/demos/sample-videos/small.webm" type="video/webm">
    </video>
  </div>
  <div class="box-shrink">
    small sized static content
  </div>
</div>

Html Solutions


Solution 1 - Html

Solution #1 - Without Scroll

Instead of flex: 1 0 auto on the video container, just use flex: 1. This sizes the item based on available space, not the intrinsic height of the content.

Then, because flex items cannot be smaller than the size of their content – min-height: auto is the default – add min-height: 0 to allow the item to shrink to fit inside the container.

.box-grow {
  flex: 1; /* formerly flex: 1 0 auto; */
  background: green;
  padding: 5px;
  margin: 5px;
  min-height: 0; /* new */
}

.my-box {
  height: 300px;
  width: 600px;
  background: red;
  padding: 5px;
}
.content-box {
  background: blue;
}
.col {
  display: flex;
  flex-direction: column;
  justify-content: space-between
}
.box-shrink {
  flex: 0 1 auto;
  background: green;
  padding: 5px;
  margin: 5px;
}
.box-grow {
  flex: 1; /* formerly flex: 1 0 auto; */
  background: green;
  padding: 5px;
  margin: 5px;
  min-height: 0; /* new */
}
video {
  max-height: 100%;
  max-width: 100%;
  margin: auto;
  display: block;
}

<div class="my-box col">
  <div class="box-shrink">
    small sized static content
  </div>
  <div class="content-box box-grow">
    <video controls>
      <source src="http://techslides.com/demos/sample-videos/small.webm" type="video/webm">
    </video>
  </div>
  <div class="box-shrink">
    small sized static content
  </div>
</div>

Solution #2 - With Scroll

Alternatively, give the video container overflow: auto, which does the same as above, except it keeps the video full-width. You need to enable flex-shrink for this to work.

.box-grow {
  flex: 1 1 auto; /* formerly flex: 1 0 auto; */
  background: green;
  padding: 5px;
  margin: 5px;
  overflow: auto; /* new */
}

.my-box {
  height: 300px;
  width: 600px;
  background: red;
  padding: 5px;
}
.content-box {
  background: blue;
}
.col {
  display: flex;
  flex-direction: column;
  justify-content: space-between
}
.box-shrink {
  flex: 0 1 auto;
  background: green;
  padding: 5px;
  margin: 5px;
}
.box-grow {
  flex: 1 1 auto; /* formerly flex: 1 0 auto; */
  background: green;
  padding: 5px;
  margin: 5px;
  overflow: auto; /* new */
}
video {
  max-height: 100%;
  max-width: 100%;
  margin: auto;
  display: block;
}

<div class="my-box col">
  <div class="box-shrink">
    small sized static content
  </div>
  <div class="content-box box-grow">
    <video controls>
      <source src="http://techslides.com/demos/sample-videos/small.webm" type="video/webm">
    </video>
  </div>
  <div class="box-shrink">
    small sized static content
  </div>
</div>

Both solutions are explained in more detail here:

Solution 2 - Html

As you said, the content (a video in this case) is allowed to shrink and scrollbars are allowed. How about putting overflow:auto; on the .box-grow class and set flex-shrink: 1; like, flex: 1 1 auto; Or if you set the flex: 1 1 100%; the video will fit center on the .box-grow class also overflow:auto will be needed.

.my-box {
    height: 300px;
    width: 600px;
    background: red;
    padding: 5px;
}

.content-box {
    background: blue;
            
}

.col {
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    
}

.box-shrink {
    flex: 0 1 auto;
    background: green;
    padding: 5px;
    margin: 5px;
}

.box-grow {
    flex: 1 1 auto;  /* Set the shrik 1 which is by default */
    background: green;
    padding: 5px;
    margin: 5px; 
    overflow:auto; /* Overflow will be needed if you set flex:1 1 100%*/
}

video {
    max-height: 100%;
    max-width: 100%;
    margin: auto;
    display: block;
}

<div class="my-box col">
    <div class="box-shrink">
        small sized static content
    </div>
    <div class="content-box box-grow">
        <video controls>
            <source src="http://techslides.com/demos/sample-videos/small.webm" type="video/webm">
        </video>
    </div>
    <div class="box-shrink">
        small sized static content
    </div>
</div>

Solution 3 - Html

In my situation I had a max-width on the child and then deep inside the leaf node had width: 100%, somehow this was taking the outer browser width rather than the inner width

the solution was to give max-width to the intermediate flex child also.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionExlordView Question on Stackoverflow
Solution 1 - HtmlMichael BenjaminView Answer on Stackoverflow
Solution 2 - HtmlBaezid MostafaView Answer on Stackoverflow
Solution 3 - HtmlOZZIEView Answer on Stackoverflow