uitableview - TableView 单元格重用和不需要的复选标记 - 这让我很伤心

标签 uitableview reusability checkmark

苹果iOS TableView和细胞重用正在杀死我。我搜索、搜索和研究,但找不到好的文档或好的答案。问题是当TableView重用单元格 在选定单元格上设置的复选标记(单元格附件)等内容在表格 View 中更下方的单元格中重复。我知道由于内存限制,单元重用是设计使然,但是如果您有一个包含 50 个项目的列表,并且它开始在不需要的地方设置额外的复选标记,这将使整个努力变得毫无用处。

我想要做的就是在我选择的单元格上设置一个复选标记。我已经尝试过使用我自己的自定义单元格类和由样板 TableView 类生成的标准单元格,但它总是以相同的方式结束。

Apple 甚至有一个名为 TouchCell 的示例项目,您可以从开发中心下载,它应该显示使用左侧带有图像控件的自定义单元格设置复选标记的不同方式。该项目使用字典对象作为数据源而不是可变数组,因此对于每个项目都有一个字符串值和 bool 检查值。这个 bool 选中的值应该设置复选标记,以便它可以跟踪所选项目。一旦您使用 15 个以上的单元格填充 TableView,此示例项目也会显示这种愚蠢的行为。单元格的重用开始设置不需要的复选标记。

我什至尝试过为每个单元格使用真正独特的单元格标识符。因此,不是每个单元格都有类似 @"Acell"的东西,我使用了一个静态整数,转换为一个字符串,这样单元格就得到了 @"cell1"、@"cell2"等。不过在测试过程中,我可以看到数百个新单元格在哪里在滚动期间生成,即使表格只有 30 个项目。

它确实解决了复选标记重复问题,但我怀疑内存使用率太高了。

就好像当前不在表格可视区域中的单元格在滚动回 View 时会重新创建。

有没有人想出一个优雅的解决方案来解决这种恼人的行为?

最佳答案

细胞重用可能很棘手,但您必须记住两件事:

  • 使用 一个标识符 类型 单元格 - 只有当您在一个表 View 中使用不同的 UITableViewCell 子类时才需要使用多个标识符,并且您必须依赖它们对不同单元格的不同行为
  • 您重用的单元格可以在 任何状态 ,这意味着您必须再次配置单元格的各个方面 - 特别是 checkmars/图像/文本/附件 View /附件类型等等

  • 您需要做的是为您的复选标记状态创建一个存储 - 一个包含 bool 的简单数组(或分别包含 bool NSNumber 对象的 NSArray )应该这样做。然后,当您必须创建/重用单元格时,请使用以下逻辑:
    -(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
        static NSString *reuseIdentifier = @"MyCellType";
        UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:reuseIdentifier];
        if(cell == nil) {
            /* create cell here */
        }
        // Configure cell now
        cell.textLabel.text = @"Cell text"; // load from datasource
        if([[stateArray objectAtIndex:indexPath.row] boolValue]) {
            cell.accessoryType = UITableViewCellAccessoryCheckmark;
        } else {
            cell.accessoryType = UITableViewCellAccessoryNone;
        }
        return cell;
    }
    

    那么你将不得不对水龙头使用react:
    - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
    {
        [stateArray replaceObjectAtIndex:indexPath.row withObject:[NSNumber numberWithBool:![[stateArray objectAtIndex:indexPath.row] boolValue]]];
        [tableView reloadRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade];
    }
    

    只要记住使用 NSMutableArray用于您的数据存储 ;)

    关于uitableview - TableView 单元格重用和不需要的复选标记 - 这让我很伤心,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6315269/

    相关文章:

    iphone - 在 UImage 中显示渲染的图标

    ios - 表格 View 中重复复选标记

    swift - 如何更改 UITableViewCellAccessoryType.Checkmark 的颜色?

    objective-c - 在编辑模式下将 UISearchBar 与 UITableView 一起使用时,搜索结果不处于编辑模式

    ios - TableView 未使用新单元格更新

    reactjs - 如何在 react-app 中重用自定义 Material-ui 按钮?

    forms - Joomla:如何使用一种表单进行前端和后端 View ?

    objective-c - 单元格 accessorytype 不会在 [tableview reloadData] 上重新加载

    ios - swift ; scrollView 搭配 tableView 可行吗?

    android - 如何创建可重用的对话框 fragment ?