読者です 読者をやめる 読者になる 読者になる

A Day In The Life

とあるプログラマの備忘録

UITableViewのハイライトについてまとめてみた

iphone objective-c/objc

UITableViewの行選択時のハイライトって普通にUITableViewControllerを使っているときは問題ないのですが、うっかりviewWillAppear:メソッドをオーバーライドしたりUIViewControllerを使ったときなんかにハイライトが解除されなくて困ることがよくあります。ハイライトの解除をキチンとやっておかないとApp Store登録時にリジェクト喰らうこともあるらしいのでそんなことにならないように行選択時のハイライトについてまとめてみました。

UITableViewControllerを継承してUITableViewを使う時に気をつけること

UITableViewControllerのviewWillAppear:メソッドにはハイライト解除の処理が定義してあります。なのでviewWillAppear:メソッドをオーバーライドするときは必ず親クラスのviewWillAppear:メソッドを呼ぶようにしましょう。[super viewWillAppear:animated];の1行を忘れるとハイライト解除されません。

@interface SampleViewController : UITableViewController
@end

@implementation SampleViewController
- (void)viewWillAppear:(BOOL)animated {
  // 必ず親クラスのviewWillAppear:メソッドを呼ぶこと
  [super viewWillAppear:animated];
  tableView.title = @"Hoge";
}
@end

UITableViewControllerを継承せずにUITableViewを使う時に気をつけること

UITableViewControllerを継承せずにUIViewControllerを継承してUITableViewを使うことがあります。その場合UITableViewControllerでやってくれていたハイライト解除処理を自分で実装してやらないといけません。UITableView#deselectRowAtIndexPath:animated:メソッドを呼べばハイライトが解除されます。

@interface SampleViewController : UIViewController <UITableViewDelegate, UITableViewDataSource> {
  UITableView *tableView;
}
@property (nonatomic, retain)IBOutlet UITableView *tableView;
@end

@implementation SampleViewController
@synthesize tableView;

- (void)viewWillAppear:(BOOL)animated {
  [super viewWillAppear:animated];
  // ハイライト解除
  [tableView deselectRowAtIndexPath:[tableView indexPathForSelectedRow] animated:YES];
  tableView.title = @"Hoge";
}

- (void)viewDidAppear:(BOOL)animated {
  // テーブルの再読み込み
  [tableView reloadData];
}

// deallocメソッド省略...
@end

ハイライトさせたくないとき

UITableViewを表示専用で使う場合はハイライトさせたくないものです。
そんな時はUITableViewCellのselectionStyleにUITableViewCellSelectionStyleNoneを設定してやればOKです。

#define CELL_ID @"Cell"

- (UITableViewCell *)tableView:(UITableView *)tv
    cellForRowAtIndexPath:(NSIndexPath *)indexPath {
  UITableViewCell *cell = [tv dequeueReusableCellWithIdentifier:CELL_ID];
  if (cell == nil) {
    cell = [[[UITableViewCell alloc] initWithFrame:CGRectZero reuseIdentifier:CELL_ID] autorelease];
    // ハイライトなし
    cell.selectionStyle = UITableViewCellSelectionStyleNone;
  }
  cell.text = @"Hoge";
  return cell;
}

また画面遷移はしないけど行を選択したときに何かアクションが発生する場合(行チェックとか)はtableView:didSelectRowAtIndexPath:メソッドでハイライトを解除してやればOKです。

-(void)tableView:(UITableView *)tv didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
  // ハイライト解除
  [tv deselectRowAtIndexPath:indexPath animated:YES];
}