我是Swift的新手。我想在我的tableview中显示图像。我正在关注这个tutorial。
在我的UITableView
中,如tutorial所示。我将图像存储在缓存中。如果tableview只有一个部分,这可以正常工作。如果我的tableview中有多个部分,我应该如何设置forKey
值?
如何根据部分和行设置此值self.cache.setObject(image!, forKey:indexPath.row)
?谢谢!!
这是我UITableView
func numberOfSectionsInTableView(tableView: UITableView) -> Int
{
if(tableView == tableview){
return categoryArray.count
}else{
return 1
}
}
func tableView(tableView : UITableView, titleForHeaderInSection section: Int)->String
{
if(tableView == tableview){
return categoryArray.objectAtIndex(section) as! String
}else{
return ""
}
}
func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int
{
if(tableView == tableview){
print("Count = \(myList[section].count)")
return myList[section].count
}
else{
return 5
}
}
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell
{
if(tableView == tableview) {
let cell = tableView.dequeueReusableCellWithIdentifier("cell", forIndexPath: indexPath) as! CustomEventCell
cell.cellBackgroundImg.image = UIImage(named: "placeholder")
if (self.cache.objectForKey(indexPath.row) != nil){
print("Cached image used, no need to download it")
cell.cellBackgroundImg?.image = self.cache.objectForKey(indexPath.row) as? UIImage
}else{
let img_url = myList[indexPath.section].objectAtIndex(indexPath.row).objectForKey("image") as? String
if img_url != nil{
print("Load the image from URL")
let url = NSURL(string: img_url!)!
let request = NSMutableURLRequest(URL:url)
let defaultSession = NSURLSession(configuration: NSURLSessionConfiguration.defaultSessionConfiguration())
let task = defaultSession.dataTaskWithRequest(request, completionHandler: {(data:NSData?, response:NSURLResponse?, error: NSError?) in
dispatch_async(dispatch_get_main_queue(), { () -> Void in
let image = UIImage(data: data!)
cell.cellBackgroundImg?.image = image
self.cache.setObject(image!, forKey:indexPath.row)
})
})
task.resume()
}
}
return cell
}
}
答案 0 :(得分:1)
本教程的作者似乎在选择使用indexPath.row
作为缓存的关键时犯了一个错误。行号与图像的链接非常脆弱;识别图像的是它的URL。通过使用该行,会出现以下问题:
您可以轻松修改cellForRowAtIndexPath
以将URL用作缓存键:
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell
{
var cell = UITableViewCell()
if(tableView == tableview) {
let customCell = tableView.dequeueReusableCellWithIdentifier("cell", forIndexPath: indexPath) as! CustomEventCell
customCell.cellBackgroundImg.image = UIImage(named: "placeholder")
if let img_url = myList[indexPath.section].objectAtIndex(indexPath.row).objectForKey("image") as? String {
if let image = self.cache.objectForKey(img_url) as? UIImage {
print("Cached image used, no need to download it")
cell.cellBackgroundImg?.image = image
} else {
print("Load the image from URL")
if let url = NSURL(string: img_url)
let request = NSMutableURLRequest(URL:url)
let defaultSession = NSURLSession(configuration: NSURLSessionConfiguration.defaultSessionConfiguration())
let task = defaultSession.dataTaskWithRequest(request, completionHandler: {(data:NSData?, response:NSURLResponse?, error: NSError?) in
guard let downloadData= data && error == nil else {
print("error downloading image:\(error)"
return
}
dispatch_async(dispatch_get_main_queue(), { () -> Void in
if let image = UIImage(data: data) {
customCell.cellBackgroundImg?.image = image
self.cache.setObject(image, forKey:img_url)
}
})
})
task.resume()
}
}
}
cell = customCell
}
return cell
}
你的代码也不是很防守。如果数据不正确,有很多强制解包会给你一个例外
答案 1 :(得分:0)
问题是您使用UITableView
引用缓存所有图片,但如果您的self.cache.setObject(image!, forKey:"\(indexPath.section)-\(indexPath.row")))
self.cache.objectForKey(indexPath.row)
有多个部分,则会有重复的行值。例如:
第0节&gt;第0行,第1行,第2行 <第1节>第0行,第1行 <第2节>第0行
所有部分都有&#34;第0行和第34行。
要修复它,你必须这样做:
1)创建格式化的键,例如&#34; SECTION-ROW&#34;,例如:
my_app_name
的库
答案 2 :(得分:0)
您也可以使用tag
。这是使用标记值的代码。您也可能需要考虑代码中的错误处理。
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell
{
var cell = UITableViewCell()
if(tableView == tableview) {
let customCell = tableView.dequeueReusableCellWithIdentifier("cell", forIndexPath: indexPath) as! CustomEventCell
customCell.eventTitle.text = title
customCell.cellBackgroundImg.image = UIImage(named: "placeholder")
// calculate tagValue and set it to cache objectForKey
// here I have taken big numbers so same number will not repeat
let tagValue = (indexPath.section * 100) + indexPath.row + 200
if (self.cache.objectForKey(tagValue) != nil){
print("Cached image used, no need to download it")
customCell.cellBackgroundImg?.image = self.cache.objectForKey(tagValue) as? UIImage
}else{
let img_url = myList[indexPath.section].objectAtIndex(indexPath.row).objectForKey("image") as? String
if img_url != nil{
print("Load the image from URL")
let url = NSURL(string: img_url!)!
let request = NSMutableURLRequest(URL:url)
let defaultSession = NSURLSession(configuration: NSURLSessionConfiguration.defaultSessionConfiguration())
let task = defaultSession.dataTaskWithRequest(request, completionHandler: {(data:NSData?, response:NSURLResponse?, error: NSError?) in
if error != nil {
print(error)
return
}else if(data != nil){
dispatch_async(dispatch_get_main_queue(), { () -> Void in
let image = UIImage(data: data!)
customCell.cellBackgroundImg?.image = image
self.cache.setObject(image!, forKey:tagValue)
})
}else {
print("Error : Image data is nil")
}
})
task.resume()
}
else {
print("Error : Image URL is nil")
}
}
cell = customCell
}
return cell
}