Jump to content
Search Community

GSAP breaks after layout changes?

nathanr test
Moderator Tag

Warning: Please note

This thread was started before GSAP 3 was released. Some information, especially the syntax, may be out of date for GSAP 3. Please see the GSAP 3 migration guide and release notes for more information about how to update the code to GSAP 3's syntax. 

Recommended Posts

It appears that once you change CSS properties that effect page layout, the effected elements can no longer be animated using GSAP.


I have an example here that is a simplified version of my project. Click on any of the colored rectangles to see what I'm describing. The first time you click, it transforms and scrolls to simulate zooming in on a rect. But since doing so also changes layout CSS properties - it breaks as soon as you start animating again in a peculiar way.


You won't be able to tell from the example why it is necessary to change layout properties, but it is something I need to do in my actual project.


You can see the behavior I expected would happen by commenting out the lines of code that effect layout. Or view the fork that does so here.


Is this a known issue? Am I the only one who needs to manipulate layout effecting properties between animations? 

Link to comment
Share on other sites

Hi and welcome to the forums.


The problem is that you're adding a position:absolute to the element but not removing it:

function doFlyUp(e) {
    var tl = new TimelineMax();
    tl.append(TweenLite.to("#container", 0.6, {scrollTo:{x:($(e.target).position().left+66.666)*4, y:30}, ease:"Expo.easeOut"}));
    tl.append(TweenLite.to("#outerRect", 0.6, {scaleX:1, scaleY:1, ease:"Expo.easeOut", onComplete:function() {
        $(e.target).css({"position": "absolute", "margin":"0px"});
		TweenLite.to("#outerRect", 0, {transformOrigin:"left top", scaleX:1, scaleY:1});
        TweenLite.to("#container", 0, {scrollTo:{x:0,y:0}});
    }}), -0.6);
function goBack(e) {

    $(e.target).css({"position": "inline-block", "width":"150px", "height":"75px", "white-space":"normal", "margin":"30px 0px 0px 75px"});
    var tl = new TimelineMax();
    tl.append(TweenLite.to("#outerRect", 0, {transformOrigin:"left top"}));
    tl.append(TweenLite.to("#container", 0.6, {scrollTo:{x:0, y:0}, ease:"Expo.easeOut"}));
    tl.append(TweenLite.to("#outerRect", 0.6, {scaleX:0.25, scaleY:0.25, ease:"Expo.easeOut"}), -0.6);

If you change it to relative, it should work as expected.




Link to comment
Share on other sites

Hi, Rodrigo. Thanks for looking at my code and the reply!


You are correct about my misuse of "inline-block" as a value for "position" when it is a value of the display property.


Unfortunately, correcting this does not alter the behavior of TimelineMax with subsequent animation. Take a look.


That was a typo I accidentally introduced when I threw together the sample -- it wasn't in my original project. It still looks to me like layout changes are breaking TimelineMax.

Link to comment
Share on other sites

Hello.. why not remove the display:inline-block property completely from your rect div's. And add float:left to your boxes so they position inline without using inline-block, since display inline-block is buggy in IE, and has some other issues in chrome.


Then add a child div within each of your rect1, rect2, and rect3 div's. And then zoom out that child div instead. So this way the rect div's will keep their position, and the child div itself will do the zooming.


Basically you will keep the positioning of the rect divs separate from its child, which will be doing the animated zoom out  ...just a thought! :)

Link to comment
Share on other sites



I became interested with your fiddle, well a little obsessed :P, because is a very neat effect the one you're after.


I came up with this codepen:

See the Pen xGbHK by rhernando (@rhernando) on CodePen


The code is commented but basically what I did was simplify as much as possible. I followed the same markup in order to keep it as similar as possible to the original layout. First took out the scrollTo plugin, which is great but IMO unnecessary in this case. Then instead of a timeline just a simple tween to animate the container, since there's no scrolling the only chances were either move every object or the container, the latter is simpler. Finally record the original positions of the child elements in order to tween simultaneously the scale and the left position of the container, based on the child positions.




  • Like 4
Link to comment
Share on other sites

Hi, Rodrigo.


Thanks for the fresh take on my problem.


Unfortunately, my situation requires that I change the position attribute of the child elements to "absolute" after the zoom. When I forked and added the layout changes I need to make into your click event, I get the same result as before.


I have settled for a less desirable effect (

See the Pen omhtj by subcreation (@subcreation) on CodePen

). I think the solution I would need to get the effect I wanted would require separating my index view entirely from the fullscreen content - which is way more work than I budgeted for.


I don't know whether this is a defect in the browser, JQuery, or Greensock, but it certainly seems like a legitimate expectation that layout changes on child elements shouldn't interfere with animating the parent later on.


Anyway, thanks again for your time and ingenuity, Rodrigo.



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