我目前正在尝试加载 Flickr 照片的 UITableView 列表(cs193p iOS 斯坦福大学,作业 5)。为了避免 UI 阻塞事件,我将每个单元格的缩略图下载推迟到不同的队列中(但确实将 UI 更新回主队列中)。此代码不会异步加载图像,但在单击 UITableViewCell 行后会添加缩略图。 (参见下面的屏幕截图)。知道我做错了什么吗?
PS:我已经查看了其他一些 stackoverflow 问题和 Apple 的 LazyTableImages 示例,但我仍然相信这是实现所需结果的最干净的方法。
Thanks!
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = @"Photo List Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
// Configure the cell
NSDictionary *photo = [self.photoList objectAtIndex:indexPath.row];
if (photo != nil) {
if ([[photo objectForKey:@"title"] length] > 0) {
cell.textLabel.text = [photo objectForKey:@"title"];
} else if ([[[photo objectForKey:@"description"] objectForKey:@"_content"] length] > 0) {
cell.textLabel.text = [[photo objectForKey:@"description"] objectForKey:@"_content"];
} else {
cell.textLabel.text = @"Unknown";
}
}
cell.imageView.image = [[UIImage alloc] initWithCIImage:nil];
// Fetch using GCD
dispatch_queue_t downloadThumbnailQueue = dispatch_queue_create("Get Photo Thumbnail", NULL);
dispatch_async(downloadThumbnailQueue, ^{
UIImage *image = [self getTopPlacePhotoThumbnail:photo];
dispatch_async(dispatch_get_main_queue(), ^{
if ([self.tableView.visibleCells containsObject:cell]) {
[cell.imageView setImage:image];
}
});
});
dispatch_release(downloadThumbnailQueue);
return cell;
}
Before clicking a row
After selecting the row
更新:对于那些感兴趣的人,这是我使用的最终代码:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = @"Photo List Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
// Configure the cell
NSDictionary *photo = [self.photoList objectAtIndex:indexPath.row];
if (photo != nil) {
if ([[photo objectForKey:@"title"] length] > 0) {
cell.textLabel.text = [photo objectForKey:@"title"];
} else if ([[[photo objectForKey:@"description"] objectForKey:@"_content"] length] > 0) {
cell.textLabel.text = [[photo objectForKey:@"description"] objectForKey:@"_content"];
} else {
cell.textLabel.text = @"Unknown";
}
}
cell.imageView.image = [[UIImage alloc] initWithCIImage:nil];
// Fetch using GCD
dispatch_queue_t downloadThumbnailQueue = dispatch_queue_create("Get Photo Thumbnail", NULL);
dispatch_async(downloadThumbnailQueue, ^{
UIImage *image = [self getTopPlacePhotoThumbnail:photo];
dispatch_async(dispatch_get_main_queue(), ^{
UITableViewCell *cellToUpdate = [self.tableView cellForRowAtIndexPath:indexPath]; // create a copy of the cell to avoid keeping a strong pointer to "cell" since that one may have been reused by the time the block is ready to update it.
if (cellToUpdate != nil) {
[cellToUpdate.imageView setImage:image];
[cellToUpdate setNeedsLayout];
}
});
});
dispatch_release(downloadThumbnailQueue);
return cell;
}
你应该打电话setNeedsLayout
设置缩略图后在单元格上。
来自苹果文档:
“当您想要调整视图子视图的布局时,请在应用程序的主线程上调用此方法。此方法会记录请求并立即返回。因为此方法不会强制立即更新,而是等待下一次更新周期,您可以使用它在更新任何视图之前使多个视图的布局无效。这种行为允许您将所有布局更新合并到一个更新周期,这通常更有利于性能。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)