When I use
tableView:didSelectRowAtIndexPath / popViewControllerAnimated
it does not work. I push the view controller by another view but when I select a row, it highlights in gray instead of immediately popping to the original view controller. But when I tap another row, it selects the first row I tapped and then goes back to the original view controller.
Here is the code:
- (void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
cell.accessoryType = UITableViewCellAccessoryCheckmark;
NSArray *allTypes = [[ItemStore sharedStore] allTypes];
NSManagedObject *raum = allTypes[indexPath.row];
self.an.leben = raum;
[self.navigationController popViewControllerAnimated:YES];
}
Any ideas?
Replacde didDeselectRowAtIndexPath with didSelectRowAtIndexPath.
The delegate method you have written is didDeselectRowAtIndexPath instead of didSelectRowAtIndexPath.
According to apple, tableView:didDeselectRowAtIndexPath:
Tells the delegate that the specified row is now deselected.
and
tableView:didSelectRowAtIndexPath:
Tells the delegate that the specified row is now selected.
So, what is happening is, when you click on a row, it becomes selected and turns gray and then when you click on the same or any other row, the previous one gets deselected because only one row is selected at once and hence calls this method to open the next view controller with the previous tapped row.
Change tableView:didDeselectRowAtIndexPath into tableView:didSelectRowAtIndexPath.
Related
I'm trying to connect two view controller into a one controller. As you can see below picture, when "plus" item is tapped the screen came and it works well. However, the other segue doesn't work properly. With my first tapping to any row, it doesn't take me to the view but after first tapping it starts taking me to the view as I wanted. I couldn't figure out why it doesn't take me to when I firstly tap any row. Here is the didSelectRowAtIndexPath code:
- (void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath{
DovizDetailViewController *detail = [self.storyboard instantiateViewControllerWithIdentifier:#"detail"];
[self.navigationController pushViewController:detail animated:YES];
}
Below is my storyboard. The problem is about with the above view and it's segue.
Hope you can help me.
Thanks!
Change didDeselectRowAtIndexPath to didSelectRowAtIndexPath
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.
EDIT: I have fixed this problem. The code is corrected to show this fix.
I have an app that uses a UITableViewController that displays a list of all 50 states separated into sections alphabetically. I have added the detail disclosure button to the prototype cell in the storyboard and the table displays all the correct information.
When I press the button on a cell, it should segue to a new viewController and display the name of the state as the view title and then display a picture of the license plate in the view.
I am using the -(void)tableView:(UITableView *)tableView accessoryButtonTappedForRowWithIndexPath:(NSIndexPath *)indexPath method to control the button press and then I am using the -(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender to control the values being passed to the new viewController.
The problem I am having is that when I press the detail disclosure button nothing gets passed. NSLogging the values in the new viewController outputs (null), (null) and the view has no title or picture. However, when I press back and then press the same cell's detail disclosure button a second time, it works like it should. The title is correct and the picture displays properly.
The same is true when I choose another cell, the viewController displays the last information sent and I have to press back and then choose the cell again for it to update. When choosing a different cell for the first time, (null, (null) is what the NSlog is outputting. So I believe what is happening is that the first time a detail disclosure button is pressed, no values are passed, but the second time it is pressed, the values are being passed.
Here is the relevant code:
-(void)tableView:(UITableView *)tableView accessoryButtonTappedForRowWithIndexPath:(NSIndexPath *)indexPath
{
//Don't even use this method now.
}
-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
UITableViewCell *cell = (UITableViewCell*)sender; //Added this line
self.path = [self.tableview indexPathForCell:cell]; //Added this line
if ([segue.identifier isEqualToString:#"stateSegue"])
{
self.controller = segue.destinationViewController;
self.controller.stateName = [self.stateArray[indexPath.section][indexPath.row]stateName];
self.controller.licensePlateURL = [self.stateArray[indexPath.section][indexPath.row]licensePlateURL];
}
}
Any help with this would be greatly appreciated.
Check which method fires first. Maybe you set properties after segue is performed.
There's no informations about how (when) do you perform segue.
You could add this line to your accessoryButton method:
[self performSegueWithIdentifier:yourIdentifierFromStoryboard sender:self];
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.
I have a storyboard with segue from a table cell. I want to set some properties with some data when a row gets selected so I do the following:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
[[ProperyManager sharedPropertyManager]setSelectedRow:[verseIds objectAtIndex:indexPath.row]];
[[ProperyManager sharedPropertyManager]setID:[poemIDs objectAtIndex:indexPath.row]];
[[ProperyManager sharedPropertyManager]setRowToReturn:[NSString stringWithFormat:#"%i",indexPath.row]];
}
The problem is, the view controller lifecycle methods (viewWillAppear etc.) of the destination view controller get called before the didSelectRow method above, because the segue pushes the view before the delegate method is executed.
How can I get around this?
Rawkode's answer is one good solution - an alternative is that, in prepareForSegue:, you can access the selected row of the table view (the sender argument will be the table view cell, you can then do [self.tableView indexPathForCell:(UITableViewCell*)sender] to get the index path) and set up whatever you need at that point.
Don't create the Segue from the Cell to the new VC, instead set the Segue from the old VC to the new VC and give the segue an identifier.
Then within
didSelectRowAtIndexPath you can call
[self performSegueWithIdentifier:#"Segue" sender:self]