My iPhone app is currently displaying a grouped table with 2 sections. I tried to change the radius of the rounded corners on the first and last cells of each section (or on the same cell in the case of sections with just one row) using:
cell.layer.cornerRadius = 4;
or acting on the whole tableview:
self.tableView.layer.cornerRadius = 4;
but no luck...Of course I've imported QuartzCore before performing this operation. It looks like it's possible to customise the corners only when the table is displayed with plain style.
The ideal solution would be to customise top corners in the first one and bottom corners in the last.
Any suggestions?
What you can do is add a UIView
on the background of a cell, make the cell background as clearcolor . Adjust the UIView
to have rounded corners.
Here's what works in Swift 4.2:
func tableView(_ tableView: UITableView, willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath)
{
let cornerRadius = 5
var corners: UIRectCorner = []
if indexPath.row == 0
{
corners.update(with: .topLeft)
corners.update(with: .topRight)
}
if indexPath.row == tableView.numberOfRows(inSection: indexPath.section) - 1
{
corners.update(with: .bottomLeft)
corners.update(with: .bottomRight)
}
let maskLayer = CAShapeLayer()
maskLayer.path = UIBezierPath(roundedRect: cell.bounds,
byRoundingCorners: corners,
cornerRadii: CGSize(width: cornerRadius, height: cornerRadius)).cgPath
cell.layer.mask = maskLayer
}
UIView *view = [UIView alloc]initWithFrame:YourFrame];
view.layer.cornerRadius = 8;
cell.backgroundView = view;
And don't forget the UITableView
background color to be transparent.
If You need just rounded corners there's another solution (inspired by grouped style of native uitableview(cell), in slowmo :) ). It should be something like this:
Cell subclass...
@interface MyCell : UITableViewCell
@property (nonatomic) top;
@property (nonatomic) bottom;
@end
@implementation MyCell
-(id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier{
self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
if (self) {
self.backgroundColor = [UIColor clearColor]; // remove white default background
//example settings, UIImageViews with resizable images can be used too
self.backgroundView = [[UIView alloc] init];
self.selectedBackgroundView = [[UIView alloc] init];
self.backgroundView.backgroundColor = [UIColor greenColor];
self.selectedBackgroundView.backgroundColor = [UIColor blueColor];
self.backgroundView.layer.cornerRadius = self.selectedBackgroundView.layer.cornerRadius = 5; //
}
return self;
}
-(void)layoutSubviews{
[super layoutSubviews];
self.backgroundView.frame = self.selectedBackgroundView.frame = UIEdgeInsetsInsetRect(self.bounds, UIEdgeInsetsMake(self.top?0:-self.backgroundView.layer.cornerRadius, 0, self.bottom?0:-self.backgroundView.layer.cornerRadius, 0));
}
-(void)setTop:(BOOL)top{
_top = top;
[self setNeedsLayout];
}
-(void)setBottom:(BOOL)bottom{
_bottom = bottom;
[self setNeedsLayout];
}
@end
In dataSource you can just do this:...
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
...cell initialization stuff...
[(MyCell *)cell setTop:(indexPath.row == 0)];
[(MyCell *)cell setBottom:(indexPath.row == [tableView numberOfRowsInSection:indexPath.section]-1)];
return cell;
}
Pros:
- one background for all cells
- easy to use
- animateable (You're changing positions instead of images)
- can be used for plain style as well (but watchout for sections :) )
Cons:
- subclass for cell is needed (I couldn't find a way to adjust backgrounds positions even after change of rowHeight)
- doesn't solve my problem with rounded corners of whole section (You have to round corners for section view manualy)
I hope this helps someone, but be aware that this code is not tested! I've implemented this idea few minutes before posting this answer and it just seems to work :)