UIView animation flickering with auto reverse

I'm trying to animate an indicator in an empty form field, so I use the method below to animate the position, cancel the animation, and repeat. In the simulator, this works great, on my 3GS it looks like a flicker happens when I click on the completion block. The indicator is briefly displayed in the middle position, not backward in it.

Any thoughts on why this is happening? Thanks.

- (void)bounceFormIndicator { if (formIndicator.superview == nil) { return; } int bounceDistance = 24; [UIView animateWithDuration:0.6 delay:0 options:UIViewAnimationOptionCurveEaseInOut | UIViewAnimationOptionAutoreverse | UIViewAnimationOptionAllowUserInteraction animations:^{ CGRect indicatorFrame = formIndicator.frame; indicatorFrame.origin.x += bounceDistance; formIndicator.frame = indicatorFrame; }completion:^(BOOL finished){ CGRect indicatorFrame = formIndicator.frame; indicatorFrame.origin.x -= bounceDistance; formIndicator.frame = indicatorFrame; [self bounceFormIndicator]; }]; } 
+6
source share
1 answer

I had the same issue and went to Apple DTS to help with the workaround.

According to the DTS, this β€œflickering” effect or drop effect is the expected behavior ... I thought I was doing something wrong with my project for a long time.

In particular, this is so, since the documentation states

UIViewAnimationOptionAutoreverse Start the animation back and forth.

Must be combined with the UIViewAnimationOptionRepeat option.

To make the flicker go away, I had to do 2 things.

My implementation was dynamic, so you may not need to implement the first step, but I will keep it here for reference only.

First, I checked if UIViewAnimationOptionAutoreverse would be part of the parameters that I was going to pass into my animation, and UIViewAnimationOptionRepeat not ... If so, I deprived it of adding a line, for example:

 animationOptions &= ~UIViewAnimationOptionAutoreverse; 

To create reverse animation without repeating, I added UIView animation as my completion block. I also inverted the attenuation if it was either UIViewAnimationOptionCurveEaseIn or UIViewAnimationOptionCurveEaseOut ...

Code from my project:

An operator that removes an autoreverse parameter from an animationOptions object:

 if ((animationOptions & AUTOREVERSE) == AUTOREVERSE) { self.shouldAutoreverse = YES; animationOptions &= ~AUTOREVERSE; } 

An example of an overridden property that handles animation:

 -(void)setCenter:(CGPoint)center { CGPoint oldCenter = CGPointMake(self.center.x, self.center.y); void (^animationBlock) (void) = ^ { super.center = center; }; void (^completionBlock) (BOOL) = nil; BOOL animationShouldNotRepeat = (self.animationOptions & REPEAT) != REPEAT; if(self.shouldAutoreverse && animationShouldNotRepeat) { completionBlock = ^ (BOOL animationIsComplete) { [self autoreverseAnimation:^ { super.center = oldCenter;}]; }; } [self animateWithBlock:animationBlock completion:completionBlock]; } 

The completion method, which is required if reversed without repetition:

 -(void)autoreverseAnimation:(void (^)(void))animationBlock { C4AnimationOptions autoreverseOptions = BEGINCURRENT; if((self.animationOptions & LINEAR) == LINEAR) autoreverseOptions |= LINEAR; else if((self.animationOptions & EASEIN) == EASEIN) autoreverseOptions |= EASEOUT; else if((self.animationOptions & EASEOUT) == EASEOUT) autoreverseOptions |= EASEIN; [UIView animateWithDuration:self.animationDuration delay:0 options:autoreverseOptions animations:animationBlock completion:nil]; } 
+13
source

Source: https://habr.com/ru/post/897571/


All Articles