I have a custom UIView subclass which grabs all the subviews in layoutSubviews and alters their layout/size depending on some custom settings.
It all works fine if I create this view programatically however if I add this UIView subclass to a storyboard and add some subviews in the storyboard, the layout changes don't seem to persist.
I can see the following logic flow using breakpoints.
The VC & custom View is initialised
The VC viewDidLayoutSubviews is called. (I'm doing nothing in here just observing it is called using a breakpoint)
The custom UIView, layoutSubviews is called.
override func layoutSubviews() { for subView in self.subviews { var subview = subView as! UIView var frame = subview.frame //some arbritary frame adjustments. frame.origin.x = 10; frame.origin.y = 50; subview.frame = frame subview.setNeedsLayout() //tried with and without this line with no difference. } }
I can see that the frames are being adjusted as I print all the subviews before adjusting them, and then again after via the debugger.
po self.subviews
VC viewDidLayoutSubviews is called again. However when I print the subviews here, I can see that they're back to their original frames again.
po customView.subviews
View appears and frames have not been adjusted.
If I call layoutSubviews again the subview frames do end up adjusting however only after the view had appeared which is too late.
override func viewDidLayoutSubviews() {
customView?.layoutSubviews();
}
The flow for this is as follows:
VC & View is initialised
VC viewDidLayoutSubviews is called
layoutSubviews is called twice in a row
The View appears and the subviews have not been readjusted, even though they were in layoutSubviews when printed via the debugger.
VC - viewDidLayoutSubviews is called again
layoutSubviews is called again.
You can see the subviews adjust but it's too late because the user would be able to see the subviews 'jump' into place.
Any ideas as to what I'm missing here? The subview frames are definitely being set correctly but they're just being reverted back before the view appears.
I just happen to be using swift for this but responses in Objective C are very welcome.
subview.layoutIfNeeded()
right aftersetNeedsLayout
- ozgur