带有六个单字符文本字段的 OTP 条目表单

Posted

技术标签:

【中文标题】带有六个单字符文本字段的 OTP 条目表单【英文标题】:Form for OTP entry with six single-character text fields 【发布时间】:2018-09-19 09:02:17 【问题描述】:

我正在开发一个应用程序,在该应用程序中,我必须通过 6 个文本字段传递 6 位 OTP,在其中您只提供一个字符,然后它会自动转到另一个文本字段。我创建了 6 个 textFields 网点并使用了这段代码。我遇到的问题是我想更改特定的textField OTP 编号,但问题是如果我想在点击十字按钮后更改文本字段 4 的 OTP 编号,它会自动转到文本字段 3。我该如何解决这个问题问题?

我使用的代码:

import UIKit

class OneTimePasswordViewController: UIViewController, UITextFieldDelegate 

    @IBOutlet weak var txtOTP1: UITextField!
    @IBOutlet weak var txtOTP2: UITextField!
    @IBOutlet weak var txtOTP3: UITextField!
    @IBOutlet weak var txtOTP4: UITextField!
    @IBOutlet weak var txtOTP5: UITextField!
    @IBOutlet weak var txtOTP6: UITextField!

    override func viewDidLoad() 
        super.viewDidLoad()
        txtOTP1.delegate = self
        txtOTP2.delegate = self
        txtOTP3.delegate = self
        txtOTP4.delegate = self
        txtOTP5.delegate = self
        txtOTP6.delegate = self

       self.txtOTP1.becomeFirstResponder()
    

这里是创建逻辑的代码:

func textField(_ textField: UITextField, shouldChangeCharactersIn range:NSRange, replacementString string: String) -> Bool 

    if (range.length == 0)
        if textField == txtOTP1 txtOTP2?.becomeFirstResponder()
        if textField == txtOTP2 txtOTP3?.becomeFirstResponder()
        if textField == txtOTP3 txtOTP4?.becomeFirstResponder()
        if textField == txtOTP4 txtOTP5?.becomeFirstResponder()
        if textField == txtOTP5 txtOTP6?.becomeFirstResponder()
        if textField == txtOTP6 txtOTP6?.resignFirstResponder()
        textField.text? = string
        return false
    
    else if (range.length == 1) 

        if textField == txtOTP6 txtOTP5?.becomeFirstResponder()
        if textField == txtOTP5 txtOTP4?.becomeFirstResponder()
        if textField == txtOTP4 txtOTP3?.becomeFirstResponder()
        if textField == txtOTP3 txtOTP2?.becomeFirstResponder()
        if textField == txtOTP2 txtOTP1?.becomeFirstResponder()
        if textField == txtOTP1 txtOTP1?.resignFirstResponder()

        textField.text? = ""
        return false
    
    return true

【问题讨论】:

首先,尝试使用 [UITextField] 的 Outlet 集合,而不是单独声明每个字段。这将减少大量或重复的代码 实际上,先生,问题是不同的,我想更改 4 文本字段,但是当单击十字按钮时,它转到 3 文本字段,我想在文本字段 4 上出现。 我的评论不能解决您的问题 - 但它会为您提供更简洁、更易于阅读和更新的代码。 好的先生,我会试试的,但你知道这个问题的解决方案吗? 这是发送到您移动设备的密码吗?如果是这样,请观看有关安全代码自动填充的 WWDC 视频……developer.apple.com/videos/play/wwdc2018/204 【参考方案1】:

你可以试试我的 3rd 方库:- https://github.com/Datt1994/DPOTPView

解决方案:-

在 viewDidLoad 中添加标签和委托给所有textfield

import UIKit

class OneTimePasswordViewController: UIViewController, UITextFieldDelegate 

     @IBOutlet weak var txtOTP1: UITextField!
     @IBOutlet weak var txtOTP2: UITextField!
     @IBOutlet weak var txtOTP3: UITextField!
     @IBOutlet weak var txtOTP4: UITextField!
     @IBOutlet weak var txtOTP5: UITextField!
     @IBOutlet weak var txtOTP6: UITextField!

    override func viewDidLoad() 
        super.viewDidLoad()
        txtOTP1.delegate = self
        txtOTP1.tag = 1000
        txtOTP2.delegate = self
        txtOTP2.tag = 2000
        txtOTP3.delegate = self
        txtOTP3.tag = 3000
        txtOTP4.delegate = self
        txtOTP4.tag = 4000
        txtOTP5.delegate = self
        txtOTP5.tag = 5000
        txtOTP6.delegate = self
        txtOTP6.tag = 6000

       self.txtOTP1.becomeFirstResponder()
   

在 UITextFieldDelegate 扩展中实现shouldChangeCharactersIn 函数,如下所示,它也适用于textField.textContentType = .oneTimeCode

extension OneTimePasswordViewController : UITextFieldDelegate  

public func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool 
    if string.trimmingCharacters(in: CharacterSet.whitespaces).count != 0 
        textField.text = string
        if textField.tag < count*1000 
            let next = textField.superview?.viewWithTag((textField.tag/1000 + 1)*1000)
            next?.becomeFirstResponder()
         else if textField.tag == count*1000 
            textField.resignFirstResponder()
        
     else if string.count == 0  // is backspace
        textField.text = ""
    

    return false



【讨论】:

以上是关于带有六个单字符文本字段的 OTP 条目表单的主要内容,如果未能解决你的问题,请参考以下文章

django 将占位符文本添加到表单字段

如何设置 xamarin 表单输入字段的禁用文本颜色?

PHP 表单邮件不会返回带有@yahoo.com 地址的条目

如何在stackview文本字段中快速获取otp的动态数字键盘中的数字

Powerpoint SaveAs 文本框表单条目

带有自定义组件的 Material ui 文本字段和 Formik 表单