tableView在iOS中是最长使用的控件了,但在对于其中具体的代理以及数据源的调用顺序相信好多人并不太清楚。刚好最近工作中遇到一个由于不熟悉其中的加载机制造成了一个很奇葩的BUG,于是顺便研究了一下其中的设置行高和设置每行内容的两个代理方法的调用
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath; // 设置行高
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath; // 设置每行的内容
先说说我遇到的奇葩bug:
由于我的cell的高度是自适应的,我把高度存在了一个字典中,用indexPath做key值,而这个高度只有在设置每行内容的时候才能计算出来,所以设置行高这个方法在开始的时候取到的一直没有值,此时问题就出现了,就算后来开始加载的时候,设置每行内容这个方法不是从indexPath.row == 0 开始,而是从下标为1的时候开始的。
问题解决:只需在设置行高的时候没有值时(准确说是当值为0时),默认设置一个大于0的数就可以了。
问题解决很简单,但是这其中具体是怎么加载的呢?
1.当tableView在确定了加载的行数之后,会循环调用设置行高的方法,即有多少行调用多少次。假如此时行高一个都没有设置(即设置行高的方法一直返回的0),此时设置行内容的方法就出现问题了,它不再是从indexPath{0-0}开始了,而是从总行数的一半开始(奇数行的话就是从行数加1除以2开始,偶数行从除以2开始)。
2.然后系统开始一行行的调用方法
先调用一次设置行高的方法,然后调用设置行内容的方法,然后又调用设置行高度的方法。
具体只涉及了这两个方法,可能相对比较简单,后续可能还会有相关的研究,当然也欢迎感兴趣的一起讨论。也欢迎大神给予指导。