进行第二次 Json 调用 Swift 3 后如何在 UITableview 中重新加载数据
Posted
技术标签:
【中文标题】进行第二次 Json 调用 Swift 3 后如何在 UITableview 中重新加载数据【英文标题】:How to reload data in UITableview after making second Json call Swift 3 【发布时间】:2017-05-31 05:08:15 【问题描述】:我正在发出 JSON 请求,如果它已完成,那么我将带有 JSON 数据的页面导航到我的表格视图控制器,一切正常,但是当我第二次调用加载更多单元格时,我无法重新加载数据,这里是我正在第二次调用我的表视图控制器的代码。
var listData:[String] = []
var videoIDData:[String] = []
var valueKeyData:[String] = []
var nextPageToken:String?
var titleNamee:[String] = []
var videoIDD :[String] = []
var valueKeyy :[String] = []
var PrevPageToken:String?
@IBOutlet weak var tableView: UITableView!
override func viewDidLoad()
super.viewDidLoad()
tableView.delegate = self
tableView.dataSource = self
override func didReceiveMemoryWarning()
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int
return listData.count
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell
let cell = tableView.dequeueReusableCell(withIdentifier: "VideoCell", for: indexPath) as! VideoTableViewCell
cell.videoTitle.text = listData[indexPath.row]
let url = NSURL(string: valueKeyData[indexPath.row])
let dataaa = NSData(contentsOf: url! as URL)
let image = UIImage(data: dataaa! as Data)
cell.videoThumnailImageView.image = image
if (indexPath.row == listData.count - 1)
makeGetCall()
return cell
func makeGetCall()
// Set up the URL request
var pageToken:String = (pageToken)
let todoEndpoint: String = "https://www.googleapis.com/youtube/v3/playlistItems?part=snippet&maxResults=50\(pageToken)&playlistId=\(id)_ItOZ8WBF5_SI_SrSN3_F&\(key)"
guard let url = URL(string: todoEndpoint) else
print("Error: cannot create URL")
return
let urlRequest = URLRequest(url: url)
// set up the session
let config = URLSessionConfiguration.default
let session = URLSession(configuration: config)
// make the request
let task = session.dataTask(with: urlRequest)
(data, response, error) in
// check for any errors
guard error == nil else
print("error calling GET on /todos/1")
print(error)
return
guard let responseData = data else
print("Error: did not receive data")
return
// parse the result as JSON, since that's what the API provides
do
guard let jsonObject = try JSONSerialization.jsonObject(with: responseData, options: []) as? [String : AnyObject] else
print("error trying to convert data to JSON")
return
self.PrevPageToken = jsonObject["prevPageToken"] as? String
self.nextPageToken = jsonObject["nextPageToken"] as? String
if let itemsArray = jsonObject["items"] as? [[String:AnyObject]]
for snippetArray in itemsArray
if var snippet = snippetArray["snippet"] as? [String : AnyObject]
if let titleItems = snippet["title"] as? String
self.titleNamee += [titleItems]
if let thumbnail = snippet["thumbnails"] as? [String : AnyObject]
if let highValue = thumbnail["high"] as? [String : AnyObject]
if let urlValueKey = highValue ["url"] as? String
self.valueKeyy += [urlValueKey]
if let resource = snippet["resourceId"] as? [String : AnyObject]
if let videoId = resource["videoId"] as? String
// self.videoIDD.append(videoId)
self.videoIDD += [videoId]
catch
print("error trying to convert data to JSON")
return
task.resume()
DispatchQueue.main.async
self.tableView.reloadData()
【问题讨论】:
您必须尝试使用Model Class
代替Multiple Array
所有要在表格视图中传递的内容,在获得second JSON
之后,您必须调用表格重新加载代码在main dispatch
内,因为该块是异步的,这就是为什么无法执行Table reload
。
我已经创建了 NSObject 自定义类,但我不知道如何在这个方法中使用这个类..任何帮助请...???
【参考方案1】:
您在错误的位置重新加载tableView
,您需要在for loop
之后的完成块内重新加载它,因为完成块将调用异步,因此请删除您当前的tableView
重新加载代码并将其放在for 循环之后。
for snippetArray in itemsArray
if var snippet = snippetArray["snippet"] as? [String : AnyObject]
if let titleItems = snippet["title"] as? String
self.titleNamee += [titleItems]
if let thumbnail = snippet["thumbnails"] as? [String : AnyObject]
if let highValue = thumbnail["high"] as? [String : AnyObject]
if let urlValueKey = highValue ["url"] as? String
self.valueKeyy += [urlValueKey]
if let resource = snippet["resourceId"] as? [String : AnyObject]
if let videoId = resource["videoId"] as? String
// self.videoIDD.append(videoId)
self.videoIDD += [videoId]
//Reload your table here
DispatchQueue.main.async
self.tableView.reloadData()
注意:您需要做的是创建一个具有所有这些属性的自定义类或结构,并创建该自定义类或结构对象的数组,而不是创建当前正在执行的多个数组。
编辑:我没有看到你在cellForRowAt
中调用这个方法,不要这样做,因为单元格将被重用,这就是你 UI 卡住的原因,所以删除从cellForRowAt
调用代码,如果你想做类似分页的东西,你可以像这样使用scrollViewDelegate
方法。
func scrollViewDidScroll(_ scrollView: UIScrollView)
if((scrollView.contentOffset.y + scrollView.frame.size.height) == scrollView.contentSize.height)
self.makeGetCall()
另外,在发出 API 请求时显示一些进程指示器会更好。
【讨论】:
感谢您的回复...我尝试过这种方式,但仍然没有重新加载数据..它总是卡在最后一个单元格上....但是当我打印每个数组时显示数据... @User786 卡住是什么意思,是应用程序崩溃了吗?如果它在cellForRowAt
崩溃,其中一个用于您使用 indexPath.row 为数组下标的行,那么您的所有数组都没有相等的对象
不,它没有崩溃......当我向上滚动时它卡住了,它的调用函数 makeGetCall() 再次 n ......当我调试函数在所有数组中平均解析数据时。 .. 但不重新加载单元格。
是的...感谢您的帮助n回复...它正在工作n在表格视图上重新加载数据但唯一的问题是卡住n然后重新加载数据...但至少它的工作...
@User786 欢迎朋友 :)以上是关于进行第二次 Json 调用 Swift 3 后如何在 UITableview 中重新加载数据的主要内容,如果未能解决你的问题,请参考以下文章
Swift UIViewController tableView.reloadData nil 在第二次调用时包装
Swift 5 - 用户第二次单击标签栏按钮后,需要帮助在视图控制器 1 上重新加载 Web 视图
Swift - 第二次加载后 Tableview 无法正确重新加载