Csswg-drafts: [css-grid] Stretching image grid items in both dimensions

Created on 22 Sep 2016  Â·  60Comments  Â·  Source: w3c/csswg-drafts

I'm wondering about how we should stretch grid items that has
an intrinsic ratio, such as images. The Grid spec just refers to
css-align which says:
https://drafts.csswg.org/css-align-3/#justify-self-property
"the stretch keyword sets the box’s used size to the length necessary
to make its outer size as close to filling the alignment container
as possible while still respecting the constraints imposed by
min-height/min-width/max-height/max-width."

which I think means that having 'stretch' in both dimensions
will resize the image to fill the grid area without respecting
the image aspect ratio
. I think this is a rather unfortunate
default behavior for Grid.

Some background; this topic was discussed for flex items here:
https://lists.w3.org/Archives/Public/www-style/2012Oct/0781.html
where everyone seems to agree that respecting the ratio is desirable,
but for various flex layout specific reasons, this could not be
achieved and it was decided to ignore the ratio (IIUC).

As far as I can tell, those reasons do not apply to Grid, so I see
no reason why we can't respect the ratio when stretching grid items
in both dimensions.

I think web authors generally prefer to preserve aspect ratios,
so that's what I think we should do for grid items.

Closed Accepted by CSSWG Resolution Commenter Not Satisfied Tracked in DoC css-grid-1

Most helpful comment

"making stretch ratio-destroying and normal ratio-preserving gives the author a lot more control over the resizing behavior. And since normal is the default, specifying center or whatever in one axis gives ratio-preserving resizing by default. It's only when the author explicitly specifies stretch that the resizing starts to be ratio-destroying."

Yes, this makes sense to me having just re-read this discussion. As an author you don't expect the ratio of an image to be changed unless you specifically request that to happen.

I can see situations occurring where in development test data doesn't highlight the ratio destroying behaviour. However once the site is live and real data is added via a CMS etc. images start to look weirdly stretched. By making the default ratio preserving then in that scenario images might overflow a box or have unwanted gaps but I think that is closer to how authors expect things to behave.

All 60 comments

We were discussing that yesterday at TPAC (@fantasai, @jensimmons and me).
The conclusion we got was that the image should stretch (grow or shrink) in both directions, so we don't respect the aspect ratio unless you manually set width (e.g. width: 100%) or use a different value for alignment (like "start").

Well, actually manually setting the width won't cause the aspect ratio to be observed: it just sets the width in that dimension, and since the initial value of align-self is stretch, the other axis will continue to just stretch.

Squishing images seems a little odd, but as a starting point it's useful: the object-fit options are then only one step away, and the alignment options can be used to release the stretch in either or both axes easily.

