How to remove the last border of the last cell in UITableView?

IphoneObjective CIosXcodeUitableview

Iphone Problem Overview


In my app, I use a UITableView My problem is that I want to remove the last border of the last cell in UITableView.

Please check the following image:

enter image description here

Iphone Solutions


Solution 1 - Iphone

The best solution is add a footer view. The following code hide the last cell's line perfectly:

Objective-C

self.tableView.tableFooterView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, self.tableView.frame.size.width, 1)];

Swift 4.0

tableView.tableFooterView = UIView(frame: CGRect(x: 0, y: 0, width: tableView.frame.size.width, height: 1))

Solution 2 - Iphone

In iOS 7 there is an easier solution. Supposing cell is your last cell:

cell.separatorInset = UIEdgeInsetsMake(0, cell.bounds.size.width, 0, 0);

Solution 3 - Iphone

Updated on 9/14/15. My original answer become obsolete, but it is still a universal solution for all iOS versions:

You can hide tableView's standard separator line, and add your custom line at the top of each cell. The easiest way to add custom separator is to add simple UIView of 1px height:

UIView* separatorLineView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, cell.bounds.size.width, 1)];
separatorLineView.backgroundColor = [UIColor grayColor];
[cell.contentView addSubview:separatorLineView];

To date, I subscribe to another way for hiding extra separators below cells (works for iOS 6.1+):

self.tableView.tableFooterView = [[UIView alloc] initWithFrame:CGRectZero];

Solution 4 - Iphone

This works for me in iOS 7 and 8:

cell.separatorInset = UIEdgeInsetsMake(0, 0, 0, CGRectGetWidth(tableView.bounds));

NOTE: be careful about using tableView.bounds as it sometimes reports the wrong value depending on when you call it. See https://stackoverflow.com/questions/5194504/reporting-incorrect-bounds-in-landscape-mode

Solution 5 - Iphone

Add this line of code in viewDidLoad().

tableView.tableFooterView = UIView(frame: CGRect(x: 0, y: 0, width: 0, height: 0.001))

This make sure the last separator will be replaced and replaced (invisible) footer view will not occupy any extra height. Since the footer view's width will be managed by UITableView, so you can set it to 0.

Solution 6 - Iphone

Extension based solution for Swift 4, tested on iOS 12

I noticed that setting a empty view of height = 1 also removes the separator of the last visible cell however setting height = 0 just removes the separator of the empty cells

extension UITableView {
    func removeSeparatorsOfEmptyCells() {
        tableFooterView = UIView(frame: .zero)
    }
    
    func removeSeparatorsOfEmptyCellsAndLastCell() {
        tableFooterView = UIView(frame: CGRect(origin: .zero, size: CGSize(width: 0, height: 1)))
    }
}

Solution 7 - Iphone

My shorter version:

self.tblView.tableFooterView = [UIView new];

Solution 8 - Iphone

In Swift simply:

tableView.tableFooterView = UIView()

Solution 9 - Iphone

Here is the remedy I currently use. it might not be the best approach, but it works.

Remove SeparatorColor and setSeparatorStyle to make custom separator

- (void)viewDidLoad
{
    [super viewDidLoad];
    
    ...
    
    [self.tableView setSeparatorStyle:UITableViewCellSeparatorStyleNone];
    [self.tableView setSeparatorColor:[UIColor clearColor]];
}

Add custom separator to each cell with tableview background

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"Cell" forIndexPath:indexPath];
    
    ...
    
    UIView* separatorLineView = [[UIView alloc] initWithFrame:CGRectMake(0, cell.frame.size.height-1, 320, 1)];
    separatorLineView.backgroundColor = self.tableView.backgroundColor;
    [cell.contentView addSubview:separatorLineView];
    
    return cell;
}

Solution 10 - Iphone

_tableView.tableFooterView = [[UIView alloc] initWithFrame:CGRectZero];

Solution 11 - Iphone

For iOS 7 and above

    -(void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
    {
        BOOL bIsLastRow = NO;
        
        //Add logic to check last row for your data source
        NSDictionary *dict = [_arrDataSource objectAtIndex:indexPath.section];
        if([_arrDataSource lastObject] == dict)
        {
           bIsLastRow = YES;
        }
        
        //Set last row separate inset left value large, so it will go outside of view
        if ([cell respondsToSelector:@selector(setSeparatorInset:)]) 
        {
            [cell setSeparatorInset:UIEdgeInsetsMake(0, bIsLastRow ? 1000 :0, 0, 0)];
        }
    }

Solution 12 - Iphone

Below code helps me to remove the separator from last row in a UITableView.

Swift 3.0

func tableView(_ tableView: UITableView, willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath) {
    if indexPath.row == tableView.numberOfRows(inSection: indexPath.section) {
        cell.separatorInset.right = cell.bounds.size.width
    }
}

Solution 13 - Iphone

Swift 4.2

To get a separator that goes from left to right in your last cell, add this in your UITableViewDataSource's tableView(_:cellForRowAt:) implementation:

if tableView.numberOfRows(inSection: indexPath.section) - 1 == indexPath.row {
        cell.separatorInset = .zero
}

If you don't want a separator for one particular cell, consider drawing your own separator and set tableView.separatorStyle = .none.

Solution 14 - Iphone

Xcode 12, Swift 5

for removing separator after last cell, select grouped UITableView style You can do that in Interface Builder or setup it in viewDidLoad

tableView.style = UITableView.Style.grouped

remove empty space before first cell, write this code in viewDidLoad:

tableView.tableHeaderView = UIView(frame: CGRect(x: 0, y: 0, width: tableView.bounds.width, height: 0.1))

for removing empty space before your cells, and you are going to scroll it under the navigation bar or have other difficulties with avoiding empty space, try to constraint your table to controller's super view Here double click the top constraint and then choose 'SuperView.Top' at the constraint settings

If you want full width separator or your own width of it, just select Separator Inset as Custom, and configure to your values, or write it in viewDidLoad:

tableView.separatorInset = UIEdgeInsets(top: 0, left: 0, bottom: 0, right: 0)

Solution 15 - Iphone

Find the last cell index in the cellForRow delegate and put the line of code from below:

cell.separatorInset = UIEdgeInsetsMake(
    0.f,
    40.0f,
    0.f,
    self.view.frame.size.width-40.0f
);

Solution 16 - Iphone

Another option is by subclassing UITableView:

@synthesize hideLastSeparator = _hideLastSeparator;
@synthesize hideLastSeparatorView = _hideLastSeparatorView;
-(void)setHideLastSeparator:(BOOL)hideLastSeparator {
    if (_hideLastSeparator == hideLastSeparator) {
        return;
    }
    _hideLastSeparator = hideLastSeparator;
    if (_hideLastSeparator) {
        _hideLastSeparatorView = [[UIView alloc] initWithFrame:CGRectMake(0, self.contentSize.height, self.bounds.size.width, 0.5f)];
        _hideLastSeparatorView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleBottomMargin;
        _hideLastSeparatorView.backgroundColor = self.backgroundColor;
        [self addSubview:_hideLastSeparatorView];
        [self hideSeparator];
    }
    else {
        [_hideLastSeparatorView removeFromSuperview];
        _hideLastSeparatorView = nil;
    }
}
-(void)setContentSize:(CGSize)contentSize {
    [super setContentSize:contentSize];
    if (_hideLastSeparator) {
        [self hideSeparator];
    }
}
-(void)hideSeparator {
    CGRect frame = _hideLastSeparatorView.frame;
    frame.origin.y = self.contentSize.height - frame.size.height;
    _hideLastSeparatorView.frame = frame;
}

The .h should only contain property declarations for hideLastSeparator and hideLastSeparatorView.
When wanting to hide the separator, use the new class and set myTableView.hideLastSeparator = YES.
The way this works is by obstructing the last separator by adding a new view over it.

This is somewhat easier to use in my opinion (than using a custom separator, or setting the last separatorInset of the last cell), and avoids some weird animations that the method of setting a tableFooterView sometimes causes (e.g. during row insertion/deletion or other table animations).

Solution 17 - Iphone

If you're using custom separators for your UITableViewCell the best solution is:

  1. Implement in your custom cell function, that hides separatorView
class YourCell: UITableViewCell {
    // Your implementation goes here...
    // Separator view in cell
    @IBOutlet private weak var separatorView: UIView!

    // This function hides the separator view
    func hideSeparator() {
		separatorView.isHidden = true
	}
}
  1. In tableView(_ tableView: UITableView, willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath) calculate if the cell is the last and hides it's separator
public func tableView(_ tableView: UITableView, willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath) {
    guard let cell = cell as? YourCell else {
			return
    }
    // Here we're checking if your cell is the last one
	if indexPath.row == tableView.numberOfRows(inSection: indexPath.section) - 1 {
	    // if true -> then hide it
        cell.hideSeparator()
	}
}

Solution 18 - Iphone

This works great for me:

func tableView(_ tableView: UITableView, willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath) {
	guard let cell = cell as? yourCell else {
			return
	}
	// Here we're checking if your cell is the last one
	if indexPath.row == numberOfCells.count - 1 {
		cell.separatorInset.left = UIScreen.main.bounds.width
	}
}

What we're doing here is setting the size of the left inset to be a big enough value so that the separator line won't be visible anymore. So when we increase the size value of our inset it will get closer and closer to the right of our screen since left inset goes towards the right direction.

Solution 19 - Iphone

The most suitable & easy way would be using this at cellForRowAt

cell.drawBottonLine = (indexPath.row != sections[0].rows.count - 1)

Solution 20 - Iphone

Expanding on Tonny Xu's answer, I have multiple sections and this seems to work for removing the last cells separator

if(indexPath.row == [self.tableView numberOfRowsInSection:indexPath.section] - 1)
{
    self.tableView.tableFooterView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, self.tableView.frame.size.width, 1)];
}

In the cellForRowAtIndexPath datasource

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
Questionuser2289379View Question on Stackoverflow
Solution 1 - IphoneTonny XuView Answer on Stackoverflow
Solution 2 - IphonedavidisdkView Answer on Stackoverflow
Solution 3 - IphoneonegrayView Answer on Stackoverflow
Solution 4 - IphoneJamie ForrestView Answer on Stackoverflow
Solution 5 - IphoneJonnyView Answer on Stackoverflow
Solution 6 - IphoneheyfrankView Answer on Stackoverflow
Solution 7 - IphoneMarco MardeganView Answer on Stackoverflow
Solution 8 - IphoneDungeonDevView Answer on Stackoverflow
Solution 9 - IphoneHiroView Answer on Stackoverflow
Solution 10 - IphoneohanaView Answer on Stackoverflow
Solution 11 - IphoneAditya DeshmaneView Answer on Stackoverflow
Solution 12 - Iphoneuser2991638View Answer on Stackoverflow
Solution 13 - IphoneJanApothekerView Answer on Stackoverflow
Solution 14 - Iphonenever-use-androidView Answer on Stackoverflow
Solution 15 - IphoneSuresh KansujiyaView Answer on Stackoverflow
Solution 16 - Iphonealex-iView Answer on Stackoverflow
Solution 17 - IphoneNazariy VlizloView Answer on Stackoverflow
Solution 18 - IphoneSimon McNeilView Answer on Stackoverflow
Solution 19 - IphoneChrishanView Answer on Stackoverflow
Solution 20 - IphoneJosh ValdiviesoView Answer on Stackoverflow