GSAP + SVG for Power Users 3: New 1.18.0 Features

By  on  

This is the third article in a series about the GreenSock Animation API and SVG. This series isn't intended for beginners, but rather a deep dive into some of the more exciting and lesser-known features that one can work with after they've gotten past the initial introduction. The first article was about Motion Along a Path. The second was about Complex Responsive Animation. Today we'll briefly explore some new GSAP features, and use them to make a more involved animation.

Stagger Cycle

The first feature we'll cover is stagger cycle. The stagger feature in a lot of JavaScript animation libraries tends to be a incredibly useful tool for creating elegant animations, and is definitely a benefit over a CSS workflow to create the same effect. To create a stagger effect in CSS, you increment the delay using the element or pseudo element with the same keyframes:

@keyframes staggerFoo {
  to {
    background: orange;
    transform: rotate(90deg);
 }
}

.css .bar:nth-child(1) { animation: staggerFoo 1s 0.1s ease-out both; }
.css .bar:nth-child(2) { animation: staggerFoo 1s 0.2s ease-out both; }
.css .bar:nth-child(3) { animation: staggerFoo 1s 0.3s ease-out both; }
.css .bar:nth-child(4) { animation: staggerFoo 1s 0.4s ease-out both; }
.css .bar:nth-child(5) { animation: staggerFoo 1s 0.5s ease-out both; }
.css .bar:nth-child(6) { animation: staggerFoo 1s 0.5s ease-out both; }

And in SASS, you could DRY it out a little:

@keyframes staggerFoo {
  to {
    background: orange;
    transform: rotate(90deg);
 }
}

@for $i from 1 through 6 {
  .sass .bar:nth-child(#{$i} ) {
      animation: staggerFoo 1s ($i * 0.1s) ease-out both;
   }
 }

However, with GSAP, you can create this effect with a single line of code:

TweenMax.staggerTo(".gsap .bar", 1, { backgroundColor: "orange", rotation: 90, ease: Sine.easeOut}, 0.1);

See the Pen here by Sarah Drasner (@sdras) on CodePen.

The conciseness is a workflow boon, especially if things need to be adjusted down the line.

With stagger cycle, we can now pass in multiple values to stagger between, something that would be exponentially complex in CSS. The syntax calls for an array of values:

TweenMax.staggerTo(".foo", 1, {
 cycle: {
   y: [75, 0, -75]
 },
 ease: Power4.easeInOut
}, 0.05);

Which you can also randomize, as well, for even more interesting effects.

var coord = [40, 800, 70, -200];

TweenMax.staggerTo(".foo", 1, {
 cycle: {
   x: function(i) {
     return coord[Math.floor(Math.random() * coord.length)];
   }
 },
 ease: Power4.easeInOut
}, 0.1);

In the following pen, I simply staggered between three values for each element, and only applied it to one element in the SVG. With very little code (22 lines of JS) you can accomplish so much:

See the Pen SVG with Cycle Stagger by Sarah Drasner (@sdras) on CodePen.

Relative HSL Color Animation

This one is relatively simple. Get it? Relative? Hoo Boy. The ability to tween relative HSL color amounts is fantastic, because if you're going to create sophisticated color effects easily in animation, slightly adjusting:

  • Hue
  • Saturation
  • Lightness

yields very powerful visuals. Say you wanted to turn a whole scene, every element a slightly different color, from day to night slowly. Previously the easiest way to do so was to slowly change the color value of each of these elements individually. You could put an overlay on the whole container, but that lacks sophistication and realism. Or, perhaps, use an SVG fe matrix filter- which is very unsemantic and not very intuitive to animate. Or even a CSS filter, that doesn't, as of yet, have a ton of support. Now, in one small piece of code, you can uniformly, and with great backwards compatibility, grab hundreds of elements and make them slightly darker, decrease their relative saturation, and slowly adjust their hue to turn them a slightly different shade. Tweening HSL also has the benefit of being able to be used for both background (for divs) or fill (for SVG) because it's not opinionated towards a certain type of property.

Here's a little demo to show how it works:

See the Pen Turtles that show Relative HSL tweening by Sarah Drasner (@sdras) on CodePen.

So many options! What's a good use case? Let's leave that up to your viewer. We can put the stagger cycle and the HSL color tweening together with some interaction. But instead of a night scene, let's make it a little more wild.

Because we are tweening relative values, we can combine effects on the buttons and get multiple outputs. We'll make two different buttons with slightly different relative effects. It's also worth mentioning that we finally have class operation on SVG in the 3.0.0 release of jquery and can easily control our tweens in interaction:

//button hue
function hued() {

//keeps the fill and background consistent relative hue changes
  var ch1 = "hsl(+=110%, +=0%, +=0%)", 
  tl = new TimelineMax({
    paused: true
  });

  tl.add("hu");

  tl.to(mult, 1.25, {
      fill: ch1
    }, "hu");

//tweens for background because of divs and css
  tl.to(body, 1.25, {
      backgroundColor: ch1
    }, "hu");

//the gauge responds to the action in the scene as if it's showing pressure

  tl.from(gauge, 2, {
      rotation: "-=70",
      transformOrigin: "50% 50%",
      ease: Bounce.easeOut
    }, "hu");

  return tl;
}

var hue = hued();

//same thing for the tweens for button saturation (has some relative hue as well)
function saturation() {
  var ch2 = "hsl(+=5%, +=2%, -=10%)",
  tl = new TimelineMax({
    paused: true
  });

  tl.add("sated");

  tl.to(body, 1, {
      backgroundColor:ch2
    }, "sated");

  tl.to(mult, 2, {
      fill:ch2
    }, "sated");

  tl.from(gauge, 2, {
      rotation: "-=100",
      transformOrigin: "50% 50%",
      ease: Bounce.easeOut
    }, "sated");

  return tl;
}

var sat = saturation();

// ...

//detect class and either start or reverse the timeline depending
$(but1).on('click', function(e) {
    e.preventDefault();

    $(this).toggleClass('a-s');
    if ($(this).hasClass('a-s')) {
      sat.restart();
    } else {
      sat.reverse();
    }
  });


  $(but2).on('click', function(e) {

    e.preventDefault();
    $(this).toggleClass('a-h');
    if ($(this).hasClass('a-h')) {
      hue.restart();
    } else {
      hue.reverse();
    }
  });

We'll also make the scene stagger in with a bit more nuance with the new stagger cycle. But because we want all of the elements to come in and eventually look the same, it makes more sense to use a staggerFrom than staggerTo:

tl.staggerFrom(city, 0.75, {
     y: -50,
     scale: 0,
     cycle:{
       x:[300, 100, 200],
       opacity:[0.5, 0.3, 0.2, 0.8],
       rotation:[50, 100, 150],
     }, 
     transformOrigin: "50% 50%",
     ease: Back.easeOut
   }, 0.02, "in");

And that becomes our city constructor set:

See the Pen City Construction Site by Sarah Drasner (@sdras) on CodePen.

There is one more key feature in this release: tweening and morphing complex string-based values. This is such a mind-blowing feature, though, we'll spend a future article focusing on this feature.

This is the third part of a several-part series. As we move forward learning each of these techniques, we'll tie together different ways of working to create increasingly complex and engaging work. Stay tuned!

Sarah Drasner

About Sarah Drasner

Sarah Drasner is currently a Senior UX Engineer at Trulia (Zillow Group) in San Francisco. She spends most of her time thinking about engaging user interfaces, animation, and how to weld together pieces of the DOM. You can find her on Codepen as sdras, on Twitter as @sarah_edo, or at sarahdrasnerdesign.com.

Recent Features

  • By
    Welcome to My New Office

    My first professional web development was at a small print shop where I sat in a windowless cubical all day. I suffered that boxed in environment for almost five years before I was able to find a remote job where I worked from home. The first...

  • By
    5 Awesome New Mozilla Technologies You’ve Never Heard Of

    My trip to Mozilla Summit 2013 was incredible.  I've spent so much time focusing on my project that I had lost sight of all of the great work Mozillians were putting out.  MozSummit provided the perfect reminder of how brilliant my colleagues are and how much...

Incredible Demos

  • By
    How to Create a Twitter Card

    One of my favorite social APIs was the Open Graph API adopted by Facebook.  Adding just a few META tags to each page allowed links to my article to be styled and presented the way I wanted them to, giving me a bit of control...

  • By
    NSFW Blocker Using MooTools and CSS

    One of my guilty pleasures is scoping out the latest celebrity gossip from PerezHilton.com, DListed.com, and JoBlo.com. Unfortunately, these sites occasionally post NSFW pictures which makes checking these sites on lunch a huge gamble -- a trip to HR's office could be just a click away. Since...

Discussion

    Wrap your code in <pre class="{language}"></pre> tags, link to a GitHub gist, JSFiddle fiddle, or CodePen pen to embed!