I'm working on an iOS5 app using storyboard, and I have a method in a view controller class that i'd like to access from the App Delegate. The trouble is, this view controller gets instantiated via a tab bar controller in storyboard, so the App Delegate has no direct way of calling the method I want...
For a view controller to get in touch with the App Delegate, all one has to do is use:
MyAppDelegate *appDelegate = (MyAppDelegate *)[[UIApplication sharedApplication] delegate];
Is there a similarly easy way of pointing to an already-instantiated view controller or class?
Thanks to Jerry (above), here's the code that got me what I wanted:
UINavigationController *navigationController = (UINavigationController *)self.window.rootViewController;
MasterViewController *result;
//check to see if navbar "get" worked
if (navigationController.viewControllers)
//look for the nav controller in tab bar views
for (UINavigationController *view in navigationController.viewControllers) {
//when found, do the same thing to find the MasterViewController under the nav controller
if ([view isKindOfClass:[UINavigationController class]])
for (UIViewController *view2 in view.viewControllers)
if ([view2 isKindOfClass:[MasterViewController class]])
result = (MasterViewController *) view2;
}
I probably would do it in reverse. Create a method in AppDelegate call registerViewController or something. In every ViewController, call the method with itself with a name. Then in AppDelegate, you can do whatever you want afterward. It is messy to do all sort of drill
In AppDelegate
- (void)registerViewController:(NSString *)name controller:(UIViewController *)controller
{
if(_viewControllers == nil)
{
_viewControllers = [[NSMutableDictionary alloc] init];
}
[_viewControllers setObject:controller forKey:name];
}
In any ViewController
- (void)viewDidLoad
{
[super viewDidLoad];
AppDelegate *appDelegate = [[UIApplication sharedApplication] delegate];
[appDelegate registerViewController:@"feelings" controller:self];
}
In AppDelegate
XViewController *vc = (XViewController *)[_viewControllers objectForKey:@"X"];
[X startSpinner];
Hope this help
BS
You'll have to traverse the view hierarchy from the app delegate. Assuming the AppDelegate
holds a reference to the UITabBarController
, you could use the viewControllers
property or selectedViewController
property to get to your view controller.
If you are using a storyboard, and you want instance of a viewController in storyboard you can use the following
UIStoryboard *mystoryboard = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
id viewcontroller = [mystoryboard instantiateViewControllerWithIdentifier:@"identifier"];
Here the 'identifier' is the name provided in the particular viewController's 'storyBoard ID' in 'Identity' section in 'Identity Inspector'.
I have a better solution. You can use window.rootViewController.storyboard
to get a reference to the storyboard of that view.
In the AppDelegate, you could simply use indexes to access the controllers via UITabBarController:
UITabBarController *tabBarController = (UITabBarController *)self.window.rootViewController;
firstViewController = [[tabBarController viewControllers] objectAtIndex:0];
secondViewController = [[tabBarController viewControllers] objectAtIndex:1];
thirdViewController = [[tabBarController viewControllers] objectAtIndex:2];
Naturally, this will get messed up if you change the ordering of the tab bar. Also, if you're looking for a controller deeper in the hierarchy, you need to do a bit more legwork.
Swift
This is the Swift version of @infiniteLoop's answer.
let storyboard = UIStoryboard(name: "Main", bundle: nil)
let myViewController = storyboard.instantiateViewControllerWithIdentifier("identifier") as! MyViewController
You need to replace the storyboard name, view controller name, and view controller identifier with whatever you used in your project.
Related tasks
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.