Jump to content
Search Community

Pinning a Contained ScrollTrigger

jh3y test
Moderator Tag

Go to solution Solved by GreenSock,

Recommended Posts

Howdy Y'all! 👋

 

This may be the way to do it or there may be a cleaner way 😅

 

But, if you want to `pin` something inside a `scroller` element, is this the way to do it?

 

const TRIGGER = ScrollTrigger.create({
  horizontal: false,
  trigger: '.scroller',
  pin: '.panel',
  end: '+=2000',                          
  scroller: '.scroller',
  onUpdate: self => {
    // Doing anything here for hypotheticals 😅
    gsap.set('.panel', {
      rotate: self.progress * 360,
    })
  },
})

The "trick" I'm using is that if you use CSS `transform` on the container, that will scope `fixed` to the container. Or is there another API way of doing this?

See the Pen eYgJJQg by jh3y (@jh3y) on CodePen

Link to comment
Share on other sites

15 minutes ago, mikel said:

Hey @jh3y,

 

Could this be an alternative?

 

 

 

 

Happy scrolling ...

Mikel

 

Hey 👋

 

Yeah, that's almost the same approach which confirms it to me 👍

`position: relative` has the same effect as applying a `transform` on the container for `fixed` children.

 

That demo you provided works with the `padding` removed and `height: 100%` set on the `#container`. In its current form, the green box will scroll up towards the end of the container 👍

 

But, thank you, this confirmed my thinking in how to approach it 🙏 I have a sneaky suspicion there will be some requests to contain the scrolling demo I've been working on into portable containers and wanted to make sure I had the right idea for doing this before going forwards 👍

 

Thanks again!

 

Jhey

Link to comment
Share on other sites

@jh3y it sounds like you got it all figured out, but I was curious - is there some reason you need position: fixed on the element? 

 

By default, ScrollTrigger pins things that are at the root (body) level with position: fixed because that's essential to avoid synchronizing issues due to the fact that modern browsers handle scrolling that root element on a different thread. But nested scrolling is handled differently, so ScrollTrigger uses transforms to simulate the pinning. In your case, that acts strangely [if the parent has no transforms] because your pinned element is position: fixed. You could set pinType: "fixed", but the position when unpinning is negatively affected. 

Link to comment
Share on other sites

Hey @GreenSock 👋

 

The use case was about being able to pin something in a container that can be moved around. For when there's nested scrolling and I want to pin something in the container with nested scroll.

 

I'm relying on CSS here where elements fix relative to the container if it has a transform or position relative. The idea is that it wouldn't be unpinned in the container kinda like the infinite scroller.

 

It was more a case of wondering how this might be done. For example, I anticipate the content scroller might want to be put in its own container and moved around without relying on body scroll. Didn't know if there was an appropriate approach. But, the pen I posted seems to work for my needs 👍

  • Like 1
Link to comment
Share on other sites

  • Solution
17 minutes ago, jh3y said:

The use case was about being able to pin something in a container that can be moved around. For when there's nested scrolling and I want to pin something in the container with nested scroll.

Yeah, I figured - I'm just not clear about why you needed to set position: fixed in the CSS for the thing getting pinned. Why not just position: absolute | relative and let ScrollTrigger do the pinning to make it appear fixed? I'm not saying you SHOULD or that there's anything "wrong" with what you were doing. It's more of a curiosity for me, that's all. 

 

Glad you've got it all working the way you want. 👍

Link to comment
Share on other sites

No worries. That was kinda what I was looking to find out with opening this thread 😁 "Was I missing something straightforward?". I haven't really played with nested scroll and ScrollTrigger 😁

 

I don't think I knew that there were two different pin styles. I think I assumed that `position: fixed` was already being used, not that it was being kept in place by `transform` which I should've noticed really 😅

 

As you say, `position: absolute` will do the trick and means I don't need to set anything on the child element 👍

 

Thanks! 

Link to comment
Share on other sites

22 minutes ago, jh3y said:

I don't think I knew that there were two different pin styles. I think I assumed that `position: fixed` was already being used, not that it was being kept in place by `transform` which I should've noticed really 😅

 

Yeah, it all has to do with the pesky ways that browsers handle things in different threads but only for the main page scrolling. 

 

Either solution should work, so use whatever fits best into your scenario. 

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...