3

我使用具有相对“重”的自定义表格视图单元格的表格视图 - 比如说单个单元格中有大约 100 个子视图(完整层次结构)。尽管如此,我已经能够实现非常平滑的滚动 - 使用标准做法,例如仅使用不透明视图、隐藏未使用的子视图(甚至从视图层次结构中删除)、预加载单元格高度等。

问题是创建单个单元实例仍然相对昂贵。由于标准 UITableView 的单元重用逻辑是如何工作的,这个问题只在特定条件下才明显。

通常在加载表格视图(并显示初始内容)时,它会创建几乎所有必需的单元格实例 - 因此,当您开始滚动时,它很少需要创建更多可重用的单元格。但是,如果由于某种原因它只在开始时显示几个单元格,那么在启动滚动时显然需要创建更多单元格。在我的情况下,如果有一个宽表视图标题或者如果第一个单元格足够大,这很明显。当您开始滚动时发生这种情况时,会有片刻的明显滞后,这显然是由创建新单元格实例引起的。没有什么丑陋但仍然引人注目,尤其是与之后的绝对平滑滚动相比。

现在,显而易见的解决方案是让单元格“更轻”——比如将它们分成不同的更具体的类型,这样每个单元格就可以包含更少的子视图。但是由于我的内容的组织方式,这将是一个非常复杂的解决方案。

所以我的问题是——有没有什么好的方法可以“欺骗”表格视图逻辑来强制加载和缓存特定数量的可重用单元格实例——尽管实际可见的单元格数量是多少?

我一直在考虑的选项之一是拥有自己的显式单元缓存,并在需要时用单元预填充它(比如在 -viewDidLoad 中)。这种方法的问题是你必须事先知道你需要的确切类型的细胞——对我来说效果不佳。改进将是在加载初始数据时构建缓存(因此至少知道内容的确切类型),但我一直想知道是否有任何简单的选项。

4

2 回答 2

3

您可以通过将自己的“二级缓存”层添加到数据源来实现。

初始化数据源时,根据需要预先创建尽可能多的单元格,并将它们放入数组中。当你dequeueReusableCellWithIdentifier失败时,先去那个数组,然后从那里取一个单元格。一旦数组用完,就开始创建新的单元格(如果您预先创建了足够多的单元格,则不需要即时创建新的单元格:当您有足够多的单元格旋转进出可见性时,出队最终将停止失败)。

于 2012-06-06T17:12:35.117 回答
0

我也有类似的情况,我想在不同的单元格中加载几个网站,并且 loadrequest 必须只触发一次。想法是在通过向上或向下滚动使单元格可见/不可见时避免重复调用。假设我的表格视图中有 5 个单元格,每个单元格都有一个加载不同网站的 web 视图。loadrequest 将被调用一次,单元格将被缓存。这是最简单的实现。

变量声明

let weblinks:[String] = ["http://www.google.com",
                         "http://www.facebook.com",
                         "http://www.yahoo.com",
                         "http://www.puthiyathalaimurai.com/",
                         "http://www.github.com"]
var mycells:[MyTableViewCell] = [MyTableViewCell(),
                                 MyTableViewCell(),
                                 MyTableViewCell(),
                                 MyTableViewCell(),
                                 MyTableViewCell()]

细胞换行。我希望你知道它的作用,

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cellIdentifier = String(describing: MyTableViewCell.self)

    let cell = tableView.dequeueReusableCell(withIdentifier: cellIdentifier) as? MyTableViewCell
    if cell?.isNewCell == true { //return from cache
        return mycells[indexPath.row]
    }
    cell?.title.text = weblinks[indexPath.row].uppercased()
    cell?.web.loadRequest(URLRequest(url: URL(string: weblinks[indexPath.row])!))
    cell?.isNewCell = true //mark it for cache
    mycells[indexPath.row] = cell!
    return cell!
}
于 2018-05-17T03:00:00.957 回答