ios - كيفية تقييد UITextField لأخذ الأرقام فقط في Swift؟




iphone ipad (20)

أريد أن يقوم المستخدم بإدخال قيم رقمية فقط في UITextField . على iPhone يمكننا إظهار لوحة المفاتيح الرقمية ، ولكن على iPad يمكن للمستخدم التبديل إلى أي لوحة مفاتيح.

هل هناك أي طريقة لتقييد المستخدم لإدخال القيم الرقمية فقط في UITextField ؟


1st عليك أن ترث فئة UITextFieldDelegate معك فئة خاصة بك

class ViewController: UIViewController, UITextFieldDelegate {

2nd إضافة IBOutlet

@IBOutlet weak var firstName: UITextField!

3 عليك التأكد من استخدام هذا الكائن

override func viewDidLoad() {
        super.viewDidLoad()
   firstName.delegate = self
}


func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    if textField == firstName {
                let allowedCharacters = "1234567890"
                let allowedCharacterSet = CharacterSet(charactersIn: allowedCharacters)
                let typedCharacterSet = CharacterSet(charactersIn: string)
                let alphabet = allowedCharacterSet.isSuperset(of: typedCharacterSet)
                return alphabet


      }
  }

حل سريع 3.0 وما فوق

func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool
  {
    let allowedCharacters = CharacterSet.decimalDigits
    let characterSet = CharacterSet(charactersIn: string)
    return allowedCharacters.isSuperset(of: characterSet)
  }

إليك حل بسيط ، تحتاج إلى توصيل الحدث "Editing change" بهذه الطريقة في وحدة التحكم الخاصة بك

سويفت 4

@IBAction func valueChanged(_ sender: UITextField) {
    if let last = sender.text?.last {
        let zero: Character = "0"
        let num: Int = Int(UnicodeScalar(String(last))!.value - UnicodeScalar(String(zero))!.value)
        if (num < 0 || num > 9) {
            //remove the last character as it is invalid
            sender.text?.removeLast()
        }
    }
}

إليك حلًا أنظف:

 guard CharacterSet(charactersIn: "123456789").isSuperset(of: CharacterSet(charactersIn: string)) else {
     return false
 }
 return true

لكسر عشرية فقط إضافة . ، مثال 123456789.


استخدام تنسيق الأرقام

سويفت 4.x

func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
      let s = NSString(string: textField.text ?? "").replacingCharacters(in: range, with: string)
      guard !s.isEmpty else { return true }
      let numberFormatter = NumberFormatter()
      numberFormatter.numberStyle = .none
      return numberFormatter.number(from: s)?.intValue != nil
 }

اقبل القيم العشرية في الحقول النصية ذات النقطة الفردية (.) في Swift 3

func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    let inverseSet = NSCharacterSet(charactersIn:"0123456789").inverted

    let components = string.components(separatedBy: inverseSet)

    let filtered = components.joined(separator: "")

    if filtered == string {
        return true
    } else {
        if string == "." {
            let countdots = textField.text!.components(separatedBy:".").count - 1
            if countdots == 0 {
                return true
            }else{
                if countdots > 0 && string == "." {
                    return false
                } else {
                    return true
                }
            }
        }else{
            return false
        }
    }
}

بينما ستنجح معظم هذه الحلول ، كن على دراية بأنه في بعض المواقع ، يتم الفصل بين الكسور العشرية بحرف "،" وليس "."

الطريقة الأنظف للقيام بذلك ستكون

func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
    let decimalCharacter = NSNumberFormatter().decimalSeparator
    let characterSet = NSMutableCharacterSet.decimalDigitCharacterSet()
    characterSet.addCharactersInString(decimalCharacter)

    return replacementString.rangeOfCharacterFromSet(characterSet.invertedSet) == nil
}

تمديد تحكم العرض الخاص بك مثل هذا:

class MyViewController: UIViewController, UITextFieldDelegate

