web-dev-qa-db-fra.com

UITextField Devrait accepter uniquement des valeurs numériques

J'ai UITexfields je veux qu'il devrait accepter uniquement le nombre d'autres émissions d'alerte qui entrent une valeur numérique . Je veux que motionSicknessTextFiled n'accepte que le nombre 

NSString*dogswithMotionSickness=motionSicknessTextField.text;
NSString*valueOne=cereniaTextField.text;
NSString*valueTwo=prescriptionTextField.text;
NSString*valueThree=otherMeansTextField.text;
NSString*valueFour=overtheCounterTextField.text;
25
james

Quel que soit le champ UITextField à partir duquel vous obtenez ces valeurs, vous pouvez spécifier le type de clavier à afficher lorsque quelqu'un touche au sein du champ de texte.

PAR EXEMPLE. un clavier uniquement numérique.

Comme cette capture d'écran:

numeric only keyboard will appear

Ceci est facilement défini lorsque vous utilisez XIB et le Générateur d'interface intégré à Xcode, mais si vous souhaitez comprendre cela par programmation, consultez la page de référence du protocole UITextInputTraits d'Apple, en particulier le keyboardType propriété information.

Pour filtrer les ponctuations, définissez le délégué du champ de texte et configurez la méthode shouldChangeCharactersInRange:

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
    NSCharacterSet *numbersOnly = [NSCharacterSet characterSetWithCharactersInString:@"0123456789"];
    NSCharacterSet *characterSetFromTextField = [NSCharacterSet characterSetWithCharactersInString:textField.text];

    BOOL stringIsValid = [numbersOnly isSupersetOfSet:characterSetFromTextField];
    return stringIsValid;
}
53

Objectif c

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
    if (!string.length) 
        return YES;

    if (textField == self.tmpTextField)
    {
        NSString *newString = [textField.text stringByReplacingCharactersInRange:range withString:string];
        NSString *expression = @"^([0-9]+)?(\\.([0-9]{1,2})?)?$";
        NSRegularExpression *regex = [NSRegularExpression regularExpressionWithPattern:expression 
                                                                               options:NSRegularExpressionCaseInsensitive 
                                                                                 error:nil];
        NSUInteger numberOfMatches = [regex numberOfMatchesInString:newString
                                                            options:0
                                                              range:NSMakeRange(0, [newString length])];        
        if (numberOfMatches == 0)
            return NO;        
    }
    return YES;
}

Swift 3.0

func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    if !string.characters.count {
        return true
    }
    do {
        if textField == self.tmpTextField {
            var newString = textField.text.replacingCharacters(inRange: range, with: string)
            var expression = "^([0-9]+)?(\\.([0-9]{1,2})?)?$"
            var regex = try NSRegularExpression(pattern: expression, options: NSRegularExpressionCaseInsensitive)
            var numberOfMatches = regex.numberOfMatches(inString: newString, options: [], range: NSRange(location: 0, length: newString.characters.count))
            if numberOfMatches == 0 {
                return false
            }
        }
    }
    catch let error {
    }
    return true
}
23
Himanshu padia
[textField setKeyboardType:UIKeyboardTypeNumberPad];
10
Martol1ni

J'ai implémenté l'extrait de code qui contient les fonctionnalités de textField:

  1. Vérifiez les maximum autorisés caractères.
  2. Vérifiez le nombre valide décimal.
  3. Vérifiez uniquement les nombres numériques.

Le code est la méthode UITextField delegate. Avant d'utiliser cet extrait, vous devez avoir les propriétés suivantes:

  1. self.maxCharacters
  2. self.numeric/ Uniquement _/int caractères.
  3. self.decimalNumeric // Seuls les chiffres et ".", "," (pour des paramètres régionaux spécifiques, comme le russe).

Code:

