Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

how to unschedule NSTimer in objective-c

I am using nested NSTimer in an application. I have two issues here.

  1. How to re-initiate time counter in this function - (void)updateLeftTime:(NSTimer *)theTimer
  2. How to kill previous timer because - (void)updateLevel:(NSTimer *)theTimer is also calling by timer.

- (void)viewDidLoad {
    [super viewDidLoad];

    tmLevel=[NSTimer scheduledTimerWithTimeInterval:20.0f target:self selector:@selector(updateLevel:) userInfo:nil repeats:YES];

    tmLeftTime=[NSTimer scheduledTimerWithTimeInterval:1.0f target:self selector:@selector(updateLeftTime:) userInfo:nil repeats:YES];
}

- (void)updateLevel:(NSTimer *)theTimer {
    static int count = 1;
    count += 1;

    lblLevel.text = [NSString stringWithFormat:@"%d", count];

    tfLeftTime.text=[NSString stringWithFormat:@"%d",ANSWER_TIME];

    tmLeftTime=[[NSTimer alloc] init];
    tmLeftTime=[NSTimer scheduledTimerWithTimeInterval:1.0f target:self selector:@selector(updateLeftTime:) userInfo:nil repeats:YES];
    [self playMusic];

}
- (void)updateLeftTime:(NSTimer *)theTimer {
    static int timeCounter=1;
    timeCounter+=1;
    tfLeftTime.text=[NSString stringWithFormat:@"%d", (ANSWER_TIME-timeCounter)];
}
like image 352
Shivomkara Chaturvedi Avatar asked Sep 07 '11 13:09

Shivomkara Chaturvedi


2 Answers

  • Use [tmLevel invalidate] to cancel schedule of a timer.
  • Don't forget to set tmLevel=nil immediately after (to avoid using the variable after the timer has been unscheduled and released by the Runloop)
  • Don't forget to invalidate the tmLevel timer before loosing the reference to it, namely call [tmLevel invalidate] also before assigning a new NSTimer to the tmLevel variable (or else the previous timer will continue to run in addition to the new one)

Note also that in your code you have useless allocations that are moreover creating a leak:

tmLeftTime=[[NSTimer alloc] init];
tmLeftTime=[NSTimer scheduledTimerWithTimeInterval:1.0f target:self selector:@selector(updateLeftTime:) userInfo:nil repeats:YES];

here you allocate an NSTimer instance, store this instance in tmLeftTime... and then immediately forget about this created instance to replace it with another one, created using [NSTimer scheduledTimerWithTimeInterval:...]! Therefore, the NSTimer created using [[NSTimer alloc] init] is lost, and is creating a leak (as it will never be released).

Your first line is totally useless, it's kinda like you were doing

int x = 5;
x = 12; // of course the value "5" is lost, replaced by the new value
like image 55
AliSoftware Avatar answered Oct 20 '22 21:10

AliSoftware


add the following lines when u want to reset the timer

[tmLeftTime invalidate]; 
tmLeftTime = nil;

you can also use

if ([tmLeftTime isValid]){
  // the timer is valid and running, how about invalidating it
  [tmLeftTime invalidate]; 
    tmLeftTime = nil;
}
like image 23
chewy Avatar answered Oct 20 '22 22:10

chewy