Understanding Flexbox: Aligning and Distributing Items Easily

Imagine you're packing a suitcase for a trip. You need to organize your clothes, shoes, and other essentials so everything fits neatly and efficiently. You might stack items, spread them out, or leave space for souvenirs. Flexbox does the same thing for your website!

Flexbox (short for Flexible Box Layout) is a powerful tool in CSS that helps you design and organize the content on your webpage. It helps you arrange and align your content—whether it’s rows, columns, or grids of items. And just like a well-packed suitcase, Flexbox ensures your layout is organized, responsive, and adapts beautifully to any screen size, from phones to desktops.

Key Concept of Flexbox

  • Flex Container: The parent element that holds the flex items.

  • Flex Items: The child elements within the flex container.

Turning a container into a Flexbox is super simple. Just use the CSS property display: flex; on the container.

  • Main Axis: The main axis of a flex container is the primary axis along which flex items are laid out. Beware, it is not necessarily horizontal; it depends on the flex-direction property.

    • If flex-direction: row, the main axis is horizontal.

    • If flex-direction: column, the main axis is vertical.

  • Cross Axis: The axis perpendicular to the main axis is called the cross axis. Its direction depends on the main axis direction.

    • If the main axis is horizontal, the cross axis is vertical.

    • If the main axis is vertical, the cross axis is horizontal.

  • Main Start/End: The beginning and end points of the main axis.

  • Cross Start/End: The beginning and end points of the cross axis.

  • Main size: The main size is the size of a flex item along the main axis. It depends on the direction set by flex-direction:

    • If flex-direction is row or row-reverse, the main size is the width of the item.

    • If flex-direction is column or column-reverse, the main size is the height of the item.

  • Cross size: The cross size is the size of a flex item along the cross axis, which is perpendicular to the main axis. It depends on the direction set by flex-direction:

    • If flex-direction is row or row-reverse, the cross size is the height of the item (since the cross axis is vertical).

    • If flex-direction is column or column-reverse, the cross size is the width of the item (since the cross axis is horizontal).

Flexbox Properties for the Parent (flex container)

display

  • The flex container becomes flexible by setting the display property to flex

  • display: flex : Turns the container into a Flexbox and arranges items in a row by default. The container behaves like a block (takes up the full width of its parent).

  • display: inline-flex: Also makes the container a Flexbox, but the container behaves like an inline element (it stays in line with other elements instead of starting on a new line).

flex-direction

The flex-direction property sets how flex items are placed in the flex container defining the main axis and the direction

Values of the flex-direction property:

  • row (default): Items are placed in a row, going left to right (or right to left if the text direction is RTL).

  • row-reverse: Items are placed in a row, but in reverse order (right to left in LTR, left to right in RTL).

  • column: Items are placed in a column, going top to bottom.

  • column-reverse: Items are placed in a column, but in reverse order (bottom to top).

justify-content

The justify-content property is used to align the items horizontally along the main axis (the direction set by flex-direction) inside a Flexbox container. It controls how the extra space between or around the items is distributed.

justify-content

Values of the justify-content property:

  • flex-start (default): Aligns items to the start of the main axis. Items are grouped together at the beginning (left for row, top for column). No extra space is added between items.

  • flex-end: Aligns items to the end of the main axis. Items are grouped together at the end (right for row, bottom for column).

  • center: Aligns items to the center of the main axis. Items are grouped in the middle, with equal space on both sides of the group.

  • space-between: Distributes items evenly across the line, with space only between the items. The first item is at the start, the last item is at the end, and equal space is between all items.

  • space-evenly: Distributes items so that the space between all items and the container edges is equal. Everything is spaced perfectly evenly, including the edges.

  • space-around: The space-around value spreads the items out, giving each item some space on both sides (left and right). However, the space between items ends up being twice as much as the space at the edges of the container.

When working with alignment properties in Flexbox (like justify-content or align-items), you might encounter the safe and unsafe keywords. These keywords are designed to ensure that items align in a way that avoids layout issues or overlapping content in specific situations.

What Are safe and unsafe Values?

  • safe: Ensures that items align safely, avoiding potential problems like items overlapping or getting cut off when there's not enough space.

  • unsafe: Allows items to align even if it causes issues, like items being cut off or overflowing the container.

flex-wrap

The flex-wrap property controls whether the items in a Flexbox container should stay on one line or wrap onto multiple lines when there isn’t enough space.

flex-wrap

Values of the flex-wrap property:

  • nowrap (default): With nowrap, all the items are forced to stay on one single line, no matter how many there are. If there’s not enough space in the container the items might shrink to fit or if they can’t shrink anymore, some items might overflow (stick out of the container).

  • wrap: Allows items to wrap onto a new line if there isn’t enough space in the container. Items automatically move to the next row or column when needed.

  • wrap-reverse: Similar to wrap, but the new line appears above the first line (or to the left in a column layout), instead of below. Items still wrap onto multiple lines, but in the reverse order.

flex-flow

The flex-flow property is like a shortcut that combines two Flexbox properties:

  1. flex-direction (controls the direction of items).

  2. flex-wrap (controls whether items wrap onto new lines).

Instead of writing them separately, you can use flex-flow to set both properties in one line. The default value is row nowrap.

.flex-container {
    flex-flow: row nowrap; /**Default value **/
    flex-flow: row wrap;
    flex-flow: column unwrap;
    flex-flow: column wrap;
    flex-flow: column wrap-reverse; 
    /** many more **/
}

