我有自定义UICollectionViewCell子类,可以在其中进行剪切,描边和透明绘制。它在Simulator和iPhone 5上运行良好,但在较旧的设备上存在明显的性能问题。
因此,我想将耗时的图形移至后台线程。由于-drawRect方法总是在主线程上调用,因此我最终将绘制的上下文保存到CGImage(原始问题包含使用CGLayer编写的代码,但正如Matt Long所指出的那样,已经过时了)。
这是我在此类内的drawRect方法的实现:
-(void)drawRect:(CGRect)rect {
CGContextRef ctx = UIGraphicsGetCurrentContext();
if (self.renderedSymbol != nil) {
CGContextDrawImage(ctx, self.bounds, self.renderedSymbol);
}
}
定义此renderSymbol属性的渲染方法:
- (void) renderCurrentSymbol {
[self.queue addOperationWithBlock:^{
// creating custom context to draw there (contexts are not thread safe)
CGColorSpaceRef space = CGColorSpaceCreateDeviceRGB();
CGContextRef ctx = CGBitmapContextCreate(nil, self.bounds.size.width, self.bounds.size.height, 8, self.bounds.size.width * (CGColorSpaceGetNumberOfComponents(space) + 1), space, kCGImageAlphaPremultipliedLast);
CGColorSpaceRelease(space);
// custom drawing goes here using 'ctx' context
// then saving context as CGImageRef to property that will be used in drawRect
self.renderedSymbol = CGBitmapContextCreateImage(ctx);
// asking main thread to update UI
[[NSOperationQueue mainQueue] addOperationWithBlock:^{
[self setNeedsDisplayInRect:self.bounds];
}];
CGContextRelease(ctx);
}];
}
此设置在主线程上可以很好地工作,但是当我用NSOperationQueue或GCD包装它时,会收到很多不同的“无效上下文0x0 ”错误。应用程序本身不会崩溃,但不会发生绘图。我想发布自定义创建的CGContextRef会有问题,但是我不知道该怎么办。
这是我的属性(property)声明。 (我尝试使用原子版本,但这无济于事)
@property (nonatomic) CGImageRef renderedSymbol;
@property (nonatomic, strong) NSOperationQueue *queue;
@property (nonatomic, strong) NSString *symbol; // used in custom drawing
属性的自定义 setter / getter :
-(NSOperationQueue *)queue {
if (!_queue) {
_queue = [[NSOperationQueue alloc] init];
_queue.name = @"Background Rendering";
}
return _queue;
}
-(void)setSymbol:(NSString *)symbol {
_symbol = symbol;
self.renderedSymbol = nil;
[self setNeedsDisplayInRect:self.bounds];
}
-(CGImageRef) renderedSymbol {
if (_renderedSymbol == nil) {
[self renderCurrentSymbol];
}
return _renderedSymbol;
}
我能做些什么?
最佳答案
您是否注意到自2006年以来没有更新过您所引用的CGLayer上的文档?您已经假设CGLayer是正确的解决方案是不正确的。苹果公司几乎已经放弃了这项技术,您可能也应该这样做:http://iosptl.com/posts/cglayer-no-longer-recommended/使用Core Animation。
关于ios - 用CGImage/CGLayer绘制另一个线程,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/16545001/