开发者

How to set selected background color on grouped UITableView

I've tried vario开发者_开发问答us approaches with no success. Its grouped UITableView. Want to change the background color of the selected cell.

I've tried creating a view, setting the background color and setting it to cell.selectedBackgroundView. It works to change the color, but the rounded corners of a section are lost.


You can create 4 different images, 1 for top, 1 for bottom, 1 for middle, and 1 for top/bottom (rounded on all 4 corners). Then set the background view to your custom image, depending on the position in the table. Alternatively, if you want to use a view, here's a custom view that rounds only specific corners:

.h

#import <UIKit/UIKit.h>

enum {
    RoundedCornerNone        = 0,
    RoundedCornerUpperRight  = 1 << 0,
    RoundedCornerLowerRight  = 1 << 1,
    RoundedCornerLowerLeft   = 1 << 2,
    RoundedCornerUpperLeft   = 1 << 3
};
typedef NSUInteger RoundedCornerOptions;

@interface PartiallyRoundedView : UIView

@property (nonatomic, assign) RoundedCornerOptions roundedCorners;

@end

.m

#import "PartiallyRoundedView.h"


@implementation PartiallyRoundedView

@synthesize roundedCorners;

- (id)initWithFrame:(CGRect)frame
{
    if ((self = [super initWithFrame:frame])) {
    }
    return self;
}

- (void)drawRect:(CGRect)rect
{
    float radius = 10;

    CGContextRef context = UIGraphicsGetCurrentContext();
    CGContextSetLineWidth(context, 1.0);
    CGContextBeginPath(context);
    CGContextSetRGBStrokeColor(context, .6, .6, .6, 1);
    CGContextSetRGBFillColor(context, .968, .968, .968, 1);

    CGContextMoveToPoint(context, rect.origin.x + rect.size.width - radius, rect.origin.y);
    CGContextAddLineToPoint(context, rect.origin.x + radius, rect.origin.y); //Draw top line

    if (self.roundedCorners >=8) { //Round upper-left corner
        CGContextAddArc(context, rect.origin.x + radius, rect.origin.y + radius, radius, 
                        -M_PI / 2, M_PI, 1);

        self.roundedCorners-=8;
    }
    else {
        CGContextAddLineToPoint(context, rect.origin.x, rect.origin.y);
        CGContextAddLineToPoint(context, rect.origin.x, rect.origin.y + radius);
    }

    CGContextAddLineToPoint(context, rect.origin.x, rect.origin.y + rect.size.height - radius); //Draw left line

    if (self.roundedCorners >=4) { //Round lower-left corner
        CGContextAddArc(context, rect.origin.x + radius , rect.origin.y + rect.size.height - radius, 
                        radius, M_PI, M_PI / 2, 1);

        self.roundedCorners-=4;
    }
    else {
        CGContextAddLineToPoint(context, rect.origin.x, rect.origin.y + rect.size.height);
        CGContextAddLineToPoint(context, rect.origin.x + radius, rect.origin.y + rect.size.height);
    }

    CGContextAddLineToPoint(context, rect.origin.x + rect.size.width - radius, rect.origin.y + rect.size.height); //Draw bottom line

    if (self.roundedCorners >=2) { //Round lower-right corner
        CGContextAddArc(context, rect.origin.x + rect.size.width - radius , 
                        rect.origin.y + rect.size.height - radius, radius, M_PI / 2, 0.0f, 1);

        self.roundedCorners-=2;
    }
    else {
        CGContextAddLineToPoint(context, rect.origin.x + rect.size.width, rect.origin.y + rect.size.height);
        CGContextAddLineToPoint(context, rect.origin.x + rect.size.width, rect.origin.y + rect.size.height - radius);
    }

    CGContextAddLineToPoint(context, rect.origin.x + rect.size.width, rect.origin.y + radius); //Draw right line

    if (self.roundedCorners ==1) { //Round upper-right corner
        CGContextAddArc(context, rect.origin.x + rect.size.width - radius, rect.origin.y + radius, 
                        radius, 0.0f, -M_PI / 2, 1);
    }
    else {
        CGContextAddLineToPoint(context, rect.origin.x + rect.size.width, rect.origin.y);
        CGContextAddLineToPoint(context, rect.origin.x + rect.size.width - radius, rect.origin.y );
    }


    CGContextClosePath(context);
    CGContextDrawPath(context, kCGPathFillStroke);
    }


    - (void)dealloc {
        [super dealloc];
    }


    @end

You can create an instance of this view (you'll need to add a bit to fill the middle with whatever color you want). Just pass in the correct corner rounding depending on if you are the first, last, middle, or first and last cell.


If you'd like to implement this feature with Core Graphics (without using images), give this a shot. My approach takes the same concept as your selected answer, yet uses a simple if/else (or switch:case depending on your data source size) to draw the correct background view for your grouped UITableViewCell. The following code only need to be included in your implementation file:

.m

UIView *bgColorView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, self.view.frame.size.width-24, 69)];
    bgColorView.backgroundColor = [UIColor magentaColor];
    UIBezierPath *maskPath;
    CAShapeLayer *maskLayer = [CAShapeLayer layer];
    maskLayer.frame = bgColorView.bounds;

    if (row == 0) {
      maskPath = [UIBezierPath bezierPathWithRoundedRect:bgColorView.bounds
                                       byRoundingCorners:(UIRectCornerTopLeft | UIRectCornerTopRight)
                                             cornerRadii:CGSizeMake(8.0, 8.0)];
      maskLayer.frame = CGRectOffset(bgColorView.bounds, 1, 0);
      if ([self.tableView numberOfRowsInSection:1] == 1) {
        maskPath = [UIBezierPath bezierPathWithRoundedRect:bgColorView.bounds
                                         byRoundingCorners:(UIRectCornerAllCorners)
                                               cornerRadii:CGSizeMake(8.0, 8.0)];
      }
    } else if (row >= [self.tableView numberOfRowsInSection:1]-1) {
      maskPath = [UIBezierPath bezierPathWithRoundedRect:bgColorView.bounds
                                       byRoundingCorners:(UIRectCornerBottomLeft | UIRectCornerBottomRight)
                                             cornerRadii:CGSizeMake(8.0, 8.0)];
      maskLayer.frame = CGRectOffset(bgColorView.bounds, 1, 0);
    } else {
      maskPath = [UIBezierPath bezierPathWithRoundedRect:bgColorView.bounds
                                       byRoundingCorners:nil
                                             cornerRadii:CGSizeMake(0.0, 0.0)];
    }

    maskLayer.path = maskPath.CGPath;

    bgColorView.layer.mask = maskLayer;
    cell.selectedBackgroundView = bgColorView;

If you've utilized reuseable cells, the drawing should only occur once for each type.

Hope this helps someone who stumbles onto this thread... Cheers!


If you just want to change the selection color, look at this suggestion: UITableView Cell selected Color? Post this in the CellForRowAtIndexPath-Method:

UIView *bgColorView = [[UIView alloc] init];
[bgColorView setBackgroundColor:[UIColor redColor]];
bgColorView.layer.cornerRadius = 10; 
[cell setSelectedBackgroundView:bgColorView];
[bgColorView release];  

and don't forget to import QuartzCore. Works for me (iOS 5)

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