[css-sizing] Decide how to handle min-width/min-height: auto for non-grid/flex items · Issue #2248 · w3c/csswg-drafts (original) (raw)

Comments

@dholbert

In #2230, the CSSWG resolved to make min-width/min-height: auto always compute to itself (though per #2230 (comment) , this was only with regards to flex and grid items).

What should happen for other elements? Right now the spec doesn't say (so it implies that it'd still compute to itself everywhere, which I don't think matches reality)... Previously it was defined as computing to 0 for these elements.

Suggestion: how about we say the resolved value of this auto keyword should be 0 for any non-grid/flex item. (This is basically what we've got implemented in Firefox, for non-grid/flex items -- i.e. we store auto internally in the computed style, and then we check the styles.) I'm guessing that might be what other engines do, too, though I don't know for sure (CC @rossen @cbiesinger)

@dholbert

Ah, now I see that the spec does actually say that auto computes to 0 for non-flex/grid items, in CSS-Sizing Section 3.2:

auto:
[...]
For min-width/min-height, specifies an automatic minimum size
Unless otherwise defined by the relevant layout module, this computes to zero.

I was misled/confused by the main definition of this property/value further up, in CSS-Sizing Section 3.1:

Name: | min-width, min-height
Initial: | auto
Computed value: | as specified, with lengths made absolute

I'm pretty sure the "lengths made absolute" text there does not affect "auto" (because "auto" is not a <length>, and also because we explicitly don't want to resolve it past auto on grid/flex items as discussed in #2230).

Perhaps we need some "see prose" caveat in the "Computed" line?

fantasai added a commit that referenced this issue

Jan 31, 2018

@fantasai

…auto; pending deferrment to css-sizing if #2248 goes through.

fantasai added a commit that referenced this issue

Jan 31, 2018

@fantasai

…ays, resolved value as zero where needed, per dholbert's proposal in #2248. Pending WG approval.

@dholbert

Per IRC conversation with @fantasai, how about: auto computes to auto always, but the resolved value of auto is 0 in some cases (really, most cases - it only stays "auto" for flex and grid items)

@fantasai

@dholbert was pointing out that this is much easier to implement correctly, and is simpler to specify. It also neatly solves the problem of distinguishing between min-width: 0 and min-width: auto on bock/inline replaced elements (despite returning 0 from getComputedStyle), which we need to do to implement #1722

@dholbert

A few nits on the recent spec-tweak commit for this issue:
(1) "this behaves as zero" - IMO we should avoid "behaves" since it's too vague. I think you're talking about the used value being zero here, correct?

(2) "For backwards-compatibility, the resolved value of this keyword is zero for [...] block and inline boxes" -- this isn't strictly what you want to say, because flex items are "block boxes" (if they're display:block, and the resolved value of this keyword is not zero for them.

(3) Is the word "zero" OK to use here, or should we use 0? (Since 0 is an actual valid value for these properties, whereas "zero" is a bit vaguer (and does it mean 0% vs 0 vs 0px, etc.)

Suggestion: maybe you can address all three of these by replacing this with some language like:

Unless other layout modules explicitly define another behavior,
the used and resolved value of this keyword is 0.

...and then other layout modes (grid/flex) should be sure to define that the resolved value is auto, and the used value is the special complex thing. (RE "resolved value", maybe there's a way to describe all the CSS21 box-children in a sufficiently-precise way, but I'm not thinking of it right now. Basically you want to say "everything which is not a grid item and not a flex item and not a future similar thing", which is a hard concept to encapsulate.)

@foolip

Here I am again, taking turns with @rakuco to look into a normative spec change without tests every week this quarter, to understand the challenges better.

This week I landed on 7272dc5 (a lot of commits in CSS, not randomly selected, but most other things I looked at were editorial, tested, or very new feautres)

That links here. Curiously, there isn't even a css-sizing directory in https://github.com/w3c/web-platform-tests/tree/master/css, so I'm probably missing something important about the nature of this spec. Maybe what it says can only be tested indirectly through its effect on other specs? The word "must" isn't used much, at least.

Anyway, 7272dc5 looks like something for which it would be straightforward to write a test using getComputedStyle or reftests, to see that the resolved style is one thing, but its effect is another. Presumably such tests would all pass since it's for backwards compat.

@dholbert, since you filed this issue, what do you think it'd take to determine whether this has been implemented or not, somewhere down the line? If this is actually a case that doesn't make sense to write tests for that's fine, I'd like to understand when that's the case too.

@dholbert

@dholbert, since you filed this issue, what do you think it'd take to determine whether this has been implemented or not, somewhere down the line? If

Here are the key things that'd be worth asserting, which are related to this issue (and please interpret "minWidth" as "both minWidth and minHeight, independently" below):

And then here's the subtle part...

That last point is the part that is new here as of 7272dc5. Previously, the spec required the parent container's default min-width to compute to 0, and since computed values are what's inherited, then the explicit min-width:inherit on the child would've made it inherit 0, rather than auto. So even though it was inheriting the default style from the parent, it would've ended up with a non-default style (since some processing was happening on the parent's computed value which was observable via inheritance). After 7272dc5, the "auto-->0" resolution will happen later, at resolved-value time, so the child would legitimately inherit auto (the same computed value it would've had by default anyway), and it'll return auto from getComputedStyle (since it's a flex item which preserves auto in its resolved min-width per 7272dc5.)

I suspect/expect that browsers already have the behavior that I'm proposing here, since it's strictly simpler (requiring less logic / special-casing at computation time). But I'm not sure.

@MatsPalmgren

I was just updating some code dealing with min-width:auto and I'm wondering if min-width:N% with an indefinite percentage basis counts as auto in this context?
In particular, does Automatic Minimum Size apply?
https://drafts.csswg.org/css-grid/#min-size-auto

@dholbert

I tend to think that it should apply, though I don't think any spec text says that it would. And really, CSS2 has text saying that for min-height (which in CSS2 was the only one of the min-{size} properties that could have an indefinite basis), it falls back to '0':

The percentage is calculated with respect to the height of the generated box's containing block. If the height of the containing block is not specified explicitly (i.e., it depends on content height), and this element is not absolutely positioned, the percentage value is treated as '0'

https://www.w3.org/TR/CSS22/visudet.html#propdef-min-height

I suspect "treated as '0'" there was really meant to signify "treated as the initial value". And so now, under that interpretation, this scenario should now fall back to auto-which-then-usually-gets-treated-as-0... This might want its own spec issue, though.

@fantasai

@css-meeting-bot

The Working Group just discussed [css-sizing] Decide how to handle `min-width/min-height: auto` for non-grid/flex items, and agreed to the following resolutions:

@dholbert

It's possible that implementations already match this new spec text, actually! Here's a testcase for this behavior:
https://jsfiddle.net/atz4t2tc/
(Look at the JS console for results)

In Firefox (nightly) and latest Chrome and Edge, that gives me:

gCS for initial value, on NON flex item: 0px
gCS for initial value, on flex item: auto
gCS for inherited initial value, on flex item: auto

Per the previous spec text, I was expecting that the last line there would say '0px' (since computed values are what are inherited, and per previous spec text, '0px' would be the computed value of the initial 'auto' on the parent of this flex item -- and so '0px' is what would inherit to the flex item that has explicit 'min-width:inherit'). But maybe the previous spec text's expectations about this edge-case were silly enough that nobody ever implemented them. :)

@gsnedders

That links here. Curiously, there isn't even a css-sizing directory in https://github.com/w3c/web-platform-tests/tree/master/css, so I'm probably missing something important about the nature of this spec. Maybe what it says can only be tested indirectly through its effect on other specs? The word "must" isn't used much, at least.

Basically all the css-sizing tests are within css/CSS2.

@fantasai

@dholbert Replying to #2248 (comment) ...
(1) OK, changed wording.
(2) Flex items are not block boxes... they can be block containers, but a block box is a block-level block container, and is specifically the CSS2.1 display type known as a block. :)
(3) OK, switched to ''0''.

