Search code examples
htmlcssflexboxword-wrap

Control width of flex items arranged vertically in a flex container


I'm trying to achieve the effect where the boxes labeled "HALF", take up only 50% of the width (aka they share the first row evenly).

The base requirement is that they remain in a single container. Is this possible to achieve using flexbox?

I've tried playing around with flex-grow, flex-shrink, and flex-basis but I'm afraid I'm not understanding how to make it work, or if it's even possible, given the single container requirement.

Consider this fiddle: http://jsfiddle.net/GyXxT/270/

div {
  border: 1px solid;
}

.container {
  width: 400px;
  display: flex;
  flex-direction: column;
}
.child {
  
  height: 200px;
}
.child.half {
  flex: 1 1 10em;
  color: green;
}

.child:not(.half) {

  flex-shrink: 2;
  flex-basis: 50%;
  color: purple; 
}
<div class="container">
  <div class="child half">
    HALF
  </div>
  
  <div class="child half">
    HALF
  </div>
  
   <div class="child">
    FULL
  </div>
   <div class="child">
    FULL
  </div>
  <div class="child">
    FULL
  </div>
   <div class="child">
    FULL
  </div>
</div>


Solution

  • Instead of flex-direction: column, you can try a wrapping flexbox using flex-wrap: wrap; and you can set:

    1. flex-basis: 50% for the half width divs

    2. flex-basis: 100% for the full width divs

    See that I have thrown in box-sizing: border-box to adjust for the widths when using flex-basis.

    See demo below:

    div {
      border: 1px solid;
      box-sizing: border-box;
    }
    .container {
      width: 400px;
      display: flex;
      flex-wrap: wrap;
    }
    .child {
      height: 200px;
    }
    .child.half {
      flex-basis: 50%;
      color: green;
    }
    .child:not(.half) {
      flex-basis: 100%;
      color: purple;
    }
    <div class="container">
      <div class="child half">
        HALF
      </div>
    
      <div class="child half">
        HALF
      </div>
    
      <div class="child">
        FULL
      </div>
      <div class="child">
        FULL
      </div>
      <div class="child">
        FULL
      </div>
      <div class="child">
        FULL
      </div>
    </div>