你必须传递一个有效NSIndexPath
的 to cellForRowAtIndexPath:
。您使用了 0,这意味着没有 indexPath。
你应该使用这样的东西:
UITableViewCell *tvc = [tv cellForRowAtIndexPath:[NSIndexPath indexPathForRow:0 inSection:0]];
但是。不要这样做。不要在 UITableViewCell 中保存状态。
当开关改变其状态时更新您的数据源。
如果您已经实现了 UITableViewDataSource 方法,那么您的 tableView 重用单元格的正确原因。这意味着当细胞被重复使用时,细胞的状态将消失。
您的方法可能适用于 6 个单元格。但它会失败 9 个单元格。
如果您将第一个单元格滚动到屏幕外,它甚至可能会失败。
我写了一个快速演示(如果你在必要的地方不使用 ARC add release
)来向你展示你应该如何做:
- (void)viewDidLoad
{
[super viewDidLoad];
self.dataSource = [NSMutableArray arrayWithCapacity:6];
for (NSInteger i = 0; i < 6; i++) {
[self.dataSource addObject:[NSNumber numberWithBool:YES]];
}
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = @"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
UISwitch *aSwitch = [[UISwitch alloc] init];
[aSwitch addTarget:self action:@selector(switchChanged:) forControlEvents:UIControlEventValueChanged];
cell.accessoryView = aSwitch;
}
UISwitch *aSwitch = (UISwitch *)cell.accessoryView;
aSwitch.on = [[self.dataSource objectAtIndex:indexPath.row] boolValue];
/* configure cell */
return cell;
}
- (IBAction)switchChanged:(UISwitch *)sender
{
// UITableViewCell *cell = (UITableViewCell *)[sender superview];
// NSIndexPath *indexPath = [self.tableView indexPathForCell:cell];
CGPoint senderOriginInTableView = [sender convertPoint:CGPointZero toView:self.tableView];
NSIndexPath *indexPath = [self.tableView indexPathForRowAtPoint:senderOriginInTableView];
[self.dataSource replaceObjectAtIndex:indexPath.row withObject:[NSNumber numberWithBool:sender.on]];
}
如您所见,不在单元格中存储状态并不是很复杂:-)