gmogames gmogames - 3 months ago 21
Objective-C Question

Spacing between cells on UITableView with Custom UITableViewCell

I have a UITableView loading a custom UITableViewCell from a XIB file. Everything is working fine, but my layout requires that the cells (all inside one single section) have spacing between them.
Any chance this can be done without having to raise the ROW height?

how it is now

how it is now

how it's supossed to be

how it's supossed to be

EDIT:

this is how the code is today

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{
return [[self.cards valueForKeyPath:@"cards"] count];
}


- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
[ccTableView setBackgroundColor:[UIColor clearColor]];
cardsCell *cell = [tableView dequeueReusableCellWithIdentifier:@"cardsCell"];

if(cell == nil){
NSArray *topLevelObjects = [[NSBundle mainBundle] loadNibNamed:@"cardsCell" owner:self options:nil];
cell = [topLevelObjects objectAtIndex:0];
}

NSString *nmCard = [[self.cards valueForKeyPath:@"cards.name"] objectAtIndex:indexPath.row];
cell.descCardLabel.text = nmCard;

return cell;
}

Answer

If you can't change the cell's height, the solution is to use invisible intermediate cells of the required height. You'll need to recalculate indexes at table view delegate and datasource in that case.

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{

    static NSString *CELL_ID2 = @"SOME_STUPID_ID2";
    // even rows will be invisible
    if (indexPath.row % 2 == 1)
    {
        UITableViewCell * cell2 = [tableView dequeueReusableCellWithIdentifier:CELL_ID2];

        if (cell2 == nil)
        {
            cell2 = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault
                                          reuseIdentifier:CELL_ID2];
            [cell2.contentView setAlpha:0];
            [cell2 setUserInteractionEnabled:NO]; // prevent selection and other stuff
        }
        return cell2;
    }

    [ccTableView setBackgroundColor:[UIColor clearColor]];
    cardsCell *cell = [tableView dequeueReusableCellWithIdentifier:@"cardsCell"];

    if(cell == nil){
      NSArray *topLevelObjects = [[NSBundle mainBundle] loadNibNamed:@"cardsCell" owner:self options:nil];
      cell = [topLevelObjects objectAtIndex:0];
    }

     // Use indexPath.row/2 instead of indexPath.row for the visible section to get the correct datasource index (number of rows is increased to add the invisible rows)
        NSString *nmCard = [[self.cards valueForKeyPath:@"cards.name"] objectAtIndex:(indexPath.row/2)];
        cell.descCardLabel.text = nmCard;

      return cell;
    }



- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{

    // two times minus one (invisible at even rows => visibleCount == invisibleCount+1)
    return [[self.cards valueForKeyPath:@"cards"] count] * 2 - 1;
}

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
    if (indexPath.row % 2 == 1)
        return 40;
    return 162;
}

You will also need to recalculate the indexPath.row for :didSelectRowAtIndexPath: and other methods where it is used.