UITextField返回键下一个bug

时间:2016-03-31 09:39:09

标签: ios swift uitextfield

问题标题的解释

这是InputViewController代码的一部分:

class InputViewController: UIViewController, UITextFieldDelegate {
    private var firstResponderTag = 0
    ...
    func textFieldDidBeginEditing(textField: UITextField) {
        firstResponderTag = textField.tag
    }

    func textFieldShouldReturn(textField: UITextField) -> Bool {
        if let nextResponder = textField.superview?.viewWithTag(textField.tag + 1) {
            nextResponder.becomeFirstResponder()
        } else {
            textField.resignFirstResponder()
        }
        return true
    }
    ...
}

和SigningInViewController:

class SigningInViewController: InputViewController {
    ...
    @IBOutlet
    private weak var emailTextField: TextField! {
        didSet {
            emailTextField.validator = EmailValidator()
        }
    }

    @IBOutlet
    private weak var passwordTextField: TextField! {
        didSet {
            passwordTextField.validator = PasswordValidator()
        }
    }

    override func viewDidLoad() {
        super.viewDidLoad()

        Observable.combineLatest(emailTextField.rx_text, passwordTextField.rx_text, resultSelector: {
            (email: String, password: String) in
            email.length > 0 && password.length > 0
        }).bindTo(signInButton.rx_enabled).addDisposableTo(bag)
    }
    ...
}

问题是,如果我按下返回键Next,下一个文本字段将成为第一响应者并立即重新响应第一个响应者。但是,如果我删除绑定返回键应该工作。那么,我做错了什么?

UPD:

我在RxSwift的官方回购中错过了类似的问题。 解决方案

if let nextResponder = textField.superview?.viewWithTag(textField.tag + 1) {
    dispatch_async(dispath_get_main_queue(), {
        nextResponder.becomeFirstResponder()
    })
} else {

2 个答案:

答案 0 :(得分:0)

我无法在代码中找到错误原因,但我可以分享我刚刚写的代码示例。

class NextTextField: UITextField, UITextFieldDelegate {

    @IBOutlet weak var returnView: UIView? {
        didSet {
            if returnView is UITextField {
                returnKeyType = UIReturnKeyType.Next
            }
        }
    }

    override func awakeFromNib() {
        super.awakeFromNib()

        delegate = self
    }

    func textFieldShouldReturn(textField: UITextField) -> Bool {

        if let nextTextField = self.returnView as? UITextField {
            nextTextField.becomeFirstResponder()
        } else if let nextButton = self.returnView as? UIButton {
            nextButton.sendActionsForControlEvents(.TouchUpInside)
        } else {
            self.resignFirstResponder()
        }

        return true
    }

}

它只是向textField添加一个弱returnView,可以通过代码或故事板轻松设置。当按下文本字段的返回键时,如果是另一个文本字段,它会使第一个响应者成为returnView,如果一个按钮是returnView则触摸该按钮,如果没有returnView则隐藏键盘。

答案 1 :(得分:0)

在Swift和RxSwift / RxCocoa 3.0.1中

placeTextField.rx.controlEvent(UIControlEvents.editingDidEndOnExit)

工作正常

而不是使用textFieldShouldReturn