2017-09-26 3 views
0

Je peux changer mon chemin pour présenter les nombres dans le champ de texte en utilisant la ligne de code suivante basée sur ce que je tape dans le champ de texte. Mais je ne peux même pas taper des nombres dans la deuxième version de mon code.Pourquoi le remplacement des caractères est-il nécessaire pour changer le texte dans le champ de texte?

Pourquoi

[let oldText = textField.text! as NSString 
var newText = oldText.replacingCharacters(in: range, with: string)] 

est nécessaire?

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

    let oldText = textField.text! as NSString 
    var newText = oldText.replacingCharacters(in: range, with: string) 

    var newTextString = String(newText) 

    let digits = CharacterSet.decimalDigits 
    var digitText = "" 
    for c in (newTextString?.unicodeScalars)! { 
     if digits.contains(UnicodeScalar(c.value)!) { 
      digitText.append("\(c)") 
     } 
    } 

    // Format the new string 
    if let numOfPennies = Int(digitText) { 
     newText = "$" + self.dollarStringFromInt(numOfPennies) + "." + self.centsStringFromInt(numOfPennies) 
    } else { 
     newText = "$0.00" 
    } 

    textField.text = newText 

    return false 
} 

func textFieldDidBeginEditing(_ textField: UITextField) { 
    if textField.text!.isEmpty { 
     textField.text = "$0.00" 
    } 
} 

func textFieldShouldReturn(_ textField: UITextField) -> Bool { 
    textField.resignFirstResponder() 

    return true; 
} 

func dollarStringFromInt(_ value: Int) -> String { 
    return String(value/100) 
} 

func centsStringFromInt(_ value: Int) -> String { 

    let cents = value % 100 
    var centsString = String(cents) 

    if cents < 10 { 
     centsString = "0" + centsString 
    } 

    return centsString 
} 

Si je le change comme ceci, ça ne marche plus.

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

    var newText = textField.text 


    let digits = CharacterSet.decimalDigits 
    var digitText = "" 
    for c in (newText?.unicodeScalars)! { 
     if digits.contains(UnicodeScalar(c.value)!) { 
      digitText.append("\(c)") 
     } 
    } 

    // Format the new string 
    if let numOfPennies = Int(digitText) { 
     newText = "$" + self.dollarStringFromInt(numOfPennies) + "." + self.centsStringFromInt(numOfPennies) 
    } else { 
     newText = "$0.00" 
    } 

    textField.text = newText 

    return false 
} 

Répondre

0

textField(_:shouldChangeCharactersIn:replacementString:) est appelé avant le texte est remplacé dans le champ de texte. Cette méthode est utilisée pour obtenir le nouveau texte avant qu'il ne soit accessible avec textField.text.

Si vous voulez simplement exécuter la logique après le remplacement, observez la notification appelée .UITextFieldTextDidChange.

NotificationCenter.default.addObserver(self, selector: #selector(textFieldTextDidChange), name: .UITextFieldTextDidChange, object: textField) 

func textFieldTextDidChange() { 
    print(textField.text) 
} 
0

"shouldChangeCharactersIn" est appelée avant le champ de texte est modifié. Comme votre code renvoie toujours false, tout ce que l'utilisateur a tapé (ou collé) ne mettra pas à jour le contenu du champ sauf si vous le faites vous-même.

Dans la deuxième version, vous ignorez complètement l'entrée de l'utilisateur afin que la valeur de votre champ ne change jamais.

0

Permet de répondre par la partie.

1) La méthode replacingCharacters(in: range, with: string) n'est pas requise. Ces méthodes remplaceront la sous-chaîne correspondant à la plage spécifiée. Ainsi, selon des docs Apple:

stringByReplacingCharactersInRange: withString:

Renvoie une nouvelle chaîne dans laquelle les caractères dans une plage spécifiée du récepteur sont remplacés par une chaîne donnée

2) La véritable raison pour laquelle le changement de code ne fonctionne pas est la valeur de retour false. Essayez de retourner true et la modification va fonctionner. Chaque fois que vous définissez la propriété text du champ de texte, la méthode textField:shouldChangeCharactersIn:replacementString: est appelée (puisque son délégué est affecté). Renvoyant false vous dites au programme qu'il ne doit pas remplacer les caractères.

MISE À JOUR

Essayez d'utiliser l'événement UIControl Value Changed comme @IBAction au lieu textField:shouldChangeCharactersIn:replacementString: cela fonctionne bien.

obs: Désolé pour mon anglais

+0

Si la méthode shouldChangeCharactersIn met directement à jour le texte du champ de texte, alors il doit retourner faux. – rmaddy

+0

@rmaddy merci avez-vous une idée de la raison pour laquelle la première version utilise la méthode .replacingCharacters pour changer le texte? Je veux dire qu'il y a plusieurs façons de changer le texte dans le champ de texte sans utiliser cette ligne supplémentaire. Y a-t-il un avantage à utiliser cela? –

+0

@willianPoliciano merci! après avoir changé la valeur de retour, cela fonctionne bien avec la deuxième version. mais j'ai encore une question à voir si vous pouvez m'aider avec. Je l'adresse à la réponse à rmaddy –