【iOS】CountDownView的封装

CountDownView的封装

今天在整理以前的代码的时候,把以前的一个控件再次封装了一次,这是一个倒计时的控件,可以用来作为一个进度条来使用。

CountDownView的四个基本类型以及一个自定义类型:
CountDownViewTypeCircle,
CountDownViewTypeRect,
CountDownViewTypeLine,
CountDownViewTypePercent

使用的时候,也是很方便的!
开源代码 - Github

使用的时候的代码

 CountDownView * Circle =[CountDownView countDownViewWithFrame:CGRectMake(10, 40, 140, 140) type:CountDownViewTypeCircle andFinishblock:^(UIView *countDownView, CADisplayLink *link) {
        NSLog(@"%s",__func__);
    }];
    [Circle showInKeyWindowTop];

    CountDownView * Rect =[CountDownView countDownViewWithFrame:CGRectMake(160, 40, 140, 140) type:CountDownViewTypeRect andFinishblock:^(UIView *countDownView, CADisplayLink *link) {
        NSLog(@"%s",__func__);
    }];
    [self.view addSubview:Rect];

    CountDownView * downV =[CountDownView countDownViewWithFrame:CGRectMake(20, 200, 280, 80) type:CountDownViewTypeLine andFinishblock:^(UIView *countDownView, CADisplayLink *link) {
        NSLog(@"%s",__func__);
    }];
    [downV showInKeyWindowTop];

    //CountDownViewTypePercent
    CountDownView * downV1 =[CountDownView countDownViewWithFrame:CGRectMake(20, 300, 280, 40) type:CountDownViewTypePercent andFinishblock:^(UIView *countDownView, CADisplayLink *link) {
        NSLog(@"%s",__func__);
    }];
    [self.view addSubview:downV1];
    downV1.lineWidth = 30;

源码

//
//  CountDownView.h
//  倒计时
//
//  Created by zzz on 15/10/9.
//  Copyright (c) 2015年 zzz. All rights reserved.
//

#import <UIKit/UIKit.h>


typedef void(^FinishCountDownBlock)(UIView *countDownView,CADisplayLink *link);


typedef enum : NSUInteger {
    CountDownViewTypeCircle,
    CountDownViewTypeRect,
    CountDownViewTypeLine,
    CountDownViewTypePercent
} CountDownViewType;

@interface CountDownView : UIView

/**
 *  倒计时最大时间
 */
@property(nonatomic, assign) CGFloat count;                //默认为: 10.00s

/**
 *  当前时间点(可以用作进度条)
 */
@property(nonatomic, assign) CGFloat currentCount;


@property(nonatomic, strong) UIColor * lineColor;           //默认为: Red:0.4 green:0 blue:0.8 alpha:0.6
@property(nonatomic, strong) UIColor * textColor;           //默认为: Red:0 green:0.4 blue:0.8 alpha:0.8
@property(nonatomic, strong) UIFont * textFont;             //默认为: 高度的一半

@property(nonatomic, assign) CGFloat lineWidth;             //默认为: 10.0

@property(nonatomic, assign) BOOL isTouchBegin;             //默认为: YES
@property(nonatomic, assign) BOOL isTouchEnd;               //默认为: YES
@property(nonatomic, assign) BOOL hiddenText;               //默认为: NO

@property(nonatomic, assign) CountDownViewType type;        // 默认为:CountDownViewTypeCircle
@property(nonatomic ,copy) FinishCountDownBlock finishblock;


+ (CountDownView *) countDownViewWithFrame:(CGRect)frame type:(CountDownViewType)type andFinishblock:(FinishCountDownBlock)block;


- (void)setFinishblock:(FinishCountDownBlock)finishblock;

- (void)beginCountDown;

/**
 *  此方法必须要有keyWindow,才有用
 */
- (void)showInKeyWindowTop;

@end


//
//  CountDownView.m
//  倒计时
//
//  Created by zzz on 15/10/9.
//  Copyright (c) 2015年 zzz. All rights reserved.
//

#import "CountDownView.h"


@interface CountDownView ()


@property (nonatomic, strong) CADisplayLink * link;
@property (nonatomic, strong) UILabel * label;

@property(nonatomic, strong) UITapGestureRecognizer * tap;
@property(nonatomic, strong) UITapGestureRecognizer * doubelTap;


@end

@implementation CountDownView


+ (CountDownView *)countDownViewWithFrame:(CGRect)frame type:(CountDownViewType)type andFinishblock:(FinishCountDownBlock)block{
    CountDownView * downV = [[CountDownView alloc] initWithFrame:frame];
    downV.type = type;
    downV.finishblock = block;
    return downV;
}
- (void)beginCountDown{
    [self.link addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
}

- (void)showInKeyWindowTop{
    
    if ([UIApplication sharedApplication].keyWindow) {
        [[UIApplication sharedApplication].keyWindow.rootViewController.view addSubview:self];
    }else{
        NSLog(@"keyWindow = %@",[UIApplication sharedApplication].keyWindow);
    }
    
}




#pragma mark - 复写方法
- (instancetype)initWithFrame:(CGRect)frame{
    if (self = [super initWithFrame:frame]) {
        
        self.backgroundColor = [UIColor colorWithRed:0.1 green:0.2 blue:0.6 alpha:0.4];
        
        UITapGestureRecognizer * tap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(beginAndEndLink)];
        [self addGestureRecognizer:tap];
        
        self.lineWidth = 10;
        self.count = 10;
        self.lineColor = [UIColor colorWithRed:0 green:0.4 blue:0.8 alpha:0.8];
        self.isTouchBegin = YES;
        self.isTouchEnd = YES;
    }
    return self;
}

- (void)layoutSubviews{
    [super layoutSubviews];
    
    self.label.frame = self.bounds;
}





// 开始画图
- (void)drawRect:(CGRect)rect{
    
    
    if (self.type == CountDownViewTypePercent) {
        self.label.text = [NSString stringWithFormat:@"%0.2f%",(1.0 - (_currentCount / self.count)) * 100];
    }else{
        
        int index =  (self.count == _currentCount)?(int)_currentCount:(int)_currentCount +1;
        index = _currentCount <= 0 ? 0 : index;
        self.label.text = [NSString stringWithFormat:@"%d",index];
        
    }
    
    if (self.type == CountDownViewTypeLine || self.type == CountDownViewTypePercent) {
        
        // 1.开启上下文
        CGContextRef context = UIGraphicsGetCurrentContext();

        
        CGFloat Width = CGRectGetWidth(self.bounds);
        CGFloat height = CGRectGetHeight(self.bounds);
        
        CGFloat Now = Width * (_currentCount / self.count);
        
        CGContextAddRect(context, CGRectMake(0, height - self.lineWidth -5,Width - Now, self.lineWidth));
        
        CGContextSetLineWidth(context, self.lineWidth);
        [(self.lineColor)?self.lineColor:[UIColor blackColor] set];
        
        CGContextSetLineCap(context, kCGLineCapRound);
        
        CGContextFillPath(context);
        
        return;
    }
    // 1.开启上下文
    CGContextRef context = UIGraphicsGetCurrentContext();
    
    CGFloat centerX = CGRectGetMidX(self.bounds);
    CGFloat centerY = CGRectGetMidY(self.bounds);
    
    CGFloat radius = (CGRectGetWidth(self.bounds) / 2.0) - 10;
    
    CGFloat startAngle = M_PI * 1.5;
    
    CGFloat endAngle = startAngle + (M_PI * 2.0) * (_currentCount / self.count);
    
    // 0 表示顺时针
    CGContextAddArc(context, centerX, centerY, radius, startAngle, endAngle, 0);
    
    CGContextSetLineWidth(context, self.lineWidth);
    [(self.lineColor)?self.lineColor:[UIColor blackColor] setStroke];

    CGContextSetLineCap(context, kCGLineCapRound);
    
    CGContextStrokePath(context);
}





#pragma mark - 私有方法
- (void)beginAndEndLink{
    if (_link && self.isTouchEnd) {
        
        [_link invalidate];
        _link = nil;
        
        return;
    
    }else if (_currentCount <= 0 || (!self.isTouchBegin)) {
        
        return;
    }
    
    [self.link addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
}




// 每秒调用60次
- (void) linkLoop{
    
    [self setNeedsDisplay];
    
    if (_currentCount <= 0) {
        [_link invalidate];
        
        if (self.finishblock) {
            self.finishblock(self,_link);
        }
        return;
    }
    
    _currentCount -= 1 / 60.000000;
}







- (CADisplayLink *)link{
    if (!_link) {
        _link = [CADisplayLink displayLinkWithTarget:self selector:@selector(linkLoop)];
        
    }
    return _link;
}

- (UILabel *)label{
    if (!_label) {
        _label = [[UILabel alloc] init];
        _label.textAlignment = NSTextAlignmentCenter;
        _label.font = [UIFont systemFontOfSize:self.frame.size.height / 2.0];
        [_label setTextColor:[UIColor colorWithRed:0.4 green:0 blue:0.8 alpha:0.6]];
        [self addSubview:_label];
    }
    return _label;
}



- (void)setTextColor:(UIColor *)textColor{
    _textColor = textColor;
    [self.label setTextColor:_textColor];
}



- (void)setCount:(CGFloat)count{
    _count = count;
    _currentCount = _count;
}
- (void)setCurrentCount:(CGFloat)currentCount{
    _currentCount = currentCount;
    [self setNeedsDisplay];
}


- (void)setTextFont:(UIFont *)textFont{
    _textFont = textFont;
    self.label.font = textFont;
}

- (void)setType:(CountDownViewType)type{
    _type = type;
    
    if (_type == CountDownViewTypeCircle) {
        self.clipsToBounds = YES;
        self.layer.cornerRadius = self.frame.size.width/2.0;

    } else if (_type == CountDownViewTypeRect){
        self.clipsToBounds = YES;
        self.layer.cornerRadius = 1;
        
    }else if (_type == CountDownViewTypeRect){
        
        
    }
}

- (void)setHiddenText:(BOOL)hiddenText{
    _hiddenText = hiddenText;
    self.label.hidden = _hiddenText;
    
}


@end

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,937评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,503评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,712评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,668评论 1 276
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,677评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,601评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,975评论 3 396
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,637评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,881评论 1 298
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,621评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,710评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,387评论 4 319
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,971评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,947评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,189评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,805评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,449评论 2 342

推荐阅读更多精彩内容

  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 171,413评论 25 707
  • 发现 关注 消息 iOS 第三方库、插件、知名博客总结 作者大灰狼的小绵羊哥哥关注 2017.06.26 09:4...
    肇东周阅读 12,016评论 4 62
  • 早睡是为了身体,早起是为了我们的内心。 今天在哪思考:内蒙古呼伦贝尔莫力达瓦治自旗尼尔基水利风景区 天气 心情:还...
    沙漠中的鱼在飞阅读 109评论 0 0
  • 天气炎热的早晨,公交车上大家都安安静静享受空调下的舒服。拿起手机看看信息什么的,突然就听到“啪”的一声,像是手打到...
    兮南楼阅读 277评论 0 1