Jump to content
Search Community

All Activity

This stream auto-updates

  1. Past hour
  2. I complain about using pre-fab code as it's generally too much work to reverse-engineer and tweak but that's what I was doing right here. Came up with a straight CSS/jQuery solution in like 30 minutes versus the hours I was working on the previous code. Plus I can expand with GSAP if need be but works great just like this if anyone else is looking for the same thing (and can add in GSAP) *I'll add to this CodePen if I end up infusing some GSAP though to keep it relevant to the community https://codepen.io/ilrobinson/pen/ExJOvga
  3. Today
  4. Yesterday
  5. I'm at a loss. This works: gsap.to("#my-square", { duration: 5, motionPath: "M 1,104 Q 111,94 86,69 61,44 76,29 91,14 151,5.43" }); albeit with an error. This fails: gsap.to("#my-square", { duration: 5, motionPath: "#curve1" }) same error then infinite loop (malformed path). Same SVG. Same path. <svg width="160" height="106" viewBox="-0.5 -0.5 150 150" id="svg3" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"> <link xmlns="http://www.w3.org/1999/xhtml" rel="stylesheet" href="../style.css" type="text/css" /> <defs id="defs1" /> <g id="g3"> <g id="g2"> <path d="M 1,104 Q 111,94 86,69 61,44 76,29 91,14 151,5.43" fill="none" stroke="#000000" stroke-width="3" stroke-miterlimit="10" pointer-events="stroke" id="curve1" /> <path d="M 157.68,4.47 149.41,10.2 151,5.43 148.13,1.29 Z" fill="#000000" stroke="#000000" stroke-width="3" stroke-miterlimit="10" pointer-events="all" id="curve2" /> </g> </g> </svg> does-not-work.log works.log
  6. Hi @hebert lima and welcome to the GSAP Forums! Is always better to use the reversed() method to toggle a GSAP Tween/Timeline instance: https://gsap.com/docs/v3/GSAP/Tween/reversed() https://gsap.com/docs/v3/GSAP/Timeline/reversed() Then you can use the browser's sessionStorage to keep the value: https://developer.mozilla.org/en-US/docs/Web/API/Window/sessionStorage Here is a fork of your demo: https://codepen.io/GreenSock/pen/GRLwEQq Hopefully this helps. Happy Tweening!
  7. Hi, The issue here is that you're not considering pinning. Pinning creates vertical space to allow the element to stay pinned so if you create a ScrollTrigger instance for an element that is after the pinned section, of course those calculations will be off because that extra space. Even though the recommendation is to create your ScrollTrigger instances in the order they appear on the screen, in this case is better to create all of them (especially since they're not pinned) after every pinning ScrollTrigger before any of those sections, has been created. This seems to work the way you intend: theme.animations = function () { const ColorChange = function () { ... }; // Horizontal Lock Scroll const horzScroll = gsap.timeline(); const horzScrollEl = document.querySelector(".horz-scroller"); var wrap = document.querySelector(".scroller__list"); if (horzScrollEl) { horzScroll.to(".scroller__list", { x: -horzScrollEl.scrollWidth + window.innerWidth + "px", ease: "none" }); ScrollTrigger.create({ pin: true, // markers: true, trigger: ".horz-scroller", // scroller: "#main", start: "center center", end: "+=" + (horzScrollEl.scrollWidth - window.innerWidth), scrub: 1, animation: horzScroll }); } ColorChange(); }; Hopefully this helps. Happy Tweening!
  8. Hi @Rohit Pathak and welcome to the GSAP Forums! Mixing ScrollTrigger with Observer is a bit more complicated than just use the Observer Plugin. If I was you I'd try to solve everything just with the Observer Plugin alone (like the website you linked). I think most of your problems could stem from this: onUp: () => { if (timeLine1.totalProgress() < 1) { timeLine1.play(); console.log(timeLine1.totalProgress()); } else if (timeLine1.totalProgress() == 1 && timeLine2.totalProgress() < 1) { timeLine2.play(); console.log(timeLine2.totalProgress()); } else if (timeLine2.totalProgress() == 1 && timeLine3.totalProgress() < 1) { timeLine3.play(); console.log(timeLine3.totalProgress()); } }, Now I wouldn't use that approach at all. What I would do is to track the amount of steps each timeline has and if the amount of taken steps of a particular section are completed (4 out of 4, if a section requires 4 wheel events to complete a timeline for example) just move onto the next section. I would approach this as a user controlled content slider where each slide has some specific internal animations that should complete (in any direction) before going to the next/previous slide (if any of course). Also instead of checking for progress I would just use a simple boolean that should be toggled to true when the user scrolls and toggle it back to false after that particular section is completed, in order to use that as something that prevents the user from keep scrolling and perhaps triggering the animations of other sections. Right now I don't have the time to dig into this and create a minimal demo for you that illustrates the approach I described above, but hopefully this gives you an approximate idea of what I think should be the best course of action for something like this. Hopefully this helps. Happy Tweening!
  9. You'll want to put all the tweens on a timeline and move the scrollTrigger to the timeline rather than the single tween. https://codepen.io/PointC/pen/gOyQWqY Hopefully that helps. Happy tweening.
  10. Hi, I don't have any experience with Astro, but maybe you might want to have a look at GSAP Context as it could provide a simpler solution for this: https://gsap.com/docs/v3/GSAP/gsap.context() Now if this approach is not too convoluted (it doesn't really seems like that), does what you need and works well in production, then just use it: "if it ain't broken, don't fix it" 🤷‍♂️ Happy Tweening!
  11. Hello, I would like some help solving an issue: I've attached a CodePen with details of the implementation: I have a menu that opens and closes, and the status of this menu is stored in the browser session (open/closed). When the initial status is "open", the animation plays normally ("start" -> "end"). The problem occurs when the initial status of the animation is "closed"; it should play ("end" -> "start"). I'm setting the position as follows: if (!toggle) { // define if the menu should inicialized closed and set seek to ("end") tl.seek("end").pause(); } But when I click play, the animation doesn't occur (nothing happens). if (this.reverseTimeline) { tl.play() } else { tl.reverse() }
  12. Thanks! Oh brilliant! thanks for the help, yeah that's what I was looking for. Its really interesting I think understand the drawSVG values a bit better now after also reading the docs page for it, I also tried to implement the appear/disappear as you mentioned, but it's not quite as clean as I would like. I added a tween at the beginning to make it appear and then I added another on update just before it ends to try and make it disappear, but it really looks rough especially if I scroll back up 😂. Is there a cleaner way I could be doing it, maybe when you enter the start and exit the end of the scroll trigger? This is where I am at so far. https://codepen.io/Jaudy/pen/vYMQxoj
  13. Hi @Fullerfort, Right now you have a logic issue since you're running your code only for the first page: PAGES.forEach((page, index) => { set(page, { z: index === 0 ? 13 : -index * 1 }); if (index === 0){ to(page, { rotateY: `-=${180 - index / 2}`, scrollTrigger: { scrub: 1, start: () => (index + 1) * (window.innerHeight * 0.25), end: () => (index + 2) * (window.innerHeight * 0.25), markers:true, }, }); to(page, { z: index === 0 ? -13 : index, scrollTrigger: { scrub: 1, start: () => (index + 1) * (window.innerHeight * 0.25), end: () => (index + 1.5) * (window.innerHeight * 0.25), }, }); } else return false; }); That code block is running only when the index is 0, so the first page. May I ask why you changed the JS logic jh3y created? If is not broken don't fix it. Just changing the content of the pages should be enough IMHO. If you want to study and learn what is being done and why, then that is mostly related with JS logic and not really a GSAP issue. I'd recommend you to have a peak at MDN: https://developer.mozilla.org/en-US/docs/Web Happy Tweening!
  14. Hey there, Thank you for you answers! I wasn't expecting the magic solution for sure. I just wanted to throw this out here see if there were some ideas. Thanks for your tips @mvaneijgen I'll experiment later when I'll have time for that. Thanks again!
  15. Also, if you think there is a better way, your suggestions are welcome!
  16. Hi @Rodrigo thanks again for your help. I've updated the CodePen (https://codepen.io/richardcool/pen/yLrqdQm), stopped the sticky header and removed the errors but I'm still getting the issue where it'll scroll to the position of the section without taking into consideration the pinning. Does scrollTo simply scroll to a Y position without taking the pinning into consideration?
  17. After having trouble integrating gsap with astro and view transitions (see thread https://discord.com/channels/830184174198718474/1230877829386735616) I think we found a possible way to do it (thanks @Fryuni for the feedback), just wondering if you can confirm I m not missing some holes. So essentially I made a proxy function where all the timelines are stored in a variable and before starting any timeline the method clear is called (https://gsap.com/docs/v3/GSAP/Timeline/clear()/). https://github.com/zanhk/astro-gsap-leak-test/blob/tl-pool/src/scripts/global.ts#L17 import gsap from "gsap"; export const gsapTimelines: { [key: string]: gsap.core.Timeline; } = {}; export function createTimeline( key: string, timelineOptions?: gsap.TimelineVars, ) { const newTimeline = gsap.timeline(timelineOptions); newTimeline.paused(true); gsapTimelines[key] = newTimeline; return newTimeline; } export function loadTimeline( key: string, timelineOptions?: gsap.TimelineVars, ): gsap.core.Timeline { // Here take the timeline from the cache if it exists, otherwise create a new one const timeline: gsap.core.Timeline = gsapTimelines[key] ?? createTimeline(key, timelineOptions); let clearAdded = false; const handler: ProxyHandler<gsap.core.Timeline> = { get(target: gsap.core.Timeline, prop: PropertyKey, receiver: any): any { const origMethod = target[prop as keyof gsap.core.Timeline]; if (typeof origMethod === "function") { return (...args: any[]) => { if (!clearAdded) { target.clear(); clearAdded = true; } const result = origMethod.apply(target, args); if (prop === "play") { clearAdded = false; } // Ensure the proxy maintains the correct this context return result === target ? receiver : result; }; } return origMethod; }, }; return new Proxy(timeline, handler); } Usage https://github.com/zanhk/astro-gsap-leak-test/blob/tl-pool/src/pages/to.astro#L53 loadTimeline("test") .to(".line span", { ease: "power4.out", y: 0, stagger: { amount: 0.3, }, duration: 0.5, }) .play(); That way the heap should be cleared before executing the timeline again. Did I miss something? Thanks
  18. Thanks a lot, i’ll try and let you know. Well with other tests, seems that the tardy pin affect mostly the iPhone, i’ll test on Android phone, Samsung, and works well too, i don’t know, but surely i’ll try your tips and let you know, Thanks a lot again ♥️
  19. Yeah I don't know what I'll do. Ill maybe have to try JS as this is what i see on my ipad (excuse the state of it, I have a 3 year old!)
  20. This appears to be funky behavior caused by Vue forcing refs to be Proxy objects. So when you access ref.value, it isn't the real object at all! It's a Proxy which alters what "this" refers to inside method calls. I think it's terrible that Vue does this actually, but maybe they have good reason for it. 🤷‍♂️ From what I can tell, the solution would be to use a shallowRef() instead of ref(): https://stackblitz.com/edit/github-vfgcdf-g52l6b?file=app.vue Does that clear things up?
  21. This is the debug link on devtools: https://i.imgur.com/CvJDG6V.mp4 I'm seeing exactly the same on an android (chrome-firefox) phone and iPad (chrome-safari) 🤷‍♂️ Sorry but I can't seem to replicate the problem you mention. Happy Tweening!
  22. This is on my actual phone after going back to portrait with your codepen. Sometimes it doesn't, sometimes it takes a few tries, but sometimes it's on first orientation. It's killing me! I'm considering trying to switch to just JS
  23. Hey there - if you open your codepen in dev tools and change the orientation, you'll see it breaks, same as my codepen which I stripped back (I also took a backup then stripped my website right back to practically nothing) the way it looks in dev tools is the same as it looks on my phone for both mine and your codepen and my stripped back site (though I have since restored the backup) The screenshot below is your codepen. I have just rebuilt the entire thing without pinning and it still does the same, it's a bit better, but the start and end pins are still way off on orientation change.
  24. Hi, I still think that this is related to something you're adding on the HTML/CSS of your project (or maybe wordpress is). I forked your demo and stripped all the CSS that wasn't need, the bare minimum, and is working as expected on my android phone on orientation change: https://codepen.io/GreenSock/pen/MWRzJJV Here is the debug view (no iframes, just like a regular website) https://cdpn.io/pen/debug/MWRzJJV If you check that link on a small screen and flip the orientation you'll see that the pinning works as expected. That gives me more ground to state that this is not a GSAP related issue, but something else in your setup that is causing this. Hopefully this helps. Happy Tweening!
  25. Function based values mean that when the ScrollTrigger instance is refreshed that end value will be whatever number/string that function returns. If oyu're doing some sort of calculation whose result might change that calculation will be run again. In the particular snippet you added the end point is based on the height of an element, if a screen resize changes the height of that element then the end point will be recalculated as well. Hopefully this clear things up. Finally it seems that you have created two different threads for the same issue, please let's keep the discussion in just one thread. That will make easier to follow and focus our efforts, thanks! Happy Tweening!
  26. Without a minimal demo, it's super difficult to offer a suggestion here or understand what you're asking for - are you saying you want to apply ScrollSmoother...but not have it actually work at all? You just want to have it pretend to work, feeding you the value that it would apply to the container's transform, without applying it? Maybe you could add a ticker listener with a high priority to grab the original transform, and then use an onUpdate on the ScrollSmoother where you grab the new value but immediately apply the old one to revert it(?) I'm totally guessing here in the absence of a minimal demo, but hopefully that gives you a little to go on at least. I wonder why you wouldn't adjust whatever you're doing with the <body> transform to more cleanly apply that in a way that integrates with ScrollSmoother(?)
  27. I'm building a site that has a page color changing function that is triggered by ScrollTrigger. It all works great until I throw a pinned section before it and all the subsequent sections only account for the actual DOM heights. Can someone point me in the right direction on the best approach to handle this type of thing? Here is a minimum viable demo of the two ScrollTriggers in action. https://codepen.io/tylorreimer/pen/OJGaRVz
  28. Does it work well for you without Lenis? That's not a GreenSock product, so we can't really support it here. If you're talking about the pin seeming to be a little bit tardy, that's likely because mobile browsers are particularly bad with using a separate, non-synchronized thread for scrolling which is why ScrollTrigger offers a anticipatePin option. You might want to try adding anticipatePin: 1 or some other value just to see if it helps. You could also see if it's any better with ScrollTrigger.normalizeScroll(true);
  1. Load more activity
×
×
  • Create New...