这篇文章主要介绍了iOS如何自定义UIButton点击动画特效,具有一定借鉴价值,感兴趣的朋友可以参考下,希望大家阅读完这篇文章之后大有收获,下面让小编带着大家一起了解一下。
代码:
ViewController:
#import <UIKit/UIKit.h>@interface ViewController : UIViewController@end#import "ViewController.h"#import "HWButton.h"#define mainW [UIScreen mainScreen].bounds.size.width#define mainH [UIScreen mainScreen].bounds.size.height@interface ViewController ()implementation ViewController- (void)viewDidLoad { [super viewDidLoad]; self.view.backgroundColor = [UIColor blackColor]; //创建控件 [self creatButton];}- (void)creatButton{ HWButton *button = [[HWButton alloc] initWithFrame:CGRectMake(mainW * 0.5 - 60, mainH - 100, 120, 72) maxLeft:100 maxRight:100 maxHeight:300]; [button setImage:[UIImage imageNamed:@"button"] forState:UIControlStateNormal]; button.images = @[[UIImage imageNamed:@"Circle 1"], [UIImage imageNamed:@"Circle 2"], [UIImage imageNamed:@"Circle 3"], [UIImage imageNamed:@"Hero"]]; button.duration = 10; [button addTarget:self action:@selector(buttonOnClick:) forControlEvents:UIControlEventTouchUpInside]; [self.view addSubview:button];}- (void)buttonOnClick:(HWButton *)btn{ [btn generateBubbleInRandom];}@end
HWButton:
#import <UIKit/UIKit.h>@interface HWButton : UIButton@property (nonatomic, assign) CGFloat maxLeft;@property (nonatomic, assign) CGFloat maxRight;@property (nonatomic, assign) CGFloat maxHeight;@property (nonatomic, assign) CGFloat duration;@property (nonatomic, strong) NSArray *images;- (instancetype)initWithFrame:(CGRect)frame maxLeft:(CGFloat)maxLeft maxRight:(CGFloat)maxRight maxHeight:(CGFloat)maxHeight;- (void)generateBubbleWithImage:(UIImage *)image;- (void)generateBubbleInRandom;@end#import "HWButton.h"@implementation HWButton{ CGPoint _startPoint; CGFloat _maxWidth; NSMutableSet *_recyclePool; NSMutableArray *_array;}- (instancetype)initWithFrame:(CGRect)frame maxLeft:(CGFloat)maxLeft maxRight:(CGFloat)maxRight maxHeight:(CGFloat)maxHeight{ self = [super initWithFrame:frame]; if (self) { _maxHeight = maxHeight; _maxLeft = maxLeft; _maxRight = maxRight; [self initData]; } return self;}- (id)initWithCoder:(NSCoder *)aDecoder{ self = [super initWithCoder:aDecoder]; if (self) { [self initData]; } return self;}- (void)initData{ _array = @[].mutableCopy; _recyclePool = [NSMutableSet set];}- (void)generateBubbleInRandom{ CALayer *layer; if (_recyclePool.count > 0) { layer = [_recyclePool anyObject]; [_recyclePool removeObject:layer]; }else { UIImage *image = self.images[arc4random() % self.images.count]; layer = [self createLayerWithImage:image]; } [self.layer addSublayer:layer]; [self generateBubbleWithCAlayer:layer];}- (void)generateBubbleWithImage:(UIImage *)image{ CALayer *layer = [self createLayerWithImage:image]; [self.layer addSublayer:layer]; [self generateBubbleWithCAlayer:layer];}- (void)generateBubbleWithCAlayer:(CALayer *)layer{ _maxWidth = _maxLeft + _maxRight + self.bounds.size.width; _startPoint = CGPointMake(self.frame.size.width / 2, 0); CGPoint endPoint = CGPointMake(_maxWidth * [self randomFloat] - _maxLeft, -_maxHeight); CGPoint controlPoint1 = CGPointMake(_maxWidth * [self randomFloat] - _maxLeft, -_maxHeight * 0.2); CGPoint controlPoint2 = CGPointMake(_maxWidth * [self randomFloat] - _maxLeft, -_maxHeight * 0.6); CGMutablePathRef curvedPath = CGPathCreateMutable(); CGPathMoveToPoint(curvedPath, NULL, _startPoint.x, _startPoint.y); CGPathAddCurveToPoint(curvedPath, NULL, controlPoint1.x, controlPoint1.y, controlPoint2.x, controlPoint2.y, endPoint.x, endPoint.y); CAKeyframeAnimation *keyFrame = [CAKeyframeAnimation animation]; keyFrame.keyPath = @"position"; keyFrame.path = CFAutorelease(curvedPath); keyFrame.duration = self.duration; keyFrame.calculationMode = kCAAnimationPaced; [layer addAnimation:keyFrame forKey:@"keyframe"]; CABasicAnimation *scale = [CABasicAnimation animation]; scale.keyPath = @"transform.scale"; scale.toValue = @1; scale.fromValue = [NSValue valueWithCATransform3D:CATransform3DMakeScale(0.1, 0.1, 0.1)]; scale.duration = 0.5; CABasicAnimation *alpha = [CABasicAnimation animation]; alpha.keyPath = @"opacity"; alpha.fromValue = @1; alpha.toValue = @0.1; alpha.duration = self.duration * 0.4; alpha.beginTime = self.duration - alpha.duration; CAAnimationGroup *group = [CAAnimationGroup animation]; group.animations = @[keyFrame, scale, alpha]; group.duration = self.duration; group.delegate = self; group.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseOut]; group.fillMode = kCAFillModeForwards; group.removedOnCompletion = NO; [layer addAnimation:group forKey:@"group"]; [_array addObject:layer];}- (CGFloat)randomFloat{ return (arc4random() % 100)/100.0f;}- (CALayer *)createLayerWithImage:(UIImage *)image{ CGFloat scale = [UIScreen mainScreen].scale; CALayer *layer = [CALayer layer]; layer.frame = CGRectMake(0, 0, image.size.width / scale, image.size.height / scale); layer.contents = (__bridge id)image.CGImage;; return layer;}- (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag{ if (flag) { CALayer *layer = [_array firstObject]; [layer removeAllAnimations]; [layer removeFromSuperlayer]; [_array removeObject:layer]; [_recyclePool addObject:layer]; }}@end
免责声明:本站发布的内容(图片、视频和文字)以原创、来自互联网转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系QQ:712375056 进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。
Copyright © 2009-2021 56dr.com. All Rights Reserved. 特网科技 特网云 版权所有 珠海市特网科技有限公司 粤ICP备16109289号
域名注册服务机构:阿里云计算有限公司(万网) 域名服务机构:烟台帝思普网络科技有限公司(DNSPod) CDN服务:阿里云计算有限公司 中国互联网举报中心 增值电信业务经营许可证B2
建议您使用Chrome、Firefox、Edge、IE10及以上版本和360等主流浏览器浏览本网站