11

My window's rootViewController is a UINavigationController Then.. In this navigation controller's rootViewController, I popup a modal view(a UITabBarController)

something like this:

UIWindow
->UINavigationController
-->MyFirstViewController<--In this class I run following code
[self.navigationController presentModalViewController:tabController animated:YES];

Then the debugger warning :Using two-stage rotation animation is not supported when rotating more than one view controller or view controllers not the window delegate

However, if the modal view is not tabController this warning does not appear.

What will this behavior do harm to the application when I popup tabController modal view in a navigation controller?

Or I should find another way to do this?

I found several similar questions on this site, but I don't get it...

Guillaume
  • 21,685
  • 6
  • 63
  • 95
Matt.Z
  • 602
  • 7
  • 19
  • http://stackoverflow.com/questions/576764/tab-bar-controller-inside-a-navigation-controller-or-sharing-a-navigation-root - this is another way to do this. Don't use the controller, but rather, make your own UIControllerView and attach a UITabBar to it. Link has reference to source code (located on GIT). – TamusJRoyce Jan 08 '12 at 18:21

7 Answers7

14

The reason is that you are using a UITabBarController outside of the intended usage of it. It is ONLY intended to be used as a root controller, and should you need something similiar to a tabbar use toolbar. I was running into trouble with the exact problem about a half year ago. You will also run into other problems if you use it like that, unfortunately.

UITabBarController documentation

Because the UITabBarController class inherits from the UIViewController class, tab bar controllers have their own view that is accessible through the view property. When deploying a tab bar interface, you must install this view as the root of your window. Unlike other view controllers, a tab bar interface should never be installed as a child of another view controller.

LuckyLuke
  • 47,771
  • 85
  • 270
  • 434
  • That said I have used a `UITabBarController` inside a `UINavigationController` since iOS 2 and never had a problem with that. – Pascal Jun 26 '13 at 02:34
  • 3
    What would be the correct way of doing a login screen and after you login going to a UITabBarController? Excepting the message from the console on ios7 i don't see any other problem of using the controller inside a UINavigationController – Cristi Băluță Oct 25 '13 at 08:41
  • @LuckyLuke What if I have a custom requirement to present uitabbarcontroller modally? What should I do? – S.J May 20 '14 at 12:00
  • @CristiBăluță I use a UITabBarController that has a login screen in the first and only tab. Once the user has successfully logged in I turn on the other tabs depending on their privilege with the following code: [self setViewControllers:hasAccess animated:Yes] where hasAccess is a NSMutableArray of view controllers. – JSWilson Jun 24 '14 at 14:45
  • But it works in iOS8. I don't get the error when putting a tab bar controller in a nav controller. – supNate Oct 16 '14 at 12:29
12

This will also happen if you only add a blank UITabbarController without any child controllers, like so:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];

    //Tab bar controller
    UITabBarController* tabBarController = [[UITabBarController alloc] init];    
    [[self window] setRootViewController:tabBarController];

    [self.window makeKeyAndVisible];
    return YES;
}

The warning will go away if you add a child view controller to the UITabBarController before declaring it the rootViewController of your UIWindow.

Maciej Swic
  • 11,139
  • 8
  • 52
  • 68
  • The cause of this is so well hidden. Well spotted! I fixed like this: `UIViewController *tempViewController = [[UIViewController alloc] init];` `UINavigationController *tempNavController = [[UINavigationController alloc] initWithRootViewController:tempViewController];` `self.tabBarViewController.viewControllers = @[tempNavController];` I no longer get the warning! But it is a little messy. – Sam Jul 25 '13 at 15:23
  • +1 for "The warning will go away if you add a child view controller to the UITabBarController before declaring it the rootViewController of your UIWindow." – SolidSun Jan 20 '14 at 09:48
12

I got the same warning when subclassing UITabBarController but forgetting to call the base class's viewWillAppear: method in my own class.

- (void) viewWillAppear:(BOOL)animated {

  [super viewWillAppear:animated]    // <--- adding this fixed the warning

  ...

}
Oliver
  • 121
  • 1
  • 3
  • 2
    +1 Thanks - I would have never thought of that causing this warning – anneblue Jun 26 '13 at 14:33
  • thanks. so simple, so easy to overlook. And indeed as anneblue says, would've taken me a long time to figure that out myself. – Pega88 Jan 30 '14 at 18:40
2

I have an app where a UITabBarController is the root view controller. Depending on an in-app purchase, the child view controllers are different.

In my NIB, I had the UITabBarController without any child view controllers. I added the child view controllers in application:didFinishLaunchingWithOptions:

This caused the warning "two-stage" rotation to appear. As soon as I added one single child view controller to the tabbar controller in the NIB it disappeared.

Pierre GM
  • 19,809
  • 3
  • 56
  • 67
Klaus Thul
  • 675
  • 5
  • 7
0

@Maciej Swic's answer helped me a bit.

In my case I had already 2 child for the UITabBarController.

For some strange reason all I need was to put

[self.window makeKeyAndVisible];

after I added the 2 children.

0

Oliver's answer did the trick for me...it was interesting, though...i had not been having any problems until i added a viewWillAppear:animated method to to the subclassed tabviewcontroller...at that point, everything went haywire, until it was fixed by adding the [super viewWillAppear:animated] statement Oliver suggests...

dave adelson
  • 853
  • 9
  • 15
0

Had problem with Two-stage animation warning with the following order:

self.window.rootViewController = self.tabBarController;
self.tabBarController.selectedIndex = 0;

But changing the order help me to eliminate the warning.

self.tabBarController.selectedIndex = 0;
self.window.rootViewController = self.tabBarController;

Hope this helps.

bollhav
  • 543
  • 6
  • 11