David Vincent Gagne
David Vincent Gagne

Reputation: 527

instantiateViewControllerWithIdentifier breaks UINavigationController flow

I have a UIViewController (with a hidden UINavigationController) which contains a UIButton. Clicking the button calls instantiateViewControllerWithIdentifier on another UIViewController (and passes the second UIViewController some data).

Try as I might, I could not get the second UIViewController to display its UINavigationController navigationBar, even though I had it embedded in the UINavigationController. That's not a catastrophe, though, because I didn't really want it there anyway and would have simply hidden it. I added a UIButton to the second UIViewController and control-click-dragged in Interface Builder to add a "Show" segue back to the first UIViewController.

But now when you visit any other UIViewController (and only after following the steps above), the UINavigationBar is missing.

Here's how I'm loading the second UIViewController:

let destinationViewController = self.storyboard?.instantiateViewControllerWithIdentifier("viewGold") as! SecondViewController
destinationViewController.results = result
self.presentViewController(destinationViewController, animated: true, completion: nil)

So:

  1. Is it terrible of me to want to not display the UINavigationBar on two of the UIViewControllers?
  2. Am I loading the SecondViewController correctly?
  3. Is there a way to mimic clicking a "Back" UINavigationBar in the UIButton click of the SecondViewController?

Upvotes: 0

Views: 149

Answers (2)

jimmyy
jimmyy

Reputation: 139

So self.presentViewController is a modal presentation, which means that it is not included in your UINavigationController's navigation stack and thus will not display your navigation bar. You are presenting the right way here.

The problem lies in the segue you made from the second view controller to the first. The Show segue actually creates a new view controller and presents it modally, which is definitely not what you want (especially since it's creating your first view controller without it's navigation controller). Instead, use self.presentingViewController.dismissViewControllerAnimated to dismiss modally.

Presenting modally doesn't offer the same kind of transition that moving along the navigation stack does, which means you won't get your left/right transitions. Generally, I would recommend keeping your navigation bar visible and working on your navigation stack if you want to navigate like that.

For reference, look at Apple's documentation on segues!

Upvotes: 1

Earl Grey
Earl Grey

Reputation: 7466

  1. This is not a programatic problem , but a design problem. Thus we cannot answer that because there is no right answer.
  2. Yes
  3. Yes, but it's pointless because that is exactly what the navigation controller with a bar is for.

You are trying to solve a lack of framework understanding by inventing workaround solutions.

To address the issue: If you wanted to present a controller embedded inside navigation controller, than in reality you needed present THE navigation controller as it would carry the desired controller with itself after presentation. So just present the navigation controller and that's it.

Any UIViewController subclass has an optional property called .navigationController. It will get you the first immediate parent that is a navigation controller if there is one. So get the navigation controller for your destination controller via this property.

Upvotes: 0

Related Questions