Easier bounce animation


#1

I tried implementing the bounce animation before I looked at the code in the book, and I thought I got it right—at least, it worked ok. When I looked at the book’s code, though, it seemed more complicated than the code I had written. I’m wondering whether or not I’m missing some subtlety.

Here’s the book’s code:

CAKeyframeAnimation *bounce = [CAKeyframeAnimation animationWithKeyPath:@"transform"];

CATransform3D forward = CATransform3DMakeScale(1.3, 1.3, 1);
CATransform3D back = CATransform3DMakeScale(0.7, 0.7, 1);
CATransform3D forward2 = CATransform3DMakeScale(1.2, 1.2, 1);
CATransform3D back2 = CATransform3DMakeScale(0.9, 0.9, 1);
[bounce setValues:[NSArray arrayWithObjects:
                   [NSValue valueWithCATransform3D:CATransform3DIdentity],
                   [NSValue valueWithCATransform3D:forward],
                   [NSValue valueWithCATransform3D:back],
                   [NSValue valueWithCATransform3D],
                   [NSValue valueWithCATransform3D:back2],
                   [NSValue valueWithCATransform3D:CATransform3DIdentity],
                   nil]];

[bounce setDuration:0.6];
    
[[timeLabel layer] addAnimation:bounce forKey:@"bounceAnimation"];

Here’s my code:

CAKeyframeAnimation *bounce = [CAKeyframeAnimation animationWithKeyPath:@"transform.scale"];
NSArray *scaleValues = [NSArray arrayWithObjects:
                        [NSNumber numberWithFloat:1.0],
                        [NSNumber numberWithFloat:1.3],
                        [NSNumber numberWithFloat:0.7],
                        [NSNumber numberWithFloat:1.2],
                        [NSNumber numberWithFloat:0.9],
                        [NSNumber numberWithFloat:1.0],
                        nil];
[bounce setValues:scaleValues];
    
[bounce setDuration:0.6];
    
[[timeLabel layer] addAnimation:bounce forKey:@"bounceAnimation"];

In other words, transform already exposes a scale property for the layer, so why bother with all this CATransform3D business?


#2

This was mostly to introduce the CATransform3D of a layer. While the .scale and .rotation key path extensions of the transform are nice, I typically go with creating the actually CATransform3D to be more explicit. (I come from a graphics background, though.)

Using the key path extensions does buy you a little: if I tell a layer to rotate 2*PI radians using the rotation key path, it will make a full revolution. Using two transforms may not, because interpolating between two transforms isn’t always straightforward, and the identity and full revolution transform look the same.