Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[css-overscroll] Whether to move position:fixed elements during overscrolling #6299

Closed
hiikezoe opened this issue May 19, 2021 · 17 comments
Closed

Comments

@hiikezoe
Copy link

As of now, Chrome and Safari move position:fixed element during overscrolling and Firefox does (since bug 1704503) to match their behavior. But WebKit thinks it's a bug.

@hiikezoe
Copy link
Author

CC @smfr

@smfr
Copy link
Contributor

smfr commented May 20, 2021

One question is whether they move at all. The other question is whether that is detectable by the page (e.g. via getBoundingClientRect()).

@bmathwig
Copy link

Would it be possible to revive this discussion? The Microsoft Edge PWA team has a use-case where fixed position elements not being included in the overscroll effect would be beneficial.

@smfr
Copy link
Contributor

smfr commented Feb 12, 2022

We currently consider it a bug that WebKit moves fixed elements on over scrolling.

@bmathwig
Copy link

bmathwig commented Mar 7, 2022

Edge will also treat it as a bug and fix accordingly. @atanassov Can we add this as an agenda item for resolution in a future WG meeting? It might be as simple as making a note in the spec about it.

@flackr
Copy link
Contributor

flackr commented Mar 23, 2022

One question is whether they move at all.

I think that is the main issue being questioned here. My opinion is that as fixed pos elements do not move with scroll they probably also shouldn't move with overscroll. However, this could make certain kinds of affordances challenging - e.g. if the browser wants to show some information at the top in the "revealed" part of the page the fixed pos elements may occlude this.

The other question is whether that is detectable by the page (e.g. via getBoundingClientRect()).

I don't have strong opinions, though it is important that on android we stretch during overscrolling which would be even more awkward to represent. I think overscrolling could be considered purely a UA effect with no developer visible effect - this is what Chrome does right now.

@chrishtr
Copy link
Contributor

I don't have strong opinions, though it is important that on android we stretch during overscrolling which would be even more awkward to represent. I think overscrolling could be considered purely a UA effect with no developer visible effect - this is what Chrome does right now.

+1 that it shouldn't be developer-exposed.

@css-meeting-bot
Copy link
Member

The CSS Working Group just discussed [css-overscroll] Whether to move position:fixed elements during overscrolling, and agreed to the following:

  • RESOLVED: fixed-position elements whose scroller is not their containing block do not participate in overscroll
  • RESOLVED: the former statement also applies to sticky element when stuck
