? ? ? 寫項(xiàng)目的時(shí)候需要一個(gè)計(jì)時(shí)器來(lái)做短信驗(yàn)證碼的倒計(jì)時(shí)嫩絮,場(chǎng)景需求是按鈕點(diǎn)擊后開(kāi)始讀秒丛肢,按鈕不可用,當(dāng)讀秒結(jié)束按鈕可用絮记,在讀秒期間切換控制器摔踱,或者將應(yīng)用切換到后臺(tái)在切換回讀秒頁(yè)面依舊在繼續(xù)讀秒。
代碼如下:
一個(gè)繼承NSObject的單例類
.h文件
#import
@interface CaptchaTimerManager : NSObject
@property (nonatomic, assign)__block int timeout;
+ (id)sharedTimerManager;
- (void)countDown;
@end
.m文件
#import "CaptchaTimerManager.h"
@implementation CaptchaTimerManager
+ (id)sharedTimerManager{
? ?static CaptchaTimerManager *manager = nil;
? ?static dispatch_once_t onceToken;
? ?dispatch_once(&onceToken, ^{
? ? ? ?if (manager == nil) {
? ? ? ? ? ?manager = [[self alloc]init];
? ? ? ?}
? ?});
? ?return manager;
}
- (void)countDown{
? ?if (_timeout > 0) {
? ? ? ?dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
? ? ? ?dispatch_source_t _timer = dispatch_source_create(DISPATCH_SOURCE_TYPE_TIMER, 0, 0,queue);
? ? ? ?dispatch_source_set_timer(_timer,dispatch_walltime(NULL, 0),1.0*NSEC_PER_SEC, 0); //每秒執(zhí)行
? ? ? ?dispatch_source_set_event_handler(_timer, ^{
? ? ? ? ? ?if(_timeout<=0){ //倒計(jì)時(shí)結(jié)束怨愤,關(guān)閉
? ? ? ? ? ? ? ?dispatch_source_cancel(_timer);
? ? ? ? ? ?}else{
? ? ? ? ? ? ? ?_timeout--;
? ? ? ? ? ?}
? ? ? ?});
? ? ? ?dispatch_resume(_timer);
? ?}
}
@end
在實(shí)際需要計(jì)時(shí)器的控制器中具體實(shí)現(xiàn)細(xì)節(jié)如下
#import "ViewController.h"
#import "CaptchaTimerManager.h"
@interface ViewController ()
@property (strong, nonatomic)UIButton *button;
@property (nonatomic, assign) __block int timeout;
@end
@implementation ViewController
//頁(yè)面出現(xiàn)前取出計(jì)時(shí)器單例的時(shí)間進(jìn)行判斷是否還在倒計(jì)時(shí)
- (void)viewWillAppear:(BOOL)animated{
? ?[super viewWillAppear:animated];
? ?CaptchaTimerManager *manager = [CaptchaTimerManager sharedTimerManager];
? ?int temp = manager.timeout;
? ? ? ?if (temp > 0) {
? ? ? ? ? ?_timeout= temp; //倒計(jì)時(shí)時(shí)間
? ? ? ? ? ?[self timerCountDown];
? ? ? ?}
}
//頁(yè)面消失前記錄倒計(jì)時(shí)時(shí)間到單例里
- (void)viewWillDisappear:(BOOL)animated{
? ?[super viewWillDisappear:animated];
? ?if (self.timeout > 0) {
? ? ? ?CaptchaTimerManager *manager = [CaptchaTimerManager sharedTimerManager];
? ? ? ?if (manager.timeout == 0) {
? ? ? ? ? ?manager.timeout = _timeout;
? ? ? ? ? ?[manager countDown];
? ? ? ?}
? ? ? ?_timeout = 0;//置為0派敷,釋放controller
? ?}
}
//按鈕點(diǎn)擊事件
- (IBAction)touch1:(id)sender {
? ?_timeout = 60; //倒計(jì)時(shí)時(shí)間
? ?[self timerCountDown];
}
//控制器里的計(jì)時(shí)器
- (void)timerCountDown{
? ?dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
? ?dispatch_source_t _timer = dispatch_source_create(DISPATCH_SOURCE_TYPE_TIMER, 0, 0,queue);
? ?dispatch_source_set_timer(_timer,dispatch_walltime(NULL, 0),1.0*NSEC_PER_SEC, 0); //每秒執(zhí)行
? ?dispatch_source_set_event_handler(_timer, ^{
? ? ? ?if(_timeout<=0){ //倒計(jì)時(shí)結(jié)束,關(guān)閉
? ? ? ? ? ?dispatch_source_cancel(_timer);
? ? ? ? ? ?dispatch_async(dispatch_get_main_queue(), ^{
? ? ? ? ? ? ? ?//這里寫倒計(jì)時(shí)結(jié)束button的處理
? ? ? ? ? ?});
? ? ? ?}else{
? ? ? ? ? ?dispatch_async(dispatch_get_main_queue(), ^{
? ? ? ? ? ? ? ?//這里寫倒計(jì)時(shí)期間button的處理(重設(shè)button的tiitle、用戶交互等)
? ? ? ? ? ?});
? ? ? ? ? ?_timeout--;
? ? ? ?}
? ?});
? ?dispatch_resume(_timer);
}
- (void)viewDidLoad {
? ?[super viewDidLoad];
? ?// button初始化處理.
}
@end