使用 SearchBar 时,复选标记与 TableView 中的错误行相关联

Posted

技术标签:

【中文标题】使用 SearchBar 时,复选标记与 TableView 中的错误行相关联【英文标题】:Checkmark's associated with wrong row in TableView when using SearchBar 【发布时间】:2018-04-25 15:42:30 【问题描述】:

我正在创建一个应用程序,当用户在 TableView 中搜索项目时,他们可以单击它,并且旁边会出现一个复选标记。但是,假设当我选择我搜索过的第一个项目并单击它然后删除我的搜索时,复选标记停留在第一行,但对于一个完全不同的对象,我开始搜索(见下图)。

When Searching

When not Searching

var searchingArray = [Symptoms]()
var filteredArray = [Symptoms]()

var selectedSymptoms = [Symptoms]()

var clicked = [String]()

var searchingUnderWay = false

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell 

    if let cell = searchingSymptomsTableView.dequeueReusableCell(withIdentifier: "ExtraSymptoms", for: indexPath) as? ExtraSymptomCell 

        let searchingArrays: Symptoms!

        if searchingUnderWay 

            searchingArrays = self.filteredArray[indexPath.row]


         else 

            searchingArrays = self.searchingArray[indexPath.row]

        

        cell.updateUI(symptomNames: searchingArrays)

        return cell

     else 

        return UITableViewCell()
    




  func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) 

    let selectedRow: Symptoms!

    let symptomName: String!

    let cell : UITableViewCell = tableView.cellForRow(at: indexPath)!

    if searchingUnderWay 

        selectedRow = filteredArray[indexPath.row]
        symptomName = filteredArray[indexPath.row].name as String

        if clicked.contains(symptomName) 

            cell.accessoryType = .none

            let indexNumber = clicked.index(of: symptomName)
            clicked.remove(at: indexNumber!)

            if let element = selectedSymptoms.index(where:  $0.name == selectedRow.name ) 

                selectedSymptoms.remove(at: element)
            

         else 

            clicked.append(symptomName)

            cell.accessoryType = .checkmark

            searchingSymptomsTableView.reloadData()

            selectedSymptoms.append(selectedRow)

        



     else 

        selectedRow = searchingArray[indexPath.row]
        symptomName = searchingArray[indexPath.row].name as String

        if clicked.contains(symptomName) 

            cell.accessoryType = .none

            let indexNumber = clicked.index(of: symptomName)
            clicked.remove(at: indexNumber!)

            if let element = selectedSymptoms.index(where:  $0.name == selectedRow.name ) 

                selectedSymptoms.remove(at: element)
            

         else 

            clicked.append(symptomName)

            cell.accessoryType = .checkmark

            searchingSymptomsTableView.reloadData()

            selectedSymptoms.append(selectedRow)

        


        print(clicked)
        print(selectedSymptoms)



    


我希望当您删除搜索时,我使用搜索栏搜索的项目仍被选中。

非常感谢

【问题讨论】:

【参考方案1】:

欢迎来到 TableViewController 逻辑。看起来很奇怪,但它工作正常) 您需要覆盖 ExtraSymptomCell 中的 prepareForReuse() 方法。并清除您的单元格包含的所有值,包括附件类型

override func prepareForReuse() 
    super.prepareForReuse()

    accessoryType = .none

在你的 tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath):

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell 
    if let cell = searchingSymptomsTableView.dequeueReusableCell(withIdentifier: "ExtraSymptoms", for: indexPath) as? ExtraSymptomCell 

        let symptomName: String!

        let searchingArrays: Symptoms!

        if searchingUnderWay 

            searchingArrays = self.filteredArray[indexPath.row]
            symptomName = filteredArray[indexPath.row].name as String

         else 

            searchingArrays = self.searchingArray[indexPath.row]
            symptomName = filteredArray[indexPath.row] as String
        

        cell.updateUI(symptomNames: searchingArrays)

        if clicked.contains(symptomName)  
            cell.accessoryType = .checkmark
         else 
            cell.accessoryType = .none
        

        return cell

     else 

        return UITableViewCell()
    

【讨论】:

非常感谢!!与其他“尝试”的答案相比,这非常有效! @Basil cell.updateUI - 是 ExtraSymptomCell 的一种方法。你在 UITableViewCell 中没有它。跳过【参考方案2】:

由于UITableViewCell 被重复使用,当您重新加载表格数据时,复选标记将出现在单元格中。

在 cellForRowAt 中将附件类型设置为 .none,以删除先前选中的单元格复选标记:

let cell : UITableViewCell = tableView.cellForRow(at: indexPath)!
cell.accessoryType = .none

这将从先前的搜索中删除检查。

【讨论】:

以上是关于使用 SearchBar 时,复选标记与 TableView 中的错误行相关联的主要内容,如果未能解决你的问题,请参考以下文章

如何以编程方式将标记 (UIControl) 添加到 UITextField 或 SearchBar?

tableView上的复选标记[重复]

滚动时 UITableView 复选标记消失

如何在加载了 JSON API 数据的 tableview 单元格中保存复选标记属性?

使用 Modal Segue 保留复选标记

滚动时重复 TableView 上的复选标记