textField Editing Changed 反应不够快(异步调用)

textField Editing Changed not reacting fast enough (Asynchronous calls)

我有一个文本字段,用于查询现有用户的 firebase 数据库,然后根据用户是否可用显示 UIImage。问题是一旦加载了异步代码,文本字段就不会对更改的值做出反应。

例子。如果我输入 12345 作为用户名,我不会查询数据库。一切都好。如果我添加 6,它会查询 firebase,它会显示用户是免费的。如果我按退格键并有 12345 再次触发 textFieldChanged,并且不查询数据库。一切都好。

但问题是,当我有 12345 时,我键入 6 并快速返回所以我有 12345,查询是 运行 并显示可用的图标(因为返回被快速按下).这是模拟器的问题,还是一个真正的问题,我可以轻松解决吗?

我的代码:

 @IBAction func textFieldChanged(_ sender: UITextField) {
        if let username = usernameInputText.text, username.count > 5 {
            checkIfUserExists(username: username) { doesExist in    //(2)
                if doesExist! {
                    self.completeSignupButton.isEnabled = false
                    self.ifAvailableImageView.image = UIImage(named: "Close")
                } else {
                    self.completeSignupButton.isEnabled = true
                    self.ifAvailableImageView.image = UIImage(named: "Check")
                }
            }
        } else {
            ifAvailableImageView.image = UIImage(named: "Close")
            self.completeSignupButton.isEnabled = false
        }
}

func checkIfUserExists(username: String, completion: @escaping (Bool?) -> Void) {
    spinner.startAnimating()
    self.ifAvailableImageView.image = nil
    let docRef = db.collection("users").document(username)
    docRef.getDocument { (document, error) in
        if error != nil {
            self.spinner.stopAnimating()
            completion(nil)
        } else {
            self.spinner.stopAnimating()
            if let document = document {
                if document.exists {
                    completion(true)
                } else {
                    completion(false)
                }
            }
        }
    }
}

您可以将正在处理的用户名与文本字段中的当前文本进行比较,如果结果不是相同,因为您只想处理最新的一个。

@IBAction func textFieldChanged(_ sender: UITextField) {
        if let username = usernameInputText.text, username.count > 5 {
            checkIfUserExists(username: username) { doesExist in    //(2)
                // Check if current text and the completion being processed are for the same username
                if username != sender.text {
                    return                    
                }
                if doesExist! {
                    self.completeSignupButton.isEnabled = false
                    self.ifAvailableImageView.image = UIImage(named: "Close")
                } else {
                    self.completeSignupButton.isEnabled = true
                    self.ifAvailableImageView.image = UIImage(named: "Check")
                }
            }
        } else {
            ifAvailableImageView.image = UIImage(named: "Close")
            self.completeSignupButton.isEnabled = false
        }
}