Последовательность CAAnimations - слой возвращается в исходное положение между последующими вызовами - PullRequest
1 голос
/ 24 сентября 2010

Я пытаюсь создать бесконечную анимацию слоя, слегка вращающегося влево, затем немного вправо и назад. Итак, я оживляю 10 градусов влево, затем 20 вправо, затем снова 10 влево. Отлично работает на симуляторе, но на устройстве слой "дрожит". Похоже, что он возвращается в свое предыдущее состояние каждый раз, прежде чем начать следующую анимацию. Я прочитал это, используя

animation.removedOnCompletion = НЕТ;
animation.fillMode = kCAFillModeForwards;

помогает в таких случаях, но если я их использую, целые слои просто замирают на месте после первой анимации и никогда никуда не движутся.

Так вот код:

- (void) initAnimations {
    float baseValue = [[self.layer valueForKey:@"transform.rotation.z"] floatValue];

    rotateLeft = [[CABasicAnimation animationWithKeyPath:@"transform.rotation.z"] retain];
    rotateLeft.fromValue = [NSNumber numberWithFloat:baseValue];
    rotateLeft.toValue = [NSNumber numberWithFloat:baseValue - DegreesToRadians(10.0f)];
    rotateLeft.duration = 0.4f;
    rotateLeft.removedOnCompletion = NO;
    rotateLeft.fillMode = kCAFillModeForwards;
    rotateLeft.repeatCount = 0;
    rotateLeft.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseOut];
    rotateLeft.delegate = self;

    rotateRight = [[CABasicAnimation animationWithKeyPath:@"transform.rotation.z"] retain];
    rotateRight.fromValue = [NSNumber numberWithFloat:baseValue - DegreesToRadians(10.0f)];
    rotateRight.toValue = [NSNumber numberWithFloat:baseValue + DegreesToRadians(10.0f)];
    rotateRight.duration = 0.6f;
    rotateRight.removedOnCompletion = NO;
    rotateRight.fillMode = kCAFillModeForwards;
    rotateRight.repeatCount = 0;
    rotateRight.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
    rotateRight.delegate = self;

    rotateRestore = [[CABasicAnimation animationWithKeyPath:@"transform.rotation.z"] retain];
    rotateRestore.fromValue = [NSNumber numberWithFloat:baseValue + DegreesToRadians(10.0f)];
    rotateRestore.toValue = [NSNumber numberWithFloat:baseValue];
    rotateRestore.duration = 0.3f;
    rotateRestore.removedOnCompletion = NO;
    rotateRestore.fillMode = kCAFillModeForwards;
    rotateRestore.repeatCount = 0;
    rotateRestore.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseIn];
    rotateRestore.delegate = self;
}

- (void) beginAnimations {
    if (animationsRunning)
        return;

    [self.layer addAnimation:rotateLeft forKey:nil];
}

- (void)animationDidStart:(CAAnimation *)theAnimation {

}

- (void)animationDidStop:(CAAnimation *)theAnimation finished:(BOOL)flag {
    [self.layer removeAllAnimations];
    if (self.superview == nil) {
        rotateLeft.delegate = nil;
        rotateRight.delegate = nil;
        rotateRestore.delegate = nil;
        return;
    }

    float dt;
    if (step == 0) {
        dt = 0.7f + (float)(random() % 3) / 10.0f;
    } else {
        dt = 0.4f + (float)(random() % 3) / 10.0f;
    }

    CABasicAnimation* nextAnimation = nil;
    if (step == 0) {
        nextAnimation = rotateRight;
    } else if (step == 1) {
        nextAnimation = rotateRestore;
    } else if (step == 2) {
        nextAnimation = rotateLeft;
    }

    nextAnimation.duration = dt;
    [self.layer addAnimation:nextAnimation forKey:nil];

    step++;
    if (step == 3)
        step = 0;
}

Почему это не работает? Я думаю, что я уже попробовал все комбинации удаленного OnCompletion / fillMode, и, кажется, ничто не помогает = (

...