Swift is new for me and I stuck at this part. I want to request some data from api when I clicked the button. After that, want to pass the data i get from this function to another view controller. So basicly want to perform segue with this data. However, when I clicked the button, request starts but it directly perform segue to 2. view without any data.
How can I wait for:
videoManager.performRequest(with: videoLinkTextField.text!)
this function to perform segue?
This is my button:
@IBAction func getVideoButtonPressed(_ sender: UIButton) {
if videoLinkTextField.text != nil, videoLinkTextField.text!.contains("tiktok") {
videoManager.performRequest(with: videoLinkTextField.text!)
DispatchQueue.main.async {
self.performSegue(withIdentifier: "GoToVideo", sender: self)
}
} else {
videoLinkTextField.text = ""
let alert = UIAlertController(title: "Error", message: "Please enter a valid link", preferredStyle: .alert)
alert.addAction(UIAlertAction(title: "Ok", style: .default))
present(alert, animated: true, completion: nil)
}
}
Here is my prepare function:
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "GoToVideo" {
DispatchQueue.main.async {
let destionationVC = segue.destination as! ResultViewController
print("Test \(self.videoUrl)")
destionationVC.videoUrl = self.videoUrl
}
}
}
And here is my performRequest function:
func performRequest(with videoUrl: String) {
let request = NSMutableURLRequest(url: NSURL(string: "https://tiktok-downloader-download-videos-without-watermark1.p.rapidapi.com/media-info/?link=\(videoUrl)")! as URL,
cachePolicy: .useProtocolCachePolicy,
timeoutInterval: 10.0)
request.httpMethod = "GET"
request.allHTTPHeaderFields = headers
let session = URLSession.shared
let dataTask = session.dataTask(with: request as URLRequest, completionHandler: { data, _, error in
if error != nil {
self.delegate?.didFailedWithError(error!)
}
if let safeData = data {
if let video = self.parseJSON(safeData) {
self.delegate?.didUpdateVideo(self, video: video)
}
}
})
dataTask.resume()
}
CodePudding user response:
You are asking:
How can I wait for:
videoManager.performRequest(with: videoLinkTextField.text!)
Looks like you may want to use a closure for this method: Check out this article to learn more about closures:
However, I'll also provide you an example of how you'd might want your function to look:
Note, I only added , completion: @escaping () -> Void
as a param and added a completion()
to indicate where the closure should finish (You can also pass params in a completion block too (e.g: String, Error, etc)
func performRequest(with videoUrl: String, completion: @escaping () -> Void) {
let request = NSMutableURLRequest(url: NSURL(string: "https://tiktok-downloader-download-videos-without-watermark1.p.rapidapi.com/media-info/?link=\(videoUrl)")! as URL,
cachePolicy: .useProtocolCachePolicy,
timeoutInterval: 10.0)
request.httpMethod = "GET"
request.allHTTPHeaderFields = headers
let session = URLSession.shared
let dataTask = session.dataTask(with: request as URLRequest, completionHandler: { data, _, error in
if error != nil {
self.delegate?.didFailedWithError(error!)
}
if let safeData = data {
if let video = self.parseJSON(safeData) {
self.delegate?.didUpdateVideo(self, video: video)
}
}
completion() // finishes the closure
})
dataTask.resume()
}
Then you'll be able to do this:
videoManager.performRequest(with: videoLinkTextField.text!) { _ in
DispatchQueue.main.async {
self.performSegue(withIdentifier: "GoToVideo", sender: self)
}
}
CodePudding user response:
Place segue here
if let video = self.parseJSON(safeData) {
self.delegate?.didUpdateVideo(self, video: video)
DispatchQueue.main.async {
self.performSegue(withIdentifier: "GoToVideo", sender: self)
}
}