ios - TableView :dequeueReusableCellWithIdentifier issues with "global" constant

标签 ios objective-c xcode uitableview

请留住我的头发,或指出我的(明显的)错误。我正在尝试在子类化的 UITableViewController 中使用 UITableViewCellStyleSubtitle 的 UITableViewStyle。

我在实现中定义了一个静态常量:

static NSString * const kAHCellIdentifier;

viewDidLoad 中,我注册了一个 tableView 类:

[self.tableView registerClass:[UITableViewCell class] forCellReuseIdentifier:kAHCellIdentifier];

然后在 tableView:cellForRowAtIndexPath 中,我按如下方式初始化单元格:

UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:kAHCellIdentifier];
if (cell == nil) {
    cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:kAHCellIdentifier];
}

当运行应用程序(设备或 sim)时,单元格加载但 detailTextLabel 不显示,但是如果我这样初始化,它可以正常工作*

我的猜测是常量实际上不是静态的,或者存在错误 (8.0.2),或者由于 sleep 不足或其他原因我完全遗漏了某些东西。

还可以注意到,如果我不注册该类,则会出现编译器错误(预期),但即使单元格标识符不同也没有错误(我猜这是预期的,因为我可以为不同的注册不同的类单元格样式。

我错过了什么?

编辑

使用 [tableView dequeueReusableCellWithIdentifier:kAHCellIdentifier forIndexPath:indexPath]; 也没有效果。

较短的问题

如果我在 cellForRowAtIndexPath 中使用静态 NSString,为什么 dequeueReusableCellWithIdentifier 返回 nil 并因此在 cell == nil block 中使用 UITableViewCellStyle 启动单元格 方法调用,而不是,如果我使用上面定义的类级全局常量。

额外的

更多的测试产生了一些不同的结果。如果您为单元格重用标识符注册一个类,然后在 cellForRowAtIndexPath 中为单元格指定一个不同的标识符,那么它就可以工作。如果您为它指定与注册类相同的名称,则它不会按预期工作。

回答

经过一些测试和@MANIAK_dobrii 的回答,一些清晰度。

如果您想使用较新的单元格出队方法 dequeueReusableCellWithIdentifier:forIndexPath 并且需要使用除默认值之外的 UITableViewCellStyle,您需要子类化 UITableViewCell 并在 initWithStyle 方法调用中覆盖 tableview 样式。

如果您乐于使用旧方法,请确保您没有为重用标识符注册一个类,否则它将无法工作。

最佳答案

这很有趣,因为我刚刚在文档中找到了一个新段落,用于 dequeueReusableCellWithIdentifier: 我上次看那里时没看到:

If you registered a class for the specified identifier and a new cell must be created, this method initializes the cell by calling its initWithStyle:reuseIdentifier: method. For nib-based cells, this method loads the cell object from the provided nib file. If an existing cell was available for reuse, this method calls the cell’s prepareForReuse method instead.

这是否意味着如果您注册一个类,甚至 dequeueReusableCellWithIdentifier: 将尝试创建单元格(如果它在重用队列中不可用)并且始终返回有效单元格?由于 -dequeueReusableCellWithIdentifier:forIndexPath: 可用,我只使用它。所以,我猜你的

if (cell == nil) {
    cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier];
}

永远不会被调用,你最终会得到通过

创建的单元格
[[registred_class alloc] initWithStyle:STANDARD_STYLE reuseIdentifier:registred_reuse_identifier];

与此同时,您已经声明,如果您不注册类(class),您会得到编译时错误,这很奇怪,您不应该得到任何错误。

所以,我的解决方案是或者:
1. 不要通过 -registerClass:forCellReuseIdentifier: 注册单元类,而是使用 -dequeueReusableCellWithIdentifier: 来获取重复使用的单元或像现在一样创建它们。同样,使用老派方法,你不注册任何东西,如果有就出队,如果没有就创建。

// I've put it here just for a clarification that that's doesn't matter for the case
static NSString *const cellID = @"CellID";
// Just this, do not register anything, cell should get the same id as you ask
// i.e. you should init cell with the same id you then try to dequeue
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellID];
    if(!cell)
    {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:cellID];
    }

    cell.textLabel.text = @"Title";
    cell.detailTextLabel.text = @"subtitle";

    return cell;
}

或者:
2. 创建 nib,将 UITableViewCell 放在那里,使其样式为 UITableViewCellStyleSubtitle 并将该 nib 注册为重用标识符,而不是使用 registerNib:forCellReuseIdentifier: 的类。

此外,请确保您正确设置了所有标题/颜色/透明度,这样您就不会只将空字符串或 nil 设置为单元格上的标签。

关于ios - TableView :dequeueReusableCellWithIdentifier issues with "global" constant,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26463023/

相关文章:

objective-c - NSUserDefaultsDidChangeNotification : What's the name Of the Key, 已更改?

ios - Xcode 错误 : NSURLSession/NSURLConnection HTTP load failed (kCFStreamErrorDomainSSL, -9814)

objective-c - 从 NSArray 中的 NSNumber 获取整数值

ios - Swift SQLite I/O 错误

ios - NSXMLParser 的错误处理

xcode - 如何为 Mac OS X 10.5 编译

ios - native 动画模块不可用 - react native

ios - PubNub 本地消息重复?

objective-c - 为什么我不能在类别中使用@synthesize 访问器?

xcode - 设置 Xcode 以使用外部编译器