Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Attempt to present a UIViewController whose view is not in the window hierarchy

I have a multi-view application with the following hierarchy:

splash -> navigation controller -> table view controller -> settings view controller

Splash is the application entry point and therefore becomes the root view controller. When I try to add a tile to the band via an action on the settings view controller, I get a debugger warning:

application[1929:1000746] Warning: Attempt to present <MSBAddTileDialogViewController_iOS: 0x15f0575b0> on <SplashViewController: 0x15dd597b0> whose view is not in the window hierarchy!

This happens immediately after the call to MSBClient.tileManager addTile:completionHandler:. The call never returns, no error is generated.

Any suggestions on how to get around this?

like image 791
chortik Avatar asked Dec 20 '15 07:12

chortik


People also ask

Which method is called before a view is removed from the view hierarchy?

viewWillDisappear: This method is called before the view is removed from the view hierarchy.

How do you dismiss the current view controller and go to another view in Swift?

This second controller has a dismiss option that just comes back to the root view controller and a button that when the user touches it dismisses the current view controller so it goes back to the root view controller for a second and presents another one.

What is the role of UIViewController?

The UIViewController class defines the shared behavior that's common to all view controllers. You rarely create instances of the UIViewController class directly. Instead, you subclass UIViewController and add the methods and properties needed to manage the view controller's view hierarchy.


1 Answers

You will need to get the root view controller and perform a segue from that view controller. This can be quite frustrating to debug but there are some answers on here about this topic.

Here is some code that I have used to perform a segue from the root view controller to a screen when the app receives a push notification.

UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"YourStoryboard" bundle:nil];

YourViewController *viewController = [storyboard instantiateViewControllerWithIdentifier:@"viewcontrolleridentifier"];

UIViewController *top = [UIApplication sharedApplication].keyWindow.rootViewController;

[top presentViewController:viewController animated:YES completion: nil];

Heres the same code in swift:

let storyboard = UIStoryboard.init(name: "YourStoryboard", bundle: nil)

let viewController = storyboard.instantiateViewController(withIdentifier: "viewcontrolleridentifier")

let top = UIApplication.shared.keyWindow?.rootViewController

top?.present(viewController, animated: true, completion: nil)

Make sure you set the view controllers identifier in your storyboard.

EDIT* If the view controller you are accessing is embedded within a navigation controller you will need to amend the above code,

Objective C:

UIViewController *top = [self topMostController];

UINavigationController *navigationController = [[UINavigationController alloc] initWithRootViewController:viewController];

[top presentViewController:navigationController animated:YES completion: nil];

Swift:

let top = UIApplication.shared.keyWindow?.rootViewController

let navigationController = UINavigationController.init(rootViewController: viewController)

top?.present(navigationController, animated: true, completion: nil)
like image 72
Axemasta Avatar answered Sep 19 '22 13:09

Axemasta