- (BOOL)textField:(UITextField *) textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
    if(self.numeric || self.decimalNumeric)
    {
        NSString *fulltext = [textField.text stringByAppendingString:string];
        NSString *charactersSetString = @"0123456789";

        // For decimal keyboard, allow "dot" and "comma" characters.
        if(self.decimalNumeric) {
            charactersSetString = [charactersSetString stringByAppendingString:@".,"];
        }

        NSCharacterSet *numbersOnly = [NSCharacterSet characterSetWithCharactersInString:charactersSetString];
        NSCharacterSet *characterSetFromTextField = [NSCharacterSet characterSetWithCharactersInString:fulltext];

        // If typed character is out of Set, ignore it.
        BOOL stringIsValid = [numbersOnly isSupersetOfSet:characterSetFromTextField];
        if(!stringIsValid) {
            return NO;
        }

        if(self.decimalNumeric)
        {
            NSString *currentText = [textField.text stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceCharacterSet]];

            // Change the "," (appears in other locale keyboards, such as russian) key ot "."
            currentText = [currentText stringByReplacingOccurrencesOfString:@"," withString:@"."];

            // Check the statements of decimal value.
            if([fulltext isEqualToString:@"."]) {
                textField.text = @"0.";
                return NO;
            }

            if([fulltext rangeOfString:@".."].location != NSNotFound) {
                textField.text = [fulltext stringByReplacingOccurrencesOfString:@".." withString:@"."];
                return NO;
            }

            // If second dot is typed, ignore it.
            NSArray *dots = [fulltext componentsSeparatedByString:@"."];
            if(dots.count > 2) {
                textField.text = currentText;
                return NO;
            }

            // If first character is zero and second character is > 0, replace first with second. 05 => 5;
            if(fulltext.length == 2) {
                if([[fulltext substringToIndex:1] isEqualToString:@"0"] && ![fulltext isEqualToString:@"0."]) {
                    textField.text = [fulltext substringWithRange:NSMakeRange(1, 1)];
                    return NO;
                }
            }
        }
    }

    // Check the max characters typed.
    NSUInteger oldLength = [textField.text length];
    NSUInteger replacementLength = [string length];
    NSUInteger rangeLength = range.length;

    NSUInteger newLength = oldLength - rangeLength + replacementLength;
    BOOL returnKey = [string rangeOfString: @"\n"].location != NSNotFound;

    return newLength <= _maxCharacters || returnKey;
}

Démo:

enter image description here

7
Almas Adilbek

Réponse modifiée de Michael Dautermann:

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
    if(string.length > 0)
    {
        NSCharacterSet *numbersOnly = [NSCharacterSet characterSetWithCharactersInString:@"0123456789"];
        NSCharacterSet *characterSetFromTextField = [NSCharacterSet characterSetWithCharactersInString:string];

        BOOL stringIsValid = [numbersOnly isSupersetOfSet:characterSetFromTextField];
        return stringIsValid;
    }
    return YES;
}
5
Hsm

Voici la solution Swift:

Dans viewDidLoad, définissez le délégué:

_yourTextField.delegate = self
let _acceptableCharacters = "0123456789."

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

    if (string.characters.count == 0) {
        return true
    }

    if (textField == self._yourTextField) {
        let cs = NSCharacterSet(charactersInString: self._acceptableCharacters)
        let filtered = string.componentsSeparatedByCharactersInSet(cs).filter {  !$0.isEmpty }
        let str = filtered.joinWithSeparator("")

        return (string != str)
    }

    return true
}
2
pchelnikov

c'est un travail pour moi

Swift 4  

ci-dessus, utilisez cette fonction pour saisir uniquement un nombre et vous pouvez également définir une limite de caractères.

func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
let aSet = NSCharacterSet(charactersIn:"0123456789").inverted
            let compSepByCharInSet = string.components(separatedBy: aSet)
            let numberFiltered = compSepByCharInSet.joined(separator: "")

            if string == numberFiltered {
                let currentText = textField.text ?? ""
                guard let stringRange = Range(range, in: currentText) else { return false }
                let updatedText = currentText.replacingCharacters(in: stringRange, with: string)
                return updatedText.count <= 10
            }else{
                return false
            }
}
1
ravi alagiya

c'est la fonction qui vérifie que la chaîne ne contient qu'une valeur numérique

+(BOOL) checkforNumeric:(NSString*) str
{
    NSString *strMatchstring=@"\\b([0-9%_.+\\-]+)\\b"; 
    NSPredicate *textpredicate=[NSPredicate predicateWithFormat:@"SELF MATCHES %@", strMatchstring];

    if(![textpredicate evaluateWithObject:str])
    {
        //////NSLog(@"Invalid email address found");
        UIAlertView *objAlert = [[UIAlertView alloc] initWithTitle:APP_NAME message:@"please enter valid text." delegate:nil cancelButtonTitle:nil otherButtonTitles:@"Close",nil];
        [objAlert show];
        [objAlert release];
        return FALSE;
    }
    return TRUE;
}

vérifiez-le sur le bouton d'envoi.

1
Prabhat Kasera

