Description
It would be useful to either:
- have the ability to enable margin-collapse on the root of a block formatting context (BFC); or
- have a new type of context that's just like BFC except that it doesn't suppress margin-collapse on the root (and have a new
display
value that creates such a context, much likeflow-root
does with BFC).
Here is the problem that this would solve:
In prose/WYSIWYG situations—where the developer isn't in control of the order that various elements end up appearing in—some kind of "clearfix" is often needed to prevent certain elements from "overlapping" a floated neighbor. A typical example would be when a left-floated image ends up next to a ul
whose bullets are styled as absolute-positioned ::before
pseudo-elements on the li
s.
The modern way to implement the "clearfix" is to give display: flow-root
to the elements that create a problem if adjacent to a float. Doing so, however, creates a new BFC on the elements in question, thereby suppressing margin-collapse on them. This is a problem because margin-collapse is extremely useful for maintaining consistent vertical rhythm in these WYSIWYG contexts.
One can more or less work around this by "undoing" the outward-facing margins at the extremities of the flow-root
element's interior, so that only the vertical-margins of the element itself remain:
ul {
display: flow-root;
}
ul > :first-child,
ul > :first-child > :first-child,
ul > :first-child > :first-child > :first-child {
margin-top: 0;
}
ul > :last-child,
ul > :last-child > :last-child,
ul > :last-child > :last-child > :last-child {
margin-bottom: 0;
}
but it's ugly and, worse, unreliable (it only works for however many layers of > :first-child
/> :last-child
you include).
In short, the suppression of margin-collapse prevents display: flow-root
from being a satisfactory "clearfix" solution in many situations. To my mind, what's missing is the ability to opt in to margin-collapse for a BFC (or to create a new type of context just like BFC but without the suppression of margin-collapse on the root).