(Plus it's consistent with how blocks behave so not surprising at all.)

@mrego I don't think that solution works, because setting width:100%
might cause the image height to overflow the grid area. So the author
needs to know upfront the relative ratio of each image vs its grid area
to know which dimension to stretch. This is very inconvenient.

My proposal doesn't have that problem.
(and if by chance an author wants a ratio-destroying stretch to fill
its area completely, they can simply use width:100%;height:100%)

@fantasai, I don't think object-fit:contain works either since
it works on the content box, not the margin box as we want for
grid items. So if you add padding/border/margin to the image it
will cause overflow. Besides, the rule becomes somewhat elaborate
and requiring that authors comes up with workarounds like that for
something that ought to be the default behavior is inconvenient.

Cover example, image proportionally sized and clipped to fit:

  img { object-fit: cover; }

Contain example, margin/border/padding fitted to grid slot and image proportionally sized into it:

  img { object-fit: contain; }

Contain example, margin/border/padding fitted to proportionally scaled-down image:

  img { justify-self: center; align-self: center; min-width: 100%; min-height: 100%; box-sizing: border-box }

Contain example with future syntax, margin/border/padding fitted to proportionally scaled-down image:

  img { foo-self: center; max-size: fill; }

img { object-fit: cover; }

As you say, this leads to the image being clipped and is thus
not a solution to the problem at hand.

img { justify-self: center; align-self: center; min-width: 100%; min-height: 100%; box-sizing: border-box }

This leads to the image overflowing when the window is very wide
or very narrow. Thus it is not a solution to the problem at hand.
(also, having a margin doesn't seem to work?)
I've made a demo here:
https://people.mozilla.org/~mpalmgren/tests/grid/grid-align-center-min-width-demo.html
(Chrome has some problems when resizing this demo)

img { foo-self: center; max-size: fill; }

Suggesting magic future tech to solve this problem isn't serious.
Besides, it still requires that you write the above workaround rule to get
what ought to be the default behavior.

img { object-fit: contain; }

I've made a demo of object-fit:contain here:
https://people.mozilla.org/~mpalmgren/tests/grid/grid-object-fit-contain-demo.html
(Firefox has some problems with this demo at the moment)

I see the following problems:

  1. Like with most object-fit values, it makes the image scale down
    inside its content box. This leads to gaps between the image
    and the border. (Try resizing the window to be very wide or
    very narrow with the demo above.) This leads to ugly layout
    if you try to use a border, box-shadow, outline etc, since users
    expects such decorations to wrap the image.
  2. Since the image doesn't fill the content box, I suspect this
    also leads to other problems... like CSSOM reporting the "wrong"
    image size, the baseline not having any relation with the actual
    image position etc. Visual effects such as opacity, filter etc,
    also applies in the gaps, i.e. "outside" the image proper. I also
    suspect min/max/-width/-height will be awkward to use when
    the image doesn't fill its content box.
  3. It requires using object-fit which I suspect is a lesser known
    property.
  4. It requires adding a rule to get the behavior that really ought
    to be the default: it's preferable if layout preserves the intrinsic
    ratio by default (which some CSSWG members seem to agree
    with in the earlier discussion about flex items).

My proposal doesn't have any of the above problems and it provides
the desired behavior by default.

To be clear, what I'm proposing is that spec says something like this
for the stretch/stretch case:

If the grid item has an intrinsic ratio, then resize the item in a ratio-preserving way
so that it fills its grid area in one axis without overflowing the other, while also
respecting its min/max size constraints.

(It's possible you might want that rule to be conditional on the element having object-fit: fill.)

It seems that the proposed text is a bit underdefined in terms of how min and max sizes interact with the "ratio-preserving way". Also I'm not sure that the current definition of min sizes in grid actually allow you to preserve the aspect ratio if the image is too big in both axes and does not have a width or height explicitly specified on the image.

(It's possible you might want that rule to be conditional on the element having object-fit: fill.)

There are some pros and cons with that, but I don't have a preference.
Either way is fine with me.

It seems that the proposed text is a bit underdefined in terms of how min and max sizes interact with the "ratio-preserving way".

Presumably using the rules in CSS2 section 10.4 that apply to this case.

Just discussed in today's teleconference (I'll try to link minutes later). The conclusion is that we can change the mapping of align-content/justify-content: normal so that normal doesn't turn into stretch for replaced elements in grid.

OK, so normal on images now means "stretch as much as possible (preserving the ratio) without overflowing the grid area" as I requested?

I really like the proposed solution to make normal behave as "stretch-with-preserved-ratio"
for grid items that has an intrinsic ratio. Thanks!
https://lists.w3.org/Archives/Public/www-style/2016Oct/0068.html

Could you please clarify which behavior you want when the *-self value
is normal in one axis and stretch in the other?

I think it should fill the grid area in the axis that has stretch and resize the item in
the other axis according to the ratio, possibly overflowing the grid area in that axis.
Is that correct?

Could you please clarify which behavior you want when the *-self value
is normal in one axis and stretch in the other?

I think it should fill the grid area in the axis that has stretch and resize the item in
the other axis according to the ratio, possibly overflowing the grid area in that axis.
Is that correct?

@fantasai / @tabatkins, I think this ^ is a question for you.

Mats' suggestion here makes sense to me, FWIW (and I can't come up with anything that's more sensible).

Checked in an attempt at fixing this per above discussion. :) Please let me know if anything is askew. I took Mats's suggestion for handling normal+stretch.

Wrt basing on object-fit... On the one hand, I think that would be very handy. On the other, no other layout mode responds to object-fit, so it might be confusing that Grid does. Note that the same effect can be had by specifying place-self: stretch in addition to object-fit: contain or whatever. I'm open to feedback on this issue, though, if anyone has a stronger opinion.

Agenda+ for certification of edits and the details wrt normal+stretch / object-fit prior to publication. Looking for review from all three implementation teams, and anyone else who wants to take a look.

Oh, just wanted to check that we're all understanding that stretch in one axis and center in another axis preserves the aspect ratio, right?

No, stretch stretches _without_ preserving the ratio, normal stretches _with_ preserved ratio.

I would summarize what we have implemented as:

  1. place-self:normal normal (default) - stretches the item with preserved intrinsic ratio to fill the grid area in one axis without overflowing the other
  2. place-self:stretch stretch - stretches the item to fill the grid area in both axis (the ratio is not preserved, unless the grid area happens to have the same ratio)
  3. Otherwise, if stretch is one of the values, stretching occurs to fill the grid area in that axis.
    If the value in the other axis is normal it is resized to preserve the ratio (may overflow in that axis)
  4. Otherwise, If normal is one of the values, stretching occurs to fill that axis, the other axis is resized to preserve the ratio (it may overflow in that axis)

IOW, the intrinsic ratio is preserved if at least one of the values is normal.

It gets more complicated when one or both axis also has min-/max-size constraints. I think we're following the CSS2 rules[1] there -- we're re-using the code that already implements that. The stretching occurs _before_ applying those rules.
[1] the "Constraint Violations" table at the end of §10.4:
https://www.w3.org/TR/CSS22/visudet.html#propdef-max-width

Also, when the track max-sizing functions are definite, clamping the item to fit the grid area (per §6.6 in CSS Grid https://drafts.csswg.org/css-grid/#min-size-auto) also affects the above rules (the "may overflow..." above should not be allowed when clamping in that axis IMO, but let's sort out the clamping effect on this in https://github.com/w3c/csswg-drafts/issues/767)

Here's a couple of testcases to illustrate our stretching behavior (I intentionally
avoided any §6.6 clamping in these tests):
Testcase for growing an image to fill a larger grid area:
https://people-mozilla.org/~mpalmgren/tests/grid/grid-item-image-grow.html
Screenshot of Firefox rendering:
https://people-mozilla.org/~mpalmgren/tests/grid/grid-item-image-grow-firefox.png

Testcase for shrinking an image to fit a smaller grid area:
https://people-mozilla.org/~mpalmgren/tests/grid/grid-item-image-shrink.html
Screenshot of Firefox rendering:
https://people-mozilla.org/~mpalmgren/tests/grid/grid-item-image-shrink-firefox.png

(You need a Nightly build for these tests to display correctly: https://nightly.mozilla.org/ )

OK, so, what I want to point out is that from an authoring point of view, the intrinsic aspect ratio should be preserved unless there's specific instructions not to. Maintaining the intrinsic aspect ratio trumps preserving the intrinsic size in any single dimension. Always. Changing a dimension effectively modifies the user-perceived "intrinsic size" in the other. Internally, we can define terms however we want, but I'm pretty sure that as far as the author is concerned, anywhere that we are failing to do this is an error.

An alignment value of center is definitely not an instruction for auto sizing in that dimension to ignore the aspect ratio. Going back to when we did not have normal... the options for alignment were stretch | start | end | center. And if one axis was stretch and the other center then the aspect ratio would have to be preserved. Only if stretch were specified in both axes would the aspect ratio be ignored: the intention of all non-stretch values of the alignment properties is to do the automatic thing that best preserves the intended presentation of the content, and would use extra space for the specified alignment. Shrink-to-fit sizing, in general, preserves the aspect ratio and Grid + Alignment should behave no different for the values that trigger it.

To address your feedback that the default behavior should be to preserve the aspect ratio, we decided to add an independent behavior for normal so that the initial behavior would not be the skewed result of stretch stretch. So normal normal is defined to be like start start except that the larger dimension is treated as stretch to contain-fit the item within the grid area. This shouldn't, however, cause the aspect ratio to be ignored by the previously-existing value combinations that were intended to honor it.

p.s. Fwiw, I'm a little concerned that the new normal complicates the field of values for the alignment properties by adding yet another sizing value, in particular one that gives a useful behavior but doesn't allow the alignment values to act upon it.

What you are suggesting is that stretch is identical to normal, except for the combination stretch/stretch which ignores the ratio.

That seems _a lot_ less useful to authors, IMHO. As you can see in the testcase:
https://people-mozilla.org/~mpalmgren/tests/grid/grid-item-image-grow.html
making stretch ratio-destroying and normal ratio-preserving gives the author _a lot_ more control over the resizing behavior. And since normal is the default, specifying center or whatever in one axis gives ratio-preserving resizing by default. It's only when the author _explicitly_ specifies stretch that the resizing starts to be ratio-destroying.
Screenshot of Firefox rendering:
https://people-mozilla.org/~mpalmgren/tests/grid/grid-item-image-grow-firefox.png

I think your suggestion is a big mistake and I would like to hear what others think about this before changing our implementation. Web developers in particular.

I agree with @MatsPalmgren .

In any case, we should not rely on object-fit to solve the<img> aspect ratio problem, because the progress of the implementation of each browser is not the same, in the CSS Grid should have a default solution.

I think this would be a regular use by developers, centering and preserving the aspect ratio(demo).

image

Equivalent to:

grid > img {
    width: 100%;
    max-height: 100%;
    object-fit: cover;  // or contain
}

And I was surprised to find that Chrome was not in the same height(line-height),inline-flex also has such a problem.

image

"making stretch ratio-destroying and normal ratio-preserving gives the author a lot more control over the resizing behavior. And since normal is the default, specifying center or whatever in one axis gives ratio-preserving resizing by default. It's only when the author explicitly specifies stretch that the resizing starts to be ratio-destroying."

Yes, this makes sense to me having just re-read this discussion. As an author you don't expect the ratio of an image to be changed unless you specifically request that to happen.

I can see situations occurring where in development test data doesn't highlight the ratio destroying behaviour. However once the site is live and real data is added via a CMS etc. images start to look weirdly stretched. By making the default ratio preserving then in that scenario images might overflow a box or have unwanted gaps but I think that is closer to how authors expect things to behave.

Just trying to clarify the issue, the part in which there is disagreement is in the difference between normal and stretch.

By default, everything is normal so aspect ratio will be always preserved in that case.

But for stretch there are 2 proposals:

  1. By @fantasai: It always preserves aspect ratio, unless it's set in both axis (align-self and justify-self).
  2. By @MatsPalmgren: It breaks aspect ratio, so it makes a difference between normal and stretch.

Example of both options

Note that if you use justify-self: normal, the behavior is going to be always 1).

Also see the difference in the example above, using the current implementation by Firefox that follows option 2):
Example of normal vs stretch

I think I support @fantasai's proposal, as I cannot think of any situation where I would want any default behavior to alter the dimensions of an image, unless I explicitly required this, using stretch on both the x and y axis.

As a side note, I would like the ability to choose a focal point on an image that would center the image if the viewport in changed in size in any way smaller than the original image, while preserving the image dimensions and cropping any aspect of the image that falls outside of the viewport. Not sure I'm explaining that too well, though. thegrid.io adversities that it does this, although i have not used it in practice yet.

But anyway, a +1 for @fantasai's suggestion :-)

I think I support @fantasai's proposal, as I cannot think of any situation where I would want any default behavior to alter the dimensions of an image...

It seems to me you have misunderstood this issue. The default value is normal which means preserving the image ratio is the default behavior, whether you want to stretch just one axis or both. What @fantasai is suggesting is to remove the possibility for you to stretch just one axis without preserving the ratio. I'm saying we should let authors do that when they explicitly ask for it by specifying (the non-default) stretch value. That gives maximum flexibility for authors to control the resizing.

As a reminder, the current CSSWG resolution is supporting my view on this:

so that is what we will ship in Gecko, unless there is a new CSSWG resolution on the matter that says otherwise.

The resolution was based on a discussion of the value specified in both dimensions.

Prior to the introduction of 'normal' as distinct from 'stretch', it seemed to me quite obvious that specifying "align-axis: center" would not cause distortion, but cause the vertical axis to trigger "shrink to fit" behavior (which preserves the aspect ratio) and use the extra space for centering. I don't see why introducing special behavior for 'normal' -- special behavior whose sole purpose was to solve the default distortion brought on by the 'stretch stretch' combined default, should cause previously-existing combinations to change behavior.

I also want to remind everyone that the purpose of the alignment properties is to manage alignment, not sizing. Stretch is a bit of an anomaly, but it does fit within the description of "specify what to do with the extra space after sizing".

The resolution was based on a discussion of the value specified in both dimensions.

Fair enough, do you mind bringing it up again in a CSSWG meeting to discuss whether all values involving stretch and normal should be ratio-preserving, with the exception of place-self: stretch stretch? Or if we should give the author the option to control the resizing behavior: stretch for ratio-destroying, normal for ratio-preserving? I'd like to know what the groups' thoughts are explicitly for these cases. (and if the former, what alternatives you recommend to authors). Thanks.

Fwiw, note that Firefox has always implemented ratio-destroying resizing for stretch (even when only specified in one axis) and so does Chrome. I assumed the CSSWG were aware of that in the last discussion. So I raised this issue in that context with the assumption that it should _stay_ ratio-destroying, i.e. "let's make normal ratio-preserving, and stretch _stay_ ratio-destroying".

Sure, I'll bring that up. It didn't even occur to me that the "shrink-to-fit" sizing of the non-stretchy alignment values would be interpreted as aspect-ratio-destroying. (The only reason that 'stretch stretch' distorts the image is because you specifically requested a size: in CSS we otherwise always preserve the aspect ratio on auto-sized images, if we can.)

Agenda+ to decide what happens if stretch or normalis combined with a positional value like start | center | end.

I like Mats proposal better.

The default is normal. I switch to stretch in the dimension where the image does not yet fill the space, and I get the result of breaking aspect ratio and having it stretch. If I want to 'fix' the aspect ratio, I can start telling the browser what I want it to do (likely with object-fit). If instead the aspect ratio was maintained, it wouldn't really be clear that the fix (to get the image to stretch to the size of the box) would be to apply stretch in the opposite dimension. That's a level of mastery unexpected. And I can't see being happy with overflow. Maybe I want the image to only stretch in one dimension — and when the grid cells change shape (responsive design), maybe I want the behavior in the other dimension to be different.

removing agenda+ because we discussed this on the last call and decided to keep the conversation going here.

Ok, so Tab and I discussed this today and came up with the following conclusions.

Things to consider:

  1. Authors expect images to maintain their aspect ratio by default.
  2. The effective “intrinsic size” of an image in a given dimension, from an author's point of view, is affected by any sizing constraints placed on it in the other axis. Nowhere in CSS is the original size of the image, independent of those constraints, the output of any automatic sizing algorithm.
  3. align-self and justify-self are defined to be alignment properties, not sizing properties.
  4. In any case, align-self and justify-self should always be able to perform their duty of assigning extra space in order to align the item within its container.

Reasoning:

  1. The previously-agreed solution of having normal do a stretch-while-preserving-aspect-ratio behavior violates classification #3 and requirement #4. (It introduces a different, non-trivial sizing behavior, and prevents the author from controlling the alignment in the axis that has leftover space.)
  2. In order to avoid these violations, normal must behave either exactly as stretch or exactly as start/end/center and not introduce a third sizing behavior. (It can however switch between the two based on some consideration.)

Proposal:

normal behaves as stretch for things without an aspect ratio, and as start for things with an aspect ratio.

  • This keeps the behavior straightforward to reason about, and maintains the aspect ratio as expected.
  • By default images will take their intrinsic size, which is their standard behavior in CSS. This can be further controlled with the sizing properties (width/height and their min/max counterparts) and object-fit as usual.
  • The common responsive-design pattern of giving a large image max-width: 100%; max-height: 100% will work as desired here - aspect ratio is maintained, and it doesn't overflow the grid area.
  • The resulting grid item can be aligned with the alignment properties as expected.

Related improvements that need to be made:

  1. Fix https://github.com/w3c/csswg-drafts/issues/794 to defer min-content/max-content sizing rules to match CSS2.1 results (as intended).
  2. Finish CSS Sizing 3 so that all of its values can be safely shipped.
  3. If possible, add a size shorthand to width/height to make it easier to specify various useful sizing behaviors such as max-size: fill, which would grant the desired sizing behavior expressed by Mats in this thread. (This is equivalent to the max-width: 100%; max-height: 100% paradigm, except it also works when margins/border/padding are specified.) https://github.com/w3c/csswg-drafts/issues/820

Is Chrome committed to making fill ratio-preserving? It appears -webkit-fill-available currently isn't. Testcase: https://bug1322780.bmoattachments.org/attachment.cgi?id=8820716

@MatsPalmgren fill is not ratio-preserving, and shouldn't be. What's the confusion here?

Well, I wanted to know to be able to properly critique your current proposal to solve this issue.
(FYI, Firefox and Chrome do in fact try to ratio-preserve images with fill in most cases:
https://people-mozilla.org/~mpalmgren/tests/img-fill.html
Anyway, I guess that's a separate issue.)

It's still not clear to me what the suggested "workaround" is to get the desired behavior. I don't see how max-width:fill; max-height:fill can fix that alone. That only works if the image intrinsic size is larger than the grid area to begin with. How do you get the image to grow to fill the grid area if it's smaller? (in a ratio-preserving way)

So, to recap, the problem at hand is that stretching images in a ratio-preserving way would fill the grid area in only one axis but (likely) not the other and that an author might want to align (start/center/end) the image in the non-filled axis.

IMHO, this seems like an edge case and a fairly minor problem.

@fantasai's proposal to solve this problem is to not stretch images at all by default. This is a very drastic and invasive change to solve such a minor problem. I think that stretching all grid items to fill their grid area by default is a fundamental part of Grid layout and any proposed solution must preserve that. To single out images to not do that is inconsistent and unexpected.

Also, I think your reasoning is flawed:

  1. align-self and justify-self are defined to be alignment properties, not sizing properties.

Well, there is a stretch keyword that is designed to do sizing and we can't remove that because Flexbox has already shipped with it. (Note also that image flex items stretch non-ratio-preserving by default, which contradicts your points 1/2.)

I agree with:

  1. In any case, align-self andjustify-self should always be able to perform their duty of assigning extra space in order to align the item within its container.

Yes, this is the problem at hand. Let's solve that in a reasonable way without destroying Grid layout completely.

Here's my proposal to solve the align-the-non-filled-axis problem:
Alternative A:
Add new syntax to align/justify-self so you can write:
align-self: normal center
align-self: normal end
Alternative B:
Add new values to align/justify-self so you can write:
align-self: normal-center
align-self: normal-end

The drawback with A is that it is two keywords and thus can't be used with the place-* shorthands. B is slightly ugly, but works as a shorthand value.

I think this solution is much more in proportion to this relatively minor problem.

So, I'd like the CSSWG to reconsider my proposal that image grid items should stretch in a ratio-preserving way by default. Authors will expect all grid items to stretch by default, and as you agree, images are expected to preserve the ratio by default. The remaining alignment problem can be solved by adding some minor CSS Box Alignment feature as I suggested above (there are likely other Align solutions too).

I also believe that this proposal has some issues:

  • Not stretching images by default when the rest of grid items stretch by default is strange.
    One option could be that normal is stretch like for the rest of items. This would break aspect-ratio but it's consistent with what already happens in Flexbox and the rest of grid items.

  • The proposed solution (max-size: 100%) only works for images bigger than the grid area, but not for stretching smaller images to fill the grid area. Maybe that's enough though.

@mrego Regarding Flexbox - see my original comment at the top. The CSSWG actually agreed at the time that it's undesirable to stretch images without preserving ratio, but there were some other issues in Flexbox that made it impossible to implement that. Those issues don't apply to Grid, which is why I think we can and should implement the optimal behavior here.

@fantasai I have already thoroughly debunked the myth that object-fit is a solution so I don't understand why you bring that up again: https://github.com/w3c/csswg-drafts/issues/523#issuecomment-249437973
Please read that comment again carefully.

Since we discussed this in Seattle I'm assuming it doesn't need to be on the agenda again so soon.

The CSSWG discussed this issue again, and stands by the conclusion in https://github.com/w3c/csswg-drafts/issues/523#issuecomment-268095890 This ensures that the alignment properties do not devolve further into sizing controls, and that behavior in grid is consistent with behavior in block layout, etc. We will however add a contain value to the width and height properties to make sure that the use cases for fitting a grid cell are easily handled.

@MatsPalmgren Wrt https://github.com/w3c/csswg-drafts/issues/523#issuecomment-271602021 I listed object-fit alongside other things, because in some cases is does solve the problem.

The CSSWG discussed this issue again, and stands by the conclusion in https://github.com/w3c/csswg-drafts/issues/523#issuecomment-268095890

That's not what the CSWG actually decided according to the IRC log at https://log.csswg.org/irc.w3.org/css/2017-01-13/#e761792

Rossen: ok, any objections to resolve on option number #1: no change to the default sizing, non replace get stretched, replaced gets start and add new sizing keywords to address the issues 11:46:21 PST

@fantasai's proposal above says "things with an aspect ratio" should use start.
As I understand it, the CSSWG resolution is that replaced elements in general (including those _without_ an intrinsic aspect ratio) should use start. Can someone who was at the meeting, and who is not fantasai, confirm that this is what the CSSWG resolved on please? (and if I misunderstood, please explain in detail what was actually decided)

We actually did mean "things with an aspect ratio" - this was very clear from the discussion in-person, but didn't make it into the minutes very well. (Not helped by our continued use of "replaced element" as the term.)

So we'll need the WG to amend the resolution to clarify that it was about things with an aspect ratio.

Additionally, we then need to verify what behavior we want for replaced elements without aspect ratios. In particular:

  1. An image with no intrinsic dimensions. I presume we want to stretch this.
  2. An image with one intrinsic dimension. We probably want to stretch the "free" axis, but do we stretch the intrinsic axis or leave it as specified and start-align it?

Fwiw, I agree that an intrinsic size should also make normal be treated as start in that dimension. I see no reason why <input> should stretch to fill its grid area by default now that images don't, for example.

Adding myself to the conversation since it seems we might change the spec again.

Also, here is a test case:

image image image
https://jsfiddle.net/1fd948nz/ (Edge, Chrome, Firefox)

Also variant https://jsfiddle.net/1fd948nz/1/
None of existing browsers would be the per-resolution expected behavior for those two tests, right?

We amended the Seattle resolution on the call today:
RESOLVED: The sentence beginning with "Items without an intrinsic ratio use," is what we as a WG wanted to use
and clarified what should happen for things without aspect ratios:
RESOLVED: replaced elements with only one intrinisic size are sized as start in that dimension and stretch in the other

Initial draft of contain is now in https://drafts.csswg.org/css-sizing/#contain-fit-sizing ; comments welcome (though please not in this thread ;)

I'm going to implement this on Chromium, just to be sure that I'm not missing anything, I understand this only applies to Grid Layout. So align-items: normal would be start or stretch depending if it's a replaced or a non-replaced element (just a summary).
However a flexbox with align-items: normal will work as stretch for both replaced and non-replaced elements.
Please let me know if I'm wrong on this assumption. Thanks.

Just a ping to allow people to review issue 1112 and give an opinion there?
(proposal to have flex and grid behave the same wrt defaults)

Wrt conclusion stated in https://github.com/w3c/csswg-drafts/issues/523#issuecomment-274928367 ... here are the minutes.

The key excerpt is that three solutions were considered for handling replaced elements:

1) Make default sizing intrinsic (could opt into contain with width/height keywords)
2) Make default sizing contain (could opt into intrinsic with width/height keywords)
3) Add sizing options to alignment (Mats's proposal in https://github.com/w3c/csswg-drafts/issues/523#issuecomment-268095890 )

The problem with option 3 is, as described in https://github.com/w3c/csswg-drafts/issues/523#issuecomment-268095890 , that what should be an alignment control devolves into a sizing control, which is objectionable.

This left two options: 1 & 2. Both allow for all of the relevant behavior to be specified, they just differ on the default. Several arguments tilted in favor of option 1:

  • François argued (during the break) that upscaling images isn't great, and it's likely people will want to place smaller images into grid areas and use alignment to control their placement.
  • There isn't a clear spec yet for how contain sizing would work. (Such a spec would have to consider not just the size of the grid area, but also the impact of min/max/specified sizing properties, so it's not hard but requires some thought.)
  • This default would be consistent with block layout, which is familiar to authors.
  • This default would be an easy place to start for common modifications like

    • simple alignment (via alignment keywords)

    • constraining the size (while preserving aspect ratio) via max-size: 100%

    • stretching to fit via stretch (and potentially using object-fit to preserve ratio)

    • fitting into the grid area contain-style via future keyword, as Mats has requested here

