Как отобразить UIAlertView из блока на iOS?

Каков наилучший способ отображения UIAlertView из блока?

У меня есть следующее действие в моем коде:

- (IBAction)connectWithTwitterClicked:(id)sender {
    ACAccountStore * account = [[ACAccountStore alloc]init];
    ACAccountType * accountType = [account accountTypeWithAccountTypeIdentifier:ACAccountTypeIdentifierTwitter];

    [account requestAccessToAccountsWithType:accountType options:nil completion:^(BOOL granted, NSError *error) {
        if (granted == YES){
            NSLog(@"Twitter account has been granted");
            NSArray * arrayOfAccounts = [account accountsWithAccountType:accountType];
            if([arrayOfAccounts count] > 0){
                ACAccount * twitterAccount = [arrayOfAccounts lastObject];
                NSLog(@"Found twitter Id of [%@]", twitterAccount.username);
                // continue on to use the twitter Id
            } else {
                // no twitter accounts found, display alert to notify user
            }
        } else{
            NSLog(@"No twitter accounts have been granted");
            // no twitter accounts found, display alert to notify user
        }
    }];
}

Я пробовал эти решения до сих пор:

  1. В любой из двух закомментированных строк, непосредственно создающих и показывающих UIAlertView, это приводит к сбою приложения. Я полагаю, это связано с тем, что блок является асинхронным процессом и не имеет доступа к потоку пользовательского интерфейса для отображения предупреждения
  2. Создал NSMutableString вне блока, пометил его__blockустановите его в закомментированных строках и затем отобразите после. Аналогичная проблема здесь, когда блок выполняется асинхронно, поэтому во время отображения предупреждения нет никакой гарантии, что NSMutableString был установлен.

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

Спасибо

2 ответа

Решение

Создайте метод, который показывает представление оповещения, затем выполните его селектор в главном потоке:

- (void)showAlertWithTitle:(NSString *)t
{
    [[[[UIAlertView alloc] initWithTitle:t
                                 message:nil
                                delegate:nil
                       cancelButtonTitle:@"OK"
                       otherButtonTitles:nil
    ] autorelease] show];
}

Назовите это следующим образом:

[SomeClass dispatchNastyAsyncBlock:^{
    // ... do stuff, then
    [self performSelectorOnMainThread:@selector(showAlertWithTitle:)
                           withObject:@"Here comes the title"
                        waitUntilDone:YES];
}];

Это способ GCD сделать это:

[SomeClass dispatchNastyAsyncBlock:^{
    // ... do stuff, then
    dispatch_async(dispatch_get_main_queue(), ^ {
        [[[[UIAlertView alloc] initWithTitle:t
                                     message:nil
                                    delegate:nil
                           cancelButtonTitle:@"OK"
                           otherButtonTitles:nil
        ] autorelease] show];
    });
}];
Другие вопросы по тегам