Card group

Trial
Free!
Basic tier
(most popular)
$10.00
Advanced tier
(only for enterprise-level professionals)
$6,000.00

Now let’s say we want to group a bunch of cards into a single Card Group component. There are two tricky requirements to consider here:

  1. We want each card to have equal width, even if one card contains more content than another card.
  2. We want the height of all the card descriptions to be equal. Again, this should hold true even if one card’s description is longer than another card.

Without flexbox, you would probably have to resort to using atable element to meet these requirements. Or possibly you could absolutely position all of the elements and use a combination of percentage-based dimensions, pixel-based dimensions, and the calc function. That sounds pretty complex!

With flexbox, the solution becomes a bit more elegant, but it does require us to use a new flexbox property. Unlike the ones we’ve used so far, this property is applied to the children, not the container.

We’ll set flex: 1 1 0% on each card, to make their widths equal within the container. This property is a short-hand for setting three specific flexbox properties:

CSS
.cardGroup {
  /**
   * Lay out the children of this container with
   * flexbox, which is horizontal by default.
   */
  display: flex;

  border: 1px solid #CAD0D2;
  border-radius: 4px;
  overflow: hidden;
}

  .cardGroup__card {
    /**
     * The flex property is a short-hand for setting
     * the flex-grow, flex-shrink, and flex-basis
     * properties. These properties control how the
     * element resizes to fill its container.
     *
     * We'll set flex-grow to 1 so that it will
     * expand to fill its container. (The default
     * default value is 0.)
     *
     * We'll also set flex-shrink to 1 so that the
     * element will shrink as its container gets
     * smaller. (The default value is 1.)
     *
     * Last, we set flex-basis to 0 so that its
     * size is solely determined by the size of
     * the container. (The default value
     * is auto, which would cause the content's
     * size to also be a factor in this calculation.)
     *
     * The net result of these properties is that the
     * element is a fluid size, and will expand and
     * shrink with its container and siblings, but
     * they will all have the same size, even if they
     * have different amounts of content.
     *
     * NOTE: IE11 ignores flex short-hand declarations
     * with unitless flex-basis values. So we have to
     * use 0% instead of 0 as a workaround. You can
     * find more info at:
     * github.com/philipwalton/flexbugs.
     */
    flex: 1 1 0%;

    border: none;
    border-radius: 0;
  }

  .cardGroup__card + .cardGroup__card {
    border-left: 1px solid #D7DBDD;
  }

  .cardGroup__cardDescription {
    /**
     * We're doing almost the exact same thing here as
     * we did above. The difference is that its
     * flex-basis is auto, so now the size of its content
     * will affect how large it is.
     */
    flex: 1 1 auto;
  }
HTML
<div class="cardGroup">
  <div class="card cardGroup__card">
    <div class="card__description cardGroup__cardDescription">
      <div class="icon fa fa-thumbs-o-up card__descriptionIcon"></div>
      <div class="card__descriptionText">Trial</div>
    </div>
    <div class="card__price">Free!</div>
  </div>
  <div class="card cardGroup__card">
    <div class="card__description cardGroup__cardDescription">
      <div class="icon fa fa-trophy card__descriptionIcon"></div>
      <div class="card__descriptionText">Basic tier<br/>(most popular)</div>
    </div>
    <div class="card__price">$10.00</div>
  </div>
  <div class="card cardGroup__card">
    <div class="card__description cardGroup__cardDescription">
      <div class="icon fa fa-bolt card__descriptionIcon"></div>
      <div class="card__descriptionText">Advanced tier<br/>(only for enterprise-level professionals)</div>
    </div>
    <div class="card__price">$6,000.00</div>
  </div>
</div>
More stuff
If you like my writing you can find more at my blog, cenizal.com. Right now I'm mostly writing about people management, software engineering, and interaction design.