.small-container { width: 200px; }
.small-container > div { margin: 16px; }
.border { box-shadow: 0 0 2px 2px black; }
.break-long-text {
width: 100%;
word-wrap: break-word;
overflow-wrap: break-word;
}
.grid-fr {
display: grid;
grid-template-columns: 1fr;
}
.grid-minmax {
display: grid;
grid-template-columns: minmax(120px, 1fr);
}
<div class="small-container">
<div class="grid-fr">
<div class="break-long-text border">
LOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOONG
</div>
</div>
<div class="grid-minmax">
<div class="break-long-text border">
LOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOONG
</div>
</div>
</div>
The two grids are completely the same, the only difference is the grid-template-columns
value. However, one grid respects the width of its parent (200px
) and the other ignores the width.
grid: grid-template-columns: 1fr;
=> ignores parent-width and continues until the content is filled
grid: grid-template-columns: minmax(120px, 1fr);
=> Only goes up to parent-width (200px
) and then becomes as high as necessary. However, it is still larger than the defined min-width (120px
), which is of course correct since 1fr
is larger than 120px
in this example.
Since in the end both should have the same width of 1fr
, I wonder about different results. Is this a bug or expected behavior? And why does the second grid work the way I expect it to and not the first?
So should I always use minmax
if I don't want one cell to be larger than its parent?
By default, a content-based minimum width could result in a large table or large image stretching the size of the entire content area, potentially into an overflow zone, and thereby making lines of text needlessly long and hard to read.
Select View > More. In the Ruler & Grid box, select Fixed for Grid spacing Horizontal and Grid spacing Vertical. Type the spacing you want between gridlines in Minimum spacing. Select OK.
By default, a grid item cannot be smaller than the size of its content. Grid items have an initial size of min-width: auto and min-height: auto . You can override this behavior by setting grid items to min-width: 0 , min-height: 0 or overflow with any value other than visible .
Here's the solution to the second grid.
.grid-minmax {
display: grid;
grid-template-columns: minmax(120px, 1fr);
}
This is how the browsers calculate the track size:
(200px container) - (120px nonflexible track size) + (1fr leftover space) = 200px
Using the guidance provided in the specification (see below), the behavior above is relatively simple and straightforward.
But why does the content in the first container overflow?
That's a tricky scenario and, at this point, I can see two potential paths to the answer.
There is an issue / problem / bug in the workings between:
.break-long-text {
word-wrap: break-word;
overflow-wrap: break-word;
}
and
grid-template-columns: 1fr;
I say this because when the string is broken up, the problem in the question doesn't exist. In other words, both grid containers behave the same (demo).
OR
I'm not finding the answer in the specification. I've reviewed the following sections.
fr
unitfr
Here's how the fr
unit works, in detail:
From the spec:
§ 7.2.3. Flexible Lengths: the
fr
unitA flexible length or
<flex>
is a dimension with thefr
unit, which represents a fraction of the leftover space in the grid container.Tracks sized with
fr
units are called flexible tracks as they flex in response to leftover space similar to how flex items fill space in a flex container.
Okay. So far, so good. The fr
unit in grid layout functions similarly to flex-grow
in flex layout.
Moving on with the spec...
The distribution of leftover space occurs after all non-flexible track sizing functions have reached their maximum.
The total size of such rows or columns is subtracted from the available space, yielding the leftover space, which is then divided among the flex-sized rows and columns in proportion to their flex factor.
(emphasis mine)
In other words all non-flexible track sizes (such as those based on pixels or ems) are first subtracted from the available space (200px, in this case). Whatever space remains is considered leftover space, which then gets targeted by the fr
unit.
Also, what exactly is a "track sizing function"?
Each track sizing function can be specified as a length, a percentage of the grid container’s size, a measurement of the contents occupying the column or row, or a fraction of the free space in the grid.
It can also be specified as a range using the
minmax()
notation, which can combine any of the previously mentioned mechanisms to specify separate min and max track sizing functions for the column or row.https://www.w3.org/TR/css3-grid-layout/#grid-template-rows-track-sizing-function
This explains the workings for the second grid container (with minmax()
) but not the first (with 1fr
).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With