- From: Dael Jackson <daelcss@gmail.com>
- Date: Mon, 24 May 2021 18:46:52 -0400
- To: www-style@w3.org
=========================================
These are the official CSSWG minutes.
Unless you're correcting the minutes,
Please respond by starting a new thread
with an appropriate subject line.
=========================================
CSS Values
----------
- RESOLVED: Work on the dynamic unit (Issues #4329 (Add vhc value)
and #6113 (Add lvh+lvw values))
- Some spec text will be created for this new unit in order to
further debate and discussion. There will need to be further
thought on interactions with things like Animations.
- A separate issue will be opened to consider if dynamic value could
be in env() instead in order to make it easier to read and to
make it not seem like a default value that authors are
frequently using.
===== FULL MEETING MINUTES ======
Agenda: https://github.com/w3c/csswg-drafts/projects/16
Scribe: TabAtkins
CSS Values 4
============
Add vhc value & Add lvh+lvw values
----------------------------------
github: https://github.com/w3c/csswg-drafts/issues/4329
github: https://github.com/w3c/csswg-drafts/issues/6113
fantasai: 6113 is a specific part of 4329
fantasai: 4329 is a long discussion about how people are really,
*really*, REALLY unhappy how on mobile the viewport units
don't represent the size of the viewport
fantasai: And the reason is that there are parts of the browser
chrome that appear and disappear dynamically as you scroll
<astearns> +1 to unhappiness
fantasai: so a bunch of UAs decided that the viewport units are the
size of the viewport with all the dynamic chrome hidden,
so a 100vh element will be partially obscured if anything
*is* showing
fantasai: Which is fine for some content, and really problematic for
others (like toolbars or headers that have to be visible
at the top/bottom of the screen)
fantasai: So we've had a discussion about what values authors need
to get the useful behavior.
fantasai: Three things are needed.
fantasai: One is size of the viewport with chrome present, so they
can size into that minimal space and never get things
overlapped.
fantasai: Another is the size without the chrome, so they can size
to the maximal space and get all the space filled when
it's all hidden.
fantasai: And finally, the dynamically-changing current size with
whatever chrome is currently showing, so it'll perfectly
fit the viewport in all cases.
fantasai: Currently we are only providing #2, and that's a problem.
iank: I thought vhc did change?
fantasai: No it's static, and also it's not defined yet because we
haven't decided on a name.
fantasai: So the issue I tagged here is someone saying "how about we
introduce lvh/lvw/etc" and that would represent the
dynamic size of the viewport.
fantasai: And then vhc would be the with-chrome static size, and
existing vh would be without-chrome static size.
<cbiesinger> what does lv stand for?
<astearns> cbiesinger: Layout Viewport height
<cbiesinger> ah
fantasai: In A Coruña we discussed this, and a suggestion was
because of the way viewport units compute, and to
emphasize the dynamic-ness, possibly exposing the dynamic
version as an env() value instead of a unit.
fantasai: And that might be less scary to implement.
fantasai: Viewport units have to be computed whenever the window
changes; making it happen on scroll would be worse.
smfr: Drill down on "dynamic change"
smfr: in iOS, when the chrome animates in, I don't think we'd
animate the unit; we'd snap it.
smfr: We have a notion of the UI being in an unstable state.
smfr: Like, position:fixed is magic that happens in the compositor.
smfr: Web content doesn't see the dynamic change, it sees things
flip, and the dynamic stuff happens behind the scenes.
fantasai: I think that's fine, as long as the layout is correct when
UI is stable.
fantasai: If the in-between state is optimized in ways that's
probably fine.
fantasai: Someday animating it might be nice and performant, but for
now it's fine. From the author's POV, it's the end states
that matter.
TabAtkins: I agree, it seems like the end states are the most
important here
emilio: Same about end states, and that Firefox Mobile uses similar
concepts. Webview only knows about the final states, not
intermediate.
emilio: Also this sounds like fullscreen, a bit. We have
display-mode MQ which tells you some stuff about the browser
screen.
emilio: Would having these units and an MQ to switch between them
work?
TabAtkins: Don't understand what you mean.
emilio: Instead of having a dynamic unit, just using the vh or vhc
based on an MQ.
fantasai: I do want to keep it open for the future to be animated.
TabAtkins: I think this supports that, if we don't do dynamic *at
all* right now.
fantasai: The computed-ness is still problematic
emilio: Computed value will *definitely* change with env(), they get
substituted at var() time
fantasai: Or we have a unit that is used-value time. I don't think
people need computed behavior here.
emilio: We have this already with percentages on a fixpos
iank: Yeah, or percent height on <html>, they dynamically change
based on chrome showing. So this concept is already exposed.
iank: So given the existence of height:100% on these elements, I
don't know if we should try to avoid exposing this by using
the MQ path.
smfr: height:100% doesn't change on iOS
emilio: It does for fixpos on Gecko, but unsure about on <html>
emilio: This is historically not the most interoperable bit of
mobile engines...
<iank> here is a testpage https://bokand.github.io/demo/urlbarsize.html
emilio: Could we spend some effort figuring out what we want the
existing primitives to do?
fantasai: Yes, but I think we also need to add the new ones.
fantasai: Either way we'll need these three kinds of values.
fantasai: Deciding which one the height:100% maps to is probably a
little more acceptable once we have the ability to change
to another one, via new units.
fantasai: But right now people are just very unhappy
chrishtr: If you set vh units it's the full size, ignoring chrome.
chrishtr: If you use vhc it subtracts chrome, so if you scroll up
you see a gap
chrishtr: lvh theoretically animates, but at least shows the right
value on stable. If you don't animate it'll show a gap
during unstable, and then snap.
fantasai: One thing you can do is make the animation always snap to
the larger size during the transition.
fantasai: It doesn't have to lag at the size you started at, could
be either; using the larger size always sounds better.
chrishtr: So when you start the animation, snap to the larger thing,
do a main-thread relayout and possible introduce jank to
the browser's interaction model.
chrishtr: Layout could take time, there could be a rAF callback...
fantasai: Right, but I think making it pretty is secondary to making
it usable at all.
chrishtr: I find the whole area pretty confusing for ideal UX.
fantasai: Example: I've got a coding tutorial page, with pretty
pictures.
fantasai: Long scrolling page.
fantasai: The elements I want to be viewport height are pictures and
code blocks, both scrollable.
fantasai: It's *really awkward* to have a scrollable block taller
than the viewport; you can't reach the scrollbars easily.
fantasai: So for usability reasons I want the code block to be at
most the height of the viewport.
fantasai: But I want the viewport size *with chrome factored in*--
the smaller size--so that scrollbars will always be
accessible, but the size of the blocks aren't constantly
changing and causing the page to shift.
fantasai: I don't want larger (overlaps) and I don't want dynamic; I
just want to make sure the entire box is visible when it's
on screen regardless, so I can access both scrollbars.
fantasai: But for the pictures, I want them to fill the viewport,
because it looks better to always fill the viewport, and
it's okay to have them be cropped a bit.
fantasai: So I want them to fill the whole viewport when the chrome
is hiding. And it's okay if the chrome comes in and
obscures a little of the top or bottom of the image.
fantasai: And similarly I don't want this to be dynamic, because
it'll cause the page to shift around, I want stable.
fantasai: And then *thirdly* I could have a sidebar that wants to
fill the height of the page, and it needs to be dynamic -
using all the height that's available when chrome is
hidden, but not cropping anything when chrome is showing.
fantasai: So we want all three behaviors; we want to make sure that
dynamic behavior is *clearly dynamic* and won't get reached
for accidentally.
chrishtr: So the sidebar example wants the dynamic example, right?
fantasai: Yeah.
TabAtkins: Have problems with the toolbars currently, even with
position:fixed. [gives example]
iank: People do dialogs, for example, that want it to fill the
viewport, but too deep in the DOM to use 100%.
iank: There's a lot of examples.
chrishtr: So a fullscreen, or fullscreen minus margin, dialog, you
probably want it to dynamically resize when you hide the
omnibox?
iank: Yes.
<plinss> https://github.com/MicrosoftEdge/MSEdgeExplainers/blob/main/VirtualKeyboardAPI/explainer.md
plinss: Microsoft is doing some virtual keyboard API (link), wanna
make sure we coordinate with this work
iank: I think this is a slightly different usecase here
iank: I don't think you want lvh to change on keyboard showing
fantasai: I agree with Ian, and think we discussed this in A Coruña
as well and came to the same conclusion.
fantasai: Wanting keyboard to change your layout is something much
less common you should opt yourself into.
iank: Especially like adding an extra keyboard above the UI keyboard
astearns: If that's the case, I'd want to see noted the reasons why
we're explicitly not doing that.
fantasai: Sure, we can add a note for that.
smfr: I think there's a diff on Android vs iOS for whether keyboard
is an overlay vs viewport shrink
smfr: There's also the visual viewport API that tells you when it
changes due to the keyboard
dlibby: There's three modes - keyboard resizes the layout viewport
(Android), keyboard resizes the visual viewport (Windows/
iOS), and virtual keyboard is third (nothing page-observable
happens besides some events firing)
dbaron: One thing to be careful about with dynamic unit is that
there's an assumption that users will make some scroll
gesture, and the toolbar will appear or disappear, and the
unit will resize things, and somehow there's magic that'll
happen that puts things in the positions they're expected to
be in.
dbaron: I think we should be careful not to assume that magic will
just work, because it's actually quite hard. When things
resize, things move.
chrishtr: You mean hard for the dev to make sure things move in
predictable ways?
dbaron: Possibly both. I think there will be unexpected results
where they use the dynamic unit, get the right size, but not
the right position.
florian: Right, and I don't think in general you can't guarantee
anyway because too much of the layout has changed.
chrishtr: What do you mean by position of content?
florian: If your page is just a linear stream of content, and you're
just using the unit for height, you can expect the position
of the resized bit to not change.
florian: But if you use the unit in width, and this changes how many
columns fit, etc, there might be arbitrary layout changes
on the page that make it undefined what it means to be
"same position"
TabAtkins: 2 items, both 100lvh
TabAtkins: both change, and bottom one ...
TabAtkins: causes unexpected position changes
smfr: Scroll anchoring can probably help there
TabAtkins: Agree
smfr: If this is a unit that changes value, we need an event to
inform you of the change. Possibly this is the resize event;
if so, we need to sync this unit changing with the resize
event firing
fantasai: Does resize change due to this?
smfr: We do fire the resize event....
smfr: It fires on inner height, which does match this I think
<dlibby> visualViewport resize does fire already, I believe
smfr: There's several things that need to be accounted for.
iank: I posted a testcase a bit ago, that should show in a
particular browser when things change based on user gesture
iank: I think resize event should fire when innerHeight changes
florian: Could this get us into loops, if the content using the
viewport units gets smaller than the viewport height?
fantasai: We can get into the details for that after we decide
whether to do this or not at all ^_^
fantasai: So we need to decide whether to add these functionalities
or not
fantasai: If so, add them as units, as env(), as something else?
astearns: Are we lacking a second stable resolution?
fantasai: We have a resolution, just not a name.
fantasai: We don't have a resolution for the dynamic version.
fantasai: We should have consistency between them.
fantasai: The proposal for dynamic uses a prefix; we might want the
small static one use a prefix as well, so Xvh rather than
vhX
chrishtr: Coming back to use-case for dynamic, a 100% height sidebar
chrishtr: Why can't that be position:fixed top/bottom:0?
iank: It can, but often people will embed sidebars deep in other
elements
iank: It'll break their site layout if it's fixpos
iank: There can be a fixpos containing block between it and the root
iank: People will often develop for desktop-first sidebars, and
handle mobile after, and their page structure is already set.
florian: Another is you might not necessarily want to be on top of
things. Think app, not document, with toolbars around a
content area - a grid with toolbars in side cells and an
overflowable center area
florian: Entire UI is supposed to fit the screen at all times. If
browser chrome pops in and out, the page's UI shifts, but
it should all always be visible.
chrishtr: So this is a site that doesn't scroll?
florian: Yes, the overall site doesn't scroll, just the regions.
jensimmons: Right, fixpos would work *only* if people were already
using abspos for their layout, not if they were using
Grid/etc.
jensimmons: Could we do a thing where we have units to measure the
constant states, and then use env() for the dynamic
things?
TabAtkins: That was fantasai's suggestion, to make it really obvious
that this is dynamic and different from the others, make
sure you really want it
chrishtr: Could one of y'all share an example that would help
explain it?
florian: [shows off a music editing app on his phone, with a toolbar
on bottom with sheet music taking up the content area]
florian: I always want the toolbar to be showing regardless of
chrome showing or not, and I don't want the toolbar to
overlap the end of the sheet music if I scroll to the
bottom.
florian: So probably the whole thing is a Grid, with a height of
env(viewport-height) or something, and the toolbar's grid
cell is fixed height, etc
fremy: Wouldn't stickypos do this, too?
sanketj: yeah, seems like stickypos too
florian: My claim isn't that you couldn't do it with stickypos or
whatever, but rather if you're thinking about your entire
layout in Grid, which you might very well do because it's
modern and convenient, you can express this all in Grid,
but then if it fails on mobile because the viewport units
don't work...
iank: Important to think about is that web devs might start by
developing with a grid, which is deep in the DOM; to size it
to the viewport they need to size all the elements in the
ancestor chain carefully. Using vh is a very simple and easy
tool there. It's a big change in thinking to instead switch to
fixpos or stickypos.
iank: So If they started with this as a grid, and were sizing to
`calc(100vh - 10px)` or whatever, it would be a big change.
TabAtkins: ...
TabAtkins: Want to make sure that we don't create cliffs
florian: And if you have stickypos, the toolbar needs to be a child
of the scroller; in Grid it's a sibling of the scroller
jensimmons: The use-cases we've seen, attaching to the bottom, is
*one* of *many* use-cases for viewport units; I've
demo'd viewport unit a bunch on stage and have never
even used this case.
jensimmons: And 100vh isn't the whole thing - 50vh items stacking is
reasonable.
chrishtr: Returning to florian's app example, the root scroller
doesn't have overflow, right?
florian: In a simplified version, yes, it's a flexbox that fills the
viewport. The content area that contains the sheet music
has overflow:auto.
chrishtr: So the interaction model they want is you can scroll the
music, nothing else; you can always tap the play button.
florian: Yeah.
chrishtr: So in this case, when it first loads on chrome mobile, the
url bar will show and then never disappear, since it only
disappears if you scroll the root scroller.
cbiesinger: I think apps sometimes do a scrollTo(1px) to cause the
URL bar to autohide
florian: That might explain why the Firefox behavior is so confusing/
uncertain
chrishtr: Yeah there's bugs around that.
chrishtr: So the site could use vhc perhaps, but if they use the
dynamic version they'll never see it adjust.
chrishtr: So I was concerned about this responding to user gestures
hiding the bar - that needs to be smooth.
chrishtr: But if it just needs to be resized to the correct new
area, I can see the use for this dynamic unit
<fremy> totally agree with cbiesinger here. if you use a fixed grid
over the screen, there is no way to auto-hide the chrome as
a user, and the problem just doesn't exist in that case
florian: So there's definitely a bunch of issues, but does it seem
reasonable to take a resolution to pursue the dynamic
thing, and possible scale it back afterwards?
astearns: And are we shooting for a unit or env() ?
iank: I'd err towards units, since that's what webdevs are already
used to.
iank: I don't find the argument about dynamic changes compelling -
the other units already dynamically change on window resize.
astearns: I think it's much more common for webdevs to resize the
tab to check it responds properly, less experience with
showing/hiding chrome on a mobile device.
fantasai: The nice thing about env() is that it's more obnoxious to
use, so it's more of an explicit decision.
fantasai: On desktop it doesn't have this dynamic problem, only on
mobile.
fantasai: So I feel like we'll get less people doing it by default.
<florian> +1 to fantasai's obnoxious-on-purpose syntax argument
astearns: People who teach CSS, do y'all have an opinion?
jensimmons: I could go both ways.
jensimmons: vh means the most pixels, vTBA means the least pixels,
and both are fixed.
jensimmons: A third unit meaning a dynamic changeable value, that
could be confusing to people.
jensimmons: But iank's point is compelling, where authors are
already used to these as units.
jensimmons: But fantasai's point about this being an env() so people
have to go look for it might make sense.
rachelandrew: My gut is a unit, same as the others, but I get how we
don't want it to be the default people use, and making
it look different can help there.
rachelandrew: So as a teacher, units are easier to teach, but I get
the reasoning behind the other.
leaverou: I think it makes more sense as a unit, due to symmetry.
leaverou: Might be easier to read as an env() because it can have a
longer name; unit names are cryptic.
leaverou: But env() names can get pretty long, especially in
calculations.
iank: There's already polyfills for this; they act like a unit
setting a css variable.
<TabAtkins> That sounds like it's similar to env(), then?
<jensimmons> I always find answering questions like this (unit vs
environmental var) are easier to understand when I code
some demos. Actually write out the code.
astearns: I propose that we resolve to work on this dynamic unit.
Get spec text together, with examples, and open separate
issues for moving it to env(), what to do with animations,
etc.
chrishtr: I think that sounds great, one more thing, I hope we can
go forward with vhc as well.
astearns: We do have a resolution for that, we just haven't gotten
it into the spec
fantasai: And haven't decided on the name. And it might make sense
to make sure these are consistent.
fantasai: Might all work best with a prefix.
fantasai: I propose to use "s" as a prefix for the small, static
size, and "d" as a prefix for dynamic one.
RESOLVED: Work on the dynamic unit.
<iank> https://www.npmjs.com/package/postcss-viewport-height-correction
is one example of substitution via postcss
chrishtr: Not only do we hear a lot that this is a problem, Chrome
is definitely interested in exploring this and working
with devs.
chrishtr: If anyone has partners who can work with us, or has more
examples, please contact me.
<fantasai> chrishtr:
https://github.com/w3c/csswg-drafts/issues/4329#issuecomment-730549876
might be worth a read
Received on Monday, 24 May 2021 22:47:34 UTC