Pictured above,

It looks something like this

Requirements and implementation ideas

The specific requirements

* Infinite loop of internal head breathing zoom in and out

* The background and one image should be enlarged and transparent for each zoom

* Click to zoom the entire background view

Implementation approach

Click Trigger to add a one-time zoom animation

Breathe animation Layer and animation

Breathing layer

CALayer *layer = [CALayer layer]; Layer. The position = CGPointMake (kHeartSizeWidth f / 2.0, kHeartSizeHeight / 2.0 f); Layer. bounds = CGRectMake(0, 0, kHeartSizeWidth/2.0f, kHeartSizeHeight/2.0f); layer.backgroundColor = [UIColor clearColor].CGColor; layer.contents = (__bridge id _Nullable)([UIImage imageNamed:@"breathImage"].CGImage); layer.contentsGravity = kCAGravityResizeAspect; [self.heartView.layer addSublayer:layer];Copy the code

KHeartSizeHeight and kHeartSizeWidth are constants and we have 100 in demo

Add animation to

CAKeyframeAnimation *animation = [CAKeyframeAnimation animationWithKeyPath:@"transform.scale"]; Animation. Values = @[@1.f, @1.4f, @1.f]; Animation. KeyTimes = @[@0.f, @0.5f, @1.f]; animation.duration = 1; //1000ms animation.repeatCount = FLT_MAX; animation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut]; [animation setValue:kBreathAnimationKey forKey:kBreathAnimationName]; [layer addAnimation:animation forKey:kBreathAnimationKey];Copy the code

Differentiators can also be customized for example:

[CAMediaTimingFunction functionWithControlPoints: 0.33:0:0.67:1]Copy the code

Here I’m doing it for 1 second

Zoom in on the gradient animation group

Create a new layer

CALayer *breathLayer = [CALayer layer];
breathLayer.position = layer.position;
breathLayer.bounds = layer.bounds;
breathLayer.backgroundColor = [UIColor clearColor].CGColor;
breathLayer.contents = (__bridge id _Nullable)([UIImage imageNamed:@"breathImage"].CGImage);
breathLayer.contentsGravity = kCAGravityResizeAspect;
[self.heartView.layer insertSublayer:breathLayer below:layer];
//[self.heartView.layer addSublayer:breathLayer];
Copy the code

I’m going to put it behind the breath layer and if I want to put it in front of the breath layer I’m going to open the comment inside and I’m going to annotate the inert line

The animation group contains zoom in gradients

// CAKeyframeAnimation *scaleAnimation = [CAKeyframeAnimation animationWithKeyPath:@"transform.scale"]; ScaleAnimation. Values = @ [@ 1 f, @ 2.4 f]; scaleAnimation.keyTimes = @[@0.f,@1.f]; scaleAnimation.duration = animation.duration; scaleAnimation.repeatCount = FLT_MAX; scaleAnimation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseIn]; CAKeyframeAnimation *opacityAnimation = [CAKeyframeAnimation animation]; opacityAnimation.keyPath = @"opacity"; opacityAnimation.values = @[@1.f, @0.f]; OpacityAnimation. Duration = 0.4 f; opacityAnimation.keyTimes = @[@0.f, @1.f]; opacityAnimation.repeatCount = FLT_MAX; opacityAnimation.duration = animation.duration; opacityAnimation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseIn]; CAAnimationGroup *scaleOpacityGroup = CAAnimationGroup animation; scaleOpacityGroup.animations = @[scaleAnimation, opacityAnimation]; scaleOpacityGroup.removedOnCompletion = NO; scaleOpacityGroup.fillMode = kCAFillModeForwards; scaleOpacityGroup.duration = animation.duration; scaleOpacityGroup.repeatCount = FLT_MAX; [breathLayer addAnimation:scaleOpacityGroup forKey:kBreathScaleName];Copy the code

Click to scale the animation

It’s the same thing as the first one but it’s executed once by default

- (void)shakeAnimation { CAKeyframeAnimation *animation = [CAKeyframeAnimation animationWithKeyPath:@"transform.scale"];  Animation. Values = @[@1.0f, @0.8f, @1.f]; Animation. KeyTimes = @ [@ 0 f, @ 0.5 f, @ 1 f]; Animation. Duration = 0.35 f; animation.timingFunctions = @[[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut],[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut]]; [self.heartView.layer addAnimation:animation forKey:@""]; }Copy the code

Called when the gesture is triggered

Problems encountered

Breath if duration is in the middle say 1 second then it needs to come back at 0.5 seconds

Then, halfway through the second animation, it feels weird

If the __ gradient animation __ is repeated for 0.5 seconds, it will start again

How do you solve it?

We added 0.5 seconds of animation to the animation group and set the duration of the animation group to the same as the breathing animation, so that the gradient animation would not restart for the remaining 0.5 seconds.

conclusion

I haven’t played animation for a long time and have basically forgotten all about it. In the future, I need to practice more, write more articles and demos, and record some more knowledge and skills. Blog is like a car, if you need regular maintenance, you can go farther and record more beautiful things.

Citation: Original address