The full IRC log of that discussion <emeyer> Topic: [css-overscroll] Whether to move position:fixed elements during overscrolling
<emeyer> github: https://github.com//issues/6299
<emeyer> ben m: A lot of browsers had fixed element not participating in overscroll, but two browsers have the participate and WebKit still has a bug open.
<TabAtkins> q+
<smfr> q+
<flackr> q+
<emeyer> …There are use cases to do both. Can we formalize this and get it in the spec?
<emeyer> astearns: Do we have any spec text asserting one way or the other?
<emeyer> ben: I didn’t find any.
<astearns> ack TabAtkins
<emeyer> TabAtkins: I don’t have a strong opinion here, both options seem potentially reasonable. Does anyone have overscroll on non-root situations?
<emeyer> Ben: Edge and Chrome don’t have overscroll on subscrollers.
<smfr> Apple platforms have overscroll on subscrollers
<emeyer> TabAtkins: It would be nice of non-root scroller behavior was similar to fixed-position and the root scrollers.
<emeyer> s/nice of/nice if/
<astearns> ack smfr
<emeyer> smfr: Apple platforms have overscroll on subscrollers, have shipped that for many years.
<emeyer> TabAtkins: What’s the abspos behavior?
<emeyer> smfr: If a scroll isn’t a container block, then the abspos will follow, meaning overscroll will apply.
<emeyer> …I think the rest here is that on the root, abspos will dissociate from the scorlling context.
<chrishtr> q+
<emeyer> …Potentially you can get negative offsets, depending on the implementation of scrolling.
<astearns> ack flackr
<emeyer> flackr: There’s no specification of what should be done for overscroll, and it can be quite different platform to platform. Maybe we should have guidelines.
<emeyer> …It would be awkward to reflect Android behavior. I realize this would result in developer-positioned things being out of alignment from positioned content.
<TabAtkins> Agree with flackr - overscroll shouldn't be reflected into APIs (or at least, not the normal ones; maybe we could produce specialized query APIs that reflect this). It's a transitory effect and UA-specific.
<smfr> q+
<emeyer> …Anything you’re trying to keep in alignment will often get out of sync during normal scrolling.
<astearns> ack smfr
<emeyer> smfr: I agree with a lot of what was just said. We consider overscroll as an unstable state. We’re willing to let things be not entirely correct.
<emeyer> astearns: flackr was saying overscroll is a stretch, not a translation.
<emeyer> flackr: On Android, content that’s at the top is still at the top, but it’s stretched by some amount.
<emeyer> smfr: So it’s like a rubber sheet that stretches more at the edge?
<astearns> ack chrishtr
<emeyer> flackr: Yep.
<emeyer> chrishtr: I agree we shouldn’t expose thing to developers during scroll. For overscroll on non-root scrollers, I would expect the right behavior to be that overscroll only applies to content that’s scrolled.
<flackr> q+ to mention sticky can be similar when it is still free to move
<emeyer> …Abspos is different than fixedpos because they have different containing blocks.
<astearns> ack flackr
<Zakim> flackr, you wanted to mention sticky can be similar when it is still free to move
<flackr> +1
<TabAtkins> On reflection, yeah, fixposes aren't fixed wrt the root scroller, but to the viewport, which is "outside" the root scroller; this is indeed consistent with the abspos behavior for subscrollers.
<smfr> q+
<emeyer> flackr: Under certain circumstances, stickypos feels very similar to fixedpos. This is the sort of case where we might want to exclude stickpos.
<astearns> ack smfr
<emeyer> smfr: I agree sticky should have the same treatment as fixed when it responds to the viewport.
<emeyer> …Do we want authors to be able to pick how overscrolls happen?
<emeyer> flackr: Fixed will not respect overscroll, is the proposal. We could add a way to opt out of that in the future.
<TabAtkins> Agreed when stickypos is sticky to the viewport that it should *remain* sticky to the viewport when the content is overscrolling, same logic as fixpos.
<emeyer> …Not reflected in getBound and clientRect.
<iank_> i wonder if that'd break existing apps that use fixed-pos as a sidebar.
<flackr> s/flackr/chrishtr
<emeyer> smfr: On Apple platforms, overscroll affects scroll position. My concern is that things could get more complicated.
<emeyer> flackr: On Chrome, we don’t have negative scroll position.
<TabAtkins> Letting overscroll be *detectable* makes sense; don't think it needs to be detectable *by the scrollOffset*
<TabAtkins> because it'll be UA-specific to do so
<flackr> +1
<emeyer> smfr: intersection observer might also be affected.
<emeyer> astearns: Do you want to look through those things before we resolve?
<TabAtkins> fixpos *and* stickpos that stick to the viewport
<emeyer> smfr: I’m okay saying UAs can choose what to do.
<iank_> how difficult is it to add a switch for this?
<emeyer> astearns: Sounds like you are suggesting merely a note about this interaction. I was hoping we could get something like overscroll is not defined, we do resolve that fixedpos do not participate in that behavior.
<emeyer> smfr: I think we also have to specify the client coordinate APIs.
<emeyer> flackr: We have to allow platofrms to diverge on how they represent overscroll.
<emeyer> iank_: How difficult would it be to add a switch to control this behavior?
<emeyer> …with regards to the fixedpos.
<emeyer> smfr: I don’t think it would be hard but we’d have to figure out what it applies to.
<emeyer> iank_: A global flag would be easier than per-element for you?
<emeyer> smfr: Yes.
<emeyer> iank_: People use fixedpos for different things. There’s clear use cases for if you want them to move or not. I worry we’ll make some subset of people unhappy either way.
<emeyer> smfr: Fixedpos layout should be defined is that it’s relative to the viewport. If you add alternate behaviors, you have to define a lot more.
<chrishtr> The proposed note will be compatible with sidebars, since it seems best for them not to overscroll
<emeyer> iank_: We already have this complexity with abs and fixed pos. They resolve against two different rectangles.
<emeyer> smfr: We certainly have code that only applies to sticky or fixed.
<emeyer> …It’s complicated and I’d prefer not to make it more complicated.
<emeyer> iank_: I can see circumstances where you want fixed pos to move with overscroll, and others where you don’t.
<emeyer> flMy high-level view is that things that move with scroll should be affected by overscroll.
<emeyer> (previous was from flackr)
<emeyer> astearns: We have WebKit considering it a bug that these things do move, do we have bugs on Firefox complaining that they don’t?
<emeyer> emilio: We used to have them moved, and we changed so they didn’t.
<emeyer> astearns: It sound like the only thing we can come to consensus on today is a non-normative note that browsers _may_ do what they like. I’m reluctant to do something that weak.
<chrishtr> q+
<emeyer> TabAtkins: I don’t think we have to be that weak. Simon’s asking for us to specify the non-moving behavior. Are there strong objections to us doing that, Simon?
<emeyer> smfr: Seems like it’s adding a non-consistency to the specs.
<emilio> q+
<emeyer> TabAtkins: We certainly wouldn’t be getting worse, since there’s no spec text right now.
<emeyer> astearns: I’d be reluctant to resolve without having gone through all the JS APIs. We don’t want to make things incoherent.
<astearns> ack chrishtr
<emeyer> chrishtr: Non-nomative note that says SHOULD as opposed to MAY?
<astearns> ack emeyer
<astearns> ack emilio
<emeyer> emilio: QA filed a bug mentioning things didn’t match between browsers.
<emeyer> …We certainly haven’t recieved complaints about the Chrome behavior.
<emeyer> astearns: Could do a non-normative SHOULD note.
<emeyer> fremy: Not sure of the point of making it non-normative if it says SHOULD.
<emeyer> s/fremy/fantasai/
<fremy> scribenick: fremy
<bmathwig> +1 to that
<fremy> chrishtr: when we make it non-normative, the practical result is that chromium considers changing the behavior
<fremy> astearns: the proposal is thus to add a normative should for this
<fremy> astearns: would anyone object to this?
<fremy> RESOLVED: fixed-position elements whose scroller is not their containing block do not participate in overscroll
<flackr> +1 support for sticky
<fremy> TabAtkins: also sticky
<fremy> astearns: any objection to adding sticky?
<fremy> RESOLVED: the former statement also applies to sticky element when stuck
<astearns> github: https://github.com//issues/4549#issuecomment-1067389586
<dbaron> no, you want to fix the github back to the original
<astearns> github: https://github.com//issues/6299

@chrishtr
Copy link
Contributor

Re JS APIs: currently, Gecko and Chromium's implementations of overscroll do not affect any developer APIS, and are purely a "UA affordance" in that sense.

Overscroll implementations differ between platforms (e.g. I know of at least 3 approaches: rubber-band/translate [iOS/Mac], stretch [Android current], glow [old Android]), and it's good to allow UAs to try out different affordances.

Pull-to-refresh was a use case @smfr mentioned as being helped by the current negative scroll offfset approach in Safari.

Therefore, I propose:

  • Specify that overscroll does not affect any JS APIs
  • Solve pull-to-refresh (which I agree is worth solving) with other APIs that will be independent of the approach to overscroll, and work on platforms without overscroll affordances

@flackr
Copy link
Contributor

flackr commented Mar 23, 2022

  • Solve pull-to-refresh (which I agree is worth solving) with other APIs that will be independent of the approach to overscroll, and work on platforms without overscroll affordances

And platforms with different overscroll affordances which are not translations (i.e. at this point, Android)

@smfr
Copy link
Contributor

smfr commented Mar 24, 2022

So if we specify that overscroll does not affect any JS APIs, then it becomes impossible for a page to use JS to position an element with fixed-like behavior during overscroll. Is that OK?

@chrishtr
Copy link
Contributor

So if we specify that overscroll does not affect any JS APIs, then it becomes impossible for a page to use JS to position an element with fixed-like behavior during overscroll. Is that OK?

I think that's ok in general.

If there are specific compelling use cases that are not yet solved, we can solve them with new CSS properties or other APIs. Do you have one in mind other than pull-to-refresh?

@jonjohnjohnson
Copy link

What about #4011 & #3801?

@chrishtr
Copy link
Contributor

What about #4011 & #3801?

#4011 ("Should overscroll ("rubber-banding") be observable?") would be closed as WontFix if we go with the approach I'm suggesting.

For #3801 ("Content has no way of understanding whether it is being overscrolled or whether scroll has ended"), I'm suggesting we add APIs focused on common use cases, such as pull-to-refresh, and solve them holistically, taking into account all relevant factors, including overscroll.

@brunostasse
Copy link

brunostasse commented May 26, 2022

If I may comment from a developer perspective on the effect of overscroll on JS APIs:

Scroll position during overscroll or intersection observer used to detect overscroll in Safari is currently used for a variety of features and effects: custom pull-to-refresh, growing page title, growing hero image, revealing hidden elements with transitions or triggering animations elsewhere past a certain threshold, keeping parallax effects going during overscroll and not stopping abruptly, animating text features, etc.

I have myself implemented such features, and have had to disable overscroll (with overscroll-behavior: none) in Firefox on macOS because it wasn't detectable, which is a shame. Removing it from Safari would be likely to break a large number of websites/web apps and make all these features and effects impossible. A new dedicated "pull-to-refresh" API might help recreate some of these, but probably not all.

Safari's overscroll behaviour is a translation that is in the continuity of the scroll, so it is quite natural that it is treated as such and reflected in all scroll related APIs. I would also expect it to work in combination with the upcoming Scroll-linked Animation CSS and JS APIs. It wouldn't make sense for a scroll-based animation to stop abruptly when reaching the end of the scroll container, while the content keeps moving during overscroll.

I would argue that any visual change to elements, whether it is a translation transformation (rubberbanding in Safari) or a skew transformation (stretching on Android) should be detectable and reflected in JS and CSS APIs. If an element can be moved, possibly over another one, or cut by an overflow, it needs to be known by developer code, or it might break. This is true for scroll positions, intersection observer, boundingClientRect, scroll-linked animations, etc.

Even though these behaviours vary between platforms/browsers, wouldn't it be possible to write specifications for them, so that interactions with the different APIs are defined? This would allow to have interoperability between the browsers implementing them.

Hoping that helps.

@atomiks
Copy link

atomiks commented Jun 25, 2022

This is a nice change 👍

However, I think this should also apply to position: sticky. In Chrome Canary, the "fixed" elements on this page still move with the page scroll as they use position: sticky.

@flackr
Copy link
Contributor

flackr commented Jun 16, 2023

However, I think this should also apply to position: sticky. In Chrome Canary, the "fixed" elements on this page still move with the page scroll as they use position: sticky.

This was part of the resolution #6299 (comment), it's just not fully implemented yet. As long as the containing block doesn't prevent it sticky elements should be free to shift with the overscroll as well.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests