In short:
- Apple does NOT set the
frameorboundsfor aCAShapeLayerautomatically (and Apple HAS NOT implemented an equivalent of[UIView sizeThatFits]) - If you set the frame using the size of the bounding-box of the path ... everything goes wrong. No matter how you try to set it, it screws-up the path
So, what's the correct way to programmatically set the frame of a newly-created CAShapeLayer with a newly-added CGPath ? Apple's docs are silent on the matter.
Things I've tried, that don't work:
- Create a
CAShapeLayer - Create a
CGPath, add it to the layer - Check the layer's
frame- it's{{0,0},{0,0}} - Set:
layer.frame = CGPathGetBoundingBox( layer.path ) Frame is now correct, but the path is now DOUBLE offset - changing the
framecauses the path to effectively be shifted an extra(x,y)pixelsSet:
layer.bounds = CGPathGetBoundingBox( layer.path )- ...it all goes nuts. Nothing makes sense any more
- Try fixing it by doing
layer.position = CGPathGetBoundingBox( layer.path ).origin - ...no dice; still nuts.
One thing I've tried that DID work, but causes problems elsewhere:
EDIT: this BREAKS as soon as you auto-rotate the screen. My guess: Apple's auto-rotate requires control of the "transform" property.
- Create a
CAShapeLayer - Create a
CGPath, add it to the layer - Check the layer's frame - it's
{{0,0},{0,0}} - Set:
layer.frame = CGPathGetBoundingBox( layer.path ) - Set:
layer.transform = CGAffineTransformMakeTranslation( CGPathGetBoundingBox( layer.path ).origin.x * -1, // same for y-coord: set it to "-1 * the path's origin
This works, but ... lots of 3rd party code assumes that the initial transform for a CALayer is Identity.
It shouldn't be this difficult! Surely there's something I'm doing wrong here?
(I've had one suggestion: "every time you add a path, manually run a custom function to shift all the points by -1 * (top-left-point.x, top-left-point.y)". Again, that works - but it's ridiculously complex)