align-items

The align-items property is used to control how Flexbox items are positioned vertically (or along the cross axis) inside a Flexbox container.

  • The cross axis is vertical by default (when flex-direction: row) or horizontal if you change the direction to column.

  • The align-items property aligns the items (not the entire group) along this cross axis.

align-items

Values of the align-items property:

  • stretch (Default): Items stretch to fill the container along the cross axis. Each item becomes as tall (or wide, in a column layout) as the container.

  • flex-start: Aligns items to the start of the cross axis. Items are all positioned at the top (or left, in a column layout).

  • flex-end: Aligns items to the end of the cross axis. Items are all positioned at the bottom (or right, in a column layout).

  • center: Aligns items to the center of the cross axis. Items are evenly spaced vertically (or horizontally for a column layout).

  • baseline: Aligns items so that their text baselines (bottom of the text) line up. Items might appear uneven in height, but their text is aligned properly.

align-content

The align-content property is used to control the space between rows or columns in a Flexbox container that has multiple lines of items (this happens when flex-wrap is set to wrap or wrap-reverse).

align-content

It doesn’t affect individual items; instead, it adjusts how the rows/lines are spaced within the container.

  • stretch (Default): Stretches all rows to fill the container evenly. Rows are stretched apart to occupy all the available space.

  • flex-start: Stacks all rows at the top (or start) of the container. Leaves extra space at the bottom.

  • flex-end: Stacks all rows at the bottom (or end) of the container. Leaves extra space at the top.

  • center: Centers all rows in the middle of the container. Equal space at the top and bottom.

  • space-between: Spreads rows evenly, with no extra space at the top or bottom. Equal space between each row, but no gaps at the edges.

  • space-evenly: Adds equal space everywhere, including between rows and at the top/bottom of the container. The space between rows and the edges of the container is the same.

  • space-around: The outer edges of the container (before the first item and after the last item) have half the space compared to the space between the items. This creates a visually balanced layout where items are spaced evenly but with slightly smaller gaps at the ends.

Gaps

  1. Gap

    • A "gap" is the space between items in a layout. In Flexbox (and CSS Grid), you can control the space between items using the gap property.

    • It's a cleaner way to add space between items without having to mess with individual margins.

    .flex-container {
        display: flex;
        flex-wrap: wrap;
        gap: 10px;
    }
  1. row-gap

    • Row gap refers to the space between items that are in different rows (horizontal direction).

    • In a layout with multiple rows, the row gap controls how far apart the rows are from each other.

    .flex-container {
        display: flex;
        flex-wrap: wrap;
        row-gap: 10px;
    }
  1. column-gap

    • Column gap refers to the space between items that are in different columns (vertical direction).

    • In a layout with multiple columns, the column gap controls the space between the columns.

    .flex-container {
        display: flex;
        flex-wrap: wrap;
        column-gap: 10px;
    }

Flexbox Properties for the Children (flex items)

order

The order property in Flexbox controls the visual order of items inside a flex container without changing the HTML structure.

  • By default, every flex item has an order value of 0.

  • You can change the order value to any integer (positive, negative, or zero). Items with lower order values appear first.

align-self

align-self allows you to override the default alignment set by the container’s align-items property for a specific item.

  • By default, items are aligned according to the align-items property of the flex container (e.g., stretch, center, etc.).

  • align-self lets you control the alignment of individual items in the cross axis (vertical axis in a row-based layout).

  • auto: Inherits from the container's align-items

  • Other values: flex-start, flex-end, center, baseline, stretch.

flex-grow

flex-grow controls how much a flex item grows relative to other items when there’s extra space in the container.

  • If set to 0, the item won’t grow.

  • If set to a positive number, it will take up that much of the available extra space.

  • Higher numbers mean the item will grow more compared to other items

.item {
  flex-grow: 1;  /* Will grow to fill the available space */
}

flex-shrink

flex-shrink controls how much a flex item shrinks relative to other items when there’s not enough space in the container.

  • If set to 1, the item can shrink (default behavior).

  • If set to 0, the item will not shrink.

  • Higher values make the item shrink more compared to others.

  • Negative numbers are invalid.

.item {
  flex-shrink: 1;  /* Item can shrink if space is tight */
}

flex-basis

flex-basis sets the initial size of a flex item before any remaining space is distributed based on flex-grow or flex-shrink.

  • It defines the starting size of the item along the main axis (horizontal in a row layout).

  • It can be a length value (e.g., 100px) or a percentage (50%).

  • If set to auto, the item’s size will be based on its content.

.item {
  flex-basis: 200px;  /* Starts with a size of 200px before growing/shrinking */
}

flex

A shorthand property that combines flex-grow, flex-shrink, and flex-basis into one. It makes it easier to set these three properties in one line.

  • The first value is for flex-grow.

  • The second value is for flex-shrink.

  • The third value is for flex-basis.

.item {
  flex: 1 1 200px;  /* flex-grow: 1, flex-shrink: 1, flex-basis: 200px */
}

/** Above code is equivalent to the below **/
.item {
  flex-grow: 1;
  flex-shrink: 1;
  flex-basis: 200px;
}

Conclusion

Flexbox makes it easy to create layouts and align items in CSS. Some parts might seem tricky at first, but with practice, they become easy to use. Once you understand it, Flexbox helps you quickly build clean and responsive designs. Keep practicing, and you’ll get better at it!