我试图运行一个url请求,以获得一个JSON文件后,某个表行被选中,基于行一个唯一的ID与url请求发送和不同的JSON生成。这是prepareforSegue
// MARK: - Navigation
// In a storyboard-based application, you will often want to do a little preparation before navigation
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
// Get the new view controller using segue.destinationViewController.
var divisionScene = segue.destinationViewController as! DivisionViewController
// Pass the selected object to the new view controller.
if let indexPath = tableView.indexPathForSelectedRow() {
let arrayIndex = indexPath.row
//println("Index: (arrayIndex)")
torneoIDTransfer = torneos[arrayIndex].torneoID
//println("(torneoIDTransfer)")
//check second url with second request type same token
//sets url to string using token
let tercerURL = NSURL(string: "http://api.zione.mx/get.json.asp?tr=3&tkn=(tkn)&tor=(torneoIDTransfer)")
//initializes request
let request = NSURLRequest(URL: tercerURL!)
NSURLConnection.sendAsynchronousRequest(request, queue: NSOperationQueue.currentQueue()) { response, jsonDataRequest3, error in
let dataRequest3 = jsonDataRequest3
//takes data, saves it as json
let tercerJSON = JSON(data: jsonDataRequest3)
//checks to see that contents != nil, meaning the JSON file was found
if tercerJSON != nil {
//checks amount of tournaments available in order to generate table.
let divisionCount = tercerJSON["lista-divisiones"].count
//sets global variable numero de torneos
numeroDeDivisiones = divisionCount
//for loop to go insert into Torneo nuevo each ID and name by using count from above
for var index = 0; index < divisionCount; ++index {
var divisionID = Int(tercerJSON["lista-divisiones" ][index]["DivisionID"].number!)
var nomDivision = tercerJSON["lista-divisiones"][index]["nomDivision"].string
//println("(divisionID)")
//println("(nomDivision)")
var divisionNuevo = listaDivisiones(divisionID: divisionID, nomDivision: nomDivision!)
divisiones.append(divisionNuevo)
numeroDeDivisiones = 10
print("WHO IS FIRST")
}
}
print("(divisiones[0].nomDivision)")
}
}
}
我通过从表格单元格拖动到新的视图控制器来创建segway。但是,当我单击表格单元格时,在请求有机会完成之前,转换立即发生,因此没有显示任何数据。
最好在用户选择表行之前就在后台获取和处理数据。如果这是不可能的,那么我建议让你的目标视图控制器做URL请求。URL请求是异步发生的,所以在你的源视图控制器被释放之前,它永远不会有机会完成。
在源视图控制器中,修改prepareForSegue
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
var divisionScene = segue.destinationViewController as! DivisionViewController
if let indexPath = tableView.indexPathForSelectedRow() {
let arrayIndex = indexPath.row
torneoIDTransfer = torneos[arrayIndex].torneoID
let tercerURL = NSURL(string: "http://api.zione.mx/get.json.asp?tr=3&tkn=(tkn)&tor=(torneoIDTransfer)")
divisionScene.fetchDataAtURL(tercerURL)
}
}
你需要在目标视图控制器中定义一个方法来处理抓取。
func fetchDataAtURL(URL: NSURL) {
let request = NSURLRequest(URL: tercerURL!)
NSURLConnection.sendAsynchronousRequest( // ... your fetching logic here
}
您还需要一些逻辑来在数据到达时显示数据。我建议将其放入请求的完成回调中(或者更确切地说,让回调触发显示更新)。如果你的divisionScene
是一个tableView,你可以调用reloadData
(在你更新数据源之后)。如果没有,您将需要其他方式来更新UI。如果您正在更新UI,请确保dispatch
到该部分的主队列。
这样做至少将URL加载责任传递给目标视图控制器,当数据最终到达那里时,它至少会存在。
"转换立即发生,在请求有机会完成之前"。
当然有,这正是异步的意思。你特意提到它是异步的,但你一定对它的含义有误解。解释一下你认为这意味着什么,以及你希望你的代码是什么,这样你就可以更好地接受我们的教育。
当你调用sendAsynchronousRequest()时,把你的程序想象成两个分支(实际上这就是有效发生的事情)。一部分是你的原始代码它会继续执行也就是说你的prepareFoSegue代码会继续执行。同时,操作系统将并行地执行请求,当请求完成时,传递给sendAsynchronousRequest()的块中的代码将被执行。因此,您的prepareForSeque()函数将在收到Json之前完成。
但除此之外,你不应该尝试或希望或希望JSon在segue转换之前被获取-这样做会中断你的ui。假设sendAsynchronousRequest()而不是sendSynchronousRequest(),它花了10秒来完成,你认为你的应用程序运行时的后果是什么?您应该在GUI准备好显示数据之前很长时间获取数据,或者如果不可能,立即显示没有数据的GUI,然后在数据到达时更新它。