Where to call setNeedsDisplay in order to update CALayer?

1.6k Views Asked by At

I have a view controller (MagmaViewController) which is managing a view called MagmaView. For the direct backing layer of MagmaView I have assigned my own customized CALayer subclass called MagmaLayer by putting the following into the implementation section of MagmaView:

+ (Class)layerClass
{
    return [MagmaLayer class];
}

I have some customized drawing that I want MagmaLayer to draw for MagmaView, so I put some drawing code into the -(void) drawInContext:(CGContextRef) context method of MagmaLayer. The problem is that when I do this and run the simulator then MagmaView appears blank. I set a breakpoint in MagmaLayer's -(void) drawInContext:(CGContextRef) context method and it appears this method is not being called at all.

Obviously, I'm confused about the need and placement of the setNeedsDisplay command for triggering the drawing of this CALayer. First, I thought that, at least for the first initial appearance of a CALayer, that issuing a setNeedsDisplay command was not needed if the CALayer is a direct backing layer for a UIView, and that any UIView makes sure that its direct backing layer is properly drawn when needed and that only non-direct CALayer backing layers required special attention to make sure that they draw themselves. Is this not so? Also, where should I place the setNeedsDisplay command to make this direct backing layer MagmaLayer draw itself? Should the setNeedsDisplay command be in the initialization method of MagmaView, which is the view hosting the MagmaLayer here? Or should I go further up the chain and put the setNeedsDisplay command in MagmaViewController, the view controller which is managing MagmaView in, say, the controller's viewWillAppear method?

1

There are 1 best solutions below

0
On

You need to tell your custom layer when to draw. The basic implementation will do not call -(void) drawInContext:(CGContextRef) context automatically. The basic setup is to set needsDisplayOnBoundsChange = YES in the layers init method. If you have custom properties which should trigger a redraw, you will have to implement / extend + (BOOL)needsDisplayForKey:(NSString *)key.