Assuming I load a view controller from a nib, and decide to do something with one of its subview behind the scene. At a later moment in time, I would show the view of this view controller.
viewController = [[MyViewController alloc] initWithNibName:@"MyViewController" bundle:nil];
[viewController.someSubview doSomething];
//later on
[mainView addSubview:viewController.view];
The problem is that, the someSubview object doesn't seem to be loaded until the view appears, so the method doSomething is not called. So far my workaround is to call:
[mainView addSubview:viewController.view];
[viewController.view removeFromSuperview];
to initialize the subviews of viewcontroller first. Is there any more elegant way (like a loadSubviews method or something) for this task?
First of all I would try simply accessing the property:
[viewController view];
This will force the lazy load of the view (and thus the subviews and outlets etc.) and this might be enough for you. View controllers by default will not load their view until you access it so this might be why you are seeing a delay.
Forcing a load like this is usually the solution when you are trying to access an outlet property but it hasn't actually been bound yet, like someSubview
in your case.
You can also improve things a bit by adding the view but making it hidden:
viewController.view.hidden = YES;
[mainView addSubview:viewController.view];
Then instead of calling addSubview
when you want to show it, just do:
viewController.view.hidden = NO;
I've used this method when animating in views using the UIViewAnimationTransitionFlipFromRight
etc. transitions. Even when forcing a lazy load of the view there is still a noticable lag, so I've used this to improve the performance a bit.
iOS 9 introduced -(void) loadViewIfNeeded
I use
if ([_myVC respondsToSelector:@selector(loadViewIfNeeded)]) {
[_myVC loadViewIfNeeded];
} else {
[_myVC view];
}