في viewDidLoad وظيفة تمتد إلى حقل النص الخاص بك مثل هذا:

myTextField.delegate = self

ثم استخدم الوظيفة التالية:

func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    let isNumber = CharacterSet.decimalDigits.isSuperset(of: CharacterSet(charactersIn: string))
    let withDecimal = (
        string == NumberFormatter().decimalSeparator &&
        textField.text?.contains(string) == false
    )
    return isNumber || withDecimal
}

سيؤدي ذلك الآن إلى التأكد من أن المستخدم يمكنه إدخال الأرقام العشرية فقط.

Swift 4 + يقبل الرقم فقط ويقبل فاصل واحد


سويفت 3

    func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    if textField==yourTextFieldOutlet {
                if(CharacterSet.decimalDigits.isSuperset(of: CharacterSet(charactersIn: yourTextFieldOutlet.text!))){
//if numbers only, then your code here
                }
                else{
                showAlert(title: "Error",message: "Enter Number only",type: "failure")
                }
            }
    return true
    }

في سويفت 4.1 و Xcode 9.4.1

أضف UITextFieldDelegate إلى فصلك

class YourViewController: UIViewController, UITextFieldDelegate

ثم اكتب هذا الكود في viewDidLoad ()

mobileNoTF.delegate = self

اكتب وظيفة مندوب textfield

//MARK - UITextField Delegates
func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    //For mobile numer validation
    if textField == mobileNoTF {
        let allowedCharacters = CharacterSet(charactersIn:"+0123456789 ")//Here change this characters based on your requirement
        let characterSet = CharacterSet(charactersIn: string)
        return allowedCharacters.isSuperset(of: characterSet)
    }
    return true
}

كما لو لم تكن هناك إجابات كافية ، فإليك إجابات. أعتقد أن كل مثال مسموح به للفواصل العشرية معيب في أي من الترجمة أو المسافات الخلفية أو النسخ / اللصق.

func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
    if string.isEmpty {return true} //allow for backspace

    let decimalSeparator = NSNumberFormatter().decimalSeparator ?? "."
    let validChars = NSMutableCharacterSet(charactersInString: decimalSeparator)
    validChars.formUnionWithCharacterSet(NSCharacterSet.decimalDigitCharacterSet())

    if validChars.isSupersetOfSet(NSCharacterSet(charactersInString: string)){
        switch string.componentsSeparatedByString(decimalSeparator).count-1 {
        case 0: //no decimals
            return true

        case 1: //if adding decimal, only allow if no existing decimal
            if let existingText = textField.text{
                return existingText.componentsSeparatedByString(decimalSeparator).count <= 1
            }
            else {return true}

        default: //invalid decimals
            return false
        }
    }

    return false
}

كنت قد فعلت هذا بالفعل عند العمل من خلال كتاب Big Nerd Ranch ، فإن الحل هو:

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

    let newCharacters = NSCharacterSet(charactersInString: string)
    return NSCharacterSet.decimalDigitCharacterSet().isSupersetOfSet(newCharacters)
}

هذا يسمح فقط للأرقام من 0 إلى 9 ، للسماح لـ "." كذلك الأمر أكثر تعقيدًا حيث يمكنك السماح لأحد فقط "."


للسماح فقط بالأرقام ومشغل عشري واحد فقط ، يمكنك استخدام هذا الحل:

func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
    let isNumber = NSCharacterSet.decimalDigitCharacterSet().isSupersetOfSet(NSCharacterSet(charactersInString: string))

    return isNumber || (string == NSNumberFormatter().decimalSeparator && textField.text?.containsString(string) == false)
}

للسماح لبعض الرموز

func CheckAddress(string:String) -> Bool  {
        let numberOnly = NSCharacterSet.init(charactersIn: "[email protected],&#/")
        let stringFromTextField = NSCharacterSet.init(charactersIn: string)
        return numberOnly.isSuperset(of: stringFromTextField as CharacterSet)
    }

