Swift Can';无法获取标头中单元格的indexPath

Swift Can';无法获取标头中单元格的indexPath,swift,uitableview,Swift,Uitableview,我已经为一个带有按钮的tableView创建了原型自定义标题单元格。我试图在点击按钮时获取单元格的索引,但没有收到。知道我做错了什么吗 protocol MediaHeaderCellDelegate: class { func editPost(cell: MediaHeaderCell) } class MediaHeaderCell: UITableViewCell { weak var delegate: MediaHeaderCellDelegate? @I

我已经为一个带有按钮的tableView创建了原型自定义标题单元格。我试图在点击按钮时获取单元格的索引,但没有收到。知道我做错了什么吗

 protocol MediaHeaderCellDelegate: class {
  func editPost(cell: MediaHeaderCell)
}

  class MediaHeaderCell: UITableViewCell {

   weak var delegate: MediaHeaderCellDelegate?
    @IBAction func moreOptionsAction(_ sender: UIButton) {
     delegate?.editPost(cell: self)
   }
}


      class NewsfeedTableViewController:UITableViewController,  MediaHeaderCellDelegate {

  func editPost(cell: MediaHeaderCell) {
        guard let indexPath = tableView.indexPath(for: cell) else {
        print("indexpath could not be given")
        return}
   }

  override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView?
{
    let cell = tableView.dequeueReusableCell(withIdentifier: Storyboard.mediaHeaderCell) as! MediaHeaderCell
    cell.delegate = self
    cell.media = media[section]
    return cell
   }

         override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell
{
    let cell = tableView.dequeueReusableCell(withIdentifier: Storyboard.mediaCell, for: indexPath) as! MediaTableViewCell

    cell.currentUser = currentUser
    cell.media = media[indexPath.section]
    cell.delegate = self        
    return cell
     }

}

当前的问题是,您正在使用表格单元格作为节标题视图。不应该这样做。解决该问题后,下一个任务是从点击其按钮的标题视图中确定表部分

首先,将您的
MediaHeaderCell
更改为扩展
UITableViewHeaderFooterView
的标题视图,并相应地更新您的协议:

protocol MediaHeaderViewDelegate: class {
    func editPost(view: MediaHeaderView)
}

class MediaHeaderView: UITableViewHeaderFooterView {
    weak var delegate: MediaHeaderViewDelegate?

    @IBAction func moreOptionsAction(_ sender: UIButton) {
        delegate?.editPost(cell: self)
    }
}
然后需要在视图控制器中注册标题视图

然后更新标题部分的
视图

override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
    let view = tableView.dequeueReusableHeaderFooterView(withIdentifier: Storyboard.mediaHeaderView) as! MediaHeaderView
    view.delegate = self
    view.media = media[section]
    view.tag = section

    return view
}
最后,更新协议方法实现:

func editPost(view: MediaHeaderView) {
    let section = view.tag
    // do something
}

这可能有一个问题。如果您的表允许添加或删除节,则点击按钮时标题视图的标记可能会出错。

因此,这实际上是了解节标题属于哪个节的全部内容??我就是这么做的。我有一个标题类:

class MyHeaderView : UITableViewHeaderFooterView {
    var section = 0
}
我注册它:

self.tableView.register(
        MyHeaderView.self, forHeaderFooterViewReuseIdentifier: self.headerID) 
我使用并配置它:

override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
    let h = tableView
        .dequeueReusableHeaderFooterView(withIdentifier: self.headerID) as! MyHeaderView
    // other stuff 
    h.section = section // *
    return h
}

现在,如果header视图是可点击的,或者包含一个按钮或其他内容,那么了解这是标题的哪个部分就很简单了

当你点击单元格中的按钮时会发生什么?是否调用单元格的
moreOptionAction
?是否在视图控制器中调用了
editPost
?是的,调用了
moreoptionAction
editPost
,但在
editPost(cell:MediaHeaderCell)
else语句中进行了计算。您为什么不使用
cellForRowAtIndexPath:(nsindepath*)indepath(而不是
查看标题部分
)?这就是问题所在。不要将表格单元格用于节标题。使用
UITableViewHeaderFooterView
。不要在
cellForRowAt
之外调用
dequeueReusableCell
。用户有可能删除帖子,因此标记可能会导致意外行为。@bibscy但那将是一行,而不是整个部分。
dequeueReusableHeaderFooterView返回值的文档状态(标识符:)
:“如果可重用视图队列中不存在此类对象,则为零。”。这个过时了吗?因为您没有测试nil…这与使用header视图的标记的潜在问题相同,如我的回答所示。使用
标记
或您自己的
属性基本上是一样的。@rmaddy当然,苹果公司的愚蠢之处在于忽略了这一关键功能。是的,
UITableView
需要一个
节(对于headerFooterView:)
方法,类似于
indexPath(对于cell:)
@rmaddy