一尘不染

在将异步图像加载到UITableViewCell后滚动时,Swift Images更改为错误图像

swift

我试图异步加载我的FriendsTableView(UITableView)单元内的图片。图像加载正常,但是当我滚动表格时,图像将更改几次,并且错误的图像被分配给错误的单元格。

我尝试了所有可以在StackOverflow中找到的方法,包括将标签添加到原始文件,然后检查它,但是那没有用。我还在验证应使用indexPath更新的单元,并检查该单元是否存在。所以我不知道为什么会这样。

这是我的代码:

    func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCellWithIdentifier("friendCell", forIndexPath: indexPath) as! FriendTableViewCell
        var avatar_url: NSURL
        let friend = sortedFriends[indexPath.row]

        //Style the cell image to be round
        cell.friendAvatar.layer.cornerRadius = 36
        cell.friendAvatar.layer.masksToBounds = true

        //Load friend photo asyncronisly
        avatar_url = NSURL(string: String(friend["friend_photo_url"]))!
        if avatar_url != "" {
                getDataFromUrl(avatar_url) { (data, response, error)  in
                    dispatch_async(dispatch_get_main_queue()) { () -> Void in
                        guard let data = data where error == nil else { return }
                        let thisCell = tableView.cellForRowAtIndexPath(indexPath)
                        if (thisCell) != nil {
                            let updateCell =  thisCell as! FriendTableViewCell
                            updateCell.friendAvatar.image = UIImage(data: data)
                        }
                    }
                }
        }
        cell.friendNameLabel.text = friend["friend_name"].string
        cell.friendHealthPoints.text = String(friend["friend_health_points"])
        return cell
    }

阅读 215

收藏
2020-07-07

共1个答案

一尘不染

这是因为UITableView重用了单元格。以这种方式加载它们会导致异步请求在不同的时间返回并弄乱顺序。

我建议您使用一些类似于Kingfisher的图书馆,这将使您的生活更轻松。它将为您下载和缓存图像。同样,您也不必担心异步调用。

https://github.com/onevcat/Kingfisher

您的代码如下所示:

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCellWithIdentifier("friendCell", forIndexPath: indexPath) as! FriendTableViewCell
        var avatar_url: NSURL
        let friend = sortedFriends[indexPath.row]

        //Style the cell image to be round
        cell.friendAvatar.layer.cornerRadius = 36
        cell.friendAvatar.layer.masksToBounds = true

        //Load friend photo asyncronisly
        avatar_url = NSURL(string: String(friend["friend_photo_url"]))!
        if avatar_url != "" {
            cell.friendAvatar.kf_setImageWithURL(avatar_url)
        }
        cell.friendNameLabel.text = friend["friend_name"].string
        cell.friendHealthPoints.text = String(friend["friend_health_points"])
        return cell
    }
2020-07-07