Jump to content
Search Community

Separate pinned elements by container. And move them from one container to another

LifescrewDesign test
Moderator Tag

Recommended Posts

Nice to meet you, I would like to discuss the GSAP ScrollTrigger.

 

I am modifying the GSAP Observer demo to GSAP ScrollTrigger.
I have pinned the sections in the .section-wrap and the image switches as it scrolls.

 

I want to do the following about this.
1. separate the section pinning for each .section-wrap.
2. when I finish scrolling a section in the first .section-wrap, I want to move to the second .section-wrap.

 

Here's the HTML, and it mentions CSS too.

      <div class="section-wrap"><!--← add position: relative;-->
        <section class="first"><!-- position: absolute;-->
          <div class="outer">
            <div class="inner">
              <!-- The background image for this element is a photo -->
            </div>
          </div>
        </section>
        <section class="second">
			<!--Abbreviations-->
        </section>
        <section class="third">
			<!--Abbreviations-->
        </section>
      </div>


      <div class="section-wrap">
        <!--Abbreviations. Same as the element above.-->
      </div>

The JavaScript is this. I have written comments where I have added from the demo.

//Change ScrollTrigger
gsap.registerPlugin(ScrollTrigger);

let sections = document.querySelectorAll("section"),
  images = document.querySelectorAll(".bg"),
  outerWrappers = gsap.utils.toArray(".outer"),
  innerWrappers = gsap.utils.toArray(".inner"),
  currentIndex = -1,
  wrap = gsap.utils.wrap(0, sections.length),
  animating;

gsap.set(outerWrappers, { yPercent: 100 });
gsap.set(innerWrappers, { yPercent: -100 });

function gotoSection(index, direction) {
  index = wrap(index);
  animating = true;
  let fromTop = direction === -1,
      dFactor = fromTop ? -1 : 1,
      tl = gsap.timeline({
        defaults: { duration: 1.25, ease: "power1.inOut" },
        onComplete: () => animating = false
      });
  if (currentIndex >= 0) {
    gsap.set(sections[currentIndex], { zIndex: 0 });
    tl.to(images[currentIndex], { yPercent: -15 * dFactor })
      .set(sections[currentIndex], { autoAlpha: 0 });
  }
  gsap.set(sections[index], { autoAlpha: 1, zIndex: 1 });
  tl.fromTo([outerWrappers[index], innerWrappers[index]], { 
      yPercent: i => i ? -100 * dFactor : 100 * dFactor
    }, { 
      yPercent: 0 
    }, 0)
    .fromTo(images[index], { yPercent: 15 * dFactor }, { yPercent: 0 }, 0)

  currentIndex = index;
}

//Change ScrollTrigger
ScrollTrigger.observe({
  target: ".section-wrap", //Add
  type: "wheel,touch,pointer",
  wheelSpeed: -1,
  onDown: () => !animating && gotoSection(currentIndex - 1, -1),
  onUp: () => !animating && gotoSection(currentIndex + 1, 1),
  tolerance: 10,
  preventDefault: true
});

gotoSection(0, 1);

I think I need to re-array the sections,outerWrappers,innerWrappers per .section-wrap, any good ideas?
Thank you in advance for your help.

See the Pen VwOpvyZ by lifescrewdesign (@lifescrewdesign) on CodePen

Link to comment
Share on other sites

Add a thought.

 wrap = gsap.utils.wrap(0, sections.length),.


If this exceeds the maximum value, it wraps at the beginning, and if it falls below the minimum value, it wraps at the end, so this causes the pinned section to loop.
If this is removed, the animation itself will be corrupted.
Do you have any good ideas to remove this loop?

Link to comment
Share on other sites

Hi,

 

What you're trying to achieve is not the simplest thing actually, since you have to track the current section and slide. The demo you're trying to expand from predicates in the fact that Observer can prevent the default scroll functionality (mostly mouse wheel and touch events), but at some point you need to disable the Observer instance of the first section, allow scrolling and when you reach the second section enable that section's Observer instance. A combination of these two demos:

See the Pen oNdNLxL by GreenSock (@GreenSock) on CodePen

 

See the Pen ExEOeJQ by GreenSock (@GreenSock) on CodePen

 

Honestly I think it would be better to prevent that and just have a single Observer instance and once all the slides of the first section are completed, just animate the second section above the first and keep animating the slides of that section.

 

Hopefully those demos help you getting started.

Happy Tweening!

Link to comment
Share on other sites

Hi @Rodrigo.
Thank you for your instruction! I have seen the demo and am verifying it.

 

Now I have one new question.
What is the difference between 'ScrollTrigger.observe' and 'ScrollTrigger.create'?

I thought it would be possible to use 'ScrollTrigger.create' instead of 'ScrollTrigger.observe' to move to the second section after all the slides in the first section are completed.

Are there any differences between the two, such as faster loading speeds?

Link to comment
Share on other sites

Thank you for your reply.

 

They are two different things, but I don't know the specific difference between them and their use.
The crucial difference between the two is: "What makes them work?" Is it?
Observer works with "swipe, mouse wheel",
ScrollTrigger moves by 'scrolling'.
Is this understanding correct?

Any other advice on differences or usage?

