繁体   English   中英

在 UITableView 中只重新加载一个部分标题

[英]Reload only one section header in UITableView

我在UITableView使用自定义单元格作为节标题。 在那个单元格中有三个按钮。 如果在该部分的单元格中单击任何按钮,则应仅重新加载该自定义部分单元格,而不是任何行。 这可能吗?

我使用以下代码重新加载该单元格:

tableViewHome.reloadSections([1], with: UITableViewRowAnimation.none)

它隐藏了我的部分单元格并扭曲了我的整个表格。

更新

我正在使用UITableView和我正在使用的以下代码:

func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {

        let cellHeader = tableViewHome.dequeueReusableCell(withIdentifier: "header") as! HeaderTableViewCell

        cellHeader.filter1btn.addTarget(self, action: #selector(filterBtnAction(_:)), for: .touchUpInside)
        cellHeader.filter2Btn.addTarget(self, action: #selector(filterBtnAction(_:)), for: .touchUpInside)
        cellHeader.filter3btn.addTarget(self, action: #selector(filterBtnAction(_:)), for: .touchUpInside)


        return cellHeader
    }


    @IBAction func filterBtnAction(_ sender: UIButton) {

        print(sender.tag)

        tableViewHome.reloadSections([1], with: UITableViewRowAnimation.none)



    }

我有点不清楚这里发生了什么,但听起来有一个UITableView概念值得在这里解释:

UITableView有自己的单元格概念,实现为UITableViewCell ,还有自己的页眉/页脚概念,实现为UITableViewHeaderFooterView

根据您的意思是这两者中的哪一个,您可以采取一些措施来获得预期的效果:

UITableViewCell方法:

如果您使用UITableViewCell作为部分的第一行以充当“标题”,并且您只想重新加载该行以排除该部分的其余部分,则可以调用yourTableViewInstance.reloadRows(at:with:) (Apple 文档)此方法采用IndexPath数组和动画样式。 您可以传入要重新加载的索引路径。

UITableViewHeaderFooterView方法:

如果您使用的是正确的UITableViewHeaderFooterView那么您需要确保在重新加载该部分时提供适当的视图。 Zack Shapiro概述了您在此答案中需要采取的步骤:

  1. 创建一个类,它是UITableViewHeaderFooterView的子类。
  2. 将它注册到您的UITableView实例。
  3. 然后在viewForHeaderInSection ,你let header = tableView.dequeueReusableHeaderFooterView(withIdentifier: "HeaderView") as! YourHeaderViewSubclass let header = tableView.dequeueReusableHeaderFooterView(withIdentifier: "HeaderView") as! YourHeaderViewSubclass

他指出的最后一件事是:

具有欺骗性的是函数调用返回UIView? 当它真的需要dequeuedReusableHeaderFooterViewreloadData会导致它消失。

这取决于您采用这两种实现路径中的哪一种,但这应该足以为您指明正确的方向。

编辑:

根据您添加的代码,它看起来像你打电话yourTableViewInstance.dequeueReusableCell(withIdentifier:for:)而不是yourTableViewInstance.dequeueReusableHeaderFooterView(withIdentifier:)viewForHeaderInSection

您需要有一个UITableViewHeaderFooterView的子类,然后正确调用它。 创建新的子类,然后更改:

func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {

        let cellHeader = tableViewHome.dequeueReusableCell(withIdentifier: "header") as! HeaderTableViewCell

   // ...

对此:

func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {

        let cellHeader = tableViewHome.dequeueReusableHeaderFooterView(withIdentifier: "header") as! HeaderTableView

   // ...

您需要在此处执行两个步骤:

  1. 创建一个新类, UITableViewHeaderFooterView而不是UITableViewCell
  2. 然后使用上面概述的适当的类。

是的。

假设这是您的方法的实现:

func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
    let customCell = .... as! YourCustomCell 
    customCell.someLabel.text = "Some Data"
    //... filling your curstom cell
    return customCell
}

你可以用这种方式改变它

func updateHeaderView(headerView:YourCustomCell, section: Int) {
    customCell.someLabel.text = "Some Data"
    //... filling your curstom cell  
}

func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
    let customCell = .... as! YourCustomCell 
    self.updateHeaderView(customCell, section)
    return customCell
}

并在需要时再次调用self.updateHeaderView(customCell, section) ,例如

func buttonClicked() {
   let customCell = self.tableView.headerView(forSection: 0) as! YourCustomCell
   self.updateHeaderView(customCell, 0)
}

我认为您的标题视图类正在扩展 UITableViewHeaderFooterView 类。 在扩展中添加功能

extension UITableViewHeaderFooterView{
     func reloadHeaderCell(){
        preconditionFailure("This method must be overridden")
    }
}

现在在您的 Header 类中覆盖它,如下所示

class HeaderView: UITableViewHeaderFooterView {
   override func reloadHeaderCell() {
      ////// add your logic to reload view
    }
}

现在你可以简单地调用下面的行来刷新视图

self.tableView?.headerView(forSection:0)?.reloadHeaderCell()

我所做的并且工作得非常正确,请按照给定的答案进行操作:

斯威夫特 3.1

第 1 步:

首先,我view xib,根据我的要求设计了它,并在我要求的课程中注册了。

其次,做了子类class HeaderView: UITableViewHeaderFooterViewUITableViewHeaderFooterView

像下图:

在此处输入图片说明

在我需要的课程(这里是家庭课程)中,我确实为我的 tableview 注册了我的xib文件。

override func viewDidLoad() {
        super.viewDidLoad()
        tableViewHome.register(UINib(nibName: "HeaderView", bundle: nil), forHeaderFooterViewReuseIdentifier: "HeaderView")
}

第 2 步:

然后在我要求的课程中,我做了以下事情:

func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {

        let cellHeader = tableViewHome.dequeueReusableHeaderFooterView(withIdentifier: "HeaderView") as! HeaderView
        cellHeader.filterAction(cellHeader.filter1Btn)


        return cellHeader
    }

它开始按照我的要求工作,后来我在我的班级中添加了自定义委托以进行更多操作,但是通过子查看,它现在可以工作了。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM