2011-05-13 36 views
33

所以我发展我的第一个iPhone应用程序,我需要帮助..Xcode Objective-C | iOS:延迟功能/ NSTimer帮助?

简易程序,现在,我有9个按键,当我按下第一个按钮,或任何按钮,我只是想第一个按钮高亮显示60毫秒,高亮显示,第二个按钮高亮显示,等待60毫秒,取消高亮显示等等,以便看起来像是移动的LED。

我已经看过尝试睡眠/睡眠,但一旦睡眠持续时间完成,它似乎像跳过突出/ unhighlight一起。

例如:

- (void) button_circleBusy:(id)sender{ 
firstButton.enabled = NO; 
sleep(1); 
firstButton.enabled = YES; 

等的按钮的其余部分。它会延迟,但不会延迟“firstButton.enabled = NO;”。我为每个按钮的“禁用状态”都有一张图片,我从来没有看到它。

任何帮助的赞赏!我研究过NSTimer,但我不确定如何实现它。

谢谢。

- 保罗

回答

50

sleep不起作用,因为该显示器只能你的主线程返回到系统后更新。 NSTimer是要走的路。为此,您需要实现将由计时器调用的方法来更改按钮。举个例子:

- (void)button_circleBusy:(id)sender { 
    firstButton.enabled = NO; 
    // 60 milliseconds is .06 seconds 
    [NSTimer scheduledTimerWithTimeInterval:.06 target:self selector:@selector(goToSecondButton:) userInfo:nil repeats:NO]; 
} 
- (void)goToSecondButton:(id)sender { 
    firstButton.enabled = YES; 
    secondButton.enabled = NO; 
    [NSTimer scheduledTimerWithTimeInterval:.06 target:self selector:@selector(goToThirdButton:) userInfo:nil repeats:NO]; 
} 
... 
+0

嘿ughoavgfhw,对答复表示感谢。 好吧,这似乎很容易!但我也有另一个叫做button_killAll()的函数,它应该在0.06秒内禁用所有的东西。我注意到NSTimer如何使用选择器:@selector(goToSecondButton :),如果我不想去另一个函数并延迟0.06秒的禁用,该怎么办? 我想另一种方式来问这个问题是,一旦我到达最后一个按钮来突出显示/禁用,我应该怎么做,因为我不希望该循环结束? – Retro 2011-05-14 00:01:22

+0

希望该循环结束* – Retro 2011-05-14 00:07:02

16

尝试

NSDate *future = [NSDate dateWithTimeIntervalSinceNow: 0.06 ]; 
[NSThread sleepUntilDate:future]; 
+0

这可以按照以下方式在一行中完成。 – Barry 2013-10-14 08:04:46

25

一个稍微不那么冗长的方法是使用performSelector:withObject:afterDelay: 其树立的NSTimer对象为你可以很容易地取消

因此,继续前面的例子,这将是

[self performSelector:@selector(goToSecondButton) withObject:nil afterDelay:.06]; 

更多info in the doc

+0

我更喜欢这个解决方案。 performSelector将详细程度降至最低。 – 2013-03-04 23:46:30

0
[NSTimer scheduledTimerWithTimeInterval:.06 target:self selector:@selector(goToSecondButton:) userInfo:nil repeats:NO]; 

是最好的一个使用。使用睡眠(15);将导致用户无法执行任何其他操作。使用以下函数,您可以用适当的选择器或命令替换goToSecondButton,这也可以来自框架。

47
int64_t delayInSeconds = 0.6; 
dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, delayInSeconds * NSEC_PER_SEC); 
dispatch_after(popTime, dispatch_get_main_queue(), ^(void){ 
    do something to the button(s) 
}); 
+1

+1我喜欢这种语法。谢谢。 – Unheilig 2013-07-02 21:05:00

+0

你太棒了!谢谢,我一直在寻找这个年龄! – 2013-09-08 01:31:12

+1

这很有用! +1和谢谢 – 2013-11-21 14:07:02

29

较少的代码是更好的代码。

[NSThread sleepForTimeInterval:0.06]; 

斯威夫特:

Thread.sleep(forTimeInterval: 0.06) 
+0

好得多。谢谢。 – Barry 2013-10-14 08:05:25

+1

只有在“可读代码比不可读代码更好”之后,这是这个答案的更重要的提倡者。 – 2013-11-18 17:09:40

+0

我喜欢少代码,但它不允许屏幕更新,因为提问者需要。来自NSThread的文档sleepForTimeInterval:'当线程被阻塞时,不会发生运行循环处理。“ – slothbear 2014-04-16 02:27:37

3

我想通过阿夫纳巴尔增添几分答案。当使用int64时,看起来当我们超过1.0值时,函数看起来延迟不同。所以我认为在这一点上,我们应该使用NSTimeInterval。

所以,最终的代码是:

NSTimeInterval delayInSeconds = 0.05; 

dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, delayInSeconds * NSEC_PER_SEC); 
dispatch_after(popTime, dispatch_get_main_queue(), ^(void){ 

//do your tasks here 

});