如何在解码后恢复UICollectionViewCell中的绑定

时间:2016-01-12 22:18:21

标签: ios encoding uicollectionview uicollectionviewcell reuseidentifier

我有一个UICollectionViewCell的子类。在故事板中可视化地设计单元格,其中包含许多组件,这些组件使用故事板绑定到Swift子类中的变量。

Swift类只提供用于从数据源检索的数据中填充组件的逻辑。

例如:

class InfoCollectionViewCell : UICollectionViewCell {

    @IBOutlet weak var mainPanel : UIView!
    @IBOutlet weak var panel1 : UIView!

    @IBOutlet weak var firstName : UILabel!
    @IBOutlet weak var lastName : UILabel!
    @IBOutlet weak var address : UILabel!
    etc ...

    func setVariousProperties(etc) {
        firstName.text = ... etc

数据源通常会这样做:

let cell = collectionView.dequeueReusableCellWithReuseIdentifier("InfoCell", forIndexPath:indexPath)
if let c : InfoCollectionViewCell = cell as? InfoCollectionViewCell {
    c.setVariousProperties(...)
}

我最初只实现了包含“未实现”断言的解码/编码方法,但很明显,框架偶尔会对类进行编码和解码。我实现了虚拟编码/解码方法而没有保存组件,导致在访问组件时出现nil值的可预测问题。

所以看来我需要逐个实现UICollectionViewCell子类中所有控件的编码和解码,或者我必须找到更好的方法。

这似乎是浪费时间,因为我实际上并不需要(我不认为)保存组件的内容,因为它们只是为了子类的重复使用:我将覆盖组件内容将来自数据源。

显然,所有控件都在故事板中定义。我可以通过init方法中的故事板手动从名称中获取它们,但这看起来同样繁琐,并使控件和变量的图形链接变得多余。

有更好的方法吗?

我可以直接说“恢复连接”或类似内容吗?

修改

在发布问题和添加赏金之间的某个地方,问题就不复存在了。我现在注意到我的组件的编码方法没有被调用。因此,由于某种原因,框架决定序列化我的对象并对它们进行反序列化,但现在却没有。因此问题没有发生,我无法提供堆栈跟踪。

可以想象,对XCode的一些更新已经解决了这个问题,或者它可能是其他问题。

我显然仍然担心某处潜伏着某些错误。

1 个答案:

答案 0 :(得分:2)

您不需要为故事板中已布局和连接的任何控件实现编码/解码。这将在运行时处理,只要其他所有内容都已准备好与正在使用的UI组件连接,您将在collectionView.dequeueReusableCellWithReuseIdentifier之后获得一个单元格。要检查的事项是:

  1. 子类在故事板自定义类部分
  2. 中指定
  3. 使用reuseIdentifier来匹配您期望的字符串
  4. 所有IBOutlet都已连接,并且还应在IBOutlet var lines旁边的代码中显示连接。
  5. 一旦确定这些是正确的,请尝试打印出组件以检查它们是否仍为零并在其中放置一些简单的文本以消除任何dataSource问题:

      func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
        let cell = collectionView.dequeueReusableCellWithReuseIdentifier("InfoCell", forIndexPath:indexPath)
        if let c = cell as? InfoCollectionViewCell{
          print(c.address)
          print(c.firstName)
          print(c.lastName)
    
          c.firstName.text = "firstName Test"
          c.lastName.text = "lastName Test"
          c.address.text = "address Test"
        }
        return cell
      }
    }