Home > Net >  How to Load TableView Cells in Batches
How to Load TableView Cells in Batches

Time:10-02

I am looking for a way to smoothen my tableview. Since I have cells that need to download images from the URL, loading tableview cells one by one is very slow and makes the tableview lag. Moreover, the tableview will reload every time when I go back to previous cells. So I hope I could load the cells in batches of 15 with animation while loading. Any ideas of how I can do this? Any help is appreciated.

PS: Is my download function appropriate? Is there any other faster or better download function?

My code:

func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return posts.count
    }
    

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        
    let post = posts[indexPath.row] // "post" are the firebase documents

    if post.posttype == 1{
        let cell = tableView.dequeueReusableCell(withIdentifier: TextPostCell.identifier, for: indexPath) as! TextPostCell
        cell.titleText.text = post.title
        cell.contentLable.text = post.content
        cell.userPhoto.downloadImage(from: post.userphoto, placeHolder: UIImage(named: "notfound")!)
        cell.username.text = post.sender
        return cell
            
    }else{
        let cell = tableView.dequeueReusableCell(withIdentifier: ImageTextPostCell.identifier, for: indexPath) as! ImageTextPostCell
        cell.titleText.text = post.title
        cell.photoImage.downloadImage(from: post.photo![0], placeHolder: UIImage(named: "notfound")!)
        print("success")
        cell.userphoto.downloadImage(from: post.userphoto, placeHolder: UIImage(named: "notfound")!)
        cell.username.text = post.sender
        return cell
    }
}
    
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
    // tableview selected
}

extension UIImageView{
    func downloadImage(from url: String?, placeHolder placeholder: UIImage) {
        print("Download Started")
        if let safeString = url{
            if let safeURL = URL(string: safeString){
                getData(from: safeURL) { data, response, error in
                    if error != nil{
                        print("Tony's Notes: Problem retrieving data")
                        print(error!)
                        self.image = placeholder
                    }
                    // always update the UI from the main thread
                    DispatchQueue.main.async() { [weak self] in
                        if let safeData = data{
                            self?.image = UIImage(data: safeData)
                            return
                        }
                    }
                }
            }else{
                self.image = placeholder
            }
        }else{
            self.image = placeholder
        }
    }
    
    func getData(from url: URL, completion: @escaping (Data?, URLResponse?, Error?) -> ()) {
        URLSession.shared.dataTask(with: url, completionHandler: completion).resume()
    }
}
  

CodePudding user response:

You may be looking for preloading: prefetch rows, and precancel rows.

https://developer.apple.com/documentation/uikit/uitableviewdatasourceprefetching

  • Related