fdev Posted October 4, 2023 Share Posted October 4, 2023 Can someone please help me as I want to use the scroll snap effect but I don't want it on the whole webpage. So you can see in my codepen which I took from a different forum you cant actually land on the white sections they just get scrolled past. If you scroll up from the blue section you will see the white section I built. I also made one at the bottom which you can't even scroll to. Thanks See the Pen ZEVqooz by fayskerritt (@fayskerritt) on CodePen Link to comment Share on other sites More sharing options...
mvaneijgen Posted October 4, 2023 Share Posted October 4, 2023 Is setting snap to the things that have ScrollTrigger not what you want? See the Pen bGOmLLN?editors=0010 by mvaneijgen (@mvaneijgen) on CodePen 1 Link to comment Share on other sites More sharing options...
fdev Posted October 4, 2023 Author Share Posted October 4, 2023 I hope this codepen explains it, its the section with the cat photos that I want to use the snap effect on but as you can see its happening on the other sections as well See the Pen zYymPGa by fayskerritt (@fayskerritt) on CodePen Link to comment Share on other sites More sharing options...
Rodrigo Posted October 4, 2023 Share Posted October 4, 2023 Hi, I think the issue stems from this: ScrollTrigger.create({ // start: 'top top', // end: 'bottom bottom', markers: true, snap: { snapTo: (progress, self) => { let panelStarts = tops.map((st) => st.start), // an Array of all the starting scroll positions. We do this on each scroll to make sure it's totally responsive. Starting positions may change when the user resizes the viewport snapScroll = gsap.utils.snap(panelStarts, self.scroll()); // find the closest one return gsap.utils.normalize( 0, ScrollTrigger.maxScroll(window), snapScroll ); // snapping requires a progress value, so convert the scroll position into a normalized progress value between 0 and 1 }, duration: 0.5 } }); That's a ScrollTrigger without any trigger element, so ScrollTrigger defaults to the viewport. If you want to pin and snap just in a specific section, then do that on a ScrollTrigger instance that applies only to that particular section. Also be sure that the ScrollTrigger instances are created in the order they appear in the screen. I'd strongly recommend you to create just the ScrollTrigger instance for that particular section, then add the other ScrollTrigger instances to your page, in order to isolate that and get it working as expected. Finally in this cases when you have a bunch of instances is better to add specific ids in order to identify each ScrollTrigger instance and you can even add indentation to the markers: ScrollTrigger.create({ id: "one", markers: true, }); ScrollTrigger.create({ id: "two", markers: { indent: 200, }, }); That will create distinctive markers for each section and that will allow you to debug easily. Hopefully this helps. Happy Tweening! 1 Link to comment Share on other sites More sharing options...
fdev Posted October 13, 2023 Author Share Posted October 13, 2023 Can I please add to this conversation and ask if it is possible to snap elements so that the top is 100px from the top of the viewport (for example so the element snaps so the top meets the bottom of the navbar). At the moment the element is going right to the top of the viewport so some of it is hidden beneath the navbar. Thanks Link to comment Share on other sites More sharing options...
GreenSock Posted October 13, 2023 Share Posted October 13, 2023 2 hours ago, fdev said: Can I please add to this conversation and ask if it is possible to snap elements so that the top is 100px from the top of the viewport (for example so the element snaps so the top meets the bottom of the navbar). At the moment the element is going right to the top of the viewport so some of it is hidden beneath the navbar. Yes, that sounds like something that's possible. If you need some help, please show us what you tried in a minimal demo (like a CodePen). Context is really key in a case like this. You can apply your own snapping logic in whatever way you want by using a function-based snapTo value. 👍 Link to comment Share on other sites More sharing options...
fdev Posted October 16, 2023 Author Share Posted October 16, 2023 Hi again, Here is my minimal demo that demonstrates when I use scrub:1 the panel will jump to the top of the viewport instead of stopping when it gets to the bottom of the navbar. See the Pen QWzRYVa by fayskerritt (@fayskerritt) on CodePen Thanks Link to comment Share on other sites More sharing options...
GreenSock Posted October 16, 2023 Share Posted October 16, 2023 @fdev the problem is that you set things up in a way that'd have the ScrollTriggers overlap with each other. I think you're only considering the "start" but forgetting that there's an "end" for each ScrollTrigger, and when you set snap: 1, that means that it'll snap to either the start or the end. But you've got ScrollTriggers with ends that are past the start of previous ones. ScrollTrigger is doing what it's supposed to do, but there's just a logic flaw in your code/setup. If your goal is to only factor in the start of each section, I'd take a totally different approach: See the Pen PoXrNVW?editors=0010 by GreenSock (@GreenSock) on CodePen Basically create an Array of ScrollTriggers purely for tracking the scroll position of each panel, and then create a single ScrollTrigger that handles all of the snapping based on those positions. I hope that helps. 1 Link to comment Share on other sites More sharing options...
fdev Posted October 17, 2023 Author Share Posted October 17, 2023 This is really thank you! One more question, is there any way to speed the snap up, it doesn't seem to have the same layout as a timeline so not sure if its as easy as adding 'duration: 0.2' or something like that? I just want it to snap a bit quicker than it does currently if possible. Thanks Sorry also to add to this, in the minimal demo the Orange section is bigger than 100vh so once the top of this section has reached the top is there a way like before allowing it to be normally scrolled until the next section reaches the viewport then to snap to that? Link to comment Share on other sites More sharing options...
Rodrigo Posted October 17, 2023 Share Posted October 17, 2023 Hi, 6 hours ago, fdev said: One more question, is there any way to speed the snap up, it doesn't seem to have the same layout as a timeline so not sure if its as easy as adding 'duration: 0.2' or something like that? Sure thing, you can tap into snap advanced config in order to set it up the way you want (scroll down to the snap section of the config): https://gsap.com/docs/v3/Plugins/ScrollTrigger/#config-object 6 hours ago, fdev said: Sorry also to add to this, in the minimal demo the Orange section is bigger than 100vh so once the top of this section has reached the top is there a way like before allowing it to be normally scrolled until the next section reaches the viewport then to snap to that? Same thing, you'll have to create your own custom logic in the snap config. In order to set a duration of the snap and also add this type of functionality you have to do something like this: ScrollTrigger.create({ trigger: element, start: "top top", end: "+=200", snap: { duration: {min: 0.2, max: 0.3}, snapTo: (value) => { // Creat your custom logic here for your specific snap values }, }, }); Another option is to create a custom array of snapping values and pass that array to snapTo Hopefully this helps. Happy Tweening! Link to comment Share on other sites More sharing options...
GreenSock Posted October 17, 2023 Share Posted October 17, 2023 9 hours ago, fdev said: I just want it to snap a bit quicker than it does currently if possible. Not really - ScrollTrigger can't do its snapping until the native scroll completely STOPS, otherwise it would interfere with the user doing their own scrolling. So even if you set the delay to 0, that isn't entirely possible because it still has to wait for native scrolling to totally stop. Link to comment Share on other sites More sharing options...
fdev Posted October 17, 2023 Author Share Posted October 17, 2023 1 hour ago, GreenSock said: Not really - ScrollTrigger can't do its snapping until the native scroll completely STOPS, otherwise it would interfere with the user doing their own scrolling. So even if you set the delay to 0, that isn't entirely possible because it still has to wait for native scrolling to totally stop. Thanks for clarifying, this makes sense! In regards to getting the scroll to not snap when the panel is taller than 100vh where would I put this logic in the demo that you sent Jack as I am struggling to figure it out in the function in the demo below: See the Pen BavgEzG by fayskerritt (@fayskerritt) on CodePen Link to comment Share on other sites More sharing options...
Rodrigo Posted October 18, 2023 Share Posted October 18, 2023 Hi, It has to go in the snap function you have here: ScrollTrigger.create({ // you can add a trigger and start/end values if you'd like to limit the snapping to only part of the page. snap(progress, self, direction) { let totalDistance = self.end - self.start, snapProgress = snaps.map((v) => v / totalDistance); return ScrollTrigger.snapDirectional(snapProgress)(progress, self.direction); } }); In that function you have to return a progress value (between 0 and 1) where ScrollTrigger will eventually land the scroll position. That's what you'll have to figure out based on the points you want your ScrollTrigger instance to snap. Happy Tweening! Link to comment Share on other sites More sharing options...
fdev Posted October 19, 2023 Author Share Posted October 19, 2023 Hey, Sorry to keep asking questions but I have read through the docs again and again and can't seem to figure out how to stop the snap happening midway through a section if the section is more than 100vh. I tried to debug and console logged the progress for each section to figure out where snapProgress was coming from but can't figure out how to stop the snap being triggered until you get to the bottom of the section. I tried changing 'start: "bottom bottom" but this then snaps to the bottom of the section instead of the top: See the Pen BavgEzG by fayskerritt (@fayskerritt) on CodePen Thanks for your advice before, but can you please point me towards which bit of the scroll function I need to edit to stop this from happening as I tried changing the return to values but this broke the function altogether. Thanks Link to comment Share on other sites More sharing options...
Rodrigo Posted October 19, 2023 Share Posted October 19, 2023 Hi, This is a simple example of using the custom snap functionality: See the Pen OJdLbme by GreenSock (@GreenSock) on CodePen Basically you check the value passed by the snapTo callback and if t matches certain criteria you can return a specific value, a specific value from an array or calculation or null if you don't want any snapping at all. Is worth noticing that using snap as a function works in the same way, sans the extra configuration properties in it: scrollTrigger: { trigger: ".wrapper", start: "top top", end: "+=" + (100 * panels.length) + "%", pin: true, scrub: true, snap (value) { if (value > 0.15 && value < 0.35) { return 0.25; } if (value > 0.65 && value < 0.85) { return 0.75; } return null; }, } Hopefully this helps. Happy Tweening! Link to comment Share on other sites More sharing options...
h-amad Posted March 4 Share Posted March 4 Hey guys, I am having an issue when applying start and end values to the ScrollTrigger so that the snapping effect happen only to certain part of the page. the snapping suddenly stops working like it did before I assign start/end values, and snaps to random values for each panel of the array I tried adding some padding to the container so the markers would not intertwine but it didn't help. here is a minimal demo. See the Pen yLrywma by hmdpenning (@hmdpenning) on CodePen ideal state would be that the snapping happens when top of the panels container reaches bottom of screen, and ends when its bottom reach bottom of the screen. Link to comment Share on other sites More sharing options...
mvaneijgen Posted March 4 Share Posted March 4 To explain the snap values. It snaps to a progress value of the ScrollTrigger where 0 is the start and 1 is the end. I have no idea what your snapper ScrollTrigger is doing, but is seems rather complicated. I've now just set a snap to all your ScrollTriggers to 1 eg only snap to the end of each ScrollTrigger. Now only on page load there is no snapping to the first section so you could add one extra ScrollTrigger that tackles that. If you want you can debug your snapping ScrollTrigger by logging the value it gets you when scrolling and then you can see if that is correct with your logic, but it is really hard to map some distance to a value between 0 and 1, it is better to just use the ScrollTriggers them self. Hope it helps and happy tweening! See the Pen RwOPbEV?editors=0010 by mvaneijgen (@mvaneijgen) on CodePen Link to comment Share on other sites More sharing options...
h-amad Posted March 4 Share Posted March 4 3 hours ago, mvaneijgen said: To explain the snap values. It snaps to a progress value of the ScrollTrigger where 0 is the start and 1 is the end. I have no idea what your snapper ScrollTrigger is doing, but is seems rather complicated. I've now just set a snap to all your ScrollTriggers to 1 eg only snap to the end of each ScrollTrigger. Now only on page load there is no snapping to the first section so you could add one extra ScrollTrigger that tackles that. If you want you can debug your snapping ScrollTrigger by logging the value it gets you when scrolling and then you can see if that is correct with your logic, but it is really hard to map some distance to a value between 0 and 1, it is better to just use the ScrollTriggers them self. Hope it helps and happy tweening! Hey. thanks for the demo, I am not sure why but sometimes it is skipping random panels when they scroll into view, and I'm curious how I can use the demo with the normalized snap values in a seperate scrolltrigger as they actually worked pretty much how I wanted it, except it started snapping before the snappable sections scrolled in view. and it only messed up when I assigned a trigger, plus the start/end values to the second ScrollTrigger (the one with snapTo) so I didn't think the values would be the reason it stopped working. I tried debugging it here with logging the normalized value and its components (min, max, snapScroll) before and after assigning a trigger, those values stay the same, yet the calculated normalizd value changes. See the Pen yLrywma?editors=0011 by hmdpenning (@hmdpenning) on CodePen Link to comment Share on other sites More sharing options...
GreenSock Posted March 4 Share Posted March 4 Is this what you were trying to do?: See the Pen bGJdRxJ?editors=0010 by GreenSock (@GreenSock) on CodePen Your previous demo didn't work properly because you were calculating the snapping progress values incorrectly. You were using the bounds of the entire page rather than the ScrollTrigger's own limited area (between the start and end). 1 Link to comment Share on other sites More sharing options...
h-amad Posted March 5 Share Posted March 5 @GreenSock thanks allot Jack! that's exactly what I was going for. quick side question, is Progress in snapTo(progress, self) being used here, or can we remove it? Link to comment Share on other sites More sharing options...
GreenSock Posted March 6 Share Posted March 6 9 hours ago, h-amad said: is Progress in snapTo(progress, self) being used here, or can we remove it? It's not being used in our calculation, but I'm not sure what you mean by "remove it". You can't really do that because we're using the "self" parameter, so you need a placeholder there. See what I mean? Or did I misunderstand your question? Link to comment Share on other sites More sharing options...
Recommended Posts
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 accountSign in
Already have an account? Sign in here.
Sign In Now