Get index of tabBar touched - iphone

How can i get the index of the tabBar when i touch a tab?
I´ve extended my class to < UITabBarController > and added the method
- (void)tabBarController:(UITabBarController *)tabBarController
didSelectViewController:(UIViewController *)viewController
{
if (viewController == tabBarController.moreNavigationController)
{
tabBarController.moreNavigationController.delegate = self;
}
}
But that method isn´t triggered when i touch a tab item.
What should i do?

UITabBarController has a property selectedIndex that you can use to find the selected tab.
More information about the UITabBarController can be found here
Also be sure to set the delegate property of your UITabBarController, otherwise the delegate messages (such as didSelectViewController:) will not be received.

Did you set the delegate of the UITabBarController to your delegate class when you create it?

Related

tab bar click delegate

I have two view controllers (FirstViewController and SecondViewController) and a Tab Bar Controller and I'm using Storyboards. In the FirstViewController user can drag and drop an imageview. So every time a user clicks on the second TabBarItem which displays the SecondViewController I would like to check if the user has dropped the image or not every time she clicks the TabBarItem.
So I understand that this can be done with UITabBarDelegate and with its method -(void)tabBar:(UITabBar *)tabBar didSelectItem:(UITabBarItem *)item. But I'm doing something wrong because the method isn't called and I believe this is because I can't set the delegate properly. So I want the SecondViewController to be the delegate for TabBarController.
So in my SecondViewController.h I have the following
#interface SecondViewController : UIViewController<UITabBarDelegate>
And in SecondViewController.m I have
-(void)tabBar:(UITabBar *)tabBar didSelectItem:(UITabBarItem *)item {
NSLog(#"%#", item);
}
- (void)viewDidLoad
{
[super viewDidLoad];
self.tabBarController.delegate = self;
}
But nothing happens and when setting the delegate I also get a compiler warning: Assigning to 'id' from incompatible type 'SecondViewController *const __strong'
Please be gentle with me, this is my first app and the first time I'm trying to use delegates.
Add the following code to any of the view controllers
UITabBarController *tabBarController = (UITabBarController*)[UIApplication sharedApplication].keyWindow.rootViewController ;
[tabBarController setDelegate:self];
// add any delegates methods to your class
-(void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController {
NSLog(#"%#", tabBarController);
}
-(void)tabBar:(UITabBar *)tabBar didSelectItem:(UITabBarItem *)item;
This method is a delegate method for UITabBar, not UITabBarController, so
self.tabBarController.delegate = self;
will not work.
Tab bar controller has its own UITabBar, but changing the delegate of a tab bar managed by a tab bar controller is not allowed, so just try UITabBarControllerDelegate method like this:
- (void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController
NSLog(#"%#", item);
}
For more detail check info
Thanks
I imported and implemented the following. Hope it helps.
- (void)tabBar:(UITabBar *)tabBar didSelectItem:(UITabBarItem *)item
{
if (_mainTab.selectedItem.tag == 1) {
NSLog(#"TAB 1");
}
else if (_mainTab.selectedItem.tag == 2) {
NSLog(#"TAB2");
}
else if (_mainTab.selectedItem.tag == 3)
{
NSLog(#"TAB3");
}
else
{
NSLog(#"TAB NOT WORKING");
}
}
You are using the wrong delegate protocol UITabBarDelegate is usually used for customizing the UITabBar objects. You need to use UITabBarControllerDelegate protocol in order to check if a tab is selected or customize the behavior of tabs.
You should implement UITabBarControllerDelegate protocol instead and use this delegates callback to track selection:
tabBarController:didSelectViewController:
Next thing is, that you should initialize delegate before it will be called. ViewDidLoad will be called after tabbarcontroller will try to talk to delegate.
In order to get rid of the compiler warning your SecondViewController should conform to the UITabBarControllerDelegate protocol instead of the UITabBarDelegate protocol.
#interface SecondViewController : UIViewController<UITabBarControllerDelegate>

iOS - is it possible to select view for a uitabbar at runtime?

I am assigning my view controller to my tab right after I create it. Is it possible to select the view that will show after the tab is clicked?
For eg
//user clicks tab 1
if(hasMessages)
//show view A
else
//show view B
Yes, it is possible. You need to set a delegate for your tab controller:
UITabBarController *tabBarController = (UITabBarController *)self.window.rootViewController;
tabBarController.delegate = self; // or whatever suitable class you have
This delegate needs to conform to the UITabBarControllerDelegate protocol.
In your delegate, implement tabBarController:didSelectViewController: and inside it, find out which view you want to present. Assuming your tab's root view controller is a navigation controller, then the delegate method implementation would be something like this:
- (void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController {
/* logic goes here */
[viewController pushViewController:someNewVC animated:YES];
}

iphone app - how to detect which tab bar item was last pressed [duplicate]

i have a tab bar based application, with more than 5 tab bar items - so i get 4 of them directly showing in the view and the rest available by selecting the "More" tab. When a tab bar item is pressed, i want to detect which one was it.
So, in the
- (void)tabBarController:(UITabBarController *)tabBarCtrl didSelectViewController:(UIViewController *)viewController method, i use tabBarCtrl.selectedViewController.title to get the item's title.
This works for the tabs visible in the view -that is the 4 first and the "More" tab- but does not work for the rest of my tab bar items which are shown in the list after pressing the "More" tab.
I can see that the didSelectViewController method is not even called when selecting a tab from the "More" list.
How can i detect any of them when pressed?
Thank you in advance.
How to get title of UITabBarItem in the More section?
- (void)tabBarController:(UITabBarController *)tabBarController
didSelectViewController:(UIViewController *)viewController
{
NSLog(#"controller class: %#", NSStringFromClass([viewController class]));
NSLog(#"controller title: %#", viewController.title);
if (viewController == tabBarController.moreNavigationController)
{
tabBarController.moreNavigationController.delegate = self;
}
}
You can access the index of selected item by using following code in your UIViewController. It will always return yout tab's index.
self.tabBarController.selectedIndex;
So if you have e.g. 6 items you can go to the "More..." tab, select your "5th" item and selectedIndex will be 4. If you go to the More tab and select 6th item, it'll return 5.
EDIT: If you want to check current position of some UITabBarItem you can do this:
Firstly, in your XIB file you should edit the tag property of each tab, so that 1st tab will have tag = 100, 2nd - 200, 3rd - 300, etc.
Then in ViewController add this code:
UIViewController *selectedVC = [self.tabBarController.viewControllers objectAtIndex:self.tabBarController.selectedIndex];
int selectedItemTag = selectedVC.tabItem.tag;
Then you can determine what viewController is it by using selectedItemTag variable. In this case, you can determine selectedIndex by doint this: selectedIndex = (selectedItemTag-100)/100.
The tag properties are not changed when customizing your UITabBar, so you can trust them :)
You can detect when a tab has been pressed using the UITabBarDelegate methods: http://developer.apple.com/library/ios/#documentation/uikit/reference/UITabBarDelegate_Protocol/Reference/Reference.html#//apple_ref/occ/intf/UITabBarDelegate
You can make your UITabBarController class be the delegate and add the method in the implementation:
- (void)tabBar:(UITabBar *)tabBar didSelectItem:(UITabBarItem *)item
{
NSLog(#"tab selected: %#", item.title);
}
1. So if you are using a UITabBarController you can make the class implement the UITabBarControllerDelegate and set your UITabBarController delegate to the class that needs to be notified when the TabBar selected item changes, then add the delegate method to your class:
-(void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController
Inside this method you can use the UITabBarController selectedIndex property to know which is the current index selected:
-(void)tabBarController:(UITabBarController *)tabBarController didSelectViewController: (UIViewController *)viewController
{
NSLog(#"Selected index: %d", tabBarController.selectedIndex);
}
2. If you are not using just the UITabBar you can follow the answer here by Ken Pespisa and iCoder in this post Ken Pespisa and iCoder in this post.
Since you add tags to your EVERY UITabBarItem (even those with index 5 and more).
You can track what tab was selected using following code:
//MARK: - UITabBarControllerDelegate
func tabBarController(tabBarController: UITabBarController, didSelectViewController viewController: UIViewController) {
if viewController == tabBarController.moreNavigationController {
tabBarController.moreNavigationController.delegate = self
} else {
setSelectedTabBarOption()
}
}
//MARK: - UINavigationControllerDelegate
func navigationController(navigationController: UINavigationController, willShowViewController viewController: UIViewController, animated: Bool) {
setSelectedTabBarOption()
}
private func setSelectedTabBarOption() {
if let viewControllers = viewControllers {
let selectedController: UIViewController? = viewControllers.count > selectedIndex ? viewControllers[selectedIndex] : nil
if let tag = selectedController?.tabBarItem.tag {
//do whatever with your tag
}
}
}
- (void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController
{
NSLog(#"Selected index: %d", tabBarController.selectedIndex);
if (viewController == tabBarController.moreNavigationController)
{
tabBarController.moreNavigationController.delegate = self;
}
NSUInteger selectedIndex = tabBarController.selectedIndex;
switch (selectedIndex) {
case 0:
NSLog(#"click tabitem %u",self.tabBarController.selectedIndex);
break;
case 1:
NSLog(#"click me again!! %u",self.tabBarController.selectedIndex);
break;
default:
break;
}
}
If you're using a tab bar controller, you should avoid knowing about the mapping between tab items and view controllers -- that's the job of the tab bar controller. If you're trying to use a tab bar for something else, then you should use UITabBar directly and not use UITabBarController. If you use UITabBar, you can set your own object as the tab bar's delegate, and the delegate will then get messages whenever the selected item changes.

Determining which UIViewController subclass that a UITabBar Item belongs to

I have a UITabBarController instansiated in my appDelegate, but I need a way to know when the user presses the different tab bar items (buttons on the tab bar).
-UITabBarDelegate protocol to the rescue (with the required didSelectViewController-method)!
With everything wired up in Interface Builder, how do I obtain a reference to the actual UIViewController subclass instance that corresponds to this tab bar item that was pressed?
I need this reference because I need to call a method in one of my UIViewControllers subclasses every time that tab bar item is pressed.
Any suggestions?
- (void)tabBarController:(UITabBarController *)theTabBarController didSelectViewController:(UIViewController *)viewController
{
NSLog(#"%#", [[self.tabBarController selectedViewController] nibName]); // nil, no success here
if ([theTabBarController selectedIndex] == 1) {
MySecondViewController *reference = (MySecondViewController *) viewController;
if ([reference isKindOfClass:[UINavigationController class]]) {
NSLog(#"OMG. It's a UINavigationController class??!"); // kicks in for some reason, shouldn't reference be a MySecondViewController
}
}
Possibly I am not understanding your question correctly, but it seems that what you're asking for is simply the "viewController" parameter which is passed into the method call you've mentioned
- (void)tabBarController:(UITabBarController *)theTabBarController didSelectViewController:(UIViewController *)viewController
UITabBarController also has a property to get the same info
#property(nonatomic, assign) UIViewController *selectedViewController

TabBarController delegate is not working

Can any one help me,
when i am using my UITabBarController delegate it is not working..
I called a delegate method like this..
- (void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController
{
[self.navigationController popToRootViewControllerAnimated:NO];
}
If what you're doing is subclassing a UITabBarController, then... oddly enough... you can get it working by setting itself as a delegate:
- (void)viewDidLoad
{
[super viewDidLoad];
self.delegate = self;
}
Then the didSelectViewController action will fire normally:
- (void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController {
NSLog(#"View Changed");
}
Don't forget to add your UITabBarControllerDelegate class to your .h file:
#interface MyTabBarController : UITabBarController <UITabBarControllerDelegate>
#end
If you are using tab bar customizing by extending UITabBarController and trying to change tab bar selected index programmatically then it will not call delegates.
Please see the note inside "UITabBarDelegate":
// Note: called when a new view is selected by the user (but not programmatically)
This might help you
-(void)applicationDidFinishLaunching:(UIApplication *)application {
tabBarController.delegate=self;
// Add the tab bar controller's current view as a subview of the window
[window addSubview:tabBarController.view];
}
specify
UITabbarcontrollerDelegate in .h file
then
-(void)applicationDidFinishLaunching:(UIApplication *)application {
tabBarController.delegate=self;
// Add the tab bar controller's current view as a subview of the window
[window addSubview:tabBarController.view];
}
Read the documents to get a deeper understanding of the relationships between navigation controllers, tabBar controllers, and the view and navigation hierarchy.
Then review the code you've provided. Which view/controller is the container? You are popping the navigationController of self, which is not the same as the tabBarController. I don't think you actually need this method if you are looking to switch between tabs.
Try commenting out this method. It is an optional method in the UITabBarController delegate protocol. If you comment it out, you should get the default behavior of the tab controller, which should be to select the appropriate viewController and switch to the new view.
You typically only need to use this method if you want some action taken as you switch between view controllers.