Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I enforce an specific direction (i.e. clockwise) of rotation in Core Animation?

I am rotating a view with this:

CGAffineTransform rotatedTransform = CGAffineTransformRotate(CGAffineTransformIdentity, rotationValue);

I have an object which I want to spin around for about 320 degrees. Now Core Animation is clever and just rotates it as much as needed, doing that by rotating it with -40 degrees. So the object rotates the other way around with a shorter amount of movement.

I want to constrain it to rotate clockwise. Would I have to do that by changing animations in little steps, or is there an more elegant way?

like image 434
Thanks Avatar asked Jul 19 '09 10:07

Thanks


2 Answers

The following snippet rotates a view called someView by using key-framed animation. The animation consists of 3 frames spread over 1 second, with the view rotated to 0º, 180º and 360º in the first, second and last frames respectively. Code follows:

CALayer* layer = someView.layer;
CAKeyframeAnimation* animation;
animation = [CAKeyframeAnimation animationWithKeyPath:@"transform.rotation.z"];

animation.duration = 1.0;
animation.cumulative = YES;
animation.repeatCount = 1;
animation.removedOnCompletion = NO;
animation.fillMode = kCAFillModeForwards;

animation.values = [NSArray arrayWithObjects:
    [NSNumber numberWithFloat:0.0 * M_PI],
    [NSNumber numberWithFloat:0.5 * M_PI],
    [NSNumber numberWithFloat:1.0 * M_PI], nil];

animation.keyTimes = [NSArray arrayWithObjects:
    [NSNumber numberWithFloat:0.0],
    [NSNumber numberWithFloat:0.5],
    [NSNumber numberWithFloat:1.0], nil];

animation.timingFunctions = [NSArray arrayWithObjects:
    [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionLinear],
    [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionLinear], nil];

[layer addAnimation:animation forKey:@"transform.rotation.z"];

If you're after counterclockwise animation, you should use negative values. For a slightly more basic animation, you can use CABasicAnimation:

CALayer* layer = someView.layer;
CABasicAnimation* animation;
animation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];

animation.fromValue = [NSNumber numberWithFloat:0.0 * M_PI];
animation.toValue = [NSNumber numberWithFloat:1.0 * M_PI];

animation.duration = 1.0;
animation.cumulative = YES;
animation.repeatCount = 1;
animation.removedOnCompletion = NO;
animation.fillMode = kCAFillModeForwards;

[layer addAnimation:rotationAnimation forKey:@"transform.rotation.z"];
like image 59
Nathan de Vries Avatar answered Nov 20 '22 07:11

Nathan de Vries


I believe you have to give it another "key frame" if you will to give Core Animation the hint that it needs to go that direction.

Make sure and turn off easing, (at least for the end/beginning of the middle step) otherwise the animation will not look smooth.

like image 37
Ben Scheirman Avatar answered Nov 20 '22 07:11

Ben Scheirman