Can I make a UITabBarController switch tabs programmatically? - ios

I have a UITabBarController template based app where the first tab is a UITableViewController with custom buttons in the cells. I need one button in one cell to call a specific tab in the parent UITabBarController. Im using this code in the didSelectRowAtIndexPath:
case 5:
NSLog(#"Search");
[tableView deselectRowAtIndexPath:indexPath animated:YES];
// Get UITabBar instance and send it message
UITabBarController *tabBar = (UITabBarController*)[self parentViewController];
[tabBar setSelectedIndex:1];
break;
When I tap on this row the app crashes without any log in the console. Im calling this in that UITableViewController which is the first tab in the UITabBarController.
PS I also want to avoid the blue selection on this cell that occurs when the user taps. So I added this code:
- (NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath{
switch (indexPath.row) {
case 1:
return nil;
break;
}
}
But it still selects blue when I tap on it. Could they be related issues?

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
[tableView deselectRowAtIndexPath:indexPath animated:NO];
UITabBarController *tabController = (UITabBarController *) UIApplication.sharedApplication.keyWindow.rootViewController;
[tabController setSelectedIndex:1];
}
the first message will deselect the row, avoiding the blue selection.
As your app is tab-based, the root controller of the key window is always an instance of UITabBarController.

Related

How can I push a new view when detail button is presses

I have a tableView. My tableView cells do have a detail accessory.
My question: How can I push another view controller when the detail button is presses.
When I normally press the cell, my ViewController1 opens. But when I tap on the little i on the right of the cell, I want to push a different view controller.
How can I do this?
it is just like DidSelectRow u need to modify DidSelectRow to accessoryButtonTappedForRowWithIndexPath
-(void)tableView:(UITableView *)tableView accessoryButtonTappedForRowWithIndexPath:(NSIndexPath *)indexPath
{
// if u using .Xib
yourviewcontrollerName *vie=[[yourviewcontrollerName alloc]init];
[self.navigationController pushViewController: vie animated:YES];
//// if u using storyboard
[self performSegueWithIdentifier:#"yoursequeName"
sender:self];
}
you need more information use this link Pushing to a Detail View from a Table View Cell using Xcode Storyboard
Use this code it works
-(void)tableView:(UITableView *)tableView accessoryButtonTappedForRowWithIndexPath:(NSIndexPath *)indexPath
{
// Push new View controller here
UIViewController *objVc=[[UIViewController alloc]init];
[self.navigationController pushViewController:objVc animated:YES]
}

deselectRowAtIndexPath issue

I have just started working with tableViews, and I have 5 cells in a tableview in a viewController embedded in a navigationController. When a cell is pressed another view is pushed in. My problem is that the cell I press is selected but the selection doesn't go away. I have tried with this code:
- (void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath
{
[self.tableView deselectRowAtIndexPath:indexPath animated:NO];
NewViewController *newViewController = [[NewViewController alloc] init];
newViewController.theTitle = [self.tableView cellForRowAtIndexPath:indexPath].textLabel.text;
[self.navigationController pushViewController: newViewController animated:YES];
}
The tableView is initialized in the viewDidLoad method. Still when I click a cell the new viewController is pushed in but the cell stays selected. What might be the issue here?
You've put your code in the didDeselectRowAtIndexPath - put it in the didSelectRowAtIndexPath. This is an easy mistake to make since didDeselect comes up in code completion before didSelect.
Summary :
You have tableview that is in a ViewController that is in a NavigationController
Use touch a cell
A new ViewController is push on the NavigationController Stack
User hit back and goes back to the screen where you have a tableView
That is what I understand from your question.
At this moment the cell in your tableView should still be selected in order for the user to have a reminder of the last action he as done, but you also want it to get unselected animated at the point ( the mail application is a good example of this behaviour).
So the best place to deselect the cell in your tableView is in - (void)viewDidAppear:(BOOL)animated method of the UIViewController that have the tableview inside it's view. By doing so you will let the user a chance to see the selection before it gently fade away like in mail.
- (void)viewDidAppear:(BOOL)animated
{
[super viewDidAppear:animated];
[self.tableView deselectRowAtIndexPath:[self.tableView indexPathForSelectedRow] animated:animated];
}
You can pass nil as argument of deselectRowAtIndexPath, tableView handles it gracefully.
Did you also implement tableView:didSelectRowAtIndexPath:? This method is called every time you tap a cell. So you should put your code there.
The method you are using, tableView:didDeselectRowAtIndexPath: is called whenever a cell is selected and you are tapping a different cell.
I think your problem is that you use wrong method. Change didDeselectRowAtIndexPath to didSelectRowAtIndexPath.

Show Navigation Bar At The End of A TableView

The navigation bar is not displayed at the end of the tableview. What am I doing wrong?
- (void)tableView:(UITableView *)tableView didEndDisplayingCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath {
if([indexPath row] == [tableView numberOfRowsInSection: 0] - 1){
[self.navigationController setNavigationBarHidden:NO
animated:YES];
DDLogVerbose(#"Reached end of tableview");
}
}
The "Reached end of tableview" is outputted to Xcode, but the navigation bar (previously hidden), does not re-appear.
I have also tried using willDisplayCell but that shows the navigation bar too early, just before the last cell is on screen, this is not ideal.
Why does the navigation bar not re-appear at the end of the tableview, even though the if statement is entered? What should I do to make it re-appear?
Update: Great answers everyone, although I'd also appreciate if someone could possibly explain to me, why the above code does not work. Thanks!
UITableView is a UIScrollView, so you can use its scrollViewDidScroll: delegate method to decide, based on its contentOffset vs. contentSize, to show or hide just about anything.
Well it's not the best solution, but you could try adding another row (dummy row at the end), then when willDisplayCell for that row gets called, you should the navigation bar, hiding the dummy row.
In view didLoad set navigation bar hidden
[self.navigationController setNavigationBarHidden:YES animated:NO];
And then check this method works or not
-(void) tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
{
if([indexPath row] == ((NSIndexPath*)[[tableView indexPathsForVisibleRows] lastObject]).row){
[self.navigationController setNavigationBarHidden:NO animated:YES];
}
}
- (void)scrollViewDidScroll:(UIScrollView *)scrollView
{
float offs = (scrollView.contentOffset.y+scrollView.bounds.size.height);
float val = (scrollView.contentSize.height);
if (offs==val)
{
// Code
}
}
May this help you .

iOS: How to keep selected/check marked cells in UITableView to stay after navigating back and forth in UINavigationController?

I have tab bar in which one tab has a UINavigationController that is assigned a root view controller which consists of a UITableView that drills down to more choices. After i select an item in my root view controller i am given another uitableview and i use the following to assign only one checkmark to that section or group using the following code in my
cellForRowAtIndexPath.
if([self.checkedIndexPath isEqual:indexPath])
{
cell.accessoryType = UITableViewCellAccessoryCheckmark;
}
else
{
cell.accessoryType = UITableViewCellAccessoryNone;
}
and the following in didSelectRowAtIndexPath:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
// Uncheck the previous checked row
if(self.checkedIndexPath)
{
UITableViewCell* uncheckCell = [tableView
cellForRowAtIndexPath:self.checkedIndexPath];
uncheckCell.accessoryType = UITableViewCellAccessoryNone;
}
UITableViewCell* cell = [tableView cellForRowAtIndexPath:indexPath];
cell.accessoryType = UITableViewCellAccessoryCheckmark;
self.checkedIndexPath = indexPath;
[tableView deselectRowAtIndexPath:indexPath animated:YES];
}
My Problem is that when i use the back button on my navigation menu and go back to the same UItableview, the checkmark disappears. however this is not the case when i scroll up and down in that view. How do i keep those checkmarks there when i go back and forth using my navigation controller.
I believe you're having this issue because you are pushing a new UIViewController instance whenever you go back and forth - the new instance doesn't know what the previous checkedPath property was.
To solve this you need to either:
Persist the checked row value somehow (NSUserDefaults, CoreData, etc..). This way any instance would get the same checked row value
Re-use the same view controller when pushing.

UITableView in UIPopover hides content while displaying keyboard

I have a UITableView embedded in a UIPopoverController, as shown below.
When I select a cell, the textField in the cell becomes firstResponder. But instead of keeping the tableview scrolled to the top, all content goes away (even though there are no more than 4 cells). It is impossible to scroll to the top will this happens. After dismissing the keyboard everything is normal again.
The following code does not resolve the problem:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
CRShoppingListItemCell *cell = (CRShoppingListItemCell *) [tableView cellForRowAtIndexPath:indexPath];
cell.itemTextField.enabled = YES;
cell.itemTextField.delegate = self;
[cell.itemTextField becomeFirstResponder];
[tableView scrollToNearestSelectedRowAtScrollPosition:UITableViewScrollPositionNone animated:YES];
[tableView deselectRowAtIndexPath:indexPath animated:YES];
}
My guess is you aren't using the UITableViewController. Inside that controller's viewWillAppear it checks for isInViewControllerThatHandlesKeyboardAvoidance (private) and one of those controllers is the popover controller. So if it is that then the keyboard avoiding behaviour you would usually want when the table is full screen is turned off.

Resources