print("\(CheckAddress(string: "123"))") //True
print("\(CheckAddress(string: "asdf-"))") //True
print("\(CheckAddress(string: "asd123$"))") //false

هنا هو بلدي 2 سنتا. (تم اختباره في Swift 2 فقط)

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

  let aSet = NSCharacterSet(charactersInString:"0123456789").invertedSet
  let compSepByCharInSet = string.componentsSeparatedByCharactersInSet(aSet)
  let numberFiltered = compSepByCharInSet.joinWithSeparator("")
  return string == numberFiltered

}

هذا هو فقط أكثر صرامة قليلا. لا الفاصلة العشرية أيضا.

آمل أن يساعد :)

ملاحظة: افترضت أنك تعتني بالمفوض على أي حال.

تحديث: سويفت 3.0 :

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: "")
    return string == numberFiltered
}

يمكنك استخدام shouldChangeCharactersInRange مع طريقة امتداد السلسلة للتحقق مما إذا كانت سلسلة الإدخال هي رقم أم لا.

extension String  {

    var isNumber : Bool {
        get{
            return !self.isEmpty && self.stringWithoutWhitespaces.rangeOfCharacter(from: CharacterSet.decimalDigits.inverted) == nil
        }
    }

    var stringWithoutWhitespaces: String {
        return self.replacingOccurrences(of: " ", with: "")
    }

}

//Mark: shouldChangeCharactersInRange
func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
    // return true if the string only contains numeric characters
    let isValid = string.stringWithoutWhitespaces.isNumber 
    return valid
}

اي فون الحل الوحيد

في كل ما تحصل عليه UITextField من هذه القيم ، يمكنك تحديد نوع لوحة المفاتيح التي تريد أن تظهر عندما يلمس شخص ما داخل حقل النص.

EG لوحة مفاتيح رقمية فقط.

مثل هذه الصورة:

اى باد

لا يدعم iPad لوحة المفاتيح الرقمية ، لذا فإن خياراتك هي إما عدم دعم iPad أو التحقق من صحة إرسال المشاركة الميدانية أو اتباع أحد الاقتراحات الأخرى هنا لإنشاء سلوكيات عقلانية أثناء تشغيله على iPad.


func isValidNumber(str:String) -> Bool{
    if str.isEmpty {
        return false
    }
    let newChar = NSCharacterSet(charactersInString: str)
    let boolValid = NSCharacterSet.decimalDigitCharacterSet().isSupersetOfSet(newChar)
    if boolValid{
        return true
    }else{
        let lst = str.componentsSeparatedByString(".")
        let newStr = lst.joinWithSeparator("")
        let currentChar = NSCharacterSet(charactersInString: newStr)
        if lst.count == 2 && !lst.contains("") && NSCharacterSet.decimalDigitCharacterSet().isSupersetOfSet(currentChar){
            return true
        }
        return false
    }
}

ضع هذه الوظيفة في طريقة "إرسال" أو "حفظ" إذا كان هناك طريقة.


func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
    if let numRange = string.rangeOfCharacterFromSet(NSCharacterSet.letterCharacterSet()) {
        return false
    } else {
        return true
    }
   }

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

        {
            let textString = (textField.text! as NSString).replacingCharacters(in: range, with: string)

            if textField == self.phoneTextField  && string.characters.count > 0{
                let numberOnly = NSCharacterSet.decimalDigits
                let strValid = numberOnly.contains(UnicodeScalar.init(string)!)
                return strValid && textString.characters.count <= 10
            }
            return true
        }

في أعلاه رمز يعمل في سويفت 3
NSCharacterSet. أرقام عشرية
أنت أيضا تستخدم الحروف فقط
NSCharacterSet. حروف
والأحرف الكبيرة ، Lowercaseand ، الأبجدية الرقمية ، المسافات البيضاء تستخدم نفس الكود أو انظر الرابط







uitextfield