今天早些时候,我问了question关于Textfields的问题。现在我被困在如何遍历每个UITextFields。
如何遍历某个部分的每个UITextfield?
到目前为止,这是我的代码:
- (IBAction)ForwardReport:(id)sender {
NSLog(@"PRESSED");
for (UITableViewCell *cell in [self.tableView.indexPathsForVisibleRows]) {
if ([cell isKindOfClass:[UITextField class]]) {
UITextField *textField = (UITextField *)cell;
NSLog(@"UITEXTFIELD TEXT = %@", textField.text);
}
}
}
我尝试了this answer,但遗憾的是我的代码无法编译。
我不知道如何在UItableView Delegate之外访问第1部分(第二部分)。
我想遍历每个UITextfield,并检索其文本值。
请建议:
这是一个截屏
我想我的另一个选择是为每个字段创建IBoutlet,并且有一堆if / else语句,但听起来有点混乱....
答案 0 :(得分:1)
您应该搜索UITextField,而不是在单元格的子视图中搜索。
尝试以下
- (IBAction)ForwardReport:(id)sender {
NSLog(@"PRESSED");
for (UITableViewCell *cell in self.tableView.visibleCells) {
for (UIView *subview in [cell.contentView subviews])
if ([subview isKindOfClass:[UITextField class]]) {
UITextField *textField = (UITextField *) subview;
NSLog(@"UITEXTFIELD TEXT = %@", textField.text);
}
}
}
}
答案 1 :(得分:1)
我的建议不是这样做的。由于可重用性,您不能依赖嵌入在tableView单元格中的UITextField
的内容。
您的视图控制器应直接绑定到模型,因此,更改textField中的文本应立即更新模型,因此,当您滚动并重复使用单元格时,将分配正确的值。当你点击“前进”时,你只需查询模型的内容(无论如何,这可能是一个简单的NSMutableArray
)。
让我们添加一个NSMutableArray,其中包含与textFields一样多的空字符串(例如5):
- (instancetype)initWithWhatever...
{
self = [super initWithWhatever];
if (self)
{
_textFieldValues = [NSMutableArray arrayWithCapacity:5];
for (NSInteger i=0; i < 5; i++)
{
_textFieldValues[i] = @"";
}
}
return self;
}
确保每个文本字段都指向cellForRowAtIndexPath:
上的viewController。
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
...
myCell.textField.text = _textFieldValues[indexPath.row];
myCell.textField.tag = 100 + indexPath.row;
myCell.textField.delegate = self;
return myCell
}
标记用于标识每个单元格,其他选项是创建自己的UITextField
子类或使用自定义setValueForKey:
。
无论您选择什么,当您获得委托方法(UITextFieldDelegate
)时,请检查您的首选方法,在我的情况下标记:
- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
NSString *replaced = [textField.text stringByReplacingCharactersInRange:range withString:string];
_textFieldValues[(textField.tag - 100)] = replaced;
return YES;
}
这将使模型始终保持最新,并且您不需要在数组上迭代文本字段:
// Method that gets called when hitting forward
- (IBOutlet)didPressForwardButton:(UIButton*)sender
{
for (NSString *text in _textFieldValues)
{
NSLog(@"UITEXTFIELD TEXT = %@", text);
}
}
课程:使用UITableView
时,您应该始终将视图上的内容映射到模型上的内容,并立即更新,您不能依赖视图来保存数据。实际上,这应该扩展到你在iOS中做的任何事情,视图用于节目。如果您无法立即修改实际模型,则必须将其封装在“事务”中间对象中,然后更新实际模型。
答案 2 :(得分:0)
在AVT的回答中,摆脱for循环中self.tableView.visibleCells周围的括号。然后它会读
for (UITableViewCell *cell in self.tableView.visibleCells)
然后下一个for循环应该真正使用单元格的内容视图的子视图:
for (UIView *subview in [cell.contentView subviews])
然而,这些都是小问题。
有一个更重要的设计问题。您不应该遍历当前可见的单元格。表视图单元是瞬态的。如果用户在屏幕上滚动表格视图单元格,它的内容将被丢弃 - 并丢失。
当用户输入该信息时,您应该从单元格中的视图对象收集信息:交换机和分段控件应该挂接到出口,立即将用户更改保存到数据模型中。与文本字段类似,您需要设置一个委托,并在完成输入后立即收集用户的输入并将其保存到数据模型中。
答案 3 :(得分:0)
您的代码中有两个错误。
第一个问题:
UITableViewCell *cell in [self.tableView.indexPathsForVisibleRows]
将无效,因为self.tableView.indexPathsForVisibleRows
会返回indexPath
s而不是UITableViewCell
的数组。试试这个:
- (IBAction)ForwardReport:(id)sender {
NSLog(@"PRESSED");
for (NSIndexPath *indexPath in [self.tableView indexPathsForVisibleRows]) {
UITableViewCell *cell = [self.tableView cellForRowAtIndexPath:indexPath];
...
}
}
第二个问题:
UITextField *textField = (UITextField *)cell;
UITextField
不是UITableViewCell
的子类,因此您无法将表格视图单元格转换为textField。相反,您必须遍历单元格中包含的所有子视图。所以整个方法是:
- (IBAction)ForwardReport:(id)sender {
NSLog(@"PRESSED");
for (NSIndexPath *indexPath in [self.tableView indexPathsForVisibleRows]) {
UITableViewCell *cell = [self.tableView cellForRowAtIndexPath:indexPath];
for (UIView *subview in cell.subviews)
if ([subview isKindOfClass:[UITextField class]]) {
UITextField *textField = (UITextField *)subview;
NSLog(@"UITEXTFIELD TEXT = %@", textField.text);
}
}
}
}
(注意:我尚未测试此代码。)