Jump to content
Search Community

Easing Feature Request

ElliotGeno 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

Other than chaining multiple tweens, it is rather difficult to adjust a property that needs to return to the same value. I've run into this a lot, but have a hard time articulating the need. Recently, I was reading a blog about various animation tools and Mo.js came up which I wasn't familiar with. (Don't worry Jack... I'm not switching!)

What was interesting is they visualized my need in a graph: http://mojs.io/tutorials/easing/path-easing/

Rather than easing from 0>1 it eases through various values back to 0. (0>0)

 

Like this:

easing.png

 

I realize you can create your own easing function, and the new modProperties feature can help with this... And it is probably a serious undertaking as there are probably some internal checks that you need to do if a custom ease is applied to allow the property to tween. But this would be extremely useful!

 

Perhaps there are some unique tricks you can pull out of your hat? ;)

 

 

Link to comment
Share on other sites

Hey @ElliotGeno,

 

I'm way behind schedule for a lot of things. Can you make an editor? SVG, canvas, doesn't matter. Paper.js has a lot of good drawing tools.

 

If you do that, I can make the easing script. I just need to make a couple modifications to my Cubic Bezier script.

 

I remember you asking about using

See the Pen wKGvVG by osublake (@osublake) on CodePen

to help make some of the curves, but I still need to do a lot of work on that. It might be better to use a more common type of curve, like a Catmull-Rom. Here's a demo of 3 different types of catmull-roms.

See the Pen 670e4e0fa926ad4ec703f65ee8f545b0?editors=0010 by osublake (@osublake) on CodePen

 

That demo is using some Three.js classes, but you wouldn't need to include them. Converting a catmull-rom to a cubic Bezier isn't that hard. I think the uniform catmull-rom is what's being pushed as a new path command in SVG2. I can post examples converting the other 2 types later. 

See the Pen BowJed?editors=0010 by osublake (@osublake) on CodePen

 

What do you think?

  • Like 3
Link to comment
Share on other sites

@OSUblake Is cubic the most performant?

 

If so, I think I could design something that automates the cubic bezier handles. (Basically balance the control points based on other neighboring points.) Optionally allow handles to be overridden by users. (each anchor would toggle between auto-bezier, manual-bezier, and point/'zero-radius')

 

What do you think of that?

Link to comment
Share on other sites

If you could design an editor, that would be awesome! I've been promising Chris Gannon an editor for the longest time, but have been too busy.
 
Cubic is very performant. That's what the browser uses for CSS easing. If you're asking about cubic vs quadratic, I don't think there's going to be much of a difference in JavaScript. If it was slow, which I've never noticed, you could have an option to precompute the values, but that's less precise and slower upfront. 
 
I just checked out how Mo.js is doing all this stuff. I must say that the API is rather confusing. Turns out the path easing doesn't use cubic bezier easing. There's a separate method for that based on this library. Same thing Velocity.js uses. I think it's based on Mozilla's bezier implementation. The one I'm using is based on Chromium's implementation.
 
Demo of their bezier easing. Like I said, confusing...

See the Pen BzWLre?editors=0010 by sol0mka (@sol0mka) on CodePen


 
Most of their code is written in coffee, which I don't really understand, but from what I gathered, they are using the path.getPointAtLength() method for path easing. I guess that's pretty close to what Jack suggested about using a bezier tween. 
 
I think a cubic bezier ease might be better though. Maybe Jack can offer some insight.

 

Link to comment
Share on other sites

I have several ideas that have been bouncing around my head regarding this, but I don't have the bandwidth to dive into it yet. I'm totally chomping at the bit though. I hate responsibilities :) 

 

Performance-wise, yes, it's essential that this thing be blazing fast because the ease gets calculated for every tween, on every render. The fewer the calculations, the better (duh). Quadratic is "better" in that sense, but I personally wouldn't use that because it's too limiting (Cubic is far better for authoring). A single Bezier isn't necessarily terrible, but my goal is to allow unlimited anchors and control points, so it becomes important to be able to quickly isolate which segment is pertinent at the given linear progress value. Again, I have some ideas that I want to sketch out and benchmark when I'm ready. One idea is to turn everything linear and approximate things and allow the end user to set the precision value (how many segments it's broken down into).

 

The path.getPointAtLength() worries me a bit both from a performance standpoint and because it doesn't really map properly to the time/progress data. It gives a certain effect, but it ain't accurate. It could be WAY off in fact (imagine a curve that has huge vertical waves that are packed tightly together horizontally at the beginning, and then halfway through it steadies out to a straight line to the end).  

 