The WG therefore resolved on option 1, and actioned me and Tab to draft up a spec for contain as a keyword to width and height.

@MatsPalmgren Sorry for taking so long to post a proper summary. Please let us know what you think, and if this is acceptable to you. For my part, I am OK with either 1 or 2, but I would have to object to 3.

I still think image grid items should grow (or shrink) to fill their grid area while preserving their intrinsic ratio _by default_. I think width/height:contain is a fine feature to have, but it's sub-optimal since authors have to opt-in to what should be the default behavior, and it will also take a while before all UAs have implemented it. (I've already explained in a previous comment why max-size:100% and object-fit are bad solutions so I won't repeat that here.)

François argued (during the break) that upscaling images isn't great, and it's likely people will want to place smaller images into grid areas and use alignment to control their placement.

Opting out from that can be done by specifying width/height:min-content, no?

If option 2 makes image grid items grow/shrink to fill their grid area in a "contain sizing" way _by default_, that's certainly acceptable to me. I'd be interested to review a more fleshed out proposal though... in particular how it interacts with align/justify-self:stretch.

The CSS Working Group just discussed Stretching image grid items in both dimensions.

The full IRC log of that discussion
<dael> Topic: Stretching image grid items in both dimensions

<dael> Github Topic: https://github.com/w3c/csswg-drafts/issues/523#issuecomment-295075752

