iOS Nested View Controllers view inside UIViewController's view?
Asked Answered
L

3

97

Is it typically bad programming practice in iOS to have a nested view controller's view inside UIViewController's view? Say for instance I wanted to have some kind of interactive element that responds to user's touches, but only takes up maybe 25% of the screen.

I suppose I would add this nested view controller to my UIViewController by saying something like:

[self.view addSubview: nestedViewController.view];
Lobo answered 6/7, 2013 at 3:28 Comment(1)
Here's a full tutorial with lots of pictures!! https://mcmap.net/q/17273/-how-to-add-a-subview-that-has-its-own-uiviewcontroller-in-objective-c EnjoyChampionship
S
152

No, this is generally good design, it helps keep your view controllers concise. However you should be using the view controller containment pattern, take a look at the following documentation.

Implementing a Container View Controller

This is incredibly simple to setup using Interface Builder with Storyboards as well, take a look at the Container View in the object library.

Here is a contrived example in a Storyboard. In this example you would have 4 view controllers, one that holds the 3 containers, and one for each container. When you present the left most controller that has all of the containers, the Storyboard will automatically initialize and embed the other 3. You can access these child view controllers via the childViewControllers property or there is a method you can override prepareForSegue:sender: and capture the destination view controllers of the segue about to be called. This is also a good point to pass properties to the child view controllers if any are needed.

enter image description here

Sprinkling answered 6/7, 2013 at 3:35 Comment(4)
how "the hell" do you do that in storyboard?! it's a basic question .. I don't know the answer to :) Sigh -- answering my own question. Add a container to the scene. Shape it. Then on the blank fields of the storyboard make a UIViewController. Then right-click-drag from that container (either in the Navigator list or the GUI) to that new UIViewController. From the popup, choose viewDidLoad-embed, to get started. Thanks Chris! :)Championship
Link is broken, by the way.Carlsen
@JoeBlow +1 "viewDidLoad-embed" Holy cow: who would have guessed that!Leanto
Thanks @ChrisWagner! This is a critical piece of the puzzle for implementing MVVM architecture and avoiding Massive View Controller/"MVC" ;)Neese
B
58

I put this code in the parent view controller. It works great for me.

Obj C

-(void)viewDidLoad{
     [super viewDidLoad];
     InnerViewController *innerViewController = [self.storyboard instantiateViewControllerWithIdentifier:INNER_VIEW_CONTROLLER];
     [self addChildViewController:innerViewController];
     [self.view addSubview:innerViewController.view];
     [innerViewController didMoveToParentViewController:self];
}

Swift:

 let childViewController = UIStoryboard(name: "Main", bundle: nil).instantiateViewController(withIdentifier: "ChildViewController"),
 self.addChildViewController(childViewController)
 self.view.addSubview(childViewController.view)
 childViewController.didMove(toParentViewController: self)

Another option is to use IB and put container view. UIViewController will show up automatically (XCode 9 in this case): enter image description here

Baculiform answered 23/7, 2015 at 10:6 Comment(2)
Yes! +1. Thanks for including an answer for how to do this programatically :)Livonia
I've just drag&drop view from child view controller to parent subview's list.Mucky
L
5

Here is my Swift 3 solution based on Swift Developers On FB's answer

 let childViewController = UIStoryboard(name: "Main", bundle: nil).instantiateViewController(withIdentifier: "ChildPageViewController"),
 self.addChildViewController(childViewController)
 self.view.addSubview(childViewController.view)
 childViewController.didMove(toParentViewController: self)
Lacrosse answered 26/7, 2017 at 14:6 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.