Вызов метода либо во второй раз, когда возникает условие, ИЛИ после тайм-аута, в зависимости от того, что наступит раньше. - PullRequest
0 голосов
/ 22 марта 2011

После большого количества кодирования в последние дни, я наконец-то (эм) застрял.

Мое приложение прослушивает внешнее уведомление NSNotification, отправленное iTunes. Уведомление отправляется всякий раз, когда изменяется текущее состояние воспроизведения, в этом случае наиболее интересно изменение названия текущего потока. При подключении к новой радиостанции обычно отправляются два уведомления - одно, как только iTunes подключается, с названием станции в качестве заголовка, и одно вскоре после этого (секунда или около того) с настоящим исполнителем. и название текущей песни. Меня интересует только комбо артист / название или уведомление second . или , если после двухсекундной паузы отправляется только одно уведомление, используйте первое. (Поскольку невозможно заранее узнать, будет ли один или два, тайм-аут - это единственный способ, о котором я могу думать.)

Короче говоря, я хочу вызывать метод только во второй раз, когда возникает условие, ИЛИ после двухсекундного перерыва, если отправлено только одно уведомление. По истечении двух секунд он должен вернуться обратно, чтобы снова выполнить всю сделку.

Есть идеи?

Ответы [ 2 ]

1 голос
/ 23 марта 2011

Это не так уж сложно. Вам просто нужно держаться за первое уведомление, пока не сработает таймер или не появится второе уведомление. Комментарии, которые я вставил в код, должны объяснить процедуру.

- (void)awakeFromNib {
    // Register for the notification you're interested in
    [[NSDistributedNotificationCenter defaultCenter] addObserver:self 
                                                        selector:@selector(iTunesNoteCallback:) 
                                                            name:NSTheiTunesNotificationImInterestedIn 
                                                          object:nil]; // @"iTunes"?
}

- (void)iTunesNoteCallback:(NSNotification *)note {
    // Check whether there's been a notification already
    if( !gotFirstNote ){
        // If so, hang on to it,
        gotFirstNote = YES;
        self.currNote = note; // With currNote declared as a retained property
        // and start a timer.
        noteTimer = [NSTimer scheduledTimerWithTimeInterval:2.0 
                                                     target:self 
                                                   selector:@selector(actOniTunesInfo:) 
                                                   userInfo:nil repeats:NO];
    }
    else {
        // However, if we got a notification already,
        // hang on to the new one,
        self.currNote = note;
        // stop the timer, 
        [noteTimer invalidate];
        // and call the same method the timer would have
        [self actOniTunesInfo:nil];
    }
}

- (void)actOniTunesInfo:(NSTimer *)timer {
    // Reset the flag
    gotFirstNote = NO;
    // Use currNote; doesn't matter which one it is,
    // it's the best info we've gotten
}

Если есть два типа уведомлений, это еще проще. Флаг вам больше не нужен, вы просто регистрируете два обратных вызова, и как только вызывается второй, вы можете сделать недействительным таймер, отменить первое уведомление и использовать только что полученную информацию.

0 голосов
/ 22 марта 2011

Вам необходимо создать модель данных, которая может хранить и моделировать уведомления, а также их порядок и сроки.

Сначала вам понадобится объект данных для хранения каждого уведомления и данных об уведомлении. - объект уведомления - отметка времени, когда пришло уведомление - тип уведомления

Тогда вам потребуется контейнер-объект, который может содержать объекты данных в массиве, а также таймеры запуска и перехвата. Таким образом, когда приходит уведомление, оно классифицируется, сохраняется в объекте данных, который затем помещается в массив. Если это первый тип уведомления, контейнерный объект запускает двухсекундный таймер. Если приходит другое уведомление второго типа, контейнерный объект убивает таймер, но если таймер срабатывает, то он возвращает объект данных последнего уведомления первого типа, возраст которого превышает две секунды.

После того, как вы запустили действие, очистите контейнер-объект и начните все сначала.

...