高仿QQ底部小红点弹簧效果

高仿QQ底部小红点弹簧效果_第1张图片高仿QQ底部小红点弹簧效果_第2张图片


1:

// 前提之前:增加几张jpg格式的图片,暂时写死为9张,命名格式为:(1.jpg-9.jpg),你也可以在代码中去修改一下、谢谢!



//
//  QQRedButton.m
//  仿照QQ小红点
//
//  Created by 李胜兵 on 15/4/18.
//  Copyright © 2015年 李胜兵. All rights reserved.
//

#import "QQRedButton.h"
#define kMaxDisance 200
#define kHeight [UIScreen mainScreen].bounds.size.height
#define kWidth [UIScreen mainScreen].bounds.size.width

@interface QQRedButton ()


@property (nonatomic, strong)UIView *smallCircleView;

@property (nonatomic, assign)CGFloat smallOriginRadius;


@property (nonatomic, strong)CAShapeLayer *shapeLayer;

@end

@implementation QQRedButton

- (instancetype)initWithFrame:(CGRect)frame {
    if (self = [super initWithFrame:frame]) {
        [self setUp];
    }
    return self;
}

#pragma mark - 设置按钮内容

- (void)setUp {
    CGFloat w = self.bounds.size.width;
    self.layer.cornerRadius = w /2;
    self.smallOriginRadius = w /2;
    
    
    [self setTitle:@"10" forState:UIControlStateNormal];
     self.titleLabel.font = [UIFont systemFontOfSize:12];
    [self setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
    [self setBackgroundColor:[UIColor redColor]];
    
  
    // 添加pan手势
    UIPanGestureRecognizer *pan = [[UIPanGestureRecognizer alloc]initWithTarget:self action:@selector(pan:)];
    [self addGestureRecognizer:pan];
    
    
    // 添加小圆到大圆的后面:设置小圆的位置和尺寸
    self.smallCircleView.center = self.center;
    self.smallCircleView.bounds = self.bounds;
    self.smallCircleView.layer.cornerRadius = w/2;
    
}

#pragma mark - 方法

- (void)pan:(UIPanGestureRecognizer *)pan {
    [self.superview insertSubview:self.smallCircleView belowSubview:self];
    CGPoint transPoint = [pan translationInView:self];
    CGPoint center = self.center;
    center.x += transPoint.x;
    center.y += transPoint.y;
    self.center = center;
    [pan setTranslation:CGPointZero inView:self];

    CGFloat d = [self circleCenterDistanceWithBigCircleViewCenter:self.center smallCircleViewCenter:self.smallCircleView.center];
    CGFloat smallRadius = (self.smallOriginRadius - d / 10)>0?(self.smallOriginRadius - d / 10):0;
    self.smallCircleView.bounds = CGRectMake(0, 0, smallRadius*2, smallRadius*2);
    self.smallCircleView.layer.cornerRadius = smallRadius;
    if (d>kMaxDisance) {
        self.smallCircleView.hidden = YES;
        
        [self.shapeLayer removeFromSuperlayer];
        self.shapeLayer = nil;
    }else if (d>0 && self.smallCircleView.hidden == NO) { // 有圆心距离而且小圆也显示的时候才绘制不
        [self.superview.layer insertSublayer:_shapeLayer below:self.layer];
        self.shapeLayer.path = [[self pathWithBigCircleView:self smallCircleView:self.smallCircleView] CGPath];
    }


    
    if (pan.state == UIGestureRecognizerStateEnded) {
        if (d>kMaxDisance) {
            NSMutableArray *arrM = [NSMutableArray array];
            UIImageView *imgV = [[UIImageView alloc]initWithFrame:self.bounds];
            
            for (int i = 1; i<10; i++) {
                UIImage *image = [UIImage imageNamed:[NSString stringWithFormat:@"%d.gif",i]];
                [arrM addObject:image];
            }
            
            imgV.animationDuration = 2.2;
            imgV.animationRepeatCount = 1;
            imgV.animationImages = arrM;
            [imgV startAnimating];
            [self addSubview:imgV];
            
            dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
                [self removeFromSuperview];
            });
            
        }else {
            [self.shapeLayer removeFromSuperlayer];
            self.shapeLayer = nil;
            self.smallCircleView.hidden = NO;
            [UIView animateWithDuration:.5 delay:0 usingSpringWithDamping:.2 initialSpringVelocity:0 options:(UIViewAnimationOptionCurveLinear) animations:^{
                self.center = self.smallCircleView.center;
            } completion:^(BOOL finished) {
                
            }];
        }
    }
}


- (CGFloat)circleCenterDistanceWithBigCircleViewCenter:(CGPoint)bigCircleViewCenter smallCircleViewCenter:(CGPoint)smallCircleViewCenter {
    CGFloat offsetX = bigCircleViewCenter.x - smallCircleViewCenter.x;
    CGFloat offsetY = bigCircleViewCenter.y - smallCircleViewCenter.y;
    return  sqrt(offsetX * offsetX + offsetY * offsetY);
    
}


- (UIBezierPath *)pathWithBigCircleView:(UIView *)bigCircleView smallCircleView:(UIView *)smallCircleView {
    
    
    CGPoint bigCenter = bigCircleView.center;
    CGFloat x2 = bigCenter.x;
    CGFloat y2 = bigCenter.y;
    CGFloat r2 = bigCircleView.bounds.size.width /2;
    
    CGPoint smallCenter = smallCircleView.center;
    CGFloat x1 = smallCenter.x;
    CGFloat y1 = smallCenter.y;
    CGFloat r1 = smallCircleView.bounds.size.width /2;
    
    CGFloat d = [self circleCenterDistanceWithBigCircleViewCenter:bigCenter smallCircleViewCenter:smallCenter];
    
    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];

    [path moveToPoint:pointA];
    

    [path addLineToPoint:pointB];
    

    [path addQuadCurveToPoint:pointC controlPoint:pointP];
    

    [path addLineToPoint:pointD];
    

    [path addQuadCurveToPoint:pointA controlPoint:pointO];
    
    return path;
}



#pragma mark - get

- (UIView *)smallCircleView {
    if (!_smallCircleView) {
        _smallCircleView = [[UIView alloc] init];
        _smallCircleView.layer.cornerRadius = self.layer.cornerRadius;
        _smallCircleView.backgroundColor = self.backgroundColor;
    }
    return _smallCircleView;
}

#pragma mark - get

- (CAShapeLayer *)shapeLayer {
    if (!_shapeLayer) {
        _shapeLayer = [CAShapeLayer layer];
        _shapeLayer.fillColor = self.backgroundColor.CGColor;
    }
    return _shapeLayer;
}



@end
//
//  QQRedButton.h
//  仿照QQ小红点
//
//  Created by 李胜兵 on 15/4/18.
//  Copyright © 2015年 李胜兵. All rights reserved.
//

#import <UIKit/UIKit.h>

@interface QQRedButton : UIButton

@end










你可能感兴趣的:(小红点,高仿qq小红点,消息小红点)