Instantiate Storyboard ViewControllers Manually

I’ve started using storyboards in XCode/iOS more frequently, but I really needed something different from the normal segues and connections that Apple provides, and while Apple briefly documents how to do this, I thought I’d share my example.  Here is the view in Interface Builder of the test app that I created:

My initial controller is on the left, and the blue area is simply a UIView that I’ve connected to  a member variable outlet named _parentView.  This is where I want my yellow and pink sub views to appear, each handled by their own controller.  Notice that there is no connection between the storyboards in this case.  The key here is to set the Storyboard ID for yellow and pink View Controllers so I can instantiate them in my code.  If I don’t set a storyboard id for the yellow and pink View Controllers, I’ll get a warning from XCode that they are unreachable. You set the Storyboard ID in the Identity inspector (see the inspector panel on the right in the picture above – make sure ‘Use Storyboard ID’ is checked).

Once I have storyboard IDs set for each of these view controllers, the code is quite simple to instantiate the view controllers and embed them using the parentView as a container.

- (IBAction)showView1:(id)sender 
{
  [self switchViews:@"yellow"];
}

- (IBAction)showView2:(id)sender 
{
  [self switchViews:@"pink"];
}

- (void)switchViews:(NSString*)storyboardId
{
  __block UIViewController *lastController = _childController;

  _childController = (UIViewController*)[self.storyboard instantiateViewControllerWithIdentifier:storyboardId];
  [self addChildViewController:_childController];
  [_parentView addSubview:_childController.view];

  CGRect parentRect = _parentView.bounds;
  parentRect.origin.x += parentRect.size.width;
  _childController.view.frame = parentRect;
  _childController.view.alpha = 0;
  [UIView animateWithDuration:0.5 animations:^{
    _childController.view.frame = _parentView.bounds;
    _childController.view.alpha = 1.0;
  } completion:^(BOOL finished) {
    if (lastController)
    {
      [lastController.view removeFromSuperview];
      [lastController removeFromParentViewController];
    }
  }];
}
The basics in the code above:
- Keep a pointer to the last view controller child
- Use instantiateViewControllerWithIdentifier using the storyboard id you set in interface builder to create and return the view controller.
- Add the new controller as a child controller to the parent
- Add the new controllers view as a subView to the parent
- Then for fun I animate the new controller onscreen
- When the new view is fully animated, then I remove the old view
With this basic flow, you can customize the user interface in just about any way you can imagine.

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>