Search code examples
iosobjective-cuitableviewdidselectrowatindexpathsections

How to implement only single cell selection in each section in the tableview in iOS, Objective C


I have a table view with 5 sections and I have set the tableview selection to multiple. Each section have different number of rows. What I want is to set that the user can select only one cell from each section(in my table user can select any number of cells). ex: 5 cells from 5 sections.

It should be impossible to select more than one cell from any section. If user select another cell from same section, previously selected cell should be deselected. How can I do this. This is a sample implementation of didSelectRowAtIndexPath.

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{


    HoteldetalcelloneTableViewCell *cellone = (HoteldetalcelloneTableViewCell *)[self.detailtableView cellForRowAtIndexPath:indexPath];
    HoteldetailcelltwoTableViewCell *celltwo = (HoteldetailcelltwoTableViewCell *)[self.detailtableView cellForRowAtIndexPath:indexPath];

    //I have implement for two sections to test.
    if(indexPath.section == 0)
    {

       HotelDetailsone *secone = [roomonearray objectAtIndex:indexPath.row];
       HoteldetailsforBooking *book = [HoteldetailsforBooking new];
        if([secone.offerallow isEqualToString:@"True"])
        {
            celltwo.selectedsignLabel.hidden = NO;

        }
        else
        {

            cellone.selectedsignLabelone.hidden = NO;

        }
//        [self.detailtableView reloadData];
      NSLog(@"price for room 1 : %@", secone.itempriceText);

    }
    else
    {
        HotelDetailsone *sectwo = [roomtwoarray objectAtIndex:indexPath.row];
        HoteldetailsforBooking *book = [HoteldetailsforBooking new];
        if([sectwo.offerallow isEqualToString:@"True"])
        {
            celltwo.selectedsignLabel.hidden = NO;

        }
        else
        {

            cellone.selectedsignLabelone.hidden = NO;

        }
        //        [self.detailtableView reloadData];
        NSLog(@"price for room 1 : %@", sectwo.itempriceText);

    }

}

Solution

  • You need to keep track on the selection of cell. So you need to store selected indexpath in array.

    in ViewController.h declare property like this

    @property(nonatomic,strong) NSMutableDictionary *selectionData;
    

    Now in ViewController.m

    - (void)viewDidLoad {
        [super viewDidLoad];
    
        self.selectionData=[[NSMutableDictionary alloc]init];
    
    }
    
    - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
    
        TestTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"mycell"];
    
    
        if ([self.selectionData objectForKey:[NSString stringWithFormat:@"%ld",(long)indexPath.section] ] != nil) {
    
            NSMutableArray *sectionData=[[self.selectionData objectForKey:[NSString stringWithFormat:@"%ld",(long)indexPath.section]] mutableCopy];
    
            if (![sectionData containsObject:[NSNumber numberWithLong:indexPath.row]])
            {
                cell.accessoryType = UITableViewCellAccessoryNone;
                cell.numberlabel.text = @"2";
            }
            else
            {
                cell.numberlabel.text = @"***";
                cell.accessoryType=UITableViewCellAccessoryCheckmark;
            }
        }
        else
        {
            cell.numberlabel.text = @"2";
            cell.accessoryType = UITableViewCellAccessoryNone;
        }
    
      cell.selectionStyle = UITableViewCellSelectionStyleNone;
        return cell;
    
    }
    
    - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
    {
    
        NSLog(@"selected section :%li ---> selected row :%li",(long)indexPath.section, (long)indexPath.row);
        [self handleSelectionForSection:indexPath.section row:indexPath.row];
        [self.tablev reloadData];
    
    }
    
    -(void)handleSelectionForSection:(long)sectionIndex row:(long)rowIndex
    {
    
    
        if ([self.selectionData objectForKey:[NSString stringWithFormat:@"%ld",sectionIndex] ] != nil) {
    
            NSMutableArray *sectionData=[[self.selectionData objectForKey:[NSString stringWithFormat:@"%ld",sectionIndex]] mutableCopy];
    
            if (![sectionData containsObject:[NSNumber numberWithLong:rowIndex]])
            {
                //removing previous selected rows
                [sectionData removeAllObjects];
                [sectionData addObject:[NSNumber numberWithLong:rowIndex]];
    
                [self.selectionData setObject:sectionData forKey:[NSString stringWithFormat:@"%ld",sectionIndex]];
            }
            else
            {
                //cell you tapped is already selected,
                // you can deselect it by removing object
    
                //if you dont want to deselect it comment following lines
                [sectionData removeObject:[NSNumber numberWithLong:rowIndex]];
    
                [self.selectionData setObject:sectionData forKey:[NSString stringWithFormat:@"%ld",sectionIndex]];
            }
    
    
        }
        else
        {
            //section key not available so we need to create it
            NSMutableArray *sectionData=[[NSMutableArray alloc]init];
            [sectionData addObject:[NSNumber numberWithLong:rowIndex]];
    
            [self.selectionData setObject:sectionData forKey:[NSString stringWithFormat:@"%ld",sectionIndex]];
    
        }
    
        NSLog(@"All Selection : %@",self.selectionData);
    
    }
    

    Your numberOfRowsInSection, numberOfSectionsInTableView and titleForHeaderInSection will remain same.

    Let me know if you have any query.