Search code examples
iosswift3uiimagealamofirealamofireimage

How to wait until alamofire image request is done


Hello I have been trying alot and looking around on SO, but I cant find a good solution to my problem.

The problem is that i do 2 requests within one function and the first one finishes, then it does updateUI function on the main thread instead of waiting for the second download to finish.

I know that i am doing something wrong but in my mind the two requests work on different threads and that is why updateUI only will trigger after first download is complete.

Is it possible to use dispatchqueue? I dont know how completionhandlers work either sadly..

I couldnt see what i have to use from their github page either, im quite new at Swift.

Please do not set this as duplicate. would really appreciate it

func getMovieData(){

    self.posterLoading.startAnimating()



        //Set up URL
        let testCall: String = "https://api.themoviedb.org/3/discover/movie?api_key=935f5ddeed3fb57e&language=en-US&sort_by=popularity.desc&include_adult=false&include_video=false&page=1&with_genres=12"

        Alamofire.request(testCall).responseJSON { response in
            //print(response.request)  // original URL request
            //print(response.response) // HTTP URL response
            //print(response.data)     // server data
            //print(response.result)   // result of response serialization

            if let json = response.result.value as? Dictionary<String,AnyObject> {
                if let movies = json["results"] as? [AnyObject]{
                    for movie in movies{
                        let movieObject: Movie = Movie()

                        let title = movie["title"] as! String
                        let releaseDate = movie["release_date"] as! String
                        let posterPath = movie["poster_path"] as! String
                        let overView = movie["overview"] as! String
                        let movieId = movie["id"] as! Int
                        let genre_ids = movie["genre_ids"] as! [AnyObject]

                        movieObject.title = title
                        movieObject.movieRelease = releaseDate
                        movieObject.posterPath = posterPath
                        movieObject.overView = overView
                        movieObject.movieId = movieId


                        for genre in genre_ids{//Genre ids, fix this
                            movieObject.movieGenre.append(genre as! Int)
                        }

                        Alamofire.request("http://image.tmdb.org/t/p/w1920" + posterPath).responseImage {
                            response in
                            debugPrint(response)

                            //print(response.request)
                            //print(response.response)
                            //debugPrint(response.result)

                            if var image = response.result.value {
                                image = UIImage(data: response.data!)!

                                movieObject.poster = image
                            }
                        }



                        self.movieArray.append(movieObject)
                        print("movie added")

                    }//End of for each movie
                    DispatchQueue.main.async(){
                    print("is ready for UI")
                        self.updateUI()
                    }

                }


            }

    }//End of Json request


}//End of getmoviedata

func updateUI(){
    uiMovieTitle.text = movieArray[movieIndex].title
    uiMoviePoster.image = movieArray[movieIndex].poster

}

Solution

  • Just make your getMovieData func with a completion block.

    func getMovieData(finished: () -> Void) {
    
     Alamofire.request(testCall).responseJSON { response in
         // call me on success or failure
         finished()
     }
    

    }

    and then you can call your update UI in the completion block of the func, where you calling it the second time getMovieData()