Ios 平滑地旋转刷新按钮图像,使其完成到最近的旋转

Ios 平滑地旋转刷新按钮图像,使其完成到最近的旋转,ios,ios7,cgaffinetransform,cabasicanimation,Ios,Ios7,Cgaffinetransform,Cabasicanimation,我正在尝试设置刷新按钮的动画,使其旋转以指示刷新正在进行。它需要平滑,这样,如果刷新只需要0.1秒,我们仍然可以进行完整的旋转,这样用户就可以确认发生了什么,这是一个平滑的过渡。它也应该继续旋转,直到我停止它,但是停止不应该突然停止它,只告诉它完成当前的旋转 最初我是这样做的 CABasicAnimation *rotationAnimation; rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rot

我正在尝试设置刷新按钮的动画,使其旋转以指示刷新正在进行。它需要平滑,这样,如果刷新只需要0.1秒,我们仍然可以进行完整的旋转,这样用户就可以确认发生了什么,这是一个平滑的过渡。它也应该继续旋转,直到我停止它,但是停止不应该突然停止它,只告诉它完成当前的旋转

最初我是这样做的

CABasicAnimation *rotationAnimation;
rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
rotationAnimation.toValue = [NSNumber numberWithFloat:M_PI * 2.0 * 10];
rotationAnimation.cumulative = YES;
rotationAnimation.duration = 10;
[self.layer addAnimation:rotationAnimation forKey:@"rotationAnimation"];
就这样停下来

[self.layer removeAllAnimations];
这在动画继续平滑地超过2pi弧度的意义上工作得很好,但是当刷新时间少于1/10秒时,它看起来不是很平滑,因为动画将获得10%的循环,然后突然停止,removeAllAnimations方法将图像重置回其默认值

我设法用另一种停止方法来解决这个问题

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

    [self.layer removeAllAnimations];   

    if (currentAngle < 0) {
        currentAngle = 2 * ABS(currentAngle);
    }

    float rotationProgressPercent = currentAngle / (2 * M_PI);    
    CABasicAnimation *rotationAnimation;
    rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
    rotationAnimation.fromValue = [NSNumber numberWithFloat:currentAngle];
    rotationAnimation.toValue = [NSNumber numberWithFloat:M_PI * 2];
    rotationAnimation.cumulative = YES;
    rotationAnimation.duration = 1 - rotationProgressPercent;
CALayer*presentLayer=self.layer.presentationLayer;
float currentAngle=[(NSNumber*)[presentLayer valueForKeyPath:@“transform.rotation.z”]floatValue];
[self.layer removeAllAnimations];
如果(当前角度<0){
currentAngle=2*ABS(currentAngle);
}
浮动旋转进度百分比=当前角度/(2*M_PI);
卡巴斯基化*旋转化;
rotationAnimation=[CABASICanimationWithKeyPath:@“transform.rotation.z”];
rotationAnimation.fromValue=[NSNumber numberWithFloat:currentAngle];
rotationAnimation.toValue=[NSNumber numberWithFloat:M_PI*2];
rotationAnimation.cumulative=是;
rotationAnimation.duration=1-rotationProgressPercent;
基本上我以弧度为单位获得当前旋转角度,停止动画并从该位置开始一个新动画,直到两个圆周率。我必须对持续时间做一些工作,以保持速度恒定,速度方面工作得很好,但问题是,在某些方面,动画有一个非常轻微的滞后/抽搐。我相信这是因为停止动画正在异步地将此请求发布到系统(这只是推测),并且在我开始执行第二个动画时,我当前的角度已过时


有没有其他方法可以尝试。

所以我最终找到了一个解决方案,这是多么有用

-(void)startSpinning {
    if (animating) {
        return;
    }
    animating = YES;
    [self rotateViewWithDuration:1 byAngle:M_PI * 2];

}

- (void)stopSpinning {
    animating = NO;
}


- (void)rotateViewWithDuration:(CFTimeInterval)duration byAngle:(CGFloat)angle {


    [CATransaction begin];
    CABasicAnimation *rotationAnimation;
    rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
    rotationAnimation.byValue = [NSNumber numberWithFloat:angle];
    rotationAnimation.duration = duration;
    rotationAnimation.removedOnCompletion = YES;

    [CATransaction setCompletionBlock:^{

        if (animating) {
            [self rotateViewWithDuration:duration byAngle:angle];
        }
    }];

    [self.layer addAnimation:rotationAnimation forKey:@"rotationAnimation"];
    [CATransaction commit];
}