我有一个文本字段,用于查询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)
}
}
}
}
}
答案 0 :(得分:1)
您可以将正在处理的用户名与文本字段中的当前文本进行比较,如果结果不相同,则不处理结果,因为您只想处理最新的。
@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
}
}