我正在尝试实现iOS 6日历中的事件表。
我有500行(事件)的UITableView。当我开始滚动动画是顺利的。
但是在两百行开始后滞后。在原生iOS 6日历活动列表中,所有工作都顺利进行。
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
double begin = CFAbsoluteTimeGetCurrent();
if(!self.isNoResults)
{
NSString *cellIdentifier = [NSString stringWithFormat: @"Cell %i %i", indexPath.row, indexPath.section];
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
UIImageView *circleImgView;
NSString *startTimeStr;
NSDateFormatter *formatter;
UILabel *timeLbl;
UILabel *titleLbl;
UILabel *endsLbl;
UIImageView *eventTypeImgView;
if(cell == nil)
{
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier];
circleImgView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"newMesIcon.png"]];
circleImgView.frame = CGRectMake(14, 19, 12, 12);
[cell.contentView addSubview:circleImgView];
timeLbl = [[UILabel alloc] init];
[timeLbl setBackgroundColor:[UIColor clearColor]];
timeLbl.frame = CGRectMake(35, 15, 200, 20);
timeLbl.font = [UIFont systemFontOfSize:13];
timeLbl.tag = 333;
[cell.contentView addSubview:timeLbl];
titleLbl = [[UILabel alloc] init];
titleLbl.frame = CGRectMake(123, 15, 200, 20);
titleLbl.font = [UIFont fontWithName:@"Arial-BoldMT" size:18];
[titleLbl setBackgroundColor:[UIColor clearColor]];
titleLbl.tag = 444;
[cell.contentView addSubview:titleLbl];
[cell.contentView setBackgroundColor:[UIColor colorWithRed:243 / 255.0 green:245 / 255.0 blue:247 / 255.0 alpha:1.0]];
endsLbl = [[UILabel alloc] init];
[endsLbl setBackgroundColor:[UIColor clearColor]];
endsLbl.frame = CGRectMake(49, 11, 40, 8);
[endsLbl setFont:[UIFont fontWithName:@"Arial-BoldMT" size:7]];
[endsLbl setTextColor:[UIColor redColor]];
endsLbl.tag = 555;
[cell.contentView addSubview:endsLbl];
eventTypeImgView = [[UIImageView alloc] init];
eventTypeImgView.frame = CGRectMake(95, 16, 16, 17);
eventTypeImgView.tag = 666;
[cell.contentView addSubview:eventTypeImgView];
}
startTimeStr = [[self.sortedEventsDict[[[[self.sortedEventsDict allKeys] sortedArrayUsingSelector:@selector(compare:)] objectAtIndex:indexPath.section]] objectAtIndex:indexPath.row] valueForKey:@"starts"];
formatter = [[NSDateFormatter alloc] init];
[formatter setDateFormat:@"yyy-MM-dd HH:mm"];
NSDate *startDate = [formatter dateFromString:startTimeStr];
NSDateFormatter *timeFormatter = [[NSDateFormatter alloc] init];
[timeFormatter setDateFormat:@"HH:mm"];
NSString *timeStr = [timeFormatter stringFromDate:startDate];
NSString *endTimeStr = [[self.sortedEventsDict[[[[self.sortedEventsDict allKeys] sortedArrayUsingSelector:@selector(compare:)] objectAtIndex:indexPath.section]] objectAtIndex:indexPath.row] valueForKey:@"ends"];
NSDateFormatter *endformatter = [[NSDateFormatter alloc] init];
[endformatter setDateFormat:@"yyy-MM-dd HH:mm"];
NSDate *endDate = [endformatter dateFromString:endTimeStr];
NSDateFormatter *endtimeFormatter = [[NSDateFormatter alloc] init];
[endtimeFormatter setDateFormat:@"HH:mm"];
NSString *endTime = [endtimeFormatter stringFromDate:endDate];
if([[[self.sortedEventsDict[[[[self.sortedEventsDict allKeys] sortedArrayUsingSelector:@selector(compare:)] objectAtIndex:indexPath.section]] objectAtIndex:indexPath.row] valueForKey:@"type"] isEqualToString:@"event"])
{
((UIImageView *)[cell.contentView viewWithTag:666]).image = [UIImage imageNamed:@"eventsIcon.png"];
}
else
{
((UIImageView *)[cell.contentView viewWithTag:666]).image = [UIImage imageNamed:@"appointmentsIcon.png"];
}
((UILabel *)[cell.contentView viewWithTag:555]).text = @"";
if([timeStr isEqualToString:@"00:00"] && [endTime isEqualToString:@"23:59"])
{
timeStr = @"all-day";
}
else if([timeStr isEqualToString:@"00:00"] && ![endTime isEqualToString:@"23:59"])
{
timeStr = endTime;
((UILabel *)[cell.contentView viewWithTag:555]).text = @"ENDS";
}
((UILabel *)[cell.contentView viewWithTag:333]).text = timeStr;
((UILabel *)[cell.contentView viewWithTag:444]).text = [[self.sortedEventsDict[[[[self.sortedEventsDict allKeys] sortedArrayUsingSelector:@selector(compare:)] objectAtIndex:indexPath.section]] objectAtIndex:indexPath.row] valueForKey:@"title"];
startDate = nil;
timeFormatter = nil;
timeStr = nil;
endTimeStr = nil;
endformatter = nil;
endDate = nil;
endtimeFormatter = nil;
endTime = nil;
startTimeStr = nil;
formatter = nil;
[cell setBackgroundColor:[UIColor colorWithRed:243 / 255.0 green:245 / 255.0 blue:247 / 255.0 alpha:1.0]];
double finish = CFAbsoluteTimeGetCurrent();
NSLog(@"TIME DIFF = %f", finish - begin);
return cell;
}
else
{
NSString *cellIdentifier = [NSString stringWithFormat: @"Cell No Results %i %i", indexPath.row, indexPath.section];
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
if(cell == nil)
{
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier];
if(indexPath.row == 2)
{
UILabel *noResultsLbl = [[UILabel alloc] init];
noResultsLbl.text = self.noResultsString;
[noResultsLbl setFont:[UIFont fontWithName:@"Arial-BoldMT" size:20]];
[noResultsLbl setTextColor:[UIColor colorWithRed:204 / 255.0 green:204 / 255.0 blue:204 / 255.0 alpha:1.0]];
noResultsLbl.frame = CGRectMake(60, 15, 200, 20);
noResultsLbl.textAlignment = NSTextAlignmentCenter;
[cell.contentView addSubview:noResultsLbl];
}
}
[cell.contentView setBackgroundColor:[UIColor colorWithRed:243 / 255.0 green:245 / 255.0 blue:247 / 255.0 alpha:1.0]];
cell.userInteractionEnabled = NO;
double finish = CFAbsoluteTimeGetCurrent();
NSLog(@"TIME DIFF = %f", finish - begin);
return cell;
}
}
请帮助我。
答案 0 :(得分:7)
你的cellForRowAtIndexPath
长140行,这就是它不能顺利运行的原因。我建议仔细阅读代码并尝试尽可能地重构代码。格式化程序非常昂贵,而且你可以分配/启动几个。制作原型或基于xib的单元格,而不是每次都以编程方式设置它。我还建议不要在视图中使用标签,将其放入xib或原型单元格中并将其作为插座。
这些更改将加快您的滚动速度。
答案 1 :(得分:3)
检查单元格中正在使用的图像的大小。当图像大于它们所需的图像时,我遇到过这个问题。尝试将图像尺寸缩小到适合桌面的最佳尺寸。
答案 2 :(得分:2)
您为每个单元格排序所有数据。
if([[[self.sortedEventsDict[[[[self.sortedEventsDict allKeys] sortedArrayUsingSelector:@selector(compare:)] objectAtIndex:indexPath.section]] objectAtIndex:indexPath.row] valueForKey:@"type"] isEqualToString:@"event"])
尝试为每个[table reloadData]调用使用准备好的数据。基本上你可以在一个地方执行所有计算,然后只用结果填充单元格。
找出问题的最佳方法是使用Profiler。它将显示代码的哪一部分在帧之间占用所有cpu。
答案 3 :(得分:1)
没有单元重用,几个alloc / init-s和很多NSDateFormatter都非常昂贵
TODO:
NSDateFormatter
或手动使用格式分隔的NSDateFormatter
,因为每种格式都像新的格式化程序重复使用细胞:
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = @"cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (!cell) {
// Setup new cell and constant elements of cell
}
// Setup data like images, strings and stuff with minimal calculations and formatting
return cell;
}
答案 4 :(得分:1)
我的解决方案可能是一个非常罕见的情况,但它肯定有帮助。
我有一个单元格,其中包含一个带有货币卢布字符串的标签"₽" (我认为这也可能是由其他货币角色引起的)。每次重复使用单元格时,此字符串都会动态添加到标签中。而且表格视图非常迟钝。然后我只删除了卢布标志和滞后消失了。
解决方案:创建一个就绪标签,并将char输入故事板中的标签。
答案 5 :(得分:0)
对我来说,滞后是由主tableView单元格内的另一个tableView引起的(我知道这很奇怪)。我已修复此问题,方法是删除其他tableView并重新考虑应用程序的体系结构,而无需使用“ tableView内置tableView”方法。