在 UITextField 上使用“下一个”版本的 Return 按钮移动到下一个 UITextField 的最佳方式

Posted

技术标签:

【中文标题】在 UITextField 上使用“下一个”版本的 Return 按钮移动到下一个 UITextField 的最佳方式【英文标题】:Best way to use "Next" version of Return button on UITextField to move to next UITextField 【发布时间】:2009-06-14 05:49:17 【问题描述】:

我使用“返回键”的“下一步”值来获取“下一步”按钮代替“完成”按钮,但(显然)按下它不会自动移动到我视图中的下一个 UITextField。

这样做的正确方法是什么?在一个更大的话题上,在 iPhone SDK 中正确构建表单有哪些技巧?

【问题讨论】:

要将答案标记为正确,只需单击答案旁边的空白复选标记图标... 【参考方案1】:

使某个对象成为第一个文本字段的委托,并实现- (BOOL)textFieldShouldReturn:(UITextField *)textField 方法;在那里,调用第二个文本字段的-becomeFirstResponder。从中返回YES 将使文本字段执行其返回按钮的默认行为——我认为这通常是发送其操作消息。如果您没有添加任何内容作为该操作的目标,那么您返回的内容并不重要。

【讨论】:

...如果你在最后一个 UITextField 你应该调用 resignFirstResponder 来隐藏键盘。 这是与此处解释的完全不同的方式 (***.com/questions/467881/…) 还是两者都可以正常工作? 两者都可以。我的回答使用委托系统,布拉德是目标行动的东西。 与纯文本相比,示例代码几乎总是更好。 感谢您的建议,Engin。【参考方案2】:

以 Noah 的回答为基础,如果您有很多文本字段并且不想拥有一堆 if,您可以这样做:

- (BOOL)textFieldShouldReturn:(UITextField *)textField

    //[[self.view viewWithTag:textField.tag+1] becomeFirstResponder];

    UIView *view = [self.view viewWithTag:textField.tag + 1];     
    if (!view)         
          [textField resignFirstResponder];     
    else         
          [view becomeFirstResponder];
    return YES;

一旦您从任意数字开始标记每个文本字段,只要它们在情节提要或代码中按顺序标记,它应该可以工作。

【讨论】:

很好的解决方案!一项(次要)建议调整 - 测试 viewWithTag == nil:UIView *view = [self.view viewWithTag:textField.tag + 1]; if (!view) [textField resignFirstResponder]; else [view becomeFirstResponder];【参考方案3】:

对于斯威夫特:

func textFieldShouldReturn(textField: UITextField) -> Bool 
//your collection of textfields
    guard let i = textFields.indexOf(textField) else  return false 
    if i + 1 < textFields.count 
        textFields[i + 1].becomeFirstResponder()
        return true
    
    textField.resignFirstResponder()
    return true

【讨论】:

【参考方案4】:

这似乎工作得很好,不需要许多人建议的标签系统。不过,此解决方案有两点需要注意:

所有 UITextFields 必须在同一个 UIView 中(具有相同的 superview)。

UITextFields 需要在界面构建器中以正确的顺序排列。

-(BOOL)textFieldShouldReturn:(UITextField *)textField    
   /*
   *  1. Loop through the textfield's superview
   *  2. Get the next textfield in the superview  
   *  3. Focus that textfield
   */

   UIView *superView = [textField superview];
   BOOL foundCurrent = false;
   for (UITextField *tf in superView.subviews) 
      // Set focus on the next textfield
      if (foundCurrent) 
         [tf becomeFirstResponder];
         return NO;
      

     //Find current textfield
     if ([tf isEqual:textField]) 
         foundCurrent = true;
      
   

   return YES;
    

【讨论】:

【参考方案5】:

我不喜欢处理标签,所以这是我的解决方案。在您的ViewController 中创建一个包含所有文本字段的IBOutletCollection,拖动以从上到下依次连接您的文本字段。

@interface ViewController () <UITextFieldDelegate>
@property (strong, nonatomic) IBOutletCollection(UITextField) NSArray *allTextFields;
@end

在 viewDidLoad 中设置您的 textFields 委托。 (或将其设置在情节提要中)。

for (VVTextField *tf in self.allTextFields) 
    tf.delegate = self;

然后实现 UITextField Delegate

#pragma mark - UITextField Delegate

- (BOOL)textFieldShouldReturn:(UITextField *)textField 
    NSUInteger currentIndex = [self.allTextFields indexOfObject:textField];
    NSUInteger nextIndex = currentIndex+1;
    if (nextIndex < self.allTextFields.count) 
        [[self.allTextFields objectAtIndex:nextIndex] becomeFirstResponder];
     else 
        [[self.allTextFields objectAtIndex:currentIndex] resignFirstResponder];
    
    return YES;

【讨论】:

这可能有效,但不能保证 IBOutletCollection 数组中的对象顺序正确。 @JAL 有一个很好的观点。您应该考虑编辑您的答案或以某种方式映射值。这可能会导致意外行为。【参考方案6】:

我也一直在努力解决这个问题……因此,我创建了用于处理多个文本字段的小型库。你可以在github上找到它GNKeyboardAwareScrollView#GNTextFieldsManager。

您可以使用文本字段数组对其进行初始化:

NSArray *myTextFields = @[...]; // the order of array matters!
GNTextFieldsManager *manager = [[GNTextFieldsManager alloc] initWithTextFields:myTextFields];

或者通过指定父视图(并为所有视图设置标签):

GNTextFieldsManager *manager = [[GNTextFieldsManager alloc] initWithView:self.view];

希望我对某人有用:)

【讨论】:

以上是关于在 UITextField 上使用“下一个”版本的 Return 按钮移动到下一个 UITextField 的最佳方式的主要内容,如果未能解决你的问题,请参考以下文章

按下返回键时如何在下一个 UITextField 上移动控件

UITextField - 检测内置 iPhone 键盘上的输入?

将存储在 IBAction 中的值传递给下一个 Nib UITextField。

跳到下一个 UItextField

自动向下滚动到下一个 UITextField

使用自定义版本的 UITextField 时引发异常