So I Wanted To Have A Custom Bézier Curve

There may come a time where, when writing an animation on iOS, that the simple, inbuilt animation curves no longer suit your requirements. If the previous words sent you for a tailspin, read on.

Let’s start with a quick lesson:

If we get into the specifics of it -

A Bézier curve (pronounced [bezje]) is a parametric curve frequently used in computer graphics and related fields.
— Wikipedia

However most iOS developers will simply know them by name. They are;

  • curveEaseIn
  • curveEaseOut
  • linear and
  • curveEaseInOut.

They are most often used with a basic UIView.animate() call.

Let’s start with Linear. If you invoke UIView.animate(withDuration:) without supplying any options, only the duration and an animation block, it will execute the animation along a linear internal path.

That is to say, the object you are moving will go from A to B at a constant rate until the animation is finished. The path is not curved.

Next up, is CurveEaseIn. It’s almost the same as linear, however this time the animation executes along an internal curved path, hence the name.

The object you are moving will go from A to B, starting off slowly (“easing in”), accelerating to a constant rate, then stopping. The path itself, should it be drawn or plotted, would look something like this:

You get the idea. curveEaseOut is the opposite of the above, meaning that the object you’re moving will go from A to B, starting off at a constant rate, and decelerating to a complete stop (“easing out”). curveEaseInOut is a combination of the two.

Oh yes, there are more. By more, I mean anything you can think of!

If your team’s UI/UX Designer said that the animation “curve” you’re using wasn’t smooth/blunt/whatever enough, what would you do? I’d hazard a bet that many of you would push back on such criticism.

As for me, I’m like a Dog hell-bent on extracting a treat from a KONG toy. I quickly found a way to make my own “curves” with CAAnimation but it required the prolific usage of “magic numbers” in the code, and they were very complex blocks of code.

If you look at the graph above, you’ll see why. The curve is controlled by two “control points”. The graph above has only 1 visible control point, and it lies at the right-hand side of the orange line.

Loosely translated into code, the graph would read something like:

let controlPoint1 = CGPoint(x: 0.34, y: 0.00)
let controlPoint2 = CGPoint(x: 1.00, y: 1.00)
// The other n lines of CA code that uses the above here

Thankfully, as of iOS 10, Apple now allow us to create our own curves, and, instead of being forced to use CAAnimation, we can use them with something called UIViewPropertyAnimator.

I got creative with my own easeInOut curve:

If we go ahead and create a class (or a struct, if that Floats your boat) calling it CustomCurves for simplicity’s sake, and define the following within it:

static private var curveTightEaseInOut: UITimingCurveProvider = {
return UICubicTimingParameters(
controlPoint1: CGPoint(x: 0.89, y: 0.38),
controlPoint2: CGPoint(x: 0.11, y: 0.61)
)
}
static var curveTightAnimator: UIViewPropertyAnimator {
return UIViewPropertyAnimator(
duration: 1.0,
timingParameters: curveTightEaseInOut
)
}

You can then use it in your code, the same way as you would a UIView.animate() as follows:

let viewFrameAnimator = CustomCurve.curveTightAnimator
viewFrameAnimator.addAnimations {
// Add Animations Here
}
viewFrameAnimator.addCompletion {}viewFrameAnimator.startAnimation()

And you know I could attach a gif with a demonstration of the above code here. But I won’t. Because you should give it a shot 😄

If you liked this post, and like what I have to write about, give me a follow on Twitter. I also appreciate a Recommend ⭐️

Aussie iOS Engineer based in Tokyo, Japan | 日英可