ios – UIActivityIndicatorView does not work

Question:

I want to display the activity indicator after clicking a button. This button will update the app. I followed examples and documentation, but it doesn't work…

- (void)viewDidLoad {
    // .. snip
    indicator = [[UIActivityIndicatorView alloc]initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleGray];
    [self.view addSubview:indicator];
    [indicator stopAnimating];
    //indicator.hidden = TRUE;
    //[indicator setHidden:YES];
}

-(IBAction)actAtualizar:(id)sender {
    //[indicator setHidden:YES];
    //indicator.hidden = FALSE;
    [indicator startAnimating];
    //[indicator setHidden:NO];
    //[indicator stopAnimating];
    //indicator.hidden = TRUE;
    [self carregaDados];
    NSLog(@"teste de atualizacao", nil);
}


-(void)carregaDados{
    // ...     
    [indicator stopAnimating];
}

Answer:

I believe that when you do startAnimation, the interface can only actually be updated when you finish an IOS runloop iteration. The problem is that there is no time for the animation to start, as the startAnimation event is posted, then the LoadData method is executed until the end, and then the event to end the animation is posted. When the events are actually going to be processed you have already executed your method.

There are a few ways to solve this, the most recommended would be to run a method that takes a long time in a separate thread, so as not to crash the interface. That way, you can start the animation, trigger the LoadData in another thread and when you're done, give the stopAnimation. This way, the bar will be animated while the data load is being processed.

Another way is to make the loadData, of course, run after the start animation. An example of how to do this is:

[indicator startAnimating];
[self performSelector:@selector(carregaDados) withObject:nil afterDelay:0.01];

...

- (void)carregaDados{
    ...
    [indicator stopAnimating];
}

Remembering that it is not recommended to run a method that crashes the application and the user has to wait. Imagine a tableView that it can't even scroll because the UI is locked.

References :

https://stackoverflow.com/questions/1850186/iphone-uiactivityindicatorview-not-starting-or-stopping

https://stackoverflow.com/questions/2391343/run-an-uiactivityindicatorview-while-the-main-thread-is-busy

https://stackoverflow.com/questions/3317068/how-do-i-show-and-start-animating-a-uiactivityindicatorview-from-within-a-method

https://developer.apple.com/library/ios/documentation/cocoa/reference/foundation/Classes/NSObject_Class/Reference/Reference.html#//apple_ref/occ/instm/NSObject/performSelector:withObject:afterDelay :

Scroll to Top