在特定点停止CABasicAnimation

时间:2012-06-19 10:07:08

标签: iphone objective-c ios ipad core-animation

我正在使用CABasicAnimation创建的旋转动画。它旋转UIView超过2秒。但我需要能够在UIView被触及时停止它。如果我删除动画,则视图与动画开始前的位置相同。

这是我的动画代码:

float duration = 2.0;
float rotationAngle = rotationDirection * ang * speed * duration;
//rotationAngle =  3*(2*M_PI);//(double)rotationAngle % (double)(2*M_PI) ;
CABasicAnimation* rotationAnimation;
rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
rotationAnimation.toValue = [NSNumber numberWithFloat: rotationAngle ];
rotationAnimation.duration = duration;
rotationAnimation.cumulative = YES;
rotationAnimation.removedOnCompletion = NO;
rotationAnimation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseOut];
rotationAnimation.fillMode = kCAFillModeForwards;
rotationAnimation.delegate = self;

[self.view.layer addAnimation:rotationAnimation forKey:@"rotationAnimation"];

如何将UIView的旋转停在原处,当它被触摸时?我知道如何管理触摸部分,但我无法弄清楚如何以动画的当前角度停止视图。

解决方案: 我通过获取表示层的角度,删除动画和设置视图的变换来解决问题。这是代码:

[self.view.layer removeAllAnimations];      
CALayer* presentLayer = self.view.layer.presentationLayer; 
float currentAngle = [(NSNumber *)[presentLayer valueForKeyPath:@"transform.rotation.z"] floatValue];
self.view.transform = CGAffineTransformMakeRotation(currentAngle);

2 个答案:

答案 0 :(得分:16)

好问题!为此,了解核心动画架构很有帮助。

如果您查看描述核心动画渲染架构的Core Animation Programming Guide中的图表,您可以看到有三棵树。

您拥有模型树。这就是您设置想要的价值的地方。然后是演示文稿树。就运行时而言,这就是几乎所发生的事情。然后,最后是渲染树。这就是用户看到的内容。

在您的情况下,您要查询演示文稿树的值。

这很容易做到。对于已附加动画的视图,请获取layer,并为layer查询presentationLayer的值。例如:

CATransform3D myTransform = [(CALayer*)[self.view.layer presentationLayer] transform];

没有办法“暂停”动画中流。您所能做的就是查询值,将其删除,然后从中断处重新创建它。

这有点痛苦!

看看我的其他一些帖子,我会更详细地介绍一下,例如

Restoring animation where it left off when app resumes from background

不要忘记,当您向视图的图层添加动画时,实际上并未更改基础视图的属性。那会发生什么?我们会在动画停止的地方产生奇怪的效果,然后你会看到它的原始位置。

这就是您需要使用CAAnimation代表的地方。看看我对这篇文章的回答:

CABasicAnimation rotate returns to original position

答案 1 :(得分:5)

您需要将旋转设置为presentationLayer的旋转,然后从图层中移除动画。您可以在我的博客文章中阅读有关Hit testing animating layers

的演示文稿图层

设置最终轮换的代码类似于:

self.view.layer.transform = [(CALayer*)[self.view.layer presentationLayer] transform];
[self.view.layer removeAnimationForKey:@"rotationAnimation"];