我正在使用以下代码在我的UITableView中实现联系人复选框功能。
我遇到的问题是,当检查几个用户然后向上/向下滚动表时,不应该被检查的用户显示为已选中,反之亦然。
我认为它与我的细胞创建中的错误有关,但我不太确定是什么。
- (void)viewDidLoad {
...
self.checkedUsers = [[NSMutableArray alloc] init];
for (int i=0; i<self.allContacts.count; i++) {
[self.checkedUsers insertObject:@"FALSE" atIndex:i];
}
...
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *simpleTableIdentifier = @"SocietyContactCell";
SocietyContactCell *cell = (SocietyContactCell *)[tableView dequeueReusableCellWithIdentifier:simpleTableIdentifier];
if (cell == nil) {
NSArray *nib = [[NSBundle mainBundle] loadNibNamed:@"SocietyContactCell" owner:self options:nil];
cell = [nib objectAtIndex:0];
}
BOOL checked = [[self.checkedUsers objectAtIndex:indexPath.row] boolValue];
UIImage *image = (checked) ? [UIImage imageNamed:@"checkedContact.png"] : [UIImage imageNamed:@"uncheckedContact.png"];
[cell.checkButton setBackgroundImage:image forState:UIControlStateNormal];
[cell.checkButton addTarget:self action:@selector(buttonPressedAction:) forControlEvents:UIControlEventTouchUpInside];
}
- (void)buttonPressedAction:(id)sender
{
UIButton *button = (UIButton *)sender;
int row = button.tag;
BOOL checked = [[self.checkedUsers objectAtIndex:row] boolValue];
[self.checkedUsers removeObjectAtIndex:row];
[self.checkedUsers insertObject:(checked) ? @"FALSE":@"TRUE" atIndex:row];
UIImage *newImage = (checked) ? [UIImage imageNamed:@"uncheckedContact.png"] : [UIImage imageNamed:@"checkedContact.png"];
[button setBackgroundImage:newImage forState:UIControlStateNormal];
}
编辑:我现在意识到这个问题很可能源于我在这个TableView中使用的部分。联系人按字母顺序排列,这会搞乱我的标签。
如何使用部分解决此问题?
答案 0 :(得分:0)
此处的问题是保留单元格中的复选标记状态。由于表单元格在滚动时被重用,因此再次调用cellForRowAtIndexPath
方法,并且不再在那里设置复选标记的值。
您必须创建一个全局数组,该数组将存储每个indexPath
的复选标记的状态。然后,您可以在checked/unchecked
方法中设置复选标记按钮cellForRowAtIndexPath
的状态。
添加以下代码段以及代码show:
[cell.checkButton addTarget:self action:@selector(buttonPressedAction:) forControlEvents:UIControlEventTouchUpInside];
[cell.checkButton setTag:indexPath.row];
另外,请替换这些行:
[self.checkedUsers removeObjectAtIndex:row];
[self.checkedUsers insertObject:(checked) ? @"FALSE":@"TRUE" atIndex:row];
用这个:
[self.checkedUsers replaceObjectAtIndex:row withObject:checked ? @"TRUE" : @"FALSE"];
答案 1 :(得分:0)
我不知道你每次在cellForRowAtIndexPath:中设置button.tag的位置,所以action方法可能会更新self.checkedUsers数组中的错误行,尽管action方法会独立更新单元格&#39 ;此刻正确的图像。然而,当您向上和向下滚动时,显示将返回到self.checkedUsers数组中的状态。
您可能需要一行:
cell.checkButton.tag = indexPath.row;
你的cellForRowAtIndexPath:方法中的。
其次,你的action方法是在self.itsToDoChecked上获取状态,然后更新self.checkedUsers数组,当它出现时它应该作用于同一个数组(简单地反转给定行索引的状态)。不确定这只是一个示例代码错误或重要的事情。
编辑:也有可能在单元子类中有状态导致问题;很难确定。您希望在该类中实现-prepareForReuse(并始终调用super)以将任何状态重置为初始值。
答案 2 :(得分:0)
在您的SocietyContactCell类中添加以下方法:
- (void)prepareForReuse {
[super prepareForReuse];
[self.checkButton setBackgroundImage:nil forState:UIControlStateNormal];
}