3

I am having a UITextField in which i get the month number as input. I am successful in limiting the no of characters to 2 in the UITextField. But i want users to enter only the values from 1 to 12 and none other than that. This has to be done simultaneously when the user types the numbers i.e in func textField(textField: UITextField!, shouldChangeCharactersInRange range: NSRange, replacementString string: String!) -> Bool. If i use a simple if condition to check the each character and return false in else part the textfield won't allow me to use clear or retype any other character. someone help me.

Kautham Krishna
  • 967
  • 1
  • 14
  • 33

6 Answers6

5

Set keyboard type as Number Pad

add this

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

    if let text = textField.text {

        let newStr = (text as NSString)
            .stringByReplacingCharactersInRange(range, withString: string)
        if newStr.isEmpty {
            return true
        }
        let intvalue = Int(newStr)
        return (intvalue >= 0 && intvalue <= 12)
    }
    return true
}
Aruna Mudnoor
  • 4,795
  • 14
  • 16
  • thanks this works great with my code`var length = (count(textField.text) + count(string) - range.length)` and returned as `return length < 3 && (intvalue > 0 && intvalue <= 12) ? true : false` – Kautham Krishna Jan 07 '16 at 09:29
  • `? true : false` is redundant `return 1...12 ~= intvalue` – Leo Dabus Apr 29 '17 at 04:56
3

You can do it simultaneously by checking the TextField value inside shouldChangeCharactersInRange.

func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
    let inputStr = textField.text?.stringByAppendingString(string)
    let inputInt = Int(inputStr!)
    if inputInt > 0 && inputInt < 13 {
        return true
    } else {
        return false
    }
}
Thanh Pham
  • 57
  • 3
2

=> you can Define limite of char like this:-

#define NUMBERS_ONLY @"1234567890"

#define  CHARACTER_LIMIT 2

=> and based on define limit char you can use and try it below method :-

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

        NSUInteger newLength = [textField.text length] + [string length] - range.length;

        NSCharacterSet *cs = [[NSCharacterSet characterSetWithCharactersInString:NUMBERS_ONLY] invertedSet];

        NSString *filtered = [[string componentsSeparatedByCharactersInSet:cs] componentsJoinedByString:@""];

        return (([string isEqualToString:filtered])&&(newLength <= CHARACTER_LIMIT));

    }
Rohit Khandelwal
  • 1,778
  • 15
  • 23
Akash
  • 461
  • 2
  • 14
  • this objective c code is nothing different than the swift answer above. it is just the objective c version with character limit . `var length = (count(textField.text) + count(string) - range.length)` and `return length < 3` this is the swift 1.2 for simple length constrain – Kautham Krishna Jan 07 '16 at 08:09
0
func textField(textField: UITextField,
    shouldChangeCharactersInRange range: NSRange,
    replacementString string: String) -> Bool {

        // Create an `NSCharacterSet` set which includes everything *but* the digits
        let inverseSet = NSCharacterSet(charactersInString:"0123456789").invertedSet

        // At every character in this "inverseSet" contained in the string,
        // split the string up into components which exclude the characters
        // in this inverse set
        let components = string.componentsSeparatedByCharactersInSet(inverseSet)

        // Rejoin these components
        let filtered = components.joinWithSeparator("")  // use join("", components) if you are using Swift 1.2

        // If the original string is equal to the filtered string, i.e. if no
        // inverse characters were present to be eliminated, the input is valid
        // and the statement returns true; else it returns false
        return string == filtered

}

see this link-- Limit UITextField input to numbers in Swift

Community
  • 1
  • 1
Rohit Khandelwal
  • 1,778
  • 15
  • 23
  • add if condition in this function to check value of textfield is less then equal to 12 and greater than equal to 1. – Rohit Khandelwal Jan 07 '16 at 07:42
  • I already tried this code it allows 13 to 99 too. also if i use if condition and return false i can no longer edit the text field even backspace. – Kautham Krishna Jan 07 '16 at 07:56
0

Check out this to set Limit the numbers and allow only numbers 0 to 9.

func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    if textField == mobileNumber {
        let aSet = NSCharacterSet(charactersIn:"0123456789").inverted
        let compSepByCharInSet = string.components(separatedBy: aSet)
        let numberFiltered = compSepByCharInSet.joined(separator: "")
        let length = (mobileNumber.text?.count)! + string.count - range.length
        return string == numberFiltered && length <= LIMIT
    }else if textField == userType {
        return false
    }
    return true
}
iSrinivasan27
  • 1,406
  • 1
  • 21
  • 28
0

I just want to post a more simplified answer based on the previous answers.

Tested on Swift 5.1

Considering that you already set textField.keyboardType = .numberPad, then you can do the following:

 func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
        guard let text = textField.text else {
            return true
        }
        let newStr = (text as NSString).replacingCharacters(in: range, with: string)

        guard let intValue = Int(newStr) else {
            return true
        }
        return intValue <= maxNumber // maxNumber: replace with your max number
    }

You dont´need to validate that intValue is greater or equal to 0 because in numberPad you can NOT write negative values.

Fernando Cardenas
  • 1,203
  • 15
  • 19