Jump to content
Search Community

Problem with timeline animations

Kutalev test
Moderator Tag

Recommended Posts

Hi everybody!
I have a problem configuring a menu animations. That's my 5th version. I realised the best way is to use master timeline.

But, trying to put it all together, I get an unpredictable behavior.

 

Animation for showing/hiding dimmer works great.

dimmer_tl
    .fromTo(dimmer, {opacity: 0, display: 'block'}, {opacity: 1})
    .set(js_dimmer, {display: 'block'})
    .add('show')
    .to(dimmer, {opacity: 0, display: 'none'})
    .set(js_dimmer, {display: 'none'})
    .add('hide')
dimmer_tl.tweenTo('show');
dimmer_tl.tweenTo('hide');

But truing to do the same with menu background doesn't work :(

bg_tl
    .fromTo(bg, {opacity: 0, display: 'block'}, {height: 200, opacity: 1})
    .add('show_list')
    .fromTo(bg, {opacity: 0, display: 'block'}, {height: 100, opacity: 1})
    .add('show_search')
    .to(bg, {opacity: 0, display: 'none'})
    .add('hide')

 

bg_tl.tweenTo('show_list');

 

bg_tl.tweenTo('hide');

It feels like the animation on show_list is not pausing and going threw all of them

bg_tl
    .fromTo(bg, {opacity: 0, display: 'block'}, {height: 200, opacity: 1})
    .add('show_list')
    // .fromTo(bg, {opacity: 0, display: 'block'}, {height: 100, opacity: 1})
    // .add('show_search')
    // .to(bg, {opacity: 0, display: 'none'})
    // .add('hide')

Or maybe I'm trying to reinvent the wheel and there are better practices to control?

I'm glad to hear any suggestions. Thanks!

 

P.S. Also moving mouse really fast between links play a timeline through all of them. I guess I need to add a delay somewhere but every time I do so it's just breaking apart.

 

 

See the Pen ZEOELmB by kutalev (@kutalev) on CodePen

Link to comment
Share on other sites

Hey Kutalev.

 

On 10/7/2020 at 8:10 AM, Kutalev said:

I realised the best way is to use master timeline.

A master timeline is only helpful when creating a very long sequence of sub-animations. If you have animations that should stay completely separate then adding them to a master timeline wouldn't be helpful. In this situation it looks to me like you have two main parts to animating these components:

  1. Opening the drawer/sub-navigation section.
  2. Animating the list elements for the currently hovered main section.

Some comments about your code:

  • Why do you need two dimmer elements? I would think one would be perfectly adequate.
  • It's best to use responsive units to size your content instead of large, arbitrary numbers like height: 2000px;.
  • I don't understand what you're trying to do with the negative margins.
  • It's best to try and avoid using methods that tween a timeline's progress if you can. Doing so unnecessarily makes it harder to get timings and easings exactly the way that you want them to be.

Instead of modifying your CSS and JS I thought it'd be more efficient for me to set up the way that I would approach this sort of thing. So here's my version:

See the Pen qBNEBba?editors=0010 by GreenSock (@GreenSock) on CodePen

  • Like 1
Link to comment
Share on other sites

Zach, thank you for the answer!

 

Two dimmers I was needed just in the case - the one covering the whole area except navigation and another one with dark background below.

I suppose my question was a bit messy) The main idea I'm trying to understand, is that a good practice to separate logic and settings with labels for complex and interactive animations.

 

Let's say I have a circle with different states, where labels, kind of, describing the state.

I made a simple codepen to describe what I mean. But even here it'n not working as I expected. Feels like it's going throw all of the states from the one I choose.

 

See the Pen eYzmZvP by kutalev (@kutalev) on CodePen

 

I believe this separation it's simpler, but maybe it's not a good practice somehow and in the future it may backfire?

// animation settings
circle_tl
    .to(circle, {width: 200, height: 200})
    .add('bigger')
    .to(circle, {width: 50, height: 50})
    .add('smaller')
    .to(circle, {borderRadius: 0})
    .add('square')
    .to(circle, {rotate: 180})
    .add('turn')
    .to(circle, {background: 'rgb(' + get_random(255) + ', ' + get_random(255) + ', ' + get_random(255) + ')'})
    .add('change_bg')
    .to(circle, {opacity: 1})
    .add('show')
    .to(circle, {opacity: 0})
    .add('hide')

// animation logic
function animateCircle(action) {
    document.getElementById('result').innerText = 'action: ' + action;
    circle_tl.tweenTo(action)
}

const buttons = document.querySelectorAll('.button');
buttons.forEach(button => button.addEventListener('click', () => animateCircle(button.dataset.gsap)))
Link to comment
Share on other sites

1 hour ago, Kutalev said:

I thought tweenTo creates a tween between current state and the one I choose skipping others.

No, not at all. tweenTo just animates the progress of another animation from wherever the progress is at to a given progress value :) 

 

If you want a bunch of standalone animations like the circle demo it'd be best to set up a bunch of functions that create a new tween each time you click, toggling between states for that button or something.

Link to comment
Share on other sites

Thanks!

I rewrote the code using functions - looks much better))

But still have a small problem. Clicking two fast pushes animations in a line even with overwrite.

 

So all of the triggered animations will play till the end. Is there anyway to stop it? Kind of stopping everything and playing only the last tween?

See the Pen dyXPOMb by kutalev (@kutalev) on CodePen

 

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