Jump to content
Search Community

Search the Community

Showing results for 'airpods' in content posted in GSAP.

  • Search By Tags

    Type tags separated by commas.
  • Search By Author

Content Type


Forums

  • GreenSock Forums
    • GSAP
    • Banner Animation
    • Jobs & Freelance
  • Flash / ActionScript Archive
    • GSAP (Flash)
    • Loading (Flash)
    • TransformManager (Flash)

Product Groups

  • Club GreenSock
  • TransformManager
  • Supercharge

Categories

There are no results to display.


Find results in...

Find results that contain...


Date Created

  • Start

    End


Last Updated

  • Start

    End


Filter by number of...

Joined

  • Start

    End


Group


Personal Website


Twitter


CodePen


Company Website


Location


Interests

Found 94 results

  1. Hi Guys This is more of a general hosting question, and not so much necessarily a GSAP specific question. We built a site based on the GSAP Airpods Pro scroll sample. Our site however loads around 900 frames, and not 147 like the Airpods example. Now the problem. We tested on 2 different hosting providers. The one provider, loads the files just fine, but the other comes up with a bunch of 508 and 404 errors, even though the files are there. In contacting the hosting provider support, they say there is nothing they can do as their servers are setup with brute force attack protection. Essentially when loading the site, its pulling so many resources that the server thinks its being attacked, and then blocks the requests, resulting in only half the site loading. This is specific to a single hosting provider, and as I say, a different hosting provider does not have this probem at all. Unfortunately the provider that works fine, is not in UK, and we would need one based in the UK. Any recommendations or general advice?
  2. Hello fellow developers, I started looking into the ScrollTrigger plugin as it seems very interesting, and while looking on the GSAP's codepen profile for different project ideas, I found this nice airpods animation. After looking into the code I figured out how 80% of it works but I still have some questions. Firstly, how does the "airpods" variable work? It obviously increments after each frame but I don't seem to find out where exactly it does that. Also, it uses the function gsap.to(airpods, {....}) which doesn't make much sense as "airpods" doesn't look like a proper html element. Fruthermore, I can't figure out why Inside the gsap.to function there is "frame: frameCount - 1", as the "frame" property doesn't appear on the docs at all. Secondly (this is more of a curiosity of mine), on the official apple website it also presents some features of the airpods while running the scroll triggered animation on the background. I was just wondering how would that be possible given the fact that the animation on the codepen acts like a fixed html canvas, so it would be a pain to display any other kind of media on the website. Thanks for reading all the way, even though some questions might not make any sense at all. Any help is appreciated.
  3. A developer refered my friend that using framework like react or next js will eleminate this issue but i dont get the point why that might do with this do u have any experience with that also have u seen the video that i have attached what my theory says is that the canvas that is rendering the images is causing the lag but i have seen apple doing it with 1000's of images with not prob can u tell me where i am loosing the performance const index = 10000; const frameCount = 240; const currentFrame = (index) => ( `/Aquatica/Renders/Char_Turn_Around${(10000 + index).toString()}.webp` ); // Example usage: const images = []; // Function to preload an image and store it in the images array const preloadImage = (index) => { const img = new Image(); img.src = currentFrame(index); img.onload = () => { console.log(`Image ${index} loaded`); // You can add additional logic here if needed }; images.push(img); }; // Preload all images for (let i = 0; i < frameCount; i++) { preloadImage(i); } // Canvas setup const canvas = document.getElementById("canvas"); const context = canvas.getContext("2d"); canvas.width = 1158; canvas.height = 770; // Airpods animation setup const airpods = { frame: 0, }; // Extend the duration to add time for fade-in and fade-out const totalAnimationDuration = 10; const frameTransitionDuration = totalAnimationDuration / frameCount; let count = 0; const modelTextList = document.getElementsByClassName("modelText"); // Step 1: Add the debounce function function debounce(func, wait) { let timeout; return function () { const context = this, args = arguments; clearTimeout(timeout); timeout = setTimeout(function () { func.apply(context, args); }, wait); }; } // Step 2: Create a debounced version of your render function const debouncedRender = debounce(render, 0); // Adjust the wait time as needed for (let i = 0; i < frameCount - 1; i++) { slidetimeline.to({}, { duration: frameTransitionDuration, onUpdate: function () { console.log("Frame Count:", i); debouncedRender(); // Use the debounced render function }, }, `+=${frameTransitionDuration}`) .to(airpods, { frame: i + 1, snap: "frame", duration: frameTransitionDuration, onUpdate: function () { console.log("Frame Count:", i); debouncedRender(); // Use the debounced render function }, }); if ( i === 25 || i === 61 || i === 93 || i === 116 || i === 151 || i === 176 || i === 215 ) { slidetimeline.to(modelTextList[count], { opacity: 1, duration: 2, }, "-=1") .to(modelTextList[count], { opacity: 0, duration: 2, }, "+=0.5"); count++; } } images[0].onload = render; function render() { context.clearRect(0, 0, canvas.width, canvas.height); const img = images[airpods.frame]; // Calculate the scaling factors to fit the image within the canvas const scaleX = canvas.width / img.width; const scaleY = canvas.height / img.height; const scale = Math.min(scaleX, scaleY); // Calculate the dimensions after scaling const scaledWidth = img.width * scaleX; const scaledHeight = img.height * scaleY; // Calculate the position to center the scaled image on the canvas const offsetX = (canvas.width - scaledWidth) / 2; const offsetY = (canvas.height - scaledHeight) / 2; // center the image const offX = (canvas.width - img.width) / 2; const offY = (canvas.height - img.height) / 2; // Draw the scaled and centered image context.drawImage(img, offsetX, offsetY, scaledWidth, scaledHeight); // context.drawImage(img, offX, offY, img.width, img.height); }
  4. here is the animation handeler Canva.js import gsap from "gsap"; import ScrollTrigger from "gsap/ScrollTrigger"; gsap.registerPlugin(ScrollTrigger); let winCount = 20; // detect if the user is on mobile if (window.innerWidth < 768) { winCount = 8; } const slidetimeline = gsap.timeline({ scrollTrigger: { trigger: "body", start: "top top", end: `+=${window.innerHeight * winCount}`, scrub: true, pin: true, anticipatePin: 1, }, }); slidetimeline .to("#slide1", { // maskPosition: "0% -4.5vh", clipPath: "polygon(0% 0%, 100% 0%, 100% 100%, 0% 100%)", duration: 2, }) .to(".contextText1", { opacity: 1, duration: 1, }, "-=1.5") .to("#slide2", { // maskPosition: "0% -4.5vh", clipPath: "polygon(0% 0%, 100% 0%, 100% 100%, 0% 100%)", duration: 2, }, "+=1") .to(".contextText2", { opacity: 1, duration: 1, }, "-=1.5") .to("#slide3", { // maskPosition: "0% -4.5vh", clipPath: "polygon(0% 0%, 100% 0%, 100% 100%, 0% 100%)", duration: 2, }, "+=0") .to(".contextText3", { opacity: 1, duration: 1, }, "-=1.5") .to("#slide4", { // maskPosition: "0% -4.5vh", clipPath: "polygon(0% 0%, 100% 0%, 100% 100%, 0% 100%)", duration: 2, }, "+=0") .to(".contextText4", { opacity: 1, duration: 1, }, "-=1.5") .to("#slide5", { // maskPosition: "0% -4.5vh", clipPath: "polygon(0% 0%, 100% 0%, 100% 100%, 0% 100%)", duration: 3, }, "+=0"); const index = 10000; const frameCount = 240; const currentFrame = (index) => ( `/Aquatica/Renders/Char_Turn_Around${(10000 + index).toString()}.webp` ); // Example usage: const images = []; for (let i = 0; i < frameCount; i++) { const img = new Image(); img.src = currentFrame(i); images.push(img); } Promise.all(images.map((img) => { return new Promise((resolve) => { img.onload = resolve; }); })).then(() => { // Initialize scroll animations here ScrollTrigger.refresh(); }); // Canvas setup const canvas = document.getElementById("canvas"); const context = canvas.getContext("2d"); canvas.width = 1158; canvas.height = 770; // Airpods animation setup const airpods = { frame: 0, }; // Extend the duration to add time for fade-in and fade-out const totalAnimationDuration = 10; const frameTransitionDuration = totalAnimationDuration / frameCount; let count = 0; const modelTextList = document.getElementsByClassName("modelText"); // Step 1: Add the debounce function function debounce(func, wait) { let timeout; return function () { const context = this, args = arguments; clearTimeout(timeout); timeout = setTimeout(function () { func.apply(context, args); }, wait); }; } // Step 2: Create a debounced version of your render function const debouncedRender = debounce(render, 0); // Adjust the wait time as needed // Step 3: Use debouncedRender in your animations // const model = gsap.timeline({ // scrollTrigger: { // trigger: "canvas", // start: "top top", // end: `+=${window.innerHeight * winCount}`, // scrub: true, // pin: true, // anticipatePin: 1, // }, // }); for (let i = 0; i < frameCount - 1; i++) { slidetimeline.to({}, { duration: frameTransitionDuration, onUpdate: function () { console.log("Frame Count:", i); debouncedRender(); // Use the debounced render function }, }, `+=${frameTransitionDuration}`) .to(airpods, { frame: i + 1, snap: "frame", duration: frameTransitionDuration, onUpdate: function () { console.log("Frame Count:", i); debouncedRender(); // Use the debounced render function }, }); if ( i === 25 || i === 61 || i === 93 || i === 116 || i === 151 || i === 176 || i === 215 ) { slidetimeline.to(modelTextList[count], { opacity: 1, duration: 2, }, "-=1") .to(modelTextList[count], { opacity: 0, duration: 2, }, "+=0.5"); count++; } } images[0].onload = render; function render() { context.clearRect(0, 0, canvas.width, canvas.height); const img = images[airpods.frame]; // Calculate the scaling factors to fit the image within the canvas const scaleX = canvas.width / img.width; const scaleY = canvas.height / img.height; const scale = Math.min(scaleX, scaleY); // Calculate the dimensions after scaling const scaledWidth = img.width * scaleX; const scaledHeight = img.height * scaleY; // Calculate the position to center the scaled image on the canvas const offsetX = (canvas.width - scaledWidth) / 2; const offsetY = (canvas.height - scaledHeight) / 2; // center the image const offX = (canvas.width - img.width) / 2; const offY = (canvas.height - img.height) / 2; // Draw the scaled and centered image context.drawImage(img, offsetX, offsetY, scaledWidth, scaledHeight); // context.drawImage(img, offX, offY, img.width, img.height); }
  5. Hi and yes another airpods question (sorry)! The animation is running fine on desktop and also iphone. but on my ipad the animation is not smooth at all. the main difference is that I pinned the canvas. const canvas = document.getElementById(hero); const context = canvas.getContext("2d"); canvas.width = 1920; canvas.height = 1080; let startTop = 75; let frameCount = 33; const currentFrame = index => ( `images/content/anim/hero/gate_${(index + 1).toString().padStart(3, '0')}.jpg` ); const images = [] const thegate = { frame: 0 }; for (let i = 0; i < frameCount; i++) { const img = new Image(); img.src = currentFrame(i); images.push(img); } gsap.to(thegate, { frame: frameCount - 1, snap: "frame", ease: "none", duration:"3", scrollTrigger: { scrub: true, pin:$("."+herocontainer), pinSpacing:true, start:"top "+startTop+"px", }, onUpdate: render // use animation onUpdate instead of scrollTrigger's onUpdate }); images[0].onload = render; function render() { context.clearRect(0, 0, canvas.width, canvas.height); context.drawImage(images[thegate.frame], 0, 0); } hope you have any idea how to improve the ipad performance. thx! ToM
  6. I'm trying to recreate Apple's Airpods Pro presentation page with ScrollTrigger. This is what I'm trying to make: https://codepen.io/j-v-w/pen/ZEbGzyv My idea is to use an array which holds all the images and then make use of ScrollTrigger.update() to update the img src based on the scrolling position.
  7. I am trying to create scroll animation using scrollTrigger plugin on my Next.js, but I'm getting error "cannot read property "_gsap" of undefined, etc. I have a spritesheet of 50 images (1.5 MB), that would be providing the scroll images. I have looked at these two, which was helpful, but only it doesn't translate very well into use for Next.js. Help would be appreciated. import Link from 'next/link' import Head from 'next/head' import Image from 'next/image' import {useEffect, useRef, useState} from 'react' import styles from '../styles/Home.module.css' import {gsap} from 'gsap' import { ScrollTrigger } from "gsap/dist/ScrollTrigger"; const Home = () => { const imageViewer = useRef(null) const imageScene = useRef(null) console.log('imageID', imageViewer) // if (process.client) { // } gsap.registerPlugin(ScrollTrigger) let frame_count = 9 let offset_value = 100 gsap.to(imageViewer.current, { // backgroundPosition: (-offset_value * frame_count * 2) + "px 50%", // ease: "steps(" + frame_count + ")", // use a stepped ease for the sprite sheet scrollTrigger: { trigger: imageScene.current, start: "top top", end: "+=" + (frame_count * offset_value), pin: true, scrub: true } }) return ( <> <Head> <title>TalkingSkunk | Home</title> <meta name='keywords' content='talkingskunk' /> <link rel="icon" href="/favicon.ico" /> {/* <script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.6.1/gsap.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.6.1/ScrollTrigger.min.js"></script> */} </Head> {/* <div className={styles.bgWrap}> <Image src="/home.png" className='cityscape' data-speed="0.2" layout="fill" objectFit="cover" quality={100} /> </div> */} <div className={`${styles.header} ${styles.section}`}> <div className={styles.center}>&darr;START</div> </div> <p className={styles.bgText}> Discover </p> <div ref={imageScene} className={`${styles.scene} ${styles.section}`} id="sticky"> <div ref={imageViewer} className={styles.viewer}></div> </div> <div className={styles.section}> <div className={styles.center}>End</div> </div> <div className={styles.canvas}> </div> <div className={styles.body}> </div> </> ) } export default Home;
  8. I am just trying to understand the concept of how to achieve apple the scroll animation. My problem is that I don't understand how the transition from one scene to the new scene works. Apple Animation As soon as the first scene is completely done with the animation, the next scene jumps in without having the scroll effect of the second scene. How do I achieve this transition in GSAP? Thanks a lot
  9. Hi all, I'm wondering why my timeline isn't behaving like a normal timeline in this example. As in: the h1 title animates immediately and doesn't wait for the previous animation to finish. I'm also wondering if it would be possible to animate a second canvas after all this and if that would be advisable (performance wise). Thanks in advance!
  10. https://gsap.com/docs/v3/Plugins/ScrollTrigger/ It's because one of those is a tween on a ScrollTrigger with scrub: 1 - so it will take 1 second to catch up to the scroll position - and the other one is natively scrolling. So there will always be a discrepancy between the two - which will only become more apparent the faster you scroll. If you want both to behave the 'exact same', set scrub: true instead of scrub: 1 to your airpods ScrollTrigger. You'll lose the smoothness of the scrub then, of course. Or instead tween the 'over-scrolling' of the video via a ScrollTrigger that also has a numeric scrub of 1 set. But then, one way or another, you'll get a discrepancy again between that video container and the subsequent containers which would scroll natively. At this point you might end up in a 'tween everything' approach like Mitchel (@mvaneijgen) suggested in his earlier answer with the thread he linked to. An alternative to that approach could be to use overall smooth-scrolling instead, e.g. via ScrollSmoother alongside scrub: true on the airpods ScrollTrigger. Technically it's also a 'tween everything' approach - just on another level. And you'll lose some native browser features like e.g. jump-to search via F3. Is it worth the extra mile? Depends on how much you're a sucker for detail and how much the - most of the time visually small - asynchrony bothers you. Is any one better than the other? Depends on you again. Each of them has its downsides, if you ask me. Personally I'd go with the overall smooth-srolling - but that is merely a suggestion, not a recommendation by any means. It will definitely add another level of complexity with some regards. The latter - here it was just to keep track of what marker is related to which ScrollTrigger. But it can also be a helpful tool if at any point in time you might need to target any specific ScrollTrigger on your page for whatever reason logic-releated.
  11. Then logically you'll need to make sure that your video is appearing on the page further up than it is now. You could e.g. calculate the distance it takes to scroll from when the 4s start fading out in your one ScrollTriggger until the point where your video enters the viewport now and then you'd know by how much you'd have to offset your video to the top for it to enter the viewport when the 4s start fading out. And this you'd have to of course do before you set up your ScrollTriggers for the video. Or - since your airpods Scrolltrigger is dependent on the window height anyway - just set a vh value that fits for you via CSS, e.g. via a negative margin-top on your video container. That is what I did in the codepen below. A bit of a warning though; keep in mind that since you have a numerical scrub on your airpods scrollTrigger, the scroll of the video and the fading out of the 4s will never be truly 'synced' - which will become more apparent when you scroll fast. You are adding the tweens for the fading of the video to your first timeline - which has a scrub set. I'm not sure if that is what you want to begin with, since you added the tweens at the very bottom of your JS after you created all the ScrollTriggers. And if you add it to the pinning Scrolltrigger like you do, of course it will only start fading in the opacity once the video has reached the top, and then the 'over-scrolling' you were trying to achieve wouldn't make any sense at all anymore. So you'll probably want to add the tweens to that other, non-pinning, ScrollTrigger instead and also set it to scrub. That out of the way, here's something from the article on the most common ScrollTrigger mistakes: https://gsap.com/resources/st-mistakes/#how-to-make-scrub-animations-take-longer ------ BTW - @GreenSock @Rodrigo @Cassie - there's a wrong link in that blue information box in that section of the article. It is an old URL which previously pointed to this content: https://gsap.com/docs/v3/Plugins/ScrollTrigger/#how-does-duration-work-with-scrub-true But although the general concept of how durations work with scrubbed: true is explained there, there isn't any mention of empty tweens as suggested in that blue information box - sort of confusing altogether. Edit: I also found a typo in the docs for the position parameter with regard to percentages, that I'm mentioning further down the post. Reporting it here, where it might be better to catch. ----- That second link explains how durations work with scrub: true, @newguy123 - you should have a thorough read on it to understand the concept. I added some comments in the codepen below that might help better understand it in combination with what the docs say. In that codepen I also make use of the aforementioned empty tween to create a 'gap' where nothing happens between the fading in and fading out. So I also got rid of your approach with the position parameter - of course you can do it with the position parameter, too, but you'd have to use the proper value - and for understanding how durations work with scrub: true to begin with it might be easier to work with empty tweens at first. Also, I'm pretty sure the value you use for the position parameter (i.e. "99%") again is invalid. Here's what the docs say with regard to percentage values in the position parameter. You see, a percentage value without any prefix is not listed in there. In your example you could in fact change it to "0%" and it would still behave exactly the same as it does now. https://gsap.com/resources/position-parameter/ That all said, here's the codepen. https://codepen.io/akapowl/pen/ExJNxJO
  12. Awesome thanks @akapowl For the video, as per your suggestion, I added the 2nd scrolltrigger for the video to make it play automatically at a different time, than what its container reaches the top of the viewport. This works great. I like the way AAA and BBB scrolls past, over the video in usual fasion, so that part is great also. The next bit of my troubles, are that I want the entire video (ie both scrolltriggers for the bunny video), to come in slightly earlier in the scroll. Currently the Airpods scroll completes, and after it is done, it scrolls out of view and the video scroll in. It would be great, if I can have the video coming in already, at the part where the Airpod's title "4444444" starts fading out. I can't figure out how to do this and seems the video will always only come in AFTER the Airpods scroll fully completes. Also, I adjusted the video scroll some more, to also fade in and fade out. The problem with this part is that my initial fade in, seems to take too long. No matter what I set the duration to, it doesnt seem to make a difference. For the fading out part, same thing, it takes too long to fade out. Also, it start to fade out too soon. I only want it to start fading out when "BBB" is almost out of view, but before "The End" comes in. https://codepen.io/newguy123/pen/dyLpxqp
  13. Helloo, I have a image secuence working on scroll with scroll trigger, and it works mostly fine, but when i scroll the whole secuence and i scroll back, the console gives me this error: Uncaught TypeError: Failed to execute 'drawImage' on 'CanvasRenderingContext2D': The provided value is not of type '(CSSImageValue or HTMLCanvasElement or HTMLImageElement or HTMLVideoElement or ImageBitmap or OffscreenCanvas or SVGImageElement or VideoFrame)'. Here is the js: gsap.registerPlugin(ScrollTrigger,ScrollSmoother); // Smooth Scroll var smoother = ScrollSmoother.create({ smooth:2,speed:2,effects:!0, }); function checkMedia(media) { if (media.matches) { smoother.kill() } else { smoother } } var m = window.matchMedia('(max-width: 820px)'); checkMedia(m); m.addListener(checkMedia); // Scroll Trigger Image Secuence const canvas = document.getElementById("hero-lightpass"); const context = canvas.getContext("2d"); canvas.width = 800; canvas.height = 500; const frameCount = 1100; const currentFrame = (index) => `/dist/images/animacionlonglow/naw_test${(index + 1).toString().padStart(4, "0")}.png`; const images = []; const airpods = { frame: 0 }; const imageUrls = []; for (let i = 0; i < frameCount; i++) { imageUrls.push(currentFrame(i)); } for (let i = 0; i < imageUrls.length; i++) { const img = new Image(); img.src = imageUrls[i]; images.push(img); } gsap.from(".scroll-title", { opacity: 0, y:100, duration: 1, delay: 3, }); gsap.to(airpods, { frame: frameCount + 1, snap: "frame", ease: "none", scrollTrigger: { trigger: ".canvas-container", start: "top top", end: "+=12000", pin: true, scrub: 0.5, onUpdate: render, images[0].onload = render; function render() { context.clearRect(0, 0, canvas.width, canvas.height); context.drawImage(images[airpods.frame], 0, 0); // . Texts Appear on Scroll / Frames if (airpods.frame >= 100 && airpods.frame < 310) { document.querySelector('#section-text-1').classList.add('active'); } else { document.querySelector('#section-text-1').classList.remove('active'); } if (airpods.frame >= 450 && airpods.frame < 600) { document.querySelector('#section-text-2').classList.add('active'); } else { document.querySelector('#section-text-2').classList.remove('active'); } if (airpods.frame >= 700 && airpods.frame < 900) { document.querySelector('#section-text-3').classList.add('active'); } else { document.querySelector('#section-text-3').classList.remove('active'); } if (airpods.frame >= 990 && airpods.frame < 1200) { document.querySelector('#section-text-4').classList.add('active'); } else { document.querySelector('#section-text-4').classList.remove('active'); }; }; Let see if someone know the issue, and also can give me a good way to preload all the image secuence before loading the page. Thanks a lot
  14. DrH

    Gsap is not defined

    Hello, Im new in this animation cooding so when i add the script src for scroll trigger in my html and when i copy some of the codes that are on the forums Like Apple Airpods pro animation ot dont work. This is what always pop out when i try it
  15. Hi Guys I have 1 X Scrolltrigger, ie the Apple Airpods example, with 4 titles appearing over it as you scroll. This works great, as expected. However, immediatly AFTER the 1st scrolltrigger finishes, I want the next one to start as it come in to view. Its a video and it should loop and only start playing when it comes into view. What's more, I want the video to STAY PINNED for a bit, enough for the next 2 titles "AAA" and "BBB" to scroll past. Then the video should unpin scroll out of view while the next section "THE END" scrolls into view. I have 2 troubles here. I can't seem to pin the video and I cant seem to play it when it comes into view, while the 2 titles scrolls over while the video is pinned. https://codepen.io/newguy123/pen/NWmReyM
  16. Hi As per the Apple Airpods example on GSAP, which currently only shows 1 image sequence in the example, what if I want to have 3 or 4 sections, each with its own sequence? Do I simply duplicate the existing code for the single section, and just rename the classes/ids in html for each section, and same in the javascript? Ie, I will then have 4 different scrolltriggers, each firing when its relevant section reaches it's start?
  17. Hello guys from GSAP community! You have created a cool tool, congratulations to you. And now, I'm trying to recreate the text animation in the second section from Apple's website: https://www.apple.com/airpods-pro/ The problem is that ScrollTrigger doesn't behave quite as I expected and instead of the Fade-In-Out effect on individual sentences like on the reference, I have the transparency of the entire text changing as soon as it enters the viewport. Can you please tell me what I'm doing wrong? Maybe someone has already tried to recreate this animation?
  18. Hello, i'm trying to do build the same video/image sequence style of the Airpods website and also add text. I googled and found this awesome codepen posted in the GSAP forum (see end of post): I'd like to have something like this codepen (scroll after panel 5) : https://codepen.io/GenSock/pen/bGexQpq?editors=0010 But I really don't know how I can do something like this (add a sort of duration maybe ? Or even "scroll-out" when there is no text left to show ?) Here is an example when I try to simply add another div (see screenshot) : you can see that the canvas is still "playing" (the scroll duration comes from the window height not the canvas height/parent height), and also that is goes way beyond the div. So, my question is: how can I make it so it does not goes beyond the div, and that the canvas duration is related to the div size (after div, the canvas is not changing). Also, I'm doing my website with React, and found this npm package : https://www.npmjs.com/package/react-gsap Do you recommend to use it, or should I stick with "basic" gsap ? Thank you .
  19. Thank you @mvaneijgen! I completely agree. However, I still think that it's vital to understand how animated content affects SEO. And, more specifically, how GSAP's animations are perceived - does Google bot generally ignore all GSAP's animations and see the content only as it is displayed initially in html and css? There are always exceptions and certain content/pages can be more heavily animated to control all aspects of users' journey and perception - think product presentations or specific About pages. For example: https://www.apple.com/airpods-3rd-generation/ or https://i2-camera.polaroid.com/ How to make the call which elements are safe to animate (and how), if one has no idea how each choice will affect the SEO strategy? This becomes even more important when dealing with clients who rely on search traffic to get users on their pages and then use design (including animations) to convert them. For now, I'll be playing around with GSAP for my personal projects only and testing as much as possible but any large scale experimentation is outside my budget. And without having any idea how GSAP's animations are perceived by Google, I'm unable to recommend it to anyone (well, besides saying that "stuff will look pretty but there's a chance that no one will see it"). Essentially, I'm hoping that someone else ran into these same questions as I have and would be generous enough to share their experience and best practices discovered. Will keep this thread "unsolved" if that's ok - perhaps someone else will have something to share or my experiments will yield at least some concrete results that I could share. For now, all I could find was a video from 2017, where John Mueller "suggested" that partly visible content or content starting invisible and becoming visible when the rendering is finished, is treated as visible: So, with this in mind, it could be said the it's best practice to have content start at 0.5/0.7 opacity and animate to 1? Or have content sliding in from position only partly offscreen? Or have elements fully visible further down on page load and then use GSAP to do whatever you want with them as user scrolls down (for example: https://codepen.io/vitaeludus/pen/gOqQGXP)?
  20. Hello everyone! I got inspired by Apple's website: https://www.apple.com/airpods-pro/ I would like to ask for help from those who know how to replicate a block animation. Specifically, I'm interested in the ability to change text and images that are in a fixed position, meaning they do not change their position when scrolling. Could you help me with how to correctly use ScrollTrigger? This block
  21. Hi, I'm new to Greensock and think it's absolutely fantastic! I'm trying to do something similar to Apple Airpods which was based on this post: https://greensock.com/forums/topic/25188-airpods-image-sequence-animation-using-scrolltrigger/ The idea is I want several products on one page and as you scroll down it loops through the images the same as Airpods and displays some text. It works fine for one product but when I add a second it overlays them on top - I'm presuming as I'm using position fixed - but I'm wondering why they are triggering at the same time and not after each other? I know I have messed something up quite badly and wondered if anyone knew what? Thanks! Chris
  22. Thanks for help! Here's an example that I almost managed to create, thanks to you! https://codepen.io/bysobi/pen/YzBEBpM I've come close, but I can't figure out the sequence of the animation. It seems too complicated. The website and the section I want to replicate: https://www.apple.com/ua/airpods-pro/ Question #1 I've almost managed to replicate the text animation. However, I encountered issues with the image. The initial appearance of text and image aligns with the example of apple. Problems arise during the display of the second block. It should be like this: 1. Scroll through text #1. It's almost gone, but image #1 is still visible and not hidden. 2. As soon as text #2 appears, image #2 smoothly appears. Question #2 Each block with text and image occupies a height of 100vh. I would like to keep it that way but reduce the amount of scrolling needed to initiate the animation. Thank you so much. I've spent over 18 hours but still couldn't solve this issue.
  23. the problem is that those examples are simple little squares ande circles and getting directly animated, where the airpods thing has its own function doing things. Its that function I'm having a hard time with to convert to React. Its getting the context of the canvas in the function, when the canvas is returned in the app, but the function is not seeing it for some reason
  24. I think you had not clicked save on the file before sharing. The original file you started with had the correct setup and I think you just removed everything and copied over the AirPods demo. In React you need to do proper cleanup in the useLayoutEffect function. I don't use React myself, but everything is explained in the example I've shared. My suggestion would be start with one of our React templates and copy over the logic you want one by one until something breaks.
  25. Hey guys, I've been working on setting up my own image sequence animations using ScrollTrigger and a method based on what @OSUblake already included in this thread. One issue I keep running into, though...I have one animation that I want to run twice during scroll, using two different triggers. It works fine on desktop, but on mobile, the first time it is supposed to run, it often runs too soon or is on a weird frame other than the first frame before I reach my trigger. Oftentimes, if I scroll past it, scroll back up, and then scroll back down, it works fine again. Here's a link to the project I'm working on: https://plantd.webflow.io/dev/product-copy-7-gsap-forum The element I'm animating is the #init-canvas <canvas> and its first trigger is #init-gsap. Can anyone offer any insight? By the way, I'm not sure if I have it set up correctly in my javascript to run the same animation twice and be triggered by two different triggers. Here's the gsap js I'm using (I can send more if you need it, or you can find all of my gsap js in the .gsap-scripts element near the bottom of the page): gsap.to(airpods, { frame: frameCount - 1, snap: "frame", ease: "none", scrollTrigger: {trigger: "#init-gsap",start: "top top",end: "bottom top", scrub: true }, onUpdate: render // use animation onUpdate instead of scrollTrigger's onUpdate});gsap.to(airpods, { frame: frameCount - 1, snap: "frame", ease: "none", scrollTrigger: {trigger: "#init-2",start: "top top",end: "bottom top", scrub: true }, onUpdate: render // use animation onUpdate instead of scrollTrigger's onUpdate}); Let me know if there's a better way I should be doing that! Thanks in advance for any help anyone can provide!
×
×
  • Create New...