Auto Layout constraint on CALayer IOS
Hi I am developing iPhone application in which I tried to set one side border for edittext. I did this in following way:
int borderWidth = 1;
CALayer *leftBorder = [CALayer layer];
leftBorder.borderColor = [UIColor whiteColor].CGColor;
leftBorder.borderWidth = borderWidth;
leftBorder.frame = CGRectMake(0, textField.frame.size.height - borderWidth, textField
.frame.size.width, borderWidth);
[textField.layer addSublayer:leftBorder];
I put some constraints on my edittext in IB so that when I rotate my device it will adjust width of text field according to that. My problem is that adjusts the width of edittext not adjusting the width of CALayer which I set for my edit text. So I think I have to put some constraints for my CALayer item as well. But I dont know how to do that. ANy one knows about this? Need Help. Thank you.
Solution 1:
the whole autoresizing business is view-specific. layers don't autoresize.
what you have to do -- in code -- is to resize the layer yourself
e.g.
in a viewController you would do
- (void) viewDidLayoutSubviews {
[super viewDidLayoutSubviews]; //if you want superclass's behaviour...
// resize your layers based on the view's new frame
self.editViewBorderLayer.frame = self.editView.bounds;
}
or in a custom UIView you could use
- (void)layoutSubviews {
[super layoutSubviews]; //if you want superclass's behaviour... (and lay outing of children)
// resize your layers based on the view's new frame
layer.frame = self.bounds;
}
Solution 2:
In Swift 5
, you can try the following solution:
Use KVO, for the path "YourView.bounds" as given below.
self.addObserver(self, forKeyPath: "YourView.bounds", options: .new, context: nil)
Then handle it as given below.
override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey : Any]?, context: UnsafeMutableRawPointer?) {
if keyPath == "YourView.bounds" {
YourLayer.frame = YourView.bounds
return
}
super.observeValue(forKeyPath: keyPath, of: object, change: change, context: context)
}
More info about this here
Solution 3:
According to this answer, layoutSubviews
does not get called in all needed cases. I have found this delegate method more effective:
- (instancetype)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if(self != nil) {
[self.layer addSublayer:self.mySublayer];
}
return self;
}
- (void)layoutSublayersOfLayer:(CALayer*)layer
{
self.mySublayer.frame = self.bounds;
}