Cette réponse jeté une erreur dans Swift 3, voici la réponse de travail:

func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    if string.characters.count == 0 {
        return true
    }
    do {
        if textField == self.numberTextField {

            let nString = textField.text as NSString?
            let newString = nString?.replacingCharacters(in: range, with: string)
            let expression = "^([0-9]+)?(\\.([0-9]{1,2})?)?$"
            let regex = try NSRegularExpression(pattern: expression, options: .caseInsensitive)
            let numberOfMatches = regex.numberOfMatches(in: newString! as String, options: [], range: NSRange(location: 0, length: (newString?.characters.count)!))

            if numberOfMatches == 0 {
                return false
            }
        }
    }
    catch let error {
    }
    return true
}
0
Arpit Dongre

Swift 4.2 port de la meilleure réponse ici par @ almas-adlibek

Un tas de variables de configuration:

private let kMaxTextLength = 8
private let kZeroDotted = "0."
private let kZero = "0"
private let kDoubleDot = ".."
private let kDot = "."
private let kPeriod = ","

Maintenant, le Swift 4 converti une partie du code.

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

    guard let oldText = textField.text, let swiftRange = Range(range, in: oldText) else {
        return true
    }

    let newText = oldText.replacingCharacters(in: swiftRange, with: string)

    var currentText =  textField.text?.trimmingCharacters(in: CharacterSet.whitespacesAndNewlines)

    // Change the "," (appears in other locale keyboards, such as russian) key ot "."
    currentText = currentText?.replacingOccurrences(of: kPeriod, with: kDot)

    // Check the statements of decimal value.
    if (newText == kDot) {
        textField.text = kZeroDotted;
        return false
    }

    if (newText.range(of: kDoubleDot) != nil) {
        textField.text = newText.replacingOccurrences(of: kDoubleDot, with: kDot);
        return false
    }

    // If second dot is typed, ignore it.
    let dots = newText.components(separatedBy: kDot)
    if(dots.count > 2) {
        textField.text = currentText;
        return false
    }

    // If first character is zero and second character is > 0, replace first with second. 05 => 5;
    if(newText.count == 2) {
        if(newText[0...0] == kZero && newText != kZeroDotted) {
            textField.text = newText[1...1]
            return false
        }
    }

    // Check the max characters typed.
    let oldLength = textField.text?.count ?? 0
    let replacementLength = string.count
    let rangeLength = range.length

    let newLength = oldLength - rangeLength + replacementLength;
    let returnKey = string.rangeOfCharacter(from: CharacterSet.newlines) != nil

    return newLength <= kMaxTextLength || returnKey;
}
0
Michael

Une autre option permettant de saisir uniquement des valeurs numériques dans votre champ de texte consiste à sélectionner l'attribut de type de clavier du champ de texte correspondant. Joindre la capture d'écran pour référence.  Number Pad Selection

0
Haseeb Mohamed

Je viens de modifier la réponse de Michael et de la rendre un peu plus facile à mettre en œuvre. Assurez-vous simplement que le délégué de votre UITextfield est défini sur lui-même.

yourTxtField.delegate = self;

De plus, copiez et collez ce code dans votre fichier principal. 

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string  {

    if (textField == yourTxtField) {
        NSCharacterSet *numbersOnly = [NSCharacterSet characterSetWithCharactersInString:@"0123456789"];
        NSCharacterSet *characterSetFromTextField = [NSCharacterSet characterSetWithCharactersInString:string];

        BOOL stringIsValid = [numbersOnly isSupersetOfSet:characterSetFromTextField];
            return stringIsValid;
        }else {
            return YES;
        }
    }

Si vous voulez autoriser l'utilisation de la barre d'espace, mettez simplement un espace vide à la fin de la CharactersInString, comme ceci

@"0123456789" -> @"0123456789 "

Aditionellement:

Si vous souhaitez limiter la longueur de la chaîne, remplacez simplement la fonction if par la suivante:

if (textField == yourTxtField) {
        NSUInteger newLength = [textField.text length] + [string length] - range.length;
        NSCharacterSet *cs = [[NSCharacterSet characterSetWithCharactersInString:@"1234567890"] invertedSet];
        NSString *filtered = [[string componentsSeparatedByCharactersInSet:cs] componentsJoinedByString:@""];
        return (([string isEqualToString:filtered])&&(newLength <= 10));

    }

Dans mon cas, le "10" à la fin représente la limite de caractères. 

À votre santé! :) 

0
MasterRazer