iOS设置需要在线程上运行
你好 我有一个复杂的日历控件,每次选择日期项等时都需要使用setneedslayout重新绘制。我曾尝试在GCD块中运行此控件,但从未运行过。但是,当我在主线程上运行它时,setNeedsLayout运行并工作。然而,这会在我的程序中造成令人讨厌的口吃/延迟,破坏用户体验 我能知道能做什么吗?这可以在另一个线程上执行吗?我可以在另一个线程上使用NSTimer或执行选择器吗iOS设置需要在线程上运行,ios,grand-central-dispatch,Ios,Grand Central Dispatch,你好 我有一个复杂的日历控件,每次选择日期项等时都需要使用setneedslayout重新绘制。我曾尝试在GCD块中运行此控件,但从未运行过。但是,当我在主线程上运行它时,setNeedsLayout运行并工作。然而,这会在我的程序中造成令人讨厌的口吃/延迟,破坏用户体验 我能知道能做什么吗?这可以在另一个线程上执行吗?我可以在另一个线程上使用NSTimer或执行选择器吗 dispatch_queue_t queue = dispatch_get_global_queue(DISPATC
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_async(queue, ^{
dispatch_async(dispatch_get_main_queue(), ^{
//[[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:YES];
});
@try {
NSLog(@"New Thread");
if (self.selectedDate) {
[datesToReload addObject:self.selectedDate];
}
if (date) {
[datesToReload addObject:date];
}
self.selectedDate = date;
[self reloadDates:datesToReload];
[self performSelectorOnMainThread:@selector(reloadDates:) withObject:datesToReload waitUntilDone:NO];
//[self perform]
if (visible && date) {
self.monthShowing = date;
}
}
@catch (NSException *exception) {
NSLog(@"Exception = %@", exception);
}
dispatch_async(dispatch_get_main_queue(), ^{
//[[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:NO];
NSLog(@"Main Thread");
});
});
所有UI更新都需要在主线程上运行,您不能从后台线程更改UI(这将产生不可预测的副作用)
如果您遇到性能问题,您应该使用
仪器
来分析您的应用程序,找出处理时间的原因并解决该问题(例如,您真的需要重新加载所有日期吗?这需要大量时间吗?)。建议,使用上面的代码示例:
1) 您两次调用重新加载日期;即使直到使用perform_selector进行第二次调用时视图才成功更新,您仍然要做两次相同的工作。仅此一项就将使您在reloadData方法中遇到的任何UI延迟加倍
2) 对大部分工作使用较低优先级的队列:
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0), ^{
if (self.selectedDate) {
[datesToReload addObject:self.selectedDate];
}
if (date) {
[datesToReload addObject:date];
}
self.selectedDate = date;
[self reloadDates:datesToReload];
if (visible && date) {
self.monthShowing = date;
}
});
在重载日期内,仅将setNeedsLayout调用放入主队列异步块中
完成后,如果仍然存在不可接受的UI延迟级别,则需要查看正在重新绘制的视图,并查看如何使其更快。Instruments的时间分析器是查看在这些重画事件期间CPU时间使用位置的良好第一步。是运行setNeedsLayout并导致问题的重载日期操作。目前,在主线程上运行它的上述修复当然仍然会导致延迟