Pushing Tabbarcontroller from a UIViewController - iphone

i`m wondering if its possible to push a TabbarController from UIViewController ?
what i want to do is:
when the user opens the app it shows a View with two buttons to select the language he want, this view does not contain anything except the two buttons, no tab bar, no navigation bar.
after selecting the preferred language it should push a tab bar view with 5 tabs in it. each tab contain a tableview controller.
is it possible ? if yes please explain how to do it i`m little bit new for this :)
thank you in advance :)

Well you can add it as subview to UIWindow of your app delegate. You have to make a property UIWindow of your AppDelegate class.
Now When in your UIViewController button is pressed, do something like this:
- (void) buttonPressed:(id)sender{
AppDelegate *delegate = (AppDelegate *)[UIApplication sharedApplication].delegate;
UITabBarController *tab = [UITabBarController youWayOfInitializingIt];
[delegate.window addSubview: tab.view];
}

Sure, just present an UITabBarController from the UIViewController using presentModalViewController.

I would try dragging out two different tab bar view controllers, one for each of your languages. Ctrl-drag each button on your UIViewController to its respective language's tab bar view controller and choose the type of transition you want. However, if you want to use the push transition I suggest embedding the original UIViewController in a navigation controller. You can do this by clicking on the UIViewController and then...
Editor --> Embed in ---> Navigation Controller
This will provide you with a navigation bar and a back button if the user wants to go back and change the language.

Related

how to use toolbar to connect two view controller

have two view controller(FirstViewController,sixViewController),i create a toolbar button in the navigation bar using interface builder,when i press the toolbar button it should direct me to sixViewcontroller,in the sixViewcontroller i have back button to return firstviewController with slide in animation,my toolbar name is Item.help need guys coz I'm still new for iOS.
UIViewController *viewController6 = [[sixViewController alloc]initWithNibName:#"FourthViewController" bundle:nil];
UIViewController *viewController5 = [[FifthViewController alloc]initWithNibName:#"FifthViewController" bundle:nil];
Sounds like you would be much better off using a NavigationController which handles placing the navigation bar and managing the viewController stack automatically.
The UINavigationController class reference is a good place to start
http://developer.apple.com/library/ios/#documentation/uikit/reference/UINavigationController_Class/Reference/Reference.html

How to make an method change the root view

My app is structured like this:
- Window
- Navigation controller
- Table view
- Button (in one of the rows)
- Tab bar controller
- tab..
- tab..
- tab..
(The tab bar controller isn't added as a sub view so it can't be seen)
How would you make the button able to manipulate the Navigation controller and tab bar controller objects?
Well you could have them as properties in your AppDelegate like this:
#property (nonatomic, retain) UINavigationController *navigationController;
#property (nonatomic, retain) UITabBarController *tabBarController;
And than in your table view you can get a pointer to them like this:
UINavigationController *navigationController = [(YourAppDelegateClass *)[[UIApplication sharedApplication] delegate] navigationController];
UITabBarController *tabBarController = [(YourAppDelegateClass *)[[UIApplication sharedApplication] delegate] tabBarController];
After this you can have your button do whatever you want to them. Let me know if this works for you.
Your description is not accurate. Both UITabbarController and UINavigationController are controllers of multiple view controllers. So, in your structure, you should add a UITableViewController between "Navigation controller" and "Table view".
According to Apple's View Controller Programming Guide for iOS, you can assign both view controllers or tab bar controllers to the items to be controlled by a tab bar controller.
Thus, you could have this structure:
- Window
- Tabbar Controller
-Navigation Controller
- Table View Controller
- Table view
- Button
- tab (another View Controller)
- tab
- etc.
You can hide the UITabbar when the table view is visible.
You could then access everything the way you would expect: from the UITableViewController it would work with self.navigationController, or self.tabbarController.
Given this description of what you would like to do:
The navigation controller is showing at the moment (its a login screen). I'd like to hide it and add the Tab bar controller as a subview
I think that you do not really need that the button has got references to the navigation controller and to the tab bar.
You can define a method in your app delegate that you can access directly from the button, like this:
[[(MyAppDelegate*)[[UIApplication sharedApplication].delegate] doSwapNavAndTabBar];
the app delegate is the most natural point to do this, since it is in a way "responsible" for the window object where you want to do the swap.
If the tab bar that you want to show depends in some way from the button, then I would suggest to pass the button reference as an argument to that method:
[[(MyAppDelegate*)[[UIApplication sharedApplication].delegate] doSwapNavAndTabBar:button];
as it is usually done to manage events generated through controls. The app delegate can then ask the button for the information necessary to decide on which tab bar to show or how to initialize it.

View before Tab Bar View

I have TabBar View combined with Navigation View.
Structure like this:
delegate -> TabBar -> (many) Navigation Views -> (many for each) Controller Views.
I want show one view (config) before any other view. I want this view without Bars and Navigation Controlls.
It is possible? How I can do this ?
Thanks for help
Yes, It's very possible. In your applicationDidFinishLaunching method, simply make your config view the root view controller like this:
UIViewController *configVC = [[ConfigVC alloc] initWithNibName:#"ConfigVC" bundle:nil];
[[self window] setRootViewController:configVC];
[configVC release];
and then, some later time when you are ready to show the tab bar, do:
[[self window] setRootViewController:tabBarViewController];
UPDATE:
You can access the application delegate like this: [[UIApplication sharedApplication] delegate];
After this, you can cast it to your app delegate to avoid any warnings, and then call the method that loads the tab bar...
As far as i can understand, you have a tabbar based application and you want to display a view in the start of your application, You can just display that page as modalviewcontroller and hide navigationbar and status bar.

Switching Views within UITabBar View

I have created an UITabView application. Each view selected from the bar is a seperate controller with own nib file. I switch between them succesfully.
In the first view I have two buttons (check out the screenshot). When clicking them I want to switch to another views which are the parts of the current view controller. I use:
[self presentModalViewController:anotherViewController animated:NO];
That switches the view, but hides the UITabBar. How to keep the bar on the screen after the switch?
P.S. Sorry for the blurred image. I am not allowed to share to much info.
Well I think you are misusing the modal view controller. For a problem like this I'll say you should put them in a view controller stack using UINavigationController. Instead of making each tab a UIViewController make it a UINavigationController, then you can push and pop view controllers on it, which still show the tab bar.
See http://developer.apple.com/iphone/library/documentation/UIKit/Reference/UINavigationController_Class/Reference/Reference.html
use: tabBarController.selectedViewController = newViewController
edit: UINavigationController is not needed here.

Tab bar controller inside a navigation controller, or sharing a navigation root view

I'm trying to implement a UI structured like in the Tweetie app, which behaves as so: the top-level view controller seems to be a navigation controller, whose root view is an "Accounts" table view. If you click on any account, it goes to the second level, which has a tab bar across the bottom. Each tab item shows a different list and lets you drill down further (the subsequent levels don't show the tab bar).
So, this seems like the implementation hierarchy is:
UINavigationController
Accounts: UITableViewController
UITabBarController
Tweets: UITableViewController
Detail view of a tweet/user/etc
Replies: UITableViewController
...
This seems to work[^1], but appears to be unsupported according to the SDK documentation for -pushViewController:animated: (emphasis added):
viewController: The view controller that is pushed onto the stack. It cannot be an instance of tab bar controller.
I would like to avoid private APIs and the like, but I'm not sure why this usage is explicitly prohibited even when it seems to work fine. Anyone know the reason?
I've thought about putting the tab bar controller as the main controller, with each of the tabs containing separate navigation controllers. The problem with this is that each nav controller needs to share a single root view controller (namely the "Accounts" table in Tweetie) -- this doesn't seem to work: pushing the table controller to a second nav controller seems to remove it from the first. Not to mention all the book-keeping when selecting a different account would probably be a pain.
How should I implement this the Right Way?
[^1]: The tab bar controller needs to be subclassed so that the tab bar controller's navigation item at that level stays in sync with the selected tab's navigation item, and the individual tab's table controller's need to push their respective detail views to self.tabBarController.navigationController instead of self.navigationController.
The two previous answers got it right - I don't use UITabBarController in Tweetie. It's pretty easy to write a custom XXTabBarController (plain subclass of UIViewController) that is happy to get pushed onto a nav controller stack, but still lives by the "view controller" philosophy. Each "tab" on the account-specific view (Tweets/Replies/Messages) is its own view controller, and as far as they are concerned they're getting swapped around on screen by a plain-ol UITabBarController.
I'm building an app that uses a similar navigation framework to Tweetie. I've written a post about how to do this on my blog www.wiredbob.com which also links to the source code. It's a full template you could take and use as a basis for another project. Good luck!
It's possible to add a UITabBar to any UIViewController. That way you don't actually have to push a UITabBarController and therefore stay within the guidelines of the Apple API.
In interface builder UITabBar is under "Windows, Views & Bars" in the Cocoa Touch Library.
I do this in a couple of my apps. The trick to adding a tab bar to a navigationController based app is to NOT use a TabBarController. Add a Tab Bar to the view, make the view controller for that view a TabBarDelegate, and respond to user selections on the tab bar in the code of the view controller.
I use Tab Bars to add additional views to the Tab Bar's view as sub-views, to reload a table view with different datasets, to reload a UIPickerView, etc.
I was struggling for the past hour to implement a UITabBar because it would get hidden when I tried to display my view; then I found this post:
Basically, make sure you insert your new view below the tabbar, per this line of code:
[self.view insertSubview:tab2ViewController.view belowSubview:myTabBar];
In my app, the root view controller is a UINavigation controller. At a certain point in the app, I need to display a UITabBar. I tried implementing a UITabBar on a UIView within the navigation hierarchy, as some of the previous posts suggested, and this does work. But I found that I wanted more of the default behavior that the tab controller provides and I found a way to use the UITabBarController with the UINavigation controller:
1) When I want to display the UITabBarController's view, I do this:
MyAppDelegate *appDelegate = [[UIApplication sharedApplication] delegate];
appDelegate.window.rootViewController = myUiTabBarControllerInstance;
2) When I want to return to where I was in the navigation hierarchy, I do this:
appDelegate.window.rootViewController = myNavControllerInstance;
This could be achieved by simply embedding the TabBarController in the Navigation Controller.
In the storyboard:
Drag a ViewController
Click on the ViewController's Scene
Click on editor >> Embed in >> Navigation Controller.
Drag a button on the same ViewController.
Drag a TabBarController
Connect the button on the ViewController to the TabBarController via push Segue Action.
In this case only the TabBarController's RootViewController would be in the Navigation Controller's stack. All The TabBarItems would have the Navigation Bar at the top and user can go to Home Screen at any time, irrespective of the selected TabBarItem
This could be done at any ViewController in the Navigation Controller's stack.
If it works, please suggest me how to increase the reputation so that I can post the images and the code in the next answer. :)
This is how i did it. This is actually pushing a tabbarcontroller onto navigation controller. It works fine. I didn't find anywhere in the documentation that apple doesn't support this way. Can someone give me link to this warning?
If this is truth, is it possible that apple refuses to publish my app to appstore?
-(void)setArrayAndPushNextController
{
MyFirstViewController *myFirstViewController = [[MyFirstViewController alloc] init];
MySecondViewController *mySecondViewController = [[MySecondViewController alloc] init];
myFirstViewController.array = self.array;
NSArray *array = [[NSArray alloc] initWithObjects:myFirstViewController, mySecondViewController, nil];
UITabBarController *tab = [[UITabBarController alloc] init];
tab.viewControllers = array;
[array release];
UITabBarItem *item1 = [[UITabBarItem alloc] initWithTitle:#"first title" image:nil tag:1];
UITabBarItem *item2 = [[UITabBarItem alloc] initWithTitle:#"second title" image:nil tag:2];
myFirstViewController.tabBarItem = item1;
mySecondViewController.tabBarItem = item2;
[self stopAnimatingSpinner];
[self.navigationController pushViewController:tab animated:YES];
[tab release];
[item1 release];
[item2 release];
}
I wrote a blog post on how I approached this problem. For me, using a modal view was a simpler solution than writing a custom tab-bar implementation.
http://www.alexmedearis.com/uitabbarcontroller-inside-a-uinavigationcontroller/