【问题标题】:How do I pass button action from a nested collectionView cell?如何从嵌套的 collectionView 单元格传递按钮操作?
【发布时间】:2018-02-14 08:34:36
【问题描述】:

我有一个 MainCollectionView 用于在项目之间滚动,在其中一个单元格内我有另一个带有单元格的 collectionView。在该集合视图中,每个单元格都有一个按钮。我的问题是如何在点击按钮时将操作从按钮传递到 MainCollectionView?我确实为单元格中的那个按钮创建了协议,但我不知道如何让 MainCollectionView 知道我的按钮何时被点击。我可以从我的单元格类中调用操作,但我认为最好在我的 MainCollectionView 模型中运行它。下面是我的按钮协议。

protocol ThanhCaHotTracksCellDelegate: class {
func handleSeeAllPressed()}

weak var delegate: ThanhCaHotTracksCellDelegate?


@objc func handleSeeAllButton(){
 delegate?.handleSeeAllPressed()
}

【问题讨论】:

  • 您可以使用UIButtonaddTarget(_ target: Any?, action: Selector, for controlEvents: UIControlEvents) 方法为该按钮的特定事件添加目标/动作

标签: ios swift uicollectionview


【解决方案1】:

就像 NSAdi 所说,您走在正确的轨道上,但委托模式对于通知按钮按下这样的单个任务来说开销有点大。

我更喜欢使用闭包,因为它们是轻量级的并且有助于将相关代码保持在一起。

使用闭包

这就是我在UITableView 一直在做的事情。所以这也适用于UICollectionView

class MyTableViewCell: UITableViewCell {
    var myButtonTapAction: ((MyTableViewCell) -> Void)?

    @IBAction func myButtonTapped(_ sender: Any) {
        myButtonTapAction?(self)
    }
}

因此,当我将单元格出列并将其转换为 MyTableViewCell 时,我可以设置如下自定义操作:

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "myCellReuseIdentifier", for: indexPath) as! MyTableViewCell

    cell.myButtonTapAction = { cell in
        // Put your button action here
        // With cell you have a strong reference to your cell, in case you need it
    }
}

使用直接引用

当您将 UICollectionView 单元格出列时,您可以通过将单元格转换为单元格的自定义子类来获取对按钮的引用。

然后只需执行以下操作

cell.button.addTarget(self, action: #selector(didTapButton(_:)), forControlEvents: .TouchUpInside)

和外面有一个功能:

@objc func didTapButton(_ sender: UIButton) {
    // Handle button tap
}

这样做的缺点是您无法直接访问您的单元格。你可以使用button.superview?,但这不是一个好主意,因为你的视图层次结构可能会改变......

【讨论】:

  • 感谢您的评论。我不能使用您的建议,因为我的 MainCollectionView 没有设置具有按钮的单元格。正如我在帖子中提到的,我的子 collectionView 负责这部分。无论如何,现在,我只是使用协议将操作传递给我的子 CollectionView,然后从它传递给 MainCollectionView。
  • 对不起,我读你的问题太快了^^。但是你也可以像你的委托一样多次传递你的闭包......
  • @fl034 现在,我已经多次实施了 Closure 解决方案,甚至使用一个按钮(实际上是一个 tvOS TVPosterView - 仍然是一个 UIControl)创建了一个新的集合视图,占据了整个单元格,而 IBAction 从来没有永远被调用。在设置委托后,我要捕捉按下按钮的唯一方法是通过“collectionView(_collectionView:UICollectionView,didSelectItemAt indexPath:IndexPath)”。我错过了什么??
  • @MicheleDall'Agata 你应该发布一个新问题,因为这可能是一个完全不同的问题。添加更多关于如何构建 UI 的详细信息...
  • @fl034 没关系,我终于解决了! 4天后..这是tvOS焦点的问题,单元格被聚焦所以UIControl无法获得动作。我修复了它,描述了我的问题中的解决方案。
【解决方案2】:

你在正确的轨道上。

确保 MainCollectionView(或包含的类)实现了ThanhCaHotTracksCellDelegate 协议。

然后将delegate 分配为self

类似...

class ViewController: ThanhCaHotTracksCellDelegate {
    override func viewDidLoad() {
        super.viewDidLoad()

        subCollectionView.delegate = self
    }
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-02-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-02
    相关资源
    最近更新 更多