将类型为NStimer的自定义类'obj调用到viewController中

时间:2014-01-13 15:39:42

标签: ios xcode nstimer

在我发现的示例教程中,我注意到使用NStimer类创建的计时器:它直接在viewController.m中实现 我试图将它作为“独立”的obj类,在它自己的timer.m和相对标题中。 这就是我得到的

#import "Timer.h"

@implementation Timer

-(void) startTimer{
    seconds = 31;


myTimer = [NSTimer scheduledTimerWithTimeInterval:1.0 target:self selector:@selector(subtractTime:) userInfo:nil repeats:YES];
  NSLog(@"%i",seconds);
}

-(void)subtractTime: (Timer*)myTimer{
    seconds--;

    NSLog(@"seconds %i",seconds);

    if (seconds == 0) {
        [myTimer invalidate];

    }
}

@end

根据NSLog的输出,倒计时本身运作良好;当我尝试使用表单label.text =将其显示到标签中时,我的问题开始于viewController.m中 (这里只是方法实现部分)
(Xcode在Timer.h和viewController.h中没有给出任何关于@implementation部分的错误,项目构建运行正常,但标签的倒计时被锁定为0)

-(void)setupGame{

count = 0;
scoreLabel.text = [NSString stringWithFormat:@"Score:\n%i",count];//these strings are to make a score label increasing of 1 every time a button's pressed

Timer *newTimer = [[Timer alloc]init]; //i create a new obj of my Timer class
[newTimer startTimer];
[newTimer subtractTime:(Timer*) myTimer]; //i set the methods i created
timerLabel.text = [NSString stringWithFormat:@"%i",seconds]; //??? i don't know which var put here, actually, i cannot get here the refreshing seconds to make timerLabel changing
NSLog(@"newTimer %@",myTimer);//just a try to see this output, it's not what i need of course

}

我做错了什么?

2 个答案:

答案 0 :(得分:0)

这里有几个问题。首先使Timer成为视图控制器的实例变量,如下所示:

-(void)setupGame{

    // blah
    Timer *newTimer = [[Timer alloc]init];
    // blah
}

当此方法返回时,Timer对象将被销毁,因为该对象超出了范围。

第二个问题是您需要在时间更改时更新UI控件,因此可能会传递对UI控件(UILabel或其他任何内容)的引用,并将其存储为实例变量Timer类,因此计时器对象可以自行更新。

在这种特殊情况下,我没有看到单独的Timer对象的值,因为在视图控制器类中实现你想要的东西会更容易。

答案 1 :(得分:0)

正如Trojanfoe所说,你过于复杂了。让视图控制器创建计时器并完成它。

如果您受到约束并决定创建自定义类来管理计时器,那么您还有很多工作要做。

我不会将标签传递给Timer对象,因为这会破坏视图控制器的封装。您应始终将视图控制器的视图视为该视图控制器的私有视图。

相反,这就是我要做的事情:

您需要将一个Timer实例变量添加到视图控制器中,正如Trojanfoe所说。

您需要定义TimerProtocol。在该协议中,定义“timerFired”方法,该方法将剩余时间值作为参数。您可能还需要“timerFinished”方法

创建Timer对象时,请将自己设置为该计时器的委托。

重写Timer对象的subtractTime方法,使用剩余时间值向代理发送消息。然后在视图控制器的timerFired方法中,更新标签。

在你的视图控制器的timerFinished方法中,将实例var清零到Timer对象,这样它就会被解除分配,因为你完成了它。

同样,这是一个过于复杂的解决方案,不会增加任何价值。这样做的唯一原因是学习练习,但这不是一个好的设计决定。