【问题标题】:Issue dequeuing UICollectionViewCell问题出队 UICollectionViewCell
【发布时间】:2015-05-07 21:56:53
【问题描述】:
我有一个 UICollectionView,我用 NSFetchedResultsControllerDelegate 填充。数据偶尔到达。我已经实现了一种插入/更新/删除/等的方法。带有 FetchedResultsController 委托回调的 collectionView 中的项目。这就是上下文。我的问题是我的自定义 UICollectionViewCell 中有一个 UIButton ,具有特定的操作和目标。因此,当 collectionview 使单元格出列时,我注意到几个单元格具有相同的 UIButton 引用。这不酷。例如,当我点击一个按钮时,就像我点击了 3 个不同单元格的按钮一样。由于出队系统,这些单元实际上是同一个单元(意味着它们具有相同的内存引用)。是否有一个系统可以为我的每个单元格提供唯一的参考。我要问的是如何绕过出队系统?
【问题讨论】:
标签:
ios
uitableview
swift
uicollectionview
uicollectionviewcell
【解决方案1】:
您想要做的是用其单元格的索引路径标记每个按钮,而不是“绕过出队系统”。您仍然希望使用可重复使用的按钮创建可重复使用的单元格,但是当您将cellForRowAtIndexPath 中的单元格出列时,将该按钮(或任何UIView)的tag 属性设置为该单元格的indexPath。
cell.someButton.tag = indexPath.row
然后当您使用该按钮作为发件人调用函数时,您可以访问该标签:
@IBAction func someButtonPressed(sender: UIButton) {
let index = sender.tag
// Do something unique to that cell with that tag
}
注意:UIView 的tag 属性是一个Int,所以如果你需要整个索引路径,这在使用获取结果控制器时非常有用,你可以继承UIButton 并给它一个您可以在其中存储索引路径的属性,并以相同的方式设置和检索它。
【解决方案2】:
我猜你在-collectionView:cellForItemAtIndexPath: 中设置了按钮的目标和操作。在您的自定义单元格中,您可以覆盖 -prepareForReuse 并从您的按钮中删除所有目标和操作。
或者,我使用的一种方法是使自定义单元格成为按钮目标,并使用委托回调将此操作公开给您的数据源,因此:
- 按下按钮
- 在单元格上调用操作方法
- Cell 通知其代理它应该做某事
这解决了您的问题,因为单元格只有一个委托,而不是您看到的多个目标操作。它还有一个额外的优点是让您将 UIButton 保持为单元格私有,因此,如果您希望将来将该按钮更改为带有手势识别器的视图,您可以只更新单元格的实现并保持其界面不变。
在第二种方法中,在-prepareForReuse 中将单元格的委托设置为nil 仍然是一种很好的做法。