<dael> Rossen: I don't see fantasai yet.

<zcorpan> Github Topic: https://github.com/w3c/csswg-drafts/issues/523

<dael> Rossen: Anyone from Mozilla want to handle this? Or do we move on? Current tag is customer not satisfied.

<dael> TabAtkins: We should wait on fantasai because she might have more to the topic to explore.

The CSS Working Group just discussed Stretching image grid items in both dimensions, and agreed to the following resolutions:

  • RESOLVED: ticking with Seattle resolution: making the default instrinsic

The full IRC log of that discussion
<dael> Topic: Stretching image grid items in both dimensions

<TabAtkins> Yeah, I think that's probably the best error, zcorpan

<dael> Github topic: https://github.com/w3c/csswg-drafts/issues/523

<dael> fantasai: In seattle we had three options. One we wouldn't take b/c violates design guidelines. Other two we would have contain & intrinsic size behavior. You could opt into either. We picked intrinsic for the default. There's details in https://github.com/w3c/csswg-drafts/issues/523#issuecomment-295075752

<dael> fantasai: We closed that, but Mats disagrees with the resolution. All other issues on Grid are closed as of when we stopped accepting issues.

<dael> fantasai: This issue has a commentor disagreement so comes back to WG. Do we stick or do we change to contain sizing by default and opt-in for intrinsic via keyword-max-content or something like that.

