我正在swift 3.0中的一个项目中醒来,在该项目中,我使用NSCache将服务器的响应缓存在UITableView中,从而缓存了这些响应。但是由于某种原因,当我第一次加载该应用程序时,我只会看到很少的图像加载,但是如果我滚动并返回时,我会看到所有内容(从服务器检索响应结束时,我也重新加载了tableview,但是似乎并非如此)。我不确定我到底在这里缺少什么,下面的代码展示了我如何缓存图像。
let imageCache = NSCache<AnyObject, AnyObject>() var imageURLString : String? extension UIImageView { public func imageFromServerURL(urlString: String) { imageURLString = urlString if let url = URL(string: urlString) { image = nil if let imageFromCache = imageCache.object(forKey: urlString as AnyObject) as? UIImage { self.image = imageFromCache return } URLSession.shared.dataTask(with: url, completionHandler: { (data, response, error) in if error != nil{ print(error as Any) return } DispatchQueue.main.async(execute: { if let imgaeToCache = UIImage(data: data!){ if imageURLString == urlString { self.image = imgaeToCache } imageCache.setObject(imgaeToCache, forKey: urlString as AnyObject)// calls when scrolling } }) }) .resume() } } }
在这里下载图像并将其存储在缓存中就可以了。问题在于更新tableview单元格。
当表格视图将单元格加载到表格上时,图像尚未下载。但是,一旦下载了图像,我们就必须有选择地更新单元格,以便立即显示图像。
由于正在滚动,因此表视图再次调用“ cellForRowatIndexpath”,这将更新滚动时显示已下载图像的单元格。
如果您仍然希望使用扩展名,建议您添加tableView和indexpath作为参数,以便我们可以调用重新加载特定行并立即更新视图。
我已经更新了表重载代码和扩展中定义的函数的结构。让我知道事情的后续。
let imageCache = NSCache<AnyObject, AnyObject>() var imageURLString : String? extension UIImageView { public func imageFromServerURL(urlString: String, tableView : UITableView, indexpath : IndexPath)) { imageURLString = urlString if let url = URL(string: urlString) { image = nil if let imageFromCache = imageCache.object(forKey: urlString as AnyObject) as? UIImage { self.image = imageFromCache return } URLSession.shared.dataTask(with: url, completionHandler: { (data, response, error) in if error != nil{ print(error as Any) return } DispatchQueue.main.async(execute: { if let imgaeToCache = UIImage(data: data!){ if imageURLString == urlString { self.image = imgaeToCache } imageCache.setObject(imgaeToCache, forKey: urlString as AnyObject)// calls when scrolling tableView.reloadRows(at: [indexpath], with: .automatic) } }) }) .resume() } }