Repeat an animation a variable number of times
I was wondering how I can set an animation to repeat. The number of repetitions needs to be determined by a variable. In the following code, the variable int newPage
should determine how often the animation is repeated.
I tried this, but the animation (which employs a block animation) was only executed once:
for (int temp = 1; temp <= newPage; temp++) {
[self animatePage];
}
If I code the following, it works like I want it to, but this is hardcoded (i.e. the animation will be repeated twice) and I can't see a way of how to change the number of how often this animation is executed in code and according to my variable newPage:
[UIView animateWithDuration:0
delay:0.1
options:UIView开发者_如何学PythonAnimationOptionCurveEaseIn
animations:^{[self animatePage];}
completion:^(BOOL finished){[self animatePage];}];
I'd be very grateful for suggestions of how to repeat the same animation without having to hardcode the number of times I want this animation to be repeated.
EDIT:
I tried to implement the following code, but only one animation will actually be carried out:
[UIView animateWithDuration:0
delay:1
options:UIViewAnimationOptionCurveEaseIn
animations:^{
[UIView setAnimationRepeatCount:2];
[self animatePage];
}
completion:nil];
Had the same problem - you were missing an an'UIViewAnimationOptionRepeat'
This should work:
[UIView animateWithDuration:0
delay:1
options:UIViewAnimationOptionCurveEaseIn | UIViewAnimationOptionRepeat
animations:^{
[UIView setAnimationRepeatCount:2]; // **This should appear in the beginning of the block**
[self animatePage];
}
completion:nil];
Did the trick for me.
Did you try to set the repeatCount? + (void)setAnimationRepeatCount:(float)repeatCount
I've tried the following code block, and it definitely repeats 2x for me (l was a UITextView that was scaled up by 2x in X dir and 3X in Y dir):
[UIView animateWithDuration:2
delay:0.1
options:UIViewAnimationOptionCurveEaseIn
animations:^{ [UIView setAnimationRepeatCount:2];
l.transform = CGAffineTransformMakeScale(2,3); } completion:nil];
the reason you arent seeing but one animation is that due to the fact that you are calling the animation from a loop in the same runloop, resuting in the last call winning (one animation)
instead of calling [self animatePage]
, try calling
[self performSelector:@selector(animatePage) withObject:nil afterDelay:.1 *temp];
this will create your calls on separate threads.
you may need to play with the delay interval
To avoid the hiccup between animations, use keyframes. I wrote an extension that works on anything conforming to UIView (which is a ton of visual elements)
Swift 4:
import UIKit
extension UIView{
func rotate(count: Float, _ complete: @escaping ()->()) {
UIView.animateKeyframes(withDuration: 1.0, delay: 0, options: [.repeat], animations: {
//to rotate infinitely, comment the next line
UIView.setAnimationRepeatCount(count)
//rotate the object to 180 degrees
UIView.addKeyframe(withRelativeStartTime: 0, relativeDuration: 0.5/1.0, animations: {
self.transform = CGAffineTransform(rotationAngle: (CGFloat(Double.pi)))
})
UIView.addKeyframe(withRelativeStartTime: 0, relativeDuration: 0.5/1.0, animations: {
//rotate the object from 180 to 360 degrees
self.transform = CGAffineTransform(rotationAngle: (CGFloat(Double.pi * 2)))
})
}, completion:{ _ in
complete()
})
}
}
To call it anywhere in the app:
view.rotate() { /*do after*/ }
精彩评论