UITableViewCellの横幅を調整する

UITableViewCellの縦幅は簡単に調整可能ですが、横幅は少し工夫して行う必要があります。 というか、 UITableViewDelegate#cellForRowAtIndexPath や、 UITableViewDelegate#willDisplayCell でframe辺りをいじって色々試してみたのですが、ちょっとうまく行かず困っていました。

色々検索していたら、 How to set the width of a cell in a UITableView in grouped style という投稿を発見しました。 その中の この返信 がまさに一番欲しいものだったので、とても参考になります。 補足で書かれている、Why is it better? Because the other two are worse. のくだりが興味深いですね。

ちなみにこんなクラスを定義して

// InsetCell.h
/**
 * マージン調整が可能なUITableViewCellの拡張クラスを提供します
 */
@interface InsetableTableCell : UITableViewCell
@property (nonatomic) CGFloat inset;
@end

メインクラスは、

// InsetCell.m
@implementation InsetableTableCell
(id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier
{
        self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
        if (self) {
                // Initialization code
        }
        return self;
}
- (void)setSelected:(BOOL)selected animated:(BOOL)animated
{
        [super setSelected:selected animated:animated];

        // Configure the view for the selected state
}
- (void)setFrame:(CGRect)frame
{
        frame.origin.x += self.inset;
        frame.size.width -= 2 * self.inset;
        [super setFrame:frame];
}

@end

こんな感じで利用します(ほぼコピーです)。

// XXXController.mから抜粋
-(UITableViewCell*)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
        InsetableTableCell *cell = [tableView dequeueReusableCellWithIdentifier:"cell"];
        return cell;
}
-(void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
{
        InsetableTableCell *iCell = (InsetableTableCell *) cell;
        iCell.inset = 9.0;
}

以上です。