Manually select row in UITableView using selectRowAtIndexPath - ios

So I am trying to pre select the a row in a table using selectRowAtIndexPath.
My question is, where is the best place to call selectRowAtIndexPath?
The only place I thought of calling this, was in cellForRowAtIndexPath:... because I had the indexPath, but that didn't seem to work.
I appreciate any answers or suggestions.
Thanks!

Approach 1 :
For the cell to appear selected, you have to call -setSelected:animated: from within -tableView:willDisplayCell:forRowAtIndexPath: like so:
- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
{
if (/* Condition */) {
[cell setSelected:YES animated:NO];
}
}
Approach 2 :
- (void)viewDidAppear:(BOOL)animated {
NSIndexPath *indexPath=[NSIndexPath indexPathForRow:0 inSection:0];
[myTableView selectRowAtIndexPath:indexPath animated:YES scrollPosition:UITableViewScrollPositionNone];
}
If you want that particular row to be selected everytime then Approach 1 is better, else if you just want it for selected initially then Approach 2 is better.

Why not just set the cell as selected manually, instead of calling the delegate method?
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:#"MyCell" forIndexPath:indexPath];
//...
if( /* some condition */ ) {
cell.selected = YES;
}
//...
return cell;
}

Related

Cant access cell from willDisplayCell method

I have two methods which are changing accerssory type of a cell.
First is called after all cells are loaded, the other one is called when user clicks on any cell.
Second method works fine, it removes checkmark from selected cell. Unfortunately the first one does nothing (I want to add checkmark to one of the cells). It makes me confused, beceause theese methods should work the same, shouldnt they?
// First method
- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath {
if ([indexPath row] == ((NSIndexPath*)[[tableView indexPathsForVisibleRows]
lastObject]).row)
{
LanguageTableViewCell *cell = [self.tableView cellForRowAtIndexPath: [NSIndexPath indexPathForRow:myNumber inSection:0]];
cell.accessoryType = UITableViewCellAccessoryCheckmark;
}
}
// Second method
- (void)tableView:(UITableView )tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
LanguageTableViewCell *cell = [tableView cellForRowAtIndexPath:[NSIndexPath indexPathForRow:myNumber inSection:0]];
cell.accessoryType = UITableViewCellAccessoryNone;
}
I tried to change class of cell, but its still not working. Im not sure if first function is called in right time = after viewDidLoad...
Thanks for help!
You want to use - (__kindofUITableViewCell *)cellForRowAtIndexPath:(NSIndexPath *)indexPath.

Perform Single Selection of Row in UITableView with custom UITableViewCell ?