Current prose is

For 'min-width'/'min-height', specifies an automatic minimum size. Unless otherwise defined by the relevant layout module, however, it resolves to a used value of ''0''.

Didn't add the resolved value bit into the general definition, because we do want that to remain as an exception for the CSS2.1 display types only.

fantasai added a commit that referenced this issue

Mar 4, 2018

@fantasai

@fantasai

@dholbert

This seems fine, yeah. I see you're right about flex items not being block boxes, since CSS2.1 defines block boxes as being a subcategory of block-level boxes, which are defined as boxes that "participate in a block formatting context".

One minor issue that still remains, with the "block and inline boxes" special callout -- technically, the new spec text doesn't define what to do with min-width:auto on table parts that honor min-width -- for example td, col, and caption all seem to honor min-width as shown here: https://jsfiddle.net/fnkdoeng/

Those table parts aren't block boxes, nor are they inline boxes, so the css-sizing spec doesn't currently define what the default min-width:auto keyword does there. Maybe this is something that can be defined in the css-tables-3 spec though?

@fantasai

@dholbert I think the current text in Sizing covers table parts adequately: https://drafts.csswg.org/css-sizing-3/#valdef-width-auto

For min-width/min-height, specifies an automatic minimum size. Unless otherwise defined by the relevant layout module, however, it resolves to a used value of 0.

For backwards-compatibility, the resolved value of this keyword is zero for boxes of all [CSS2] display types: block and inline boxes, inline blocks, and all the table layout boxes.

There's a separate question of how tables interpret min-width, which is up to the css-tables-3 spec, yes. IIRC, the effective minimum is the larger of the min-width and the min-content width.