我有一个带有自定义单元格的TableView,其中一些有图像,有些则没有。一切正常,但是当我开始滚动时,细胞显示不正确(图像被放置在“错误的”单元格中并在中间切割)。现在有人怎么解决这个问题?
答案 0 :(得分:4)
要理解的关键是你的桌子的细胞被重复使用。这样做是为了提高滚动性能,因为创建一个新单元 - 这是一个视图 - 非常昂贵。
在方法cellForRowAtIndexPath中,返回一个单元格。使用dequeue方法的现有单元格,或者您创建一个新单元格。在该单元格上,您可以设置您希望表示的任何属性。
我的猜测是你直接在单元格上设置图像等属性。然后滚动时,该单元格会被重复使用,您会再次看到相同的图像但是在错误的单元格上。
所以,你需要的是像NSArray这样的单独索引来维护你的模型对象。该模型对象包含图像的所有细节等。
我们举一个例子。我有一个包含10个对象的数组,前五个是图像“a.png”,第二个是“b.png”。
如果我收到cellForRowAtIndexPath的回调,我想按以下步骤操作:
cellForRowAtIndexPath:(0,0)从数组中提供索引0的对象,即a.png cellForRowAtIndexPath:(0,1)从数组中提供索引1的对象,即a.png cellForRowAtIndexPath:(0,2)从数组中提供索引2的对象,即a.png cellForRowAtIndexPath:(0,3)从数组中提供索引3的对象,即a.png cellForRowAtIndexPath:(0,4)从数组中提供索引4的对象,即a.png cellForRowAtIndexPath:(0,5)从数组中提供索引5的对象,即b.png cellForRowAtIndexPath:(0,6)从数组中提供索引6的对象,即b.png cellForRowAtIndexPath:(0,7)从数组提供索引7的对象,即b.png cellForRowAtIndexPath:(0,8)从数组中提供索引8的对象,即b.png cellForRowAtIndexPath:(0,9)从数组中提供索引9的对象,即b.png
现在,让我们考虑在UITableView中,在封面下,五个单元格正在被重用。
对于上面的每个电话,都会发生以下情况:
cellForRowAtIndexPath:(0,1)从数组中提供索引1的对象,即a.png - 您尝试将现有单元格出列但它返回“nil”,因此您创建了一个新单元格。您可以设置模型对象的详细信息。
cellForRowAtIndexPath:(0,2)从数组中提供索引2的对象,即a.png - 您尝试将现有单元格出列但它返回“nil”,因此您创建了一个新单元格。您可以设置模型对象的详细信息。
cellForRowAtIndexPath:(0,3)从数组中提供索引3的对象,即a.png - 您尝试将现有单元格出列但它返回“nil”,因此您创建了一个新单元格。您可以设置模型对象的详细信息。
cellForRowAtIndexPath:(0,4)从数组中提供索引4的对象,即a.png - 您尝试将现有单元格出列但它返回“nil”,因此您创建了一个新单元格。您可以设置模型对象的详细信息。
cellForRowAtIndexPath:(0,5)从数组中提供索引5的对象,即b.png - 你试图将现有的单元格出列并且它有效!您可以通过设置模型对象的详细信息再次使用该单元格
cellForRowAtIndexPath:(0,6)从数组中提供索引6的对象,即b.png - 你试图将现有的单元格出列并且它有效!您可以通过设置模型对象的详细信息再次使用该单元格
cellForRowAtIndexPath:(0,7)从数组中提供索引7的对象,即b.png - 你试图将现有的单元格出列并且它有效!您可以通过设置模型对象的详细信息再次使用该单元格
cellForRowAtIndexPath:(0,8)从数组中提供索引8的对象,即b.png - 你试图将现有的单元格出列并且它有效!您可以通过设置模型对象的详细信息再次使用该单元格
cellForRowAtIndexPath:(0,9)从数组中提供索引9的对象,即b.png - 你试图将现有的单元格出列并且它有效!您可以通过设置模型对象的详细信息再次使用该单元格
很抱歉这么冗长!我希望这有帮助。也许值得通过一个好的表视图教程。肯定会有很多人。
答案 1 :(得分:2)
尝试更改单元格的标识符值。
NSString* identifierStr = [NSString stringWithFormat:@"ident_%d",indexPath.row];
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:identifierStr];
答案 2 :(得分:0)
您可能在创建单元格实例时添加图像,而不是在表格视图要求单元格视图时添加图像。例如:
这是正确的方法。每次表格视图要求一个单元格时,我们都会设置图像。
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"ident"];
UIImageView *imageView;
if (cell == nil) {
cell = [UITableViewCell alloc] init ....];
imageView = [[UIIMageView alloc] init];
imageView.tag = 123;
[cell addSubview:imageView];
[imageView release];
} else {
imageView = [cell viewWithTag:123];
}
imageView.image = ...; // load image here
}
这是错误的方式。我们在创建单元格时设置图像。这将导致细胞在重复使用时出现错误的图像。
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"ident"];
if (cell == nil) {
cell = [UITableViewCell alloc] init ....];
UIImageView *imageView = [[UIIMageView alloc] init];
imageView.image = ...;
[cell addSubview:imageView];
[imageView release];
}
}