I know there are lot of answers to this question . But it didn't achieved the desired result . didDEselectrow is not working . I have a UIImageView which i have set to hidden True in cellforRowAtIndex. And when someone selects any row value for hidden is set to false .
**My main problem is when i select another row , the previous row status does not change and it also shows selected . I have attached the necessary snippet of my code ,Please check and help me through this . **
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
EventTypeTableViewCell *cell = [self.tableView dequeueReusableCellWithIdentifier:#"Event_Type" forIndexPath:indexPath];
cell.selectionStyle = UITableViewCellSelectionStyleNone;
if (cell.selectionStatus)
[cell.selectEvent setHidden:NO];
else
[cell.selectEvent setHidden:YES];
[cell.eventTypeName setText:[eventTypeName objectAtIndex:indexPath.row]];
return cell;
}
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
EventTypeTableViewCell *cell = (EventTypeTableViewCell *)[self.tableView cellForRowAtIndexPath:indexPath];
if(cell.selectionStatus == TRUE)
{
cell.selectionStatus = FALSE;
}
else
{
] cell.selectionStatus = TRUE;
}
[tableView reloadData];
}
-(void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath {
EventTypeTableViewCell *cell = (EventTypeTableViewCell *)[self.tableView cellForRowAtIndexPath:indexPath];
if(cell.selectionStatus == FALSE)
{
//Do your stuff
cell.selectionStatus = TRUE;
}
else
{
//Do your stuff
cell.selectionStatus = FALSE;
}
[tableView reloadData];
}
I suspect that didDeselect is not being called because you are allowing multiple selections in your tableView.
Have you set your table view's selection style to "single selection"? You can either do it in interface builder/storyboard or you can do it programmatically:
- (void) viewDidLoad {
self.tableView.allowsMultipleSelection = NO;
}
That way when you select another row it will deselect the old selection. Also you can simplify your code and make everything look better by not calling [tableView reloadData] every time one cell's selected state changes. The way I would suggest doing that is to change the hidden state of selectEvent within EventTypeTableViewCell whenever the cell's selection changes.
That leaves you with this:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
EventTypeTableViewCell *cell = [self.tableView dequeueReusableCellWithIdentifier:#"Event_Type" forIndexPath:indexPath];
[cell.eventTypeName setText:[eventTypeName objectAtIndex:indexPath.row]];
return cell;
}
And some method overrides within your definition of EventTypeTableViewCell:
#implementation EventTypeTableViewCell
/// Your code ///
- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
[super setSelected:selected animated:animated];
self.selectEvent.hidden = !selected;
}
#end
Try this ::
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
[tableView cellForRowAtIndexPath:indexPath].accessoryType = UITableViewCellAccessoryCheckmark;
}
-(void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath
{
[tableView cellForRowAtIndexPath:indexPath].accessoryType = UITableViewCellAccessoryNone;
}

UITableViewCells disappears randomly on drag after resize another row

I have a UITableView. I use this code to resize the selected row:
-(void) viewWillAppear:(BOOL)animated {
....
[self.tableView registerNib:[UINib nibWithNibName:#"ICSceneDetailViewTableViewCell" bundle:[NSBundle mainBundle]] forCellReuseIdentifier:IC_CELL_SCENE_EDITOR_CELL];
...
}
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return 1;
}
-(int) tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
if (tableView == nil)
return 0;
if (self.scenes != nil) {
return self.scenes.count;
}
return 0;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
ICSceneDetailViewTableViewCell *cell = (ICSceneDetailViewTableViewCell*)[tableView dequeueReusableCellWithIdentifier:IC_CELL_SCENE_EDITOR_CELL forIndexPath:indexPath];
if (cell == nil) {
cell = [[ICSceneDetailViewTableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:IC_CELL_SCENE_EDITOR_CELL];
}
ICScene *scene = [self.scenes objectAtIndex:[indexPath row]];
[cell.titleTextField setText:scene.title];
return cell;
}
-(void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
self.selectedRow = indexPath.row;
[self.tableView reloadRowsAtIndexPaths:[NSArray arrayWithObjects:indexPath, nil] withRowAnimation:UITableViewRowAnimationNone];
[self.tableView scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionTop animated:NO];
}
-(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
if ([indexPath row] == self.selectedRow) {
return 250;
}
if (IS_IPAD) {
return 80;
}
else {
return 40;
}
}
-(UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath {
return UITableViewCellEditingStyleNone;
}
BUT, after selecting any row (name it A, and A become resized):
if I drag another row (name it B) then randomly other rows disappears (except A).
if I scroll tableview and back to drag on same row (B) then, again randomly, other(s) cell(s) disappear(s), but not always the same(s).
if I comment heightForRowAtIndexPath then drag behavior is normal, but row can't be resized :(
I already searched many similar answers (adjusting selectedBackgroundView on cell, backgroundView cell, drawRect on cell, etc) but no one solution/workaround works for this simple (i think) code.
Thanks in advance :)
Yeh, answering my own question.
I found an alternative to resize selected UITableViewCell without calling to reloadRowsAtIndexPaths.
Replacing reloadRowsAtIndexPaths with:
[self.tableView beginUpdates];
[self.tableView endUpdates];
refreshes visible rows without calling cellForRowAtIndexPath. Imho the problem where dequeuing cells on every row being reloaded.
The resulting code is:
-(void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
self.selectedRow = indexPath.row;
[self.tableView scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionTop animated:NO];
[self.tableView beginUpdates];
[self.tableView endUpdates];
}
So, automagically there isn't any disappearing row :)

UITableView select and deselect row

I have a UITableViewcell that stays highlighted after touching it. I would like to know how to remove the highlight right after it becomes visible after your touch.
So when you touch the UITableViewCell I would like it to become selected and highlighted then when the user raises their finger I would like to deselect and unhighlight the UITableViewCell.
This is what I am doing so far, and the deselect works but the cell is still highlighted.
#pragma mark -- select row
- (void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
NSLog(#"%#", indexPath);
NSLog(#"%#", cell.textLabel.text);
}
#pragma mark -- deselect row
-(void) tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath {
[tableView deselectRowAtIndexPath:indexPath animated:YES];
}
-(void) tableView:(UITableView *)tableView didDeselectRowAtIndexPath:
(NSIndexPath *)indexPath {
[tableView deselectRowAtIndexPath:indexPath animated:YES];
}
That's an infinite loop, I'm quite certain. However... it's sort of on the right track. You can move that method call into didSelectRowAtIndexPath:.
- (void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:
(NSIndexPath *)indexPath {
//stuff
//as last line:
[tableView deselectRowAtIndexPath:indexPath animated:YES];
}
For that matter, deselectRowAtIndexPath can be called from anywhere at any time you want the row to be deselected.
[self.myTableView deselectRowAtIndexPath:[self.myTableView
indexPathForSelectedRow] animated: YES];
You need to deselect row on didSelectRowAtIndexPath method
Example code
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
[tableView deselectRowAtIndexPath:indexPath animated:NO];
}

How to make auto deselecting tableview cell

I have a table view
and when I click the cell everything is fine
however, when I remove my fingers from the phone, the cell stays selected
how can I make it become deselected when the user stops touching the given cell and does not touch another cell
Simple :
In this method : didSelectRowAtIndexPath
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
UIActionSheet *photoPicker ;
[tableView deselectRowAtIndexPath:indexPath animated:YES];
}
you have to set the style in cellForRowAtIndexPath or change the cell in willSelectRowAtIndexPath and change back in didSelectRowAtIndexPath.
For example
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
// ...
cell.selectionStyle = UITableViewCellSelectionStyleBlue; // or an other style
// ...
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
// ...
[tableView deselectRowAtIndexPath:indexPath animated:NO];
// ...
}
Put the following in the UITableView delegate.
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
[cell setSelected:NO animated:YES];
}
Have you considered to handle the touch events?
For example: Add a UITapGestureRecognizer, detect which cell is being touched by using the -(CGPoint)locationInView:(UIView *)view method. Mark the cell as selected when the touch begins and mark as deselected when the touch ends.
Have you assigned delegate to UITableView?
self.tableView.delegate = self;
That is the reason why you experience this
this does not work - the cell does not show indication of being
selected
In tableView:didSelectRowAtIndexPath:, set the selected property of the cell to NO using the method setSelected:animated:.
E.g.
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell * cell = [tableView cellForRowAtIndexPath:indexPath];
[cell setSelected:NO animated:YES];
}
NOTE:
Setting the cell's selected property = NO and animated = YES with the above method will cause the separator to disappear. The only way I've found to circumvent this is to set animated = NO but, if I find another way I will update my answer.

Resources