Link to comment
Share on other sites

Yes, the Observer plugin can watch for certain events and then do logic based on that. 

 

ScrollTrigger is build to hook animations to the users scrollbar. 

 

They both can do something based on the scroll of the user, but they go about it in completely different ways.

 

As always the docs are your best friend and will tell you everything, even thins you didn't know you needed!

 

https://gsap.com/docs/v3/Plugins/Observer/ 

https://gsap.com/docs/v3/Plugins/ScrollTrigger/?page=1

 

  • Like 2
Link to comment
Share on other sites

Thank you for your answer.
I am Japanese and develop while translating English, so it is taking me a while to decipher the Docs.


After watching the demo you introduced, I have a better idea of how to use Observer and ScrollTrigger!

-------

Observer :

Used to animate parts (child elements) within a pinned tag


ScrollTrigge.creative :

Used to pin the parent element. Once inside the parent element, turn on Observer to animate the child elements.

-------

Based on the above ideas, I have improved the demo.
There is one more thing I would like to discuss with you.

 

I would like to ask you about the Observer's "wheelSpeed" and "tolerance" settings.
In Safari on the iPhone, if I set the duration of yPercent(transform:translateY) to 1, it moves jerkily, so I set it to "duration: 0.3," which is faster.
Then, a slight movement of the mouse wheel would move two or more child elements.


So I adjusted the Observer's "wheelSpeed" and "tolerance" so that only one child element moves with each mouse wheel movement.


However, when scrolling from bottom to top on a smartphone, when I move from footer → 1-3 → 1-2,

I get the phenomenon of rolling back to 1-2 → 1-3.
Any advice would be appreciated.

See the Pen yLWoKMN by lifescrewdesign (@lifescrewdesign) on CodePen

 

▽[video record] I get the phenomenon of rolling back to 1-2 → 1-3.

 

Link to comment
Share on other sites

Postscript to the above question.
I would like to add a note on the cause of the rollback from 1-2 to 1-2, when moving from footer → 1-3 → 1-2,.

 

In this case, not only onEnterBack is called, but also onEnter.

How can I call only onEnterBack?

Link to comment
Share on other sites

Hi,

 

Right now I don't have time to dig into all of this and provide a demo. As mentioned before this is not the simplest thing to achieve. I'll se if I can create a simple demo that  shows how to create two different Observer instances that work with ScrollTrigger but please understand that we don't have all the time resources to create demos for complex issues, I just want to manage expectations.

 

Finally regarding this:

16 hours ago, LifescrewDesign said:

In this case, not only onEnterBack is called, but also onEnter.

That seems super odd because onEnter and onEnterBack trigger in very different ways. The onEnter callback is triggered when scrolling forward or down while the onEnterBack is triggered when scrolling back or up.

 

Finally I recommend you to use the same settings for wheel speed and tolerance as the demo we have, since most likely the scroll event is still being triggered when the animation is completed, perhaps add an extra conditional logic there until the touch event is no longer firing. Keep in mind that mobile devices have momentum scroll baked in, so is not just a one off event like the mouse wheel. You can test this URL on your device and see if you get the same issue:

See the Pen oNdNLxL by pen (@pen) on CodePen

 

Happy Tweening!

Link to comment
Share on other sites

  • 2 weeks later...

Thank you for the demo.

 

This demo does not cause the error I am experiencing.
However, this demo does not escape from the Observer element.

 

My demo also does not have the error if I do not escape from the Observer element.
In other words, GSAP Observer may not work properly if you escape from the Observer element.

 

This error, however, occurs in Safari on both smartphones and PCs.
In Chrome, it only occurs on smartphones.

 

It seems difficult to achieve what I want to do with GSAP Observer.
I will try to verify this using GSAP ScrollTrigger only.

 

Thank you for your instruction.

Link to comment
Share on other sites

10 hours ago, LifescrewDesign said:

However, this demo does not escape from the Observer element.

It does, actually after some scroll/pointer events the normal scroll resumes. I'm not sure what you're expecting to happen here.

 

Honestly I think you should start as simple as possible, that's why I suggested to combine the two demos I posted before. Create a single Observer instance then after that is completed, get the normal scrolling going and then using the logic of the second demo start a second Observer instance.

 

I'll check that demo on my devices tomorrow and see what happens. I insist in starting as simple as possible and then start adding complexity to this.

 

Happy Tweening!

Link to comment
Share on other sites

Quote

Honestly I think you should start as simple as possible, that's why I suggested to combine the two demos I posted before. Create a single Observer instance then after that is completed, get the normal scrolling going and then using the logic of the second demo start a second Observer instance.

I understand your point.
So you are saying that I should make a simple demo with these two demos.
But the second one of these demos behaves incorrectly on a smartphone.
That's why I didn't refer to it.
It behaves wrong on iPhone13 in safari .

If I can find the time, I will verify this when I have it.

 

Link to comment
Share on other sites

The behaviour of the second demo was checked again on an iPhone 13.
The movement seems awkward, is this correct?
Incidentally, we checked the same behaviour on iPhone13 chrome and Android. 

 

The error in the previous post seems to occur at a higher rate when a sideways swiping action is entered.

 

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...