0
votes

I'm writing an app where I've got multiple TableViews. If you click the cell from the first one, it opens a second one with specific parameters. For each one of them I parse some content from a website, which often takes some time. I want my users to know that they have to wait a bit, so I wrote a class where I overlay a progressview while the app is parsing. My problem is, that if I try to start it before parsing and hide it after, it gets hidden before the content is completely parsed.

I tried using threads and grand central dispatch, but it didn't work out.

The last thing I tried was this:

    LoadingScreen.shared.showOverlay(self.view)
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)) {
        self.parse()
    }
    LoadingScreen.shared.hideOverlayView()

LoadingScreen.shared.hideOverlayView() is always called too early. Any ideas on how to fix this? :(

2

2 Answers

1
votes

The solution is to add a closure to your parse function i.e.:

func parse(_completion:(finished: Bool) -> Void) {
    // do your logic after finishing call your closure
    _completion(finished: true);

}

And if you want to call your parse function you have to do something like this:

parse { (finished) -> Void in
        dispatch_async(dispatch_get_main_queue(), { () -> Void in
            // make your UI stuff after finishing parsing
        })
    }
-1
votes

When you are calling hideOverlayView, the parse hasn't finished because you are making the hide call back on the main thread while your background thread in still performing the parsing.

You will want to dispatch back to the main thread within that first dispatch_async block. It would look like so:

dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0)) {
    self.parse()

    dispatch_async(dispatch_get_main_queue()) {
        LoadingScreen.shared.hideOverlayView()
    }
}

This will wait for the parsing to finish before dispatching back to the main thread to hide the overlay.