Я создал подкласс CALayer, чтобы нарисовать фоновый узор в шахматном порядке. Все работает хорошо и рендерится правильно, однако я обнаружил, что производительность падает, когда CALayer получает большой кадр.
Кажется довольно очевидным, что я мог бы оптимизировать, переместив распределение моих CGColorRef и CGPatternRef вне вызова drawLayer: inContext:, но я не уверен, как это сделать, поскольку оба полагаются на наличие CGContextRef.
Насколько я понимаю, контекст рисования CALayer фактически принадлежит его родительскому NSView и передается только во время рисования. Если это так, как лучше оптимизировать следующий код?
void drawCheckerboardPattern(void *info, CGContextRef context)
{
CGColorRef alternateColor = CGColorCreateGenericRGB(1.0, 1.0, 1.0, 0.25);
CGContextSetFillColorWithColor(context, alternateColor);
CGContextAddRect(context, CGRectMake(0.0f, 0.0f, kCheckerboardSize, kCheckerboardSize));
CGContextFillPath(context);
CGContextAddRect(context, CGRectMake(kCheckerboardSize, kCheckerboardSize, kCheckerboardSize, kCheckerboardSize));
CGContextFillPath(context);
CGColorRelease(alternateColor);
}
- (void)drawLayer:(CALayer *)layer inContext:(CGContextRef)context
{
CGFloat red = 0.0f, green = 0.0f, blue = 0.0f, alpha = 0.0f;
NSColor *originalBackgroundColor = [self.document.backgroundColor colorUsingColorSpaceName:NSCalibratedRGBColorSpace];
[originalBackgroundColor getRed:&red green:&green blue:&blue alpha:&alpha];
CGColorRef bgColor = CGColorCreateGenericRGB(red, green, blue, alpha);
CGContextSetFillColorWithColor(context, bgColor);
CGContextFillRect(context, layer.bounds);
// Should we draw a checkerboard pattern?
if([self.document.drawCheckerboard boolValue])
{
static const CGPatternCallbacks callbacks = { 0, &drawCheckerboardPattern, NULL };
CGContextSaveGState(context);
CGColorSpaceRef patternSpace = CGColorSpaceCreatePattern(NULL);
CGContextSetFillColorSpace(context, patternSpace);
CGColorSpaceRelease(patternSpace);
CGPatternRef pattern = CGPatternCreate(NULL,
CGRectMake(0.0f, 0.0f, kCheckerboardSize*2, kCheckerboardSize*2),
CGAffineTransformIdentity,
kCheckerboardSize*2,
kCheckerboardSize*2,
kCGPatternTilingConstantSpacing,
true,
&callbacks);
alpha = 1.0f;
CGContextSetFillPattern(context, pattern, &alpha);
CGPatternRelease(pattern);
CGContextFillRect(context, layer.bounds);
CGContextRestoreGState(context);
}
CGColorRelease(bgColor);
}