iOS7에서 UITableViewCell의 AccessoryView에 버튼을 배치하고 버튼의 selector에서 cell을 참조하기

아래와 같이 특정 서비스에서 친구를 초대하거나 follow할 때 주로 쓰는 UI화면이 있다.

aaaa

UITableView에 UITableViewCell 혹은 이를 상속받는 클래스 구조인데,
여기서 Invite 버튼을 터치했을 때 버튼이 속하는 NSIndexPath를 받기 위해 아래와 같이 코딩을 할 때가 있다.

/* UITableView의 data source 메소드 중 cellForRowAtIndexPath: 메소드 */

- (UITableViewCell *)tableView:(UITableView *)tableView 
         cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];

    if (!cell) {

        UIButton *inviteButton = [UIButton buttonWithType:UIButtonTypeRoundedRect];

        /* 프로퍼티 정의는 생략 */

        [inviteButton addTarget:self 
                         action:@selector(onInvite:) 
               forControlEvents:UIControlEventTouchUpInside];

        cell.accessoryView = inviteButton;
    }

    return cell;
}

/* Invite 버튼의 selector 메소드 */

- (void)onInvite:(id)sender
{
    if ([sender isKindOfClass:[UIButton class]]) {

        UIButton *inviteButton = (UIButton *)sender;

        UITableViewCell *selectedCell = (UITableViewCell *)[inviteButton superview];
        NSIndexPath *indexPath = [_tableView indexPathForCell:selectedCell];

        NSLog(@"selected row is :%d", indexPath.row);
    }
}

이 경우 onInvite: 메소드의 [inviteButton superview] 가 iOS7 미만에서는 포인터를 가져오는데 문제가 없었지만
iOS7 부터는 문제가 된다.

view의 구조를 봤을 때 Invite 버튼은 UITableViewCell의 accesoryView로 대치되었기 때문에 superview는 UITableViewCell이 된다.
하지만 iOS7에서는 Invite 버튼과 UITableViewCell 사이에 UITableViewScroll이라는 뷰가 위치한다.

iOS 7 미만일 때의 결과

iOS 7 미만일 때의 결과

iOS7 일 때의 결과

iOS7 일 때의 결과

이와 같이 iOS7에서 여러 View에서 상위 view를 참조할 경우에는 꼭 확인을 해보길 바란다.

Leave a Comment

This site uses Akismet to reduce spam. Learn how your comment data is processed.