How to create an accurate timer event in Objective-C / iOS?

I am looking to create a countdown timer for the SMPTE timecode (HH: MM: SS: FF) on iOS. Basically, it's just a countdown timer with a resolution of 33.33333ms. I'm not sure if NSTimer is accurate enough to count on triggering events to create this timer. I would like to fire an event or trigger a piece of code every time this timer increments / decrements.

I'm new to Objective-C, so I'm looking for wisdom from the community. Someone suggested the CADisplayLink class , looking for expert advice.

+5
source share
3 answers

Try CADisplayLink. It fires at a refresh rate (60 frames per second).

CADisplayLink *displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(timerFired:)];
displayLink.frameInterval = 2;
[displayLink addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];

2 , 30 , , .

, , .

+12

NSTimer dispatch_after; , - , , .

, ( -), .

, , , , , , SMPTE , , , . , . , :

// Setup
timerStartDate = [[NSDate alloc] init];
[NSTimer scheduledTimer...

- (void)timerDidFire:(NSTimer *)timer
{
    NSTImeInterval elapsed = [timerStartDate timeIntervalSinceNow];
    NSString *smtpeCode = [self formatSMTPEFromMilliseconds:elapsed];
    self.label.text = smtpeCode;
}

, . ( , , . .)

CADisplayLink, , . , , , . , , .

+4

iOS 4+, Grand Central Dispatch:

// Set the time, '33333333' nanoseconds in the future (33.333333ms)
dispatch_time_t time = dispatch_time(DISPATCH_TIME_NOW, 33333333);
// Schedule our code to run
dispatch_after(time, dispatch_get_main_queue(), ^{
    // your code to run here...
});

33.333333ms. , dispatch_after_f , :

void DoWork(void *context);

void ScheduleWork() {
    // Set the time, '33333333' nanoseconds in the future (33.333333ms)
    dispatch_time_t time = dispatch_time(DISPATCH_TIME_NOW, 33333333);
    // Schedule our 'DoWork' function to run
    // Here I pass in NULL for the 'context', whatever you set that to will
    // get passed to the DoWork function
    dispatch_after_f(time, dispatch_get_main_queue(), NULL, &DoWork);
}

void DoWork(void *context) {
    // ...
    // Do your work here, updating an on screen counter or something
    // ...

    // Schedule our DoWork function again, maybe add an if statement
    // so it eventually stops
    ScheduleWork();
}

ScheduleWork();, . , , , .

. Grand Central Dispatch docs.

+1

All Articles