123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278 |
- //
- // TabbarButton.m
- // WFChat UIKit
- //
- // Created by WF Chat on 2017/9/12.
- // Copyright © 2017年 WildFireChat. All rights reserved.
- //
- #define kBtnWidth self.bounds.size.width
- #define kBtnHeight self.bounds.size.height
- #import "TabbarButton.h"
- #import "WFCUImage.h"
- NSString *const kTabBarClearBadgeNotification = @"kTabBarClearBadgeNotification";
- @interface TabbarButton()
- @end
- @implementation TabbarButton
- - (instancetype)initWithFrame:(CGRect)frame
- {
- if (self = [super initWithFrame:frame]) {
-
- [self setUp];
- }
-
- return self;
- }
- - (void)awakeFromNib
- {
- [super awakeFromNib];
- [self setUp];
- }
- //- (void)layoutSubviews
- //{
- // [self setUp];
- //}
- #pragma mark - 懒加载
- - (NSMutableArray *)images
- {
- if (_images == nil) {
- _images = [NSMutableArray array];
- for (int i = 1; i < 9; i++) {
- UIImage *image = [WFCUImage imageNamed:[NSString stringWithFormat:@"%d", i]];
- [_images addObject:image];
- }
- }
-
- return _images;
- }
- - (CAShapeLayer *)shapeLayer
- {
- if (!_shapeLayer) {
- _shapeLayer = [CAShapeLayer layer];
- _shapeLayer.fillColor = [self.backgroundColor CGColor];
- [self.superview.layer insertSublayer:_shapeLayer below:self.layer];
- }
-
- return _shapeLayer;
- }
- - (UIView *)samllCircleView
- {
- if (!_samllCircleView) {
- _samllCircleView = [[UIView alloc] init];
- _samllCircleView.backgroundColor = self.backgroundColor;
- [self.superview insertSubview:_samllCircleView belowSubview:self];
- }
-
- return _samllCircleView;
- }
- - (void)setUp
- {
- CGFloat cornerRadius = (kBtnHeight > kBtnWidth ? kBtnWidth / 2.0 : kBtnHeight / 2.0);
- self.backgroundColor = [UIColor redColor];
- [self setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
- self.titleLabel.font = [UIFont systemFontOfSize:12.f];
- _maxDistance = cornerRadius * 5;
-
- self.layer.masksToBounds = YES;
- self.layer.cornerRadius = cornerRadius;
-
- CGRect samllCireleRect = CGRectMake(0, 0, cornerRadius * (2 - 0.5) , cornerRadius * (2 - 0.5));
- self.samllCircleView.bounds = samllCireleRect;
- _samllCircleView.center = self.center;
- _samllCircleView.layer.cornerRadius = _samllCircleView.bounds.size.width / 2;
-
- UIPanGestureRecognizer *pan = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(pan:)];
- [self addGestureRecognizer:pan];
-
- // [self addTarget:self action:@selector(btnClick) forControlEvents:UIControlEventTouchUpInside];
- }
- #pragma mark - 手势
- - (void)pan:(UIPanGestureRecognizer *)pan
- {
- [self.layer removeAnimationForKey:@"shake"];
-
- CGPoint panPoint = [pan translationInView:self];
-
- CGPoint changeCenter = self.center;
-
- changeCenter.x += panPoint.x;
- changeCenter.y += panPoint.y;
- self.center = changeCenter;
- [pan setTranslation:CGPointZero inView:self];
-
- //俩个圆的中心点之间的距离
- CGFloat dist = [self pointToPoitnDistanceWithPoint:self.center potintB:self.samllCircleView.center];
-
- if (dist < _maxDistance) {
-
- CGFloat cornerRadius = (kBtnHeight > kBtnWidth ? kBtnWidth / 2 : kBtnHeight / 2);
- CGFloat samllCrecleRadius = cornerRadius - dist / 10;
- _samllCircleView.bounds = CGRectMake(0, 0, samllCrecleRadius * (2 - 0.5), samllCrecleRadius * (2 - 0.5));
- _samllCircleView.layer.cornerRadius = _samllCircleView.bounds.size.width / 2;
-
- if (_samllCircleView.hidden == NO && dist > 0) {
- //画不规则矩形
- self.shapeLayer.path = [self pathWithBigCirCleView:self smallCirCleView:_samllCircleView].CGPath;
- }
- } else {
-
- [self.shapeLayer removeFromSuperlayer];
- self.shapeLayer = nil;
-
- self.samllCircleView.hidden = YES;
- }
-
- if (pan.state == UIGestureRecognizerStateEnded) {
-
- if (dist > _maxDistance) {
-
- //播放销毁动画
- // [self startDestroyAnimations];
-
- //销毁全部控件
- [self killAll];
-
- } else {
-
- [self.shapeLayer removeFromSuperlayer];
- self.shapeLayer = nil;
-
- [UIView animateWithDuration:0.3 delay:0 usingSpringWithDamping:0.2 initialSpringVelocity:1 options:UIViewAnimationOptionCurveEaseInOut animations:^{
- self.center = self.samllCircleView.center;
- } completion:^(BOOL finished) {
- self.samllCircleView.hidden = NO;
- }];
- }
- }
- }
- #pragma mark - 俩个圆心之间的距离
- - (CGFloat)pointToPoitnDistanceWithPoint:(CGPoint)pointA potintB:(CGPoint)pointB
- {
- CGFloat offestX = pointA.x - pointB.x;
- CGFloat offestY = pointA.y - pointB.y;
- CGFloat dist = sqrtf(offestX * offestX + offestY * offestY);
-
- return dist;
- }
- - (void)killAll
- {
- [self.samllCircleView removeFromSuperview];
- [self.shapeLayer removeFromSuperlayer];
- [self removeFromSuperview];
- [[NSNotificationCenter defaultCenter] postNotificationName:kTabBarClearBadgeNotification object:@(self.tag - 888)];
- }
- #pragma mark - 不规则路径
- - (UIBezierPath *)pathWithBigCirCleView:(UIView *)bigCirCleView smallCirCleView:(UIView *)smallCirCleView
- {
- CGPoint bigCenter = bigCirCleView.center;
- CGFloat x2 = bigCenter.x;
- CGFloat y2 = bigCenter.y;
- CGFloat r2 = bigCirCleView.bounds.size.height / 2;
-
- CGPoint smallCenter = smallCirCleView.center;
- CGFloat x1 = smallCenter.x;
- CGFloat y1 = smallCenter.y;
- CGFloat r1 = smallCirCleView.bounds.size.width / 2;
-
- // 获取圆心距离
- CGFloat d = [self pointToPoitnDistanceWithPoint:self.samllCircleView.center potintB:self.center];
- CGFloat sinθ = (x2 - x1) / d;
- CGFloat cosθ = (y2 - y1) / d;
-
- // 坐标系基于父控件
- CGPoint pointA = CGPointMake(x1 - r1 * cosθ , y1 + r1 * sinθ);
- CGPoint pointB = CGPointMake(x1 + r1 * cosθ , y1 - r1 * sinθ);
- CGPoint pointC = CGPointMake(x2 + r2 * cosθ , y2 - r2 * sinθ);
- CGPoint pointD = CGPointMake(x2 - r2 * cosθ , y2 + r2 * sinθ);
- CGPoint pointO = CGPointMake(pointA.x + d / 2 * sinθ , pointA.y + d / 2 * cosθ);
- CGPoint pointP = CGPointMake(pointB.x + d / 2 * sinθ , pointB.y + d / 2 * cosθ);
-
- UIBezierPath *path = [UIBezierPath bezierPath];
- // A
- [path moveToPoint:pointA];
- // AB
- [path addLineToPoint:pointB];
- // 绘制BC曲线
- [path addQuadCurveToPoint:pointC controlPoint:pointP];
- // CD
- [path addLineToPoint:pointD];
- // 绘制DA曲线
- [path addQuadCurveToPoint:pointA controlPoint:pointO];
-
- return path;
- }
- #pragma mark - button消失动画
- - (void)startDestroyAnimations
- {
- UIImageView *ainmImageView = [[UIImageView alloc] initWithFrame:self.frame];
- ainmImageView.animationImages = self.images;
- ainmImageView.animationRepeatCount = 1;
- ainmImageView.animationDuration = 0.5;
- [ainmImageView startAnimating];
-
- [self.superview addSubview:ainmImageView];
- }
- - (void)btnClick
- {
-
- }
- #pragma mark - 设置长按时候左右摇摆的动画
- - (void)setHighlighted:(BOOL)highlighted
- {
- [self.layer removeAnimationForKey:@"shake"];
-
- //长按左右晃动的幅度大小
- CGFloat shake = 3;
-
- CAKeyframeAnimation *keyAnim = [CAKeyframeAnimation animation];
- keyAnim.keyPath = @"transform.translation.x";
- keyAnim.values = @[@(-shake), @(shake), @(-shake)];
- keyAnim.removedOnCompletion = NO;
- keyAnim.repeatCount = 2;
- //左右晃动一次的时间
- keyAnim.duration = 0.3;
- if ( [self.layer animationForKey:@"shake"] == nil) {
- [self.layer addAnimation:keyAnim forKey:@"shake"];
- }
- }
- -(void)setUnreadCount:(NSString *)unreadCount
- {
- [self setTitle:unreadCount forState:UIControlStateNormal];
- }
- - (BOOL)pointInside:(CGPoint)point withEvent:(UIEvent*)event
- {
- CGRect bounds = self.bounds;
- //若原热区小于44x44,则放大热区,否则保持原大小不变
- // CGFloat widthDelta = MAX(44.0 - bounds.size.width, 0);
- // CGFloat heightDelta = MAX(44.0 - bounds.size.height, 0);
- bounds = CGRectInset(bounds, 3, 3);
- //Todo: check is the message table
- return CGRectContainsPoint(bounds, point);
- }
- -(void)dealloc {
- [[NSNotificationCenter defaultCenter] removeObserver:self];
- }
- @end
|