<dael> Rossen: Opinions?

<dael> jensimmons: My opinion is I agree #3 should not be considered. I'd be okay with leave as-is, but I agree with Mats that as an author having the default be contain would be more handy and make more sense. We need both as an option and the tool to switch definitely. The default I'd lean contain.

<dael> TabAtkins: Reason why we didn't go for contain is it puts sizing control in this prop...

<dael> fantasai: TabAtkins we changed.

<dael> jensimmons: That was 3 which we agreed not to do

<dael> fantasai: Option was default is contian on all keywords, not jsut normal.

<tantek> do we have comments from anyone else who is actually implementing this besides Mats?

<tantek> reviews the issue

<dael> jensimmons: Ideally we would have tool to switch between, but the wayt he world works if we set default to contain we would get the switching tools quicker. Not certainly, but might.

<rachelandrew> I'm still keen on the resolution

<dael> Rossen: But forcing a less then optimal default as a forcing tool i sn't doing much good.

<tantek> long issue is long

<dael> jensimmons: Agreed. I still like contain as a default. That's a secondary non-heavy

<dael> TabAtkins: I'm concerned that when we have contain sizing....having different defaults based on layout of parent it makes the design confusing. It's better if we have consistancy.

<dael> jensimmons: [missed]

<Rossen> +1 to what Tab said

<dael> fantasai: Flexbox resizes to fit hte container. It does only do that with a single line. If you have wrapping it takes intrinisic

<dael> TabAtkins: It obeys constraint of flexbox and a bit of aspect ratio magic. The sizing is normal flexbox, not just images.

<dael> jensimmons: You can make the same arguments here.

<dael> TabAtkins: I disagree. Part of flex is doing this one thing. We're not adding a different way of sizing.

<dael> jensimmons: I think from author prospective there would be something similar to having default of flexbox where they are both text and image contained. If there's an image just left with intrinisic size it starts to overflow and that's not typically what authors want. Authors expect content to stay in grid cells.

<tantek> "won't spill outside" e.g. the [CSS is Awe]some problem

<dael> fantasai: Things that are smaller then grid size, contain will cause them to size up.

<dael> rachelandrew: I don't like the upscalling. I like the original resolution b/c i t's the most consistant and easier to explain. the upscalling will cause problems.

<tantek> didn't follow Rachel's comment

<gregwhitworth> +1 to TabAtkins rachelandrew

<dael> fantasai: Another thing to consider is grid is being deployed and we don't have a definition of contains that WG approved. Changing will c ause impl stress.

<dael> TabAtkins: Adding that, even if we had a contain definition, it's still transition stress because it's shipped without this. They're getting things to look well and then this change will break pages.

<dael> fantasai: I would say if it was significantly better thing to do it might be worth doing, but since we're debating and there's good for both sides, given the status we're at it makes sense to go with intrinsic a nd add the contain keyword. That would be my position.

<dael> TabAtkins: I agree.

<rachelandrew> +1 to fantasai

<dael> fantasai: I'm sympathetic, but it's not so clearly better that it's definitely the right answer.

<dael> TabAtkins: I would also threat it differently if it was obvious fix instead of possibly better.

<dael> Rossen: I'm seeing people favor option 1. Let's try for resolution.

<dael> Rossen: Unless jensimmons you feel there's something else you want to add.

<dael> jensimmons: I don't want to block it, but I think we need to define contain.

<dael> fantasai: We have a definition, we need comments. THere is a definition in sizing 4. Mostly waiting for dbaron and Mats there.

<dael> jensimmons: We should keep going forward on getting that done b/c it's desperately needed.

<dael> dbaron: Does option 1 match what impl ship today?

<dael> Rossen: I believe so.

<dael> tantek: It does.

<dael> s/tantek/ TabAtkins

<dael> jensimmons: I'm curious about that. I'm not sure what Mats impl and he did Gecko.

<dael> TabAtkins: I'd hope he's not impl something different. Even if he is, the other browsers aren't.

<dael> dbaron: I would disagree with TabAtkins' hope. But I don't know what he did.

<tantek> this issue feels like it has many aspects, are there at least some aspects we can converge on?

<dael> Rossen: Let's go back to this. Sincec Mats' isn't here I'd liket o call for consensus on #1. We'll continue working on contain.

<tantek> I'm having trouble keeping track of n resolutions over the past on this and n options

<dael> Rossen: Obj to sticking with Seattle resolution: making the default instrinsic?

<fantasai> testcase -

<jensimmons> we don’t have interop on https://jsfiddle.net/1fd948nz/1/ at the moment, fyi

<dael> RESOLVED: ticking with Seattle resolution: making the default instrinsic

Test case for the above discussion added by fantasai:
https://software.hixie.ch/utilities/js/live-dom-viewer/?saved=5143

Was just tech-editing someone's introduction to Grid Layout and noticed her description of the default alignment behavior for grid: it's stretching unless there's a specified size, in which case it's start. Having replaced elements behave as start by default matches this -- technically they don't have a “specified” size, but the intrinsic size stands in for that specified size, yielding consistent behavior for items that have a concrete size. I think this behavior makes sense and is understandable for authors.

Was this page helpful?
0 / 5 - 0 ratings