Teja Nandamuri
Teja Nandamuri

Reputation: 11201

How to change root controller after a server call on App Delegate?

I am trying to change root controller on app delegate.

I am making a server call to check if login session is valid or not. If valid, show welcome page, else show login page.

In the appDelegate , I am making server call in the method didFinishLaunchingWithOptions.

I get response through my datamodel delegate, but by the time I get response from server, the old root controller is already presented on screen.

At present, old root controller is presented first and within a fraction of seconds, new root controller is presented! So it looks like a flickering thing!

Is there a way to hold the old root controller to present untill I get repsonse from server ?

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
    // Override point for customization after application launch.

    _dataModel=[DataModal sharedInstance];
    _dataModel.delegate=self;

    NSString *token=[[NSUserDefaults standardUserDefaults]objectForKey:@"token"];
    if (!token) {
        token=@"jkfhgjkfg908";
    }else{
         _dataModel.auth_token=token;
    }

    [_dataModel checkToken:token];

    return YES;
}

//By the time it reaches here, the old root controller is already present on screen
-(void)checkToken:(NSDictionary *)items{

    if ([items[@"success"] isEqual:@1]) {
        AppDelegate *app = (AppDelegate*)[[UIApplication sharedApplication] delegate];
        UIStoryboard *storyboard=[UIStoryboard storyboardWithName:@"Main" bundle:nil];
        app.window.rootViewController=[storyboard instantiateViewControllerWithIdentifier:@"DashboardNavController"];

    }else{
        //do nothing, defualt is login view
    }

}

Upvotes: 2

Views: 431

Answers (4)

davbryn
davbryn

Reputation: 7176

You should not be waiting on a server call to decide on your root view controller - once didFinishLaunchingWithOptions is called you need to be presenting a view.

Have one Root View Controller present an initial view controller on load and stick to it - it's root for a reason.

If you have a token cached, skip your loginViewController and segue on. Plan for no internet/poor connection/ expired tokens, but don't put asynchronous actions in app delegate that prevent your UI being presented.

Upvotes: 2

meth
meth

Reputation: 1885

Rather than changing rootViewController, using initialViewController as an entrance is a better approach in my opinion. When app is launched there must be a screen to make the user feel everything is going well. Also, you are making a request to server and this process may fail or timed out.

My advice is to make navigation through initialViewController. Make it visible and put some animation or activity indicator and then when the response come, if logged in, go to your apps mainViewController, else go to loginViewController. Also you can check internet connection here and advice user to connect to internet.

Upvotes: 1

satheesh
satheesh

Reputation: 2834

You cannot hold the old view controller to present, but instead you can present a view controller with black screen and then after you got the response form the server about the session you could present the view controller based on your needs.

Upvotes: 0

mbelsky
mbelsky

Reputation: 6608

  1. Uncheck Is initial View Controller checkbox for a controller in Main.storyboard
  2. Initialize appDelegate's window property: appDelegate.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].bounds];
  3. Set rootViewController: appDelegate.window.rootViewController = controller;
  4. And call makeKeyAndVisible method: [appDelegate.window makeKeyAndVisible];

Upvotes: 1

Related Questions