ios - 使用 reloaddata 时,UITableViewCell 未从 UITableView 中移除

标签 ios swift uitableview

我正在使用表格 View 在左侧菜单中显示一些类别。选择它时,单元格中的数据会更改为该类别中的类(class)(“Cursussen”)。

每个单元格都包含一个 UIImageView 和一个 UILabel

我刚才注意到,当您在左侧菜单中选择类(class)时,标签将变为类别标签。那时候这不是什么大问题,但现在我正在努力禁用某些类(class),如果它们不可用,它突然变成了一个大问题。为了指示不可用的类(class),我设置了 label.enabled = false,它工作正常,但我还需要防止用户点击它并导航到不可用的类(class)。为此,我使用 tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) 检查是否启用了 UILabel。如果它被禁用,应用程序将不会导航到类(class)。

回到问题上来,点击一个不可用的类(class)(显示正确的图像和标签)将触发 didSelectRowAtIndexPath 委托(delegate),但是当我出列 Cell 并检查其中的 UILabel 是否被禁用,所以它恰好被启用,而且 label.text 不等于我在应用程序中看到的值。

选择行前的状态: unselected

选中一行后的状态: selected

cellForRowAtIndexPath 方法:

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath)
    -> UITableViewCell {
        let cell = tableView.dequeueReusableCellWithIdentifier("LeftCell", forIndexPath: indexPath)
        let label = cell.contentView.subviews[0] as! UILabel
        let image = cell.contentView.subviews[1] as! UIImageView
        if(selectedCategory.ID > 0 || searchCursusses.count > 0) {
            //Category is selected, load course into cell
            var cursus : Cursus
            if(selectedCategory.ID > 0) {
                cursus = cursusses[indexPath.row] as Cursus
            } else {
                cursus = searchCursusses[indexPath.row] as Cursus
            }
            image.image = self.chooseImage(false, name: cursus.category!.Name)
            label.numberOfLines = 0
            label.text = cursus.name
            label.lineBreakMode = .ByTruncatingTail
            if(defaults.boolForKey("offline-mode")) {
                let realm = try! Realm()
                let videos = realm.objects(DownloadedVideo).filter("video.cursus.ID = %@", cursus.ID)
                if(videos.count > 0) {
                    label.enabled = true
                } else {
                    label.enabled = false
                }
            } else {
                label.textColor = UIColor.blackColor()
            }
            cell.backgroundColor = UIColor(red: 1.0, green: 1.0, blue: 1.0, alpha: 1.0)
            cell.setSelected(false, animated: false)
        } else {
            let category = categories[indexPath.row] as Category
            image.image = self.chooseImage(false, name: category.Name)
            label.numberOfLines = 0
            label.text = category.Name
            label.lineBreakMode = .ByTruncatingTail
            label.textColor = UIColor.blackColor()
            cell.backgroundColor = UIColor(red: 1.0, green: 1.0, blue: 1.0, alpha: 1.0)
        }
        return cell
}

didSelectRowAtIndexPath 方法:

func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
    let cell = tableView.dequeueReusableCellWithIdentifier( "LeftCell", forIndexPath: indexPath)
    cell.selectionStyle = .None
    if(selectedCategory.ID > 0 || searchCursusses.count > 0) {
        let label = cell.contentView.subviews[0] as! UILabel
        if(!label.enabled) {
            return
        }
        let storyBoard : UIStoryboard = UIStoryboard(name: "Main", bundle:nil)
        let resultViewController = storyBoard.instantiateViewControllerWithIdentifier("CursusView") as! CursusViewController
        if(selectedCategory.ID > 0) {
            resultViewController.loadCursus(self.cursusses[indexPath.row], completionHandler: {
                self.presentViewController(resultViewController, animated:true, completion:nil)
            })
        } else {
            resultViewController.loadCursus(self.searchCursusses[indexPath.row], completionHandler: {
                self.presentViewController(resultViewController, animated:true, completion:nil)
            })
        }
    } else {
        let category = categories[indexPath.row] as Category
        cell.setSelected(true, animated: false)
        let label = cell.contentView.subviews[0] as! UILabel
        let image = cell.contentView.subviews[1] as! UIImageView
        if(label.textColor == UIColor.lightGrayColor()) {
            return
        } else {
            image.image = self.chooseImage(true, name: category.Name)
            label.numberOfLines = 0
            label.text = category.Name
            label.textColor = UIColor.whiteColor()
            label.lineBreakMode = .ByTruncatingTail
            cell.backgroundColor = UIColor(red: 45.0/255.0, green: 145.0/255.0, blue: 220.0/255.0, alpha: 1.0)
            self.selectedCategory = category
            self.topBarTitle.text = category.Name
            let realm = try! Realm()
            let cursusses = realm.objects(Cursus).filter("category.ID = %@", selectedCategory.ID)
            for cursus in cursusses {
                self.cursusses.append(cursus)
            }
            let title = self.leftMenuNav.subviews[0] as! UILabel
            let titleImg = self.leftMenuNav.subviews[1] as! UIImageView
            titleImg.image = UIImage(named: "back-icon")
            title.text = "Cursussen"
            dispatch_async(dispatch_get_main_queue(), { () -> Void in
                self.tableView.slideInFromRight(0.5)
                self.tableView.reloadData()
                self.collectionView.crossFade(0.3)
                self.collectionView.reloadData()
            })
        }
    }
}

似乎在调用reloaddata 后旧单元格没有正确清理,导致多个单元格在同一个 IndexPath。

我在这里不知所措,请帮忙!

最佳答案

问题是线路

let cell = tableView.dequeueReusableCellWithIdentifier( "LeftCell", forIndexPath: indexPath)

didSelectRowAtIndexPath 函数中,因为它正在创建一个新单元格(或尝试重用一个单元格)并破坏 TableView 单元格缓存。

您应该使用 cellForRowAtIndexPath 函数获取现有单元格。

关于ios - 使用 reloaddata 时,UITableViewCell 未从 UITableView 中移除,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35558419/

相关文章:

swift - 将 CoreData 从 UITableViewCell 传递到 View Controller

ios - 如何使用 realm swift 检索另一个对象列表中的对象?

ios - UISearchBar 未在 ios 8 的 UIStatusBar 下扩展其背景颜色

ios - CIGaussianBlur 处理过多

swift - 核心数据+本地化

ios - 分块解析 XML 文件,无需等待 Swift 中的完整下载

ios - NSArray objectAtIndex : shorthand

ios - 如何检查 AVPlayer 中的音频 channel 数?

ios - tableView imageView 内容模式不起作用?

ios - 如何从另一种方法访问tableviewCell中的文本字段