Creating Animation for search - ios

I am writing an animation for my search button, so when the user clicks on search I want to make a transition on my button and then move it to left and push the search view on it's back. I am trying to use the following code:
CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:#"transform.rotation.z"];
animation.repeatDuration = 1000;
animation.duration = 30;
animation.additive = YES;
animation.removedOnCompletion = NO;
animation.fillMode = kCAFillModeBoth;
animation.fromValue = [NSNumber numberWithFloat:0];
animation.toValue = [NSNumber numberWithFloat:360];
[self.SearchButton.layer addAnimation:animation forKey:#"rotationAnimation"];
[CATransaction begin]; {
[CATransaction setCompletionBlock:^{
[UIView animateWithDuration:0.6 delay:2 options:UIViewAnimationOptionCurveEaseIn animations:^{
[self.SearchButton setFrame:CGRectMake(self.slideMenuButton.frame.origin.x, self.slideMenuButton.frame.origin.y, self.SearchButton.frame.size.width, self.SearchButton.frame.size.height)];
[UIView animateWithDuration:0.6 delay:10.f options:UIViewAnimationOptionCurveEaseIn animations:^{
[self.navigationController presentViewController:Search animated:YES completion:nil];
}completion:^(BOOL finished) {
[self.SearchButton setFrame:CGRectMake(searchOrigin.x, searchOrigin.y, self.SearchButton.frame.size.width, self.SearchButton.frame.size.height)];
}];
} completion:^(BOOL finished) {
[self.SearchButton.layer removeAnimationForKey:#"rotationAnimation"];
}];
}];
}
Each animation is working correctly but I want them to follow each other so the feeling of movements be good. It means I want the button to do a transition and then move to the new point and the new view push to my view by following that.
It would be appreciated if you help me or give me any idea so I can implement that.

Related

UIView Animation is far from smooth

I am trying to scale a button up and down to call attention to it.
I have tried two animation methods:
method 1
CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:#"transform.scale"];
animation.autoreverses = YES;
animation.repeatDuration = 2;
animation.duration = 0.4;
animation.fromValue = #(1.0f);
animation.toValue= #(1.2f);
[button.layer addAnimation:animation forKey:#"scale"];
method 2
CGAffineTransform scaleUp = CGAffineTransformMakeScale(1.2f, 1.2f);
[UIView animateWithDuration:0.5 delay:1 options:UIViewAnimationOptionAutoreverse
animations:^{
[button setTransform:scaleUp];
} completion:^(BOOL finished) {
}];
Same problem with both animations. Near the end, when the button is scaling down to its normal scale, the animation jumps directly to scale 1.0.
Something like:
1.2 ... 1.18 ... 1.15 ... boom ... 1.0
and I see the button popping from one huge scale value to 1, instead of being smooth.
You need to set the final state of the button.In your case,the scale change like
1.0->1.1->1.2->1.1->1.0 ->1.2(jump to final state)
Gif
CGAffineTransform scaleUp = CGAffineTransformMakeScale(1.5f, 1.5f);
[UIView animateWithDuration:0.5 delay:1 options:UIViewAnimationOptionAutoreverse
animations:^{
[self.button setTransform:scaleUp];
} completion:^(BOOL finished) {
self.button.transform = CGAffineTransformIdentity;
}];

Converting code from CABasicAnimation

I have a animation code that is written using CABasicAnimation just as following:
CABasicAnimation *anim = [CABasicAnimation animationWithKeyPath:#"position"];
[anim setDelegate:self];
anim.fromValue = [NSValue valueWithCGPoint:img.center];
if (newValue == 0) {
imgCentre.y = centerStart.y - 11 * kCounterDigitDiff;
anim.toValue = [NSValue valueWithCGPoint:imgCentre];
} else
anim.toValue = [NSValue valueWithCGPoint:imgCentre];
anim.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
anim.duration = 0.3;
[img.layer addAnimation:anim forKey:#"rollLeft"];
img.frame = frame;
Due to some reason I wish to apply same animation but by using following type of approach:
[UIView animateWithDuration:0.3 delay:0.0 options:(UIViewAnimationOptionBeginFromCurrentState|UIViewAnimationOptionCurveEaseOut) animations:^{
...
} completion:^(BOOL finished) {
...
}
What I come up with is like following:
[img setCenter:imgCentre];
[UIView animateWithDuration:0.3 delay:0.0 options:(UIViewAnimationOptionBeginFromCurrentState|UIViewAnimationOptionCurveEaseOut) animations:^{
if (newValue == 0) {
CGPoint newPoint= CGPointMake(imgCentre.x, centerStart.y - 11 * kCounterDigitDiff);
[img setCenter:newPoint];
} else{
[img setCenter:imgCentre];
}
} completion:^(BOOL finished) {
// animation completion code
}];
img.frame = frame;
Overall things look good but I am a little bit pessimistic about the conversion? is there something that i have missed?
You've got the right idea. However, unlike with CAAnimations, you don't have to set the properties to the end value. The UIView animation call takes care of all that for you.
UIView animation is generally easier and more intuitive to use than CAAnimation.

Spin and move UIView

How to move continuously spinning UIView with animation blocks? Eg., I have this code for spinning:
- (void)spinView:(UIView *)view {
[UIView animateWithDuration:0.2f
delay:0.0f
options:UIViewAnimationOptionCurveLinear
animations:^{
view.transform = CGAffineTransformRotate(view.transform, M_PI_2);
}
completion:^(BOOL finished) {
if (finished) {
[self spinView:view];
}
}];
}
How to combine it with animation like this:
[UIView animateWithDuration:4.0f animations:^{
myView.transform = CGAffineTransformTranslate(myView.transform, 400, 0);
}];
I've tried with CGAffineTransformConcat(), UIViewAnimationOptionBeginFromCurrentState, but without success.
Have you try something like,
[UIView animateWithDuration:2.0f animations:^{
vw.transform = CGAffineTransformTranslate(vw.transform, 400, 0);
CABasicAnimation* animation = [CABasicAnimation animationWithKeyPath:#"transform.rotation.z"];
animation.fromValue = [NSNumber numberWithFloat:0.0f];
animation.toValue = [NSNumber numberWithFloat: 2*M_PI];
animation.duration = 5.0f;
animation.repeatCount = 1;
[vw.layer addAnimation:animation forKey:#"SpinAnimation"];
}];
vw is your view to move. set frame according to your wish.

iOS animation with duration and autoreverse

I am animating an UIImageView with the UIView block API. My animation fades the UIImageView In and Out continuously. How can I animate this only for a specific time duration ?
I have put up this piece of code
float tempDuration = 5.0;
[UIView animateWithDuration:tempDuration
delay:0
options:UIViewAnimationOptionAutoreverse | UIViewAnimationOptionAllowUserInteraction
animations:^{
_imageView.alpha = 1;
}
completion:nil];
First of all allow me to introduce an article that is awesome to understand some features of the animations:
Controlling Animation Timming
In this article you have a part that shows what you want.
You want something like this:
Therefore you can configure that in the following way:
-(void) animateImageView:(UIImageView*) imageView
withDuration:(int) duration
withRepeatCount: (int) repeatCount {
CABasicAnimation *opacityAnim = [CABasicAnimation animationWithKeyPath:#"opacity"];
opacityAnim.fromValue = #1.0;
opacityAnim.toValue = #0.0;
opacityAnim.autoreverses = YES;
opacityAnim.duration = duration/2.0/repeatCount;
opacityAnim.removedOnCompletion = YES;
opacityAnim.repeatCount = repeatCount;
[imageView.layer addAnimation:opacityAnim forKey:nil];
}
This way you guarantee that your animation will always be 5 seconds and you can tune in the number of repetitions.
Maybe you could try CABasicAnimation instead if [UIView animateWithDiration: ... ]
it should be something like this:
CABasicAnimation *opacityAnim = [CABasicAnimation animationWithKeyPath:#"opacity"];
opacityAnim.fromValue = [NSNumber numberWithFloat:1.0];
opacityAnim.toValue = [NSNumber numberWithFloat:0.0];
opacityAnim.autoreverses = YES;
opacityAnim.duration = duration;
opacityAnim.removedOnCompletion = YES;
opacityAnim.repeatCount = 5;
[imageView.layer addAnimation:opacityAnim forKey:nil];
You can do the following changes to do your work.
- (void)animateImageView{
static int animcount = 1;
float tempDuration = 1.0;
[UIView animateWithDuration:tempDuration
delay:0
options: UIViewAnimationOptionAutoreverse
animations:^{
self.imgView.alpha = 1;
}
completion:^(BOOL finished) {
if(finished && animcount<5){
animcount+=1;
[self animateImageView];
}
else if (finished && animcount==5){
[self.imgView.layer removeAllAnimations];
}
}];
}

ios CoreAnimation

I'm trying to skew an object cards it's an UIView I'm doing :
[UIView beginAnimations:nil context:NULL];
[UIView setAnimationDuration:DEPLACEMENT_ANIMATION_DUREE_SECONDES_DROITE];
scene.carte17.layer.position = positionInit;
if (scene.carte17.angleCarte == 15.f) {
scene.carte17.transform = CGAffineTransformRotate(scene.carte17.transform, degreesToRadians(30));
scene.carte17.angleCarte = 45.f;
}
[UIView commitAnimations];
And it's working ! My card incline to 30° and it's good. I'm playing with setAnimationDuration to control the speed.
I would like to use CoreAnimation and kCAMediaTimingFunctionEaseInEaseOut to have a better animation but I'm not ok to do the same think with core animation I'm trying this :
[CATransaction begin];
[CATransaction setAnimationDuration:.5f];
[CATransaction setAnimationTimingFunction:[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut]];
scene.carte17.layer.position = positionInit;
if (scene.carte17.angleCarte == 15.f) {
CABasicAnimation *animation;
animation = [CABasicAnimation animationWithKeyPath:#"transform.rotation.z"];
animation.fromValue = [NSNumber numberWithFloat:0.0];
animation.toValue = [NSValue valueWithCGAffineTransform:CGAffineTransformRotate(scene.carte17.transform, degreesToRadians(30))];
animation.timingFunction = [CAMediaTimingFunction functionWithName: kCAMediaTimingFunctionEaseInEaseOut];
animation.delegate = self;
[scene.carte17.layer addAnimation:animation forKey:#"rotationAnimation"];
scene.carte17.angleCarte = 45.f;
}
[CATransaction commit];
But it's not working ... Could you help me please !
Why not just call this:
[UIView setAnimationCurve:UIViewAnimationCurveEaseInOut];
But that is an overkill since UIViewAnimationCurveEaseInOut is the default value.

Resources