I have a CALayer
with hitTesting that works fine. The code is something like this:
- (void)setup
{
_maskLayer = [CAShapeLayer layer];
_maskLayer.fillColor = [UIColor whiteColor].CGColor;
_maskLayer.path = somePath;
_theLayer.frame = CGRectMake(0, 0, size.width, size.height);
// Taps work fine if we do not apply the mask
// _theLayer.mask = _maskLayer;
}
- (IBAction)tapOnView:(UITapGestureRecognizer *)sender
{
CGPoint point = [sender locationInView:theView];
CALayer *subLayer = [_theLayer.presentationLayer hitTest:point].modelLayer;
if (subLayer != _theLayer && subLayer != nil) {
// Do something with the sublayer which the user touched
}
}
The problem is that if I uncomment the line with the mask
, my hit testing always returns nil
. Why does the mask kill hit testing? It appears correct visually.
It turns out that hit testing requires the point to be inside the bounds of the CALayer
, but what is not documented is that it also has to be inside the bounds of the mask
. So I changed my code like this and it worked:
_theLayer.frame = CGRectMake(0, 0, size.width, size.height);
// Apply a mask
_maskLayer.frame = _theLayer.frame;
_theLayer.mask = _maskLayer;
It took me a few hours to figure this out, so I wanted to share.