• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
CAShapeLayer as a mask for CALayer: rounded corners are stretched
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

CAShapeLayer as a mask for CALayer: rounded corners are stretched


  • Subject: CAShapeLayer as a mask for CALayer: rounded corners are stretched
  • From: Anton Sotkov <email@hidden>
  • Date: Sat, 22 Oct 2011 06:23:21 +0300

Hi!

I want to mask a CALayer with CAShapeLayer, because changes to the shape can be animated.

When I use the CAShapeLayer as a mask, its rounded corners are stretched. However, if I take the same shape, create an image with it, and use the image to mask my CALayer, the rounded corners are perfectly fine.

Here's a screenshot of this behavior: http://pxl.fi/0t3Z0e2R2n1l2N2t2c3J (image-based mask on the left, shape-based on the right).

Here's the code I'm using to mask the layers (and you can download the whole example project at http://pxl.fi/1A2D2z0F1I030e1x1z1c).

CALayer *imageBasedMaskLayer = [CALayer layer];
[imageBasedMaskLayer setContents:(id)[[self maskWithSize:NSMakeSize(50, 50)] CGImageForProposedRect:NULL context:nil hints:nil]];
[imageBasedMaskLayer setFrame:CGRectMake(0, 0, 50, 50)];

CALayer *layerWithImageBasedMaskLayer = [CALayer layer];
[layerWithImageBasedMaskLayer setBackgroundColor:backgroundColor];
[layerWithImageBasedMaskLayer setMask:imageBasedMaskLayer];


CAShapeLayer *shapeBasedMaskLayer = [CAShapeLayer layer];
CGPathRef maskShape = [self newMaskPathWithFrame:NSMakeRect(0, 0, 50, 50)];
[shapeBasedMaskLayer setPath:maskShape];
[shapeBasedMaskLayer setFillRule:kCAFillRuleEvenOdd];
CGPathRelease(maskShape);
[shapeBasedMaskLayer setFrame:CGRectMake(0, 0, 50, 50)];

CALayer *layerWithShapeBasedMaskLayer = [CALayer layer];
[layerWithShapeBasedMaskLayer setBackgroundColor:backgroundColor];
[layerWithShapeBasedMaskLayer setMask:nil];
[layerWithShapeBasedMaskLayer setMask:shapeBasedMaskLayer];

And the two methods I'm creating NSImage and CGPathRef with.

- (NSImage *)maskWithSize:(CGSize)size;
{
	NSImage *maskImage = [[NSImage alloc] initWithSize:size];

	[maskImage lockFocus];
	[[NSColor blackColor] setFill];

	CGPathRef mask = [self newMaskPathWithFrame:CGRectMake(0, 0, size.width, size.height)];
	CGContextRef context = [[NSGraphicsContext currentContext] graphicsPort];
	CGContextAddPath(context, mask);
	CGContextFillPath(context);
	CGPathRelease(mask);

	[maskImage unlockFocus];

	return [maskImage autorelease];
}

- (CGPathRef)newMaskPathWithFrame:(CGRect)frame;
{
	CGFloat cornerRadius = 3;

	CGFloat height = CGRectGetMaxY(frame);
	CGFloat width = CGRectGetMaxX(frame);

	CGMutablePathRef maskPath = CGPathCreateMutable();

	CGPathMoveToPoint(maskPath, NULL, 0, height-cornerRadius);
	CGPathAddArcToPoint(maskPath, NULL, 0, height, cornerRadius, height, cornerRadius);
	CGPathAddLineToPoint(maskPath, NULL, width-cornerRadius, height);
	CGPathAddArcToPoint(maskPath, NULL, width, height, width, height-cornerRadius, cornerRadius);
	CGPathAddLineToPoint(maskPath, NULL, width, cornerRadius);
	CGPathAddArcToPoint(maskPath, NULL, width, 0, width-cornerRadius, 0, cornerRadius);
	CGPathAddLineToPoint(maskPath, NULL, cornerRadius, 0);
	CGPathAddArcToPoint(maskPath, NULL, 0, 0, 0, cornerRadius, cornerRadius);

	CGPathCloseSubpath(maskPath);

	return maskPath;
}

Please note that the actual mask I want to create is more complicated than a rounded rect, otherwise I would've used some of the simpler drawing techniques. I've tried various CGPath drawing functions, but nothing changed. I've tried masking the layer on iOS and observed the same problem. There must be a mistake in my code, I just don't see where it is.

What am I missing here?

Thank you,
Anton._______________________________________________

Cocoa-dev mailing list (email@hidden)

Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com

Help/Unsubscribe/Update your Subscription:

This email sent to email@hidden

  • Follow-Ups:
    • Re: CAShapeLayer as a mask for CALayer: rounded corners are stretched
      • From: David Duncan <email@hidden>
  • Prev by Date: Re: Core Data: Determine if managed object is deleted
  • Next by Date: Re: Exception when entering too big value in text field (with number formatter)
  • Previous by thread: Re: Can I jsut use @2x images without supplying a @1x image?
  • Next by thread: Re: CAShapeLayer as a mask for CALayer: rounded corners are stretched
  • Index(es):
    • Date
    • Thread