这让我在一天中的大部分时间都疯了。
我有一个带UIImageViews的UITableView。这些图像视图在tableview的cellForRow函数中加载了一个本地保存的PNG文件,这个工作正常,但是当一个带有图像的单元格滚动到视线中时,tableview将停止滚动几分之一秒。我已经搜索了StackOverflow并谷歌寻求答案,但我已经做了简短 - 所以任何帮助将不胜感激。
这是我的CellForRow函数代码:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"MyIdentifier"];
if (cell == nil) {
cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:@"MyIdentifier"] autorelease];
cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
}
if([currSection isEqualToString:@"composer"]){
MySlide *s = [slidesArray objectAtIndex:indexPath.row];
cell.textLabel.hidden = YES;
UIImageView *whiteView = [[UIImageView alloc] initWithFrame:CGRectMake((projectsTable.frame.size.width/2)-150, 4, 204.8, 153.6)];
if([s.slideImage isEqualToString:@""] || s.slideImage == nil){
//no custom image in this cell - go with default background image
whiteView.image = [UIImage imageNamed:@"cellback2.png"];
whiteView.backgroundColor = [UIColor whiteColor];
}else{
cell.layer.shouldRasterize = YES;
cell.layer.rasterizationScale = [UIScreen mainScreen].scale;
NSData *data = [[NSData alloc] initWithContentsOfFile:s.slideImage];
UIImage *im = [[UIImage alloc] initWithData:data];
whiteView.image = im;
whiteView.image = [self imageWithImage:whiteView.image CovertToSize:CGSizeMake(204.8,153.6)];
whiteView.backgroundColor = [UIColor whiteColor];
}
[cell.contentView addSubview:whiteView];
[whiteView release];
cell.accessoryType = UITableViewCellAccessoryNone;
}
return cell;
}
答案 0 :(得分:6)
要进行一些更改,首先应在生成单元格时添加UIImageView
,而不是每次都tableView:cellForRowAtIndexPath:
被点击(如@Vishy建议的那样)。其次,您应该从文档目录中缓存正在加载的图像([UIImage imageNamed:]
自动为包资源执行此操作。)
@interface MyViewController () {
NSMutableDictionary *_imageCache;
}
@end
@implementation MyViewController
- (void)viewDidLoad {
[super viewDidLoad];
// other viewDidLoad stuff...
_imageCache = [[NSMutableDictionary alloc] init];
}
- (void)viewDidUnload {
[super viewDidUnload];
// other viewDidUnload stuff...
[_imageCache release];
_imageCache = nil;
}
- (void)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"MyIdentifier"];
if (cell == nil) {
cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:@"MyIdentifier"] autorelease];
cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
UIImageView *whiteView = [[UIImageView alloc] initWithFrame:CGRectMake((projectsTable.frame.size.width/2)-150, 4, 204.8, 153.6)];
whiteView.tag = 111;
whiteView.backgroundColor = [UIColor whiteColor];
[cell.contentView addSubview:whiteView];
[whiteView release];
cell.accessoryType = UITableViewCellAccessoryNone;
cell.textLabel.hidden = YES;
}
UIImageView* iView = (UIImageView*) [cell.contentView viewWithTag:111];
if([currSection isEqualToString:@"composer"]) {
MySlide *s = [slidesArray objectAtIndex:indexPath.row];
if([s.slideImage isEqualToString:@""] || s.slideImage == nil) {
//no custom image in this cell - go with default background image
iView.image = [UIImage imageNamed:@"cellback2.png"];
}
else {
cell.layer.shouldRasterize = YES;
cell.layer.rasterizationScale = [UIScreen mainScreen].scale;
// use the image path as the cache key
UIImage *theImage = [_imageCache objectForKey:s.slideImage];
if (theImage == nil) {
// load the image and save into the cache
theImage = [UIImage imageWithContentsOfFile:s.slideImage];
theImage = [self imageWithImage:theImage CovertToSize:CGSizeMake(204.8, 153.6)];
[_imageCache setObject:theImage forKey:s.slideImage];
}
iView.image = theImage;
}
}
}
@end
作为一般规则,tableView:cellForRowAtIndexPath:
是您需要摆脱快速的方法,因此应尽可能避免从磁盘加载图片。
答案 1 :(得分:0)
按以下方式更改代码......
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"MyIdentifier"];
if (cell == nil)
{
cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:@"MyIdentifier"] autorelease];
cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
UIImageView *whiteView = [[UIImageView alloc] initWithFrame:CGRectMake((projectsTable.frame.size.width/2)-150, 4, 204.8, 153.6)];
whiteView.tag = 111;
whiteView.backgroundColor = [UIColor whiteColor];
[cell.contentView addSubview:whiteView];
[whiteView release];
cell.accessoryType = UITableViewCellAccessoryNone;
cell.textLabel.hidden = YES;
}
UIImageView* iView = (UIImageView*) [cell.contentView viewWithTag:111];
if([currSection isEqualToString:@"composer"])
{
MySlide *s = [slidesArray objectAtIndex:indexPath.row];
if([s.slideImage isEqualToString:@""] || s.slideImage == nil)
{
//no custom image in this cell - go with default background image
iView.image = [UIImage imageNamed:@"cellback2.png"];
}
else
{
cell.layer.shouldRasterize = YES;
cell.layer.rasterizationScale = [UIScreen mainScreen].scale;
iView.image = [UIImage imageWithContentsOfFile:s.slideImage];
iView.image = [self imageWithImage:iView.image CovertToSize:CGSizeMake(204.8,153.6)];
}
}
}
答案 2 :(得分:0)
第一次显示每个UIImage时也会有延迟。有关在缓存时提示工作而不是显示时间的详细信息,请参阅此帖: