解决iOS程序UI主线程和定时器相互阻塞的问题
发布日期:2021-10-02 15:44:13 浏览次数:4 分类:技术文章

本文共 3695 字,大约阅读时间需要 12 分钟。

我的问题是这样,我的页面上有一个UIScrollView和一个定时器用来记录当前考试模式下的剩余时间,问题出现了:当我滑动滚动试图时,定时器的方法便不在运行(即被UI主线程阻塞)。google一下找到了解决办法:将定时器放在非主线程中执行将更新UI的操作放到主线程,这样UI主线程和定时器就能互不干扰的相互工作了。

在另一个项目中,还解决了一个问题:手机验证码,获取按钮,点击获取后,会开始倒计时一段时间,按钮不可点,按钮上的文字不断变化。

获取验证码

120秒后重新获取

119秒后重新获取

以下是主要代码:

1 #import "CountdownTool.h"  2   3 @interface CountdownTool()  4 {  5     UILabel *_lblShow;  6     NSTimer *_timer;  7 }  8 @property (nonatomic, assign) NSInteger hour;  9 @property (nonatomic, assign) NSInteger minute; 10 @property (nonatomic, assign) NSInteger second; 11 @property (nonatomic, copy) NSString  *strHour; 12 @property (nonatomic, copy) NSString  *strMinute; 13 @property (nonatomic, copy) NSString  *strSecond; 14 @property (nonatomic, assign) NSInteger totalSeconds; 15 @end 16 @implementation CountdownTool 17 @synthesize hour = _hour; 18 @synthesize minute = _minute; 19 @synthesize second = _second; 20 @synthesize totalSeconds = _totalSeconds; 21  22 - (void)dealloc 23 { 24     [_lblShow release]; 25     [_strHour release]; 26     [_strMinute release]; 27     [_strSecond release]; 28     [super dealloc]; 29 } 30  31 - (id)initWithFrame:(CGRect)frame 32 { 33     self = [super initWithFrame:frame]; 34     if (self) { 35         _lblShow = [[UILabel alloc] initWithFrame:self.bounds]; 36         _lblShow.backgroundColor = [UIColor clearColor]; 37         _lblShow.font = [UIFont systemFontOfSize:15]; 38         _lblShow.textColor = [UIColor yellowColor]; 39         _lblShow.textAlignment = NSTextAlignmentCenter; 40         _lblShow.numberOfLines = 1; 41         [self addSubview:_lblShow]; 42     } 43     return self; 44 } 45  46 - (id)initWithFrame:(CGRect)frame andMinutesNum:(NSInteger)minute 47 { 48     if (self = [self initWithFrame:frame]) { 49         self.totalSeconds = minute * 60; 50         //多线程启动定时器 51        [NSThread detachNewThreadSelector:@selector(startTimer) toTarget:self withObject:nil]; 52     } 53     return self; 54 } 55 - (void)startTimer 56 { 57     _timer = [NSTimer scheduledTimerWithTimeInterval:1.0f target:self selector:@selector(timerFire) userInfo:nil repeats:YES]; 58     [[NSRunLoop currentRunLoop] run]; 59 } 60 - (void)handleWithTotalSeconds 61 { 62     self.hour = _totalSeconds/3600; 63     self.minute = _totalSeconds%3600/60; 64     self.second = _totalSeconds%3600%60; 65     if (_hour <= 0) { 66         _lblShow.text = [NSString stringWithFormat:@"%@:%@",_strMinute,_strSecond]; 67     }else{ 68         _lblShow.text = [NSString stringWithFormat:@"%@:%@:%@",_strHour,_strMinute,_strSecond]; 69     } 70 } 71 - (void)setHour:(NSInteger)hour 72 { 73     _hour = hour; 74     if (_hour < 10) { 75         self.strHour = [NSString stringWithFormat:@"0%d",_hour]; 76     }else{ 77         self.strHour = [NSString stringWithFormat:@"%d",_hour]; 78     } 79 } 80 - (void)setMinute:(NSInteger)minute 81 { 82     _minute = minute; 83     if (_minute < 10) { 84         self.strMinute = [NSString stringWithFormat:@"0%d",_minute]; 85     }else{ 86         self.strMinute = [NSString stringWithFormat:@"%d",_minute]; 87     } 88 } 89 - (void)setSecond:(NSInteger)second 90 { 91     _second = second; 92     if (_second < 10) { 93         self.strSecond = [NSString stringWithFormat:@"0%d",_second]; 94     }else{ 95         self.strSecond = [NSString stringWithFormat:@"%d",_second]; 96     } 97 } 98 - (void)setTotalSeconds:(NSInteger)totalSeconds 99 {100     _totalSeconds = totalSeconds;101     [self performSelectorOnMainThread:@selector(handleWithTotalSeconds) withObject:nil waitUntilDone:YES];102 }103 - (void)timerFire104 {105     if (_totalSeconds == 0) {106         [_timer invalidate];107         return;108     }109     self.totalSeconds -= 1;110 }111 @end

转载地址:https://blog.csdn.net/jinyeweiyang/article/details/41217547 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!

上一篇:iOS应用程序生命周期(前后台切换,应用的各种状态)详解
下一篇:60个开发者不容错过的免费资源库

发表评论

最新留言

逛到本站,mark一下
[***.202.152.39]2024年04月12日 15时31分58秒