Like Blake said, a big piece of this challenge is just making sure there's a solid curve editor in the browser (SVG). If you want to tackle that so people can interactively build a curve, that'd be awesome and likely accelerate the time frame for this kind of feature. 

 

Oh, and you can't just divide the progress by the number of segments to find which one is the current one, as some of the segments may be much longer than others. And the editor should probably prevent folks from overlapping anchors on the x-axis. 

 

Does someone have a pressing need for this right now that can't be accomplished with any of the other eases or even Blake's tool? 

  • Like 2
Link to comment
Share on other sites

A single Bezier isn't necessarily terrible, but my goal is to allow unlimited anchors and control points, so it becomes important to be able to quickly isolate which segment is pertinent at the given linear progress value. Again, I have some ideas that I want to sketch out and benchmark when I'm ready. One idea is to turn everything linear and approximate things and allow the end user to set the precision value (how many segments it's broken down into).

 

By turning everything linear, do you mean like this?

See the Pen doBQMR?editors=0010 by osublake (@osublake) on CodePen

 

And if so, would the segments be equal, or adaptive like that demo? Adaptive, meaning there are more points in the curved sections, and less in a straight sections.

 

Like Blake said, a big piece of this challenge is just making sure there's a solid curve editor in the browser (SVG). If you want to tackle that so people can interactively build a curve, that'd be awesome and likely accelerate the time frame for this kind of feature

 

I know people got really excited when those mo.js demos came out, but they're overlooking a huge part of making motion graphics, and that's a proper editor.

 

Using a graphics editor like Illustrator is not going to cut it. You need to be able to see the changes in real-time. Using a graphics editor, you would have to export or copy and paste your shape to make any adjustments. I don't see how that workflow could be an effective solution.

 

Try creating an animation like this in Illustrator... (graph editor from Maya)

 

MVY9Qla.png

 

 

 

  • Like 1
Link to comment
Share on other sites

Here's an awesome site about animation. Check out the first slide show. It's about using Catmull-Rom splines for timelines. If you don't recognize the name Catmull, it comes Edwin Catmull, the president of Pixar.
http://acko.net/blog/animate-your-way-to-glory-pt2/
 
Easing + motion path = win! That's why most camera path animations use them, like this tube camera. That's made by @ZachSaucier, a frequent GSAP forum helper.

See the Pen XKPKwo?editors=0010 by osublake (@osublake) on CodePen


 
But you don't need Three.js. Here's how to convert a set of points to the 3 different types of Catmull-Rom splines. I set them up to return SVG paths as cubic Beziers.

See the Pen 5902d293353bbefe1447d350fbd79cdc?editors=0010 by osublake (@osublake) on CodePen


 
Here's a quick overview of differences.
http://www.cemyuksel.com/research/catmullrom_param/

Another reason why I would recommend having an option to use Catmull-Roms is that some cubic Beziers are going to be really hard to draw. There's just not enough screen real-estate to move the control points around for some types of curves.
 
I setup a

See the Pen fea46b4aff67a5b423eb9cd12548ef22?editors=0010 by osublake (@osublake) on CodePen

to play around with. Try making a curve like this with the Bezier editor. There's not enough room!
 
KBD06Ml.png
 
Side-by-side demo...

See the Pen fea46b4aff67a5b423eb9cd12548ef22?editors=0010 by osublake (@osublake) on CodePen

Link to comment
Share on other sites

Great info, Blake. Super helpful. Love the links.

 

I'm not nearly as familiar with Catmull-Roms and I'm a little worried about the costs (complexity-wise and kb-wise) of supporting both Cubic Beziers and Catmull-Roms, but can you confirm that Catmull-Roms would allow you to easily create corner anchors like the ones necessary for "Bounce" eases (where there's **not** a smooth transition)?

 

I totally agree about the necessity for a proper in-browser editor for this type of thing. I don't think, however, that the "it might be hard to fit the handles into the viewport" thing with Cubic Beziers means that Catmull-Rom support is necessary; If the user is allowed to zoom in/out and drag the work area around, it could pretty easily solve that issue with Cubic Beziers. 

 

Oh and as for the adaptive question, I'm not 100% sure yet. I'd need to do some experimentation and benchmarking. If you've got strong preferences and research to back it up, I'd love to hear them. But to be clear, this is not something I'm planning to dig into yet...there are several more pressing things I need to work on in the codebase but as I said earlier, I'm chomping at the bit to get to work on this. It's quite painful not to be able to yet :(

  • Like 1
Link to comment
Share on other sites

The Catmull-Roms would be converted to cubic Beziers in the editor, so you wouldn't necessarily have to support them for easing. Whatever method you're using for the Beziers should work for them.

 

The curvature is determined by the previous (p0) and next point (p3).

xBdfyBt.png

 

So creating a corner like in a bounce ease should work if p2 and p3 are at the same position.

 

8wtCxZf.png

 

But that would only work for a centripetal one though. For the other two types, you would have to terminate and start a new curve at the corner.

 

 

  • Like 3
Link to comment
Share on other sites

  • 2 weeks later...

I was working with Paper.js earlier today and decided to make a very simple editor.

See the Pen c9a2eb1b0ff6400b473e2c80d23d3128?editors=0010 by osublake (@osublake) on CodePen

 

It's very primitive, and I didn't setup the easing yet. I was wondering what would be the best way to determine the current segment for a linear ease? The points are normalized to a length of 1.

Link to comment
Share on other sites

That's great, Blake. I wouldn't exactly call that "very primative" :)

 

I didn't quite understand your question about the "current segment for a linear ease". Do you just mean, for example, that at a progress of 0.5 (halfway through the tween/curve), you want to determine which Bezier segment that lands on given the fact that there could be an unlimited number of segments? If so, the general concept (at least in my mind) would be to pre-calculate the progress value for each anchor/node and then take whatever value that comes in (0.5 in this case) and find the corresponding segment (the value is between the start and end node progress values). Then you just plot the progress on that particular segment based on the ratio. Does that help at all? 

Link to comment
Share on other sites

I was trying to figure out the fastest way to find the y value, maybe using a linked list, typed array, or maybe using a binary search. For now, I'm just looping through a normal array.

 

Question, does using the getRatio ease method always set the final value to 1? If you change the final point, you'll notice that always jumps back to 1 at the end.

 

Update version...

See the Pen 48970ccf28b71ef55372eecec155864f?editors=0010 by osublake (@osublake) on CodePen

  • Like 1
Link to comment
Share on other sites

Yep, a linked list would be much better, but I've got some ideas about further optimization but I've gotta sketch it out and do some tests. 

 

As for the final value always going to 1, you just have to set the _calcEnd property of the Ease to true if you want to make it actually calculate the final value (typically that's a total waste of CPU cycles and can actually lead to glitches due to rare scenarios where the math spits back something like 0.9999997 which throws final renders off - that's why by default GSAP just assumes the value will be 1 when the tween is done). 

  • Like 1
Link to comment
Share on other sites

Gotcha. I just made the _caclEnd conditional. I also converted the ease points into a linked list. So there you go, first proof of concept!

See the Pen b7f5c5b3456eef085930d08d91b1cb1c?editors=0010 by osublake (@osublake) on CodePen

 

EDIT: And after making those changes, I realized that I could have used a lot of code from the RoughEase, like the linked list and the getRatio method.  :huh:

  • Like 3
Link to comment
Share on other sites

Looking good, Blake! The biggest help, quite frankly, is the visual editor for building the curve. Good stuff, man. 

 

So the GUI just relies on PaperJS? How easy do you think it'd be to make it zoomable and style it differently? 

 

Yep, the GUI is all done using PaperJS. I've been using it a lot lately to build some tools. CodePen actually picked a tool I made the other day. It will zoom to where ever the mouse cursor is when you scroll.

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

 

And styling is real easy...

path.style = {
  strokeColor: "red",
  strokeWidth: 2
};

PaperJS actually started out as an Illustrator extension that allows you to interface with it using JavaScript, so it has a lot of the same functionality. Check out some of the tools in this demo. You should feel right at home using it if you know Illustrator. I didn't setup the mouse cursor to change, but the rotate handles are just slightly offset from the corners of a selection box.

See the Pen ae8d5b6197b49972ac6176d4ca784e23?editors=0010 by osublake (@osublake) on CodePen

 

It also has SVG import/export. It probably wouldn't be too hard to setup a morphing editor/playground. Check out the graphics from your MorphSVG demo. Looks like the greensock hero is wearing a sweater. 

See the Pen b62a31cbc472770dad1f6e0dc16c9f27?editors=1000 by osublake (@osublake) on CodePen

 

One really nice thing PaperJS can do is find the closest point on a curve. Here's a updated version that shows the time and tween value when you move the mouse around. The tween is 2 seconds long, and goes from y=400 to y=0.  

See the Pen 4fb3f66a2a138e9c76e7c2592cc1adf1?editors=0010 by osublake (@osublake) on CodePen

 

That could be very useful! I'm thinking this could also be used as a keyframe editor. I know people have been dying for a GSAP based GUI. This could definitely be used as a starting point to build from.

 

1jtwQbp.png

  • Like 3
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...