HTML was once exciting before everyone found all the bugs. So Flex is finally something fascinating and new. Something new where things just might go wrong.
Meouzer
Meouzer is fascinated by bugs. Especially the IE11 bugs concerning wrap-reverse that are still in place after years. For that reason we suggest you do not use IE11 for the demo in order not to get the wrong ideas. Edge, Firefox, Chrome, and Opera are OK.
Flex is a two dimensional layout design based in CSS that positions flex-items within a flex-box. The flex-items are laid out either in rows or columns with wrapping available to prevent overflow. Each row or column is a flex-strip. Every flex-strip is assigned an alignment-box/confinement-box that the items are free to move and stretch around in both vertically and horizontally. In a special circumstance, the alignment boxes themselves can be moved about in a small number of preset ways.
Every flex-box and in fact every alignment-box has a main-axis and a cross-axis to specify position.
However, position is not specified by coordinates, which sounds more strange than it actually is. Flex provides a spectrum of numberless positioning presets.
With row layouts, the main-axis is horizontal, but with column layouts it is vertical. Movement of flex-items is most restricted along the main axis since flex-items can move only so far until they bump into another flex-item in the same flex-strip. Along the cross-axis there is more freedom of movement since there is nothing in the way inside its alignment-box.
Along both the main-axis and cross-axis there are preset means of positioning that are esthetically pleasing. By adjusting margins of flex-items, you have more fine-grained control.
To position with respect to the main-axis use the css style attribute justify-content. To position with respect to the cross-axis use align-items. They work across all alignment boxes in parallel. So if the flex-items in one alignment-box are centered with respect to the cross axis, so are the flex-items in any other alignment-box. If the flex-items in one alignment box are spaced out evenly along the main-axis, so are the flex-items in any other alignment-box.
Flex-items are numbered by the order in which they are entered into the flex-box in HTML code. The first flex-box will be closest to the origin of the two axes. The flex-strips are also numbered. The first flex-strip is the strip containing the first flex-item and will be the flex-strip closest to the origin.
Flex-items always flow along the main axis, i.e., flex-items increase in numbering as you move along the main axis.
Flex-strips flow along the cross axis, i.e., flex-strip numbers increase as you move along in the direction of the cross axis.
Setting the flex-box's css style attribute flex-wrap to wrap-reverse will flip the direction of the cross axis to let the flex-strips flow in the direction opposite to what they otherwise would.
To make an element a flex-box, assign its css style property display a value of "flex" or "inline-flex". Its items or flex-items are simply its direct children.
If a text-node is a direct child of a flex-box, the text-node is a flex-item.
A flex-box may have one of four possible layouts.
See the diagrams below. The yellow box is a flex box with six flex-items. The row and row-reverse layouts each depict two flex-strips (rows). The column and column-reverse layouts each depict two flex-strips (columns).
The numeric labeling indicates the order in which the items were added to the flex-box in HTML code.
Once the axes rules have been read, go over the top row of diagrams very carefully. Based on flex-item numbering, the main-axis is always easy to determine: as mentioned previously, flex-items flow along the main axis. Then the cross axis will be perpendicular to the main axis and point right or down. Once the top row is understood, go over the bottom row where the cross axis has been flipped (so now points left or up). Another way to determine the cross axis is to observe how the flex-strips flow: As mentioned previously, flex-strips flow along the cross-axis.
To describe placement within the flexbox we need a pair of axes relative to which flex items are placed. The following discussion describes how it's done.
It's very convent to take our axes as finite directional lines with a start and an end. Their origin is always at one of the corners of the flexbox. In the diagrams above the axes are supposed to meet precisely at a corner of the flex-box. We simply had to move them so they could be seen.
Suppose a rectangle has sides parallel to the axes. The two sides parallel to the cross-axis are called main-start and main-end. main-end is the one that is furthest along in the direction of the main axis. The two sides parallel to the main-axis are cross-start and cross-end. cross-end is the one that is furthers along in the direction of the cross axis.
The flex-box has four css style properties related to the axes: flex-direction, justify-content, and align-items.
Axes | flex‑direction |
|
---|---|---|
flex-wrap |
|
|
Positioning | justify‑content | Positions flex-items along the main-axis (in their containment box) |
align‑items | Positions flex-items along the cross-axis (in their containment box) |
flex-direction specifies the type of layout. It has the four possible values
Refer to the diagrams in lesson three.
- | |
Explore flex-direction | Go through all four possibilities for flex-direction in the interactive demo. |
Once you are clear, repeatedly quiz/randomize and determine what flex-direction is. |
justify-content positions flex-strips along the main axis. It has five possible values.
- | |
Explore justify-content | Go through all five possibilities for justify-content in the interactive demo. |
Once you are clear, repeatedly quiz/randomize and determine what justify-content is. |
align-items aligns flex-items along the cross-axis. It has four possible values.
- | |
Explore align-items | Go through all four possibilities for align-items in the interactive demo |
Once you are clear, repeatedly randomize and determine what align-items is. |
A flex-item will never stretch past its cross-size and max-cross size. For example if the cross-axis is horizontal, width is 200px and max-width is 300px, the flex-item's stretched length will be 200px. If the width wasn't set, then the flex-item's stretched length will be 300px.
Each flex item may set its own align-self property to override the alignment along the cross axis specified by the align-items property. In the demo, as stands for align-self.
The values for align-self follow, and they are the same as the values for align-items.
A flex-box with three items set its align-items property to flex-end However, the third and somewhat pink like box decided to overrule align-items and set itself at the start of the cross-axis by setting its align-self property to flex-start.
So far we have dealt with only one flex strip, but with wrapping there could be more. Each flex-strip gets it's own alignment box, which with respect to alignment takes place. align-self, self-align and even justify-content work with respect to the flex-strip's alignment box. The cross-sizes of the alignment boxes are computed in advance and don't depend upon any css style properties, including justify-content and align-items. Just like the flex-box itself, each alignment box has its own cross-start and cross-end.
Enlarging a flex strip by one extra share of the total amount of free space produces its alignment area.
- A flex box is 200px tall with a flex-direction of row or row-reverse. It has three flex-strips of heights 36px, 60px and 80px with center positioning along the cross axis, what are the sizes of the individual free spaces?
Solution Subtracting the total three sizes from 200px gives a total free space of 24px. Draw a picture and you will see two free spaces get 1/2-share and two free spaces get 1-share for a total of 3-shares = 24px. Each share must then be 8px. Whence, the individual free sizes are 4px, 8px, 8px, and 4px. ■
Remember that normally the cross-axis points down or to the right. Setting flex-wrap to wrap-reverse flips the direction of the cross-axis. Flex strips always flow along the cross axis.
In each of the following exercises start by refreshing the web page an choosing five flex items.
- | Choose 5 items, hide the axes. | Go through all four possibilities for flex-direction, but each time switch between wrap and wrap-reverse to observe how the cross axis flips direction by examining the item numbering in the flex strips. |
OK! Squishing is more dramatic.
With overflow along the main-axis, Flex in an attempt to prevent overflow will squish, if possible, each flex-item. Flex will ignore widths/heights set on the flex-items and squish them anyway. However, flex will respect min-width/min-heights.
Flex will squish up to but not past the min-width or min-height as the case may be.
- |
Set flex‑wrap to nowrap |
Toggle between three and five flex-items |
With row or row-reverse, the flex-items get squished horizontally along the main-axis.
With column or column-reverse, the flex-items get squished vertically along the main-axis. |
A flex-area is the smallest cross sectional area of the flex-box that contains a flex-strip. If a flex-box sets its align-content property, then the alignment-boxes are the flex-areas: they aren't as described previously. The items in a flex-strip are free to wiggle around in the flex-area as determined by justify-content, align-content, self-align. Of course we now that justify-content, align-content produces parallel wiggling across all flex-areas/alignment-boxes.
Since the cross-size of the alignment-box is smaller than it was before, there is less wiggling room along the cross-axis of any flex-area. In fact the longest flex-item within any given flex-area can't move along the cross-axis at all. It is already at cross-start so setting align-items to start does nothing. It is already centered in the flex-area so setting align-items to center does nothing. It is already at cross-end so setting align-items to end does nothing. It is already stretched across the flex-area so setting align-items to stretch does nothing.
OK! Why are the flex-items in each flex-area above positioned differently? Aren't they supposed to be in positioned in parallel? Well the second and third WERE just like the first, but their purple and green flex-items set their self-align properties individually. Can you tell to what? (to center and to end respectively).
The programming team, meouzer and the cows, decided not to include align-content in the demo because someone will set a value for it and then wonder why the rest of the demo doesn't work as expected.
align-content aligns flex-strips along the cross-axis. It has five possible values.
These are the same values that justify-content has. How align-content works on flex-areas along the cross-axis is the same way that justify-content acts on flex-items along the main-axis.
-Chose 5 items and set flex-wrap to wrap or wrap-reverse. Set align-content to any of its values. Then go through all the possibilities for align-items. You will see very limited movement because the flex-areas are so restricted. Also, pick a flex-item and go through the values for self-align.