UITextField की अधिकतम वर्ण लंबाई निर्धारित करें


474

UITextFieldजब मैं लोड करता हूं तो मैं iPhone SDK पर अधिकतम वर्ण कैसे सेट कर सकता हूं UIView?


यह अविश्वसनीय रूप से पुराना उत्तर बहुत पुराना है - उत्तर अब तुच्छ है: stackoverflow.com/a/38306929/294884
Fattie

जवाबों:


1029

जबकि UITextFieldकक्षा में अधिकतम लंबाई की संपत्ति नहीं है, पाठ क्षेत्र को सेट करके delegateऔर निम्नलिखित प्रतिनिधि विधि को लागू करके इस कार्यक्षमता को प्राप्त करना अपेक्षाकृत सरल है :

उद्देश्य सी

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string {
    // Prevent crashing undo bug – see note below.
    if(range.length + range.location > textField.text.length)
    {
        return NO;
    }

    NSUInteger newLength = [textField.text length] + [string length] - range.length;
    return newLength <= 25;
}

तीव्र

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

    let currentCharacterCount = textField.text?.count ?? 0
    if range.length + range.location > currentCharacterCount {
        return false
    }
    let newLength = currentCharacterCount + string.count - range.length
    return newLength <= 25
}

पाठ फ़ील्ड में परिवर्तन से पहले, UITextField प्रतिनिधि से पूछता है कि क्या निर्दिष्ट पाठ को बदला जाना चाहिए। पाठ फ़ील्ड इस बिंदु पर नहीं बदला है, इसलिए हम इसे वर्तमान लंबाई और स्ट्रिंग लंबाई जो हम सम्मिलित कर रहे हैं (या तो कॉपी किए गए पाठ को चिपकाने या कीबोर्ड का उपयोग करके एकल वर्ण टाइपिंग के माध्यम से) पकड़ते हैं, रेंज की लंबाई शून्य से। यदि यह मान बहुत लंबा है (इस उदाहरण में 25 से अधिक वर्ण), NOतो परिवर्तन को प्रतिबंधित करने के लिए वापस लौटें ।

जब एक टेक्स्ट फ़ील्ड के अंत में किसी एकल वर्ण में टाइप किया जाता है, range.locationतो वर्तमान फ़ील्ड की लंबाई range.lengthहोगी , और 0 होगा क्योंकि हम कुछ भी नहीं बदल रहे हैं / हटा रहे हैं। एक पाठ क्षेत्र के बीच में सम्मिलित करने का अर्थ है एक अलग range.location, और कई वर्णों को चिपकाने का अर्थ stringहै कि इसमें एक से अधिक वर्ण हैं।

एकल वर्णों को हटाना या कई वर्णों को काटना rangeगैर-शून्य लंबाई और एक रिक्त स्ट्रिंग के साथ निर्दिष्ट किया गया है । गैर-रिक्त स्ट्रिंग के साथ प्रतिस्थापन केवल एक श्रेणी विलोपन है।

दुर्घटनाग्रस्त "पूर्ववत" बग पर एक नोट

जैसा कि टिप्पणियों में उल्लेख किया गया है, एक बग है UITextFieldजिससे दुर्घटना हो सकती है।

यदि आप फ़ील्ड में पेस्ट करते हैं, लेकिन पेस्ट को आपके सत्यापन कार्यान्वयन से रोका जाता है, तो पेस्ट ऑपरेशन अभी भी एप्लिकेशन के अनडू बफर में रिकॉर्ड किया जाता है। यदि आप एक पूर्ववत करते हैं (डिवाइस को हिलाकर और एक पूर्ववत की पुष्टि करके), UITextFieldतो स्ट्रिंग को प्रतिस्थापित करने का प्रयास करेगा , यह सोचता है कि यह खाली स्ट्रिंग के साथ खुद को चिपकाया हुआ है। यह दुर्घटनाग्रस्त हो जाएगा क्योंकि यह वास्तव में कभी भी अपने आप में स्ट्रिंग को चिपकाता नहीं है। यह स्ट्रिंग के एक हिस्से को बदलने की कोशिश करेगा जो मौजूद नहीं है।

सौभाग्य से आप UITextFieldइस तरह से खुद को मारने से बचा सकते हैं । तुम बस यह सुनिश्चित करें कि सीमा बदलने के लिए प्रस्ताव की जरूरत नहीं करता है अपने वर्तमान स्ट्रिंग के भीतर मौजूद। यह वही है जो ऊपर प्रारंभिक प्रारंभिक जांच करता है।

तेजी से 3.0 कॉपी और पेस्ट के साथ ठीक काम कर रहा है।

func textView(_ textView: UITextView, shouldChangeTextIn range: NSRange, replacementText text: String) -> Bool {
        let str = (textView.text + text)
        if str.characters.count <= 10 {
            return true
        }
        textView.text = str.substring(to: str.index(str.startIndex, offsetBy: 10))
        return false
    }

आशा है कि यह आपके लिए उपयोगी है।


7
अगर (textField == _ssn) {} और रिटर्न यस को जोड़ने के साथ उन 2 लाइनों के आसपास एक समाधान मिला; विधि के अंत में, जो अन्य सभी UITextFields को बिना किसी प्रतिबंध के पाठ को स्वीकार करने की अनुमति देगा। निफ्टी!
काइल क्लेग

55
अच्छा जवाब है, लेकिन टर्नरी ऑपरेटर शानदार है; आप बस डाल सकते हैंreturn newLength <= 25;
jowie

2
क्या होगा यदि आप केवल पाठ को टेक्स्टफील्ड के फ्रेम पर नहीं फैलाना चाहते हैं; सभी वर्ण समान चौड़ाई वाले नहीं हैं, है ना?
मोर्क्रोम सेप

2
वहाँ वास्तव में @bcherry उल्लेख के रूप में एक पूर्ववत बग है - UITextFieldiPad iOS 8.1 पर परीक्षण किया गया। (टिप्पणी करने के लिए +1)। क्या लेखक इसके बारे में कुछ जोड़ देगा क्योंकि यह शीर्ष रेटेड उत्तर है? मुझे एक संपादन करने में खुशी हो रही है, लेकिन मेरा नियमित रूप से अस्वीकार करने के लिए लगता है! :-)
बेंजोएन

8
@bherry Swift में, पूर्ववत मामले की जाँच इमोजी के प्रवेश को तोड़ती हुई प्रतीत होती है। गणना नहीं की जानी चाहिए (textField.text) रेंज में objc / uikit रिपोर्टिंग से मेल खाने के लिए वास्तव में काउंट (textField.text.utf16) होना चाहिए (स्ट्रिंग्स पर गिनती का स्विफ्ट संस्करण) बनाम?
rcw3

62

स्विफ्ट 4

import UIKit

private var kAssociationKeyMaxLength: Int = 0

extension UITextField {

    @IBInspectable var maxLength: Int {
        get {
            if let length = objc_getAssociatedObject(self, &kAssociationKeyMaxLength) as? Int {
                return length
            } else {
                return Int.max
            }
        }
        set {
            objc_setAssociatedObject(self, &kAssociationKeyMaxLength, newValue, .OBJC_ASSOCIATION_RETAIN)
            addTarget(self, action: #selector(checkMaxLength), for: .editingChanged)
        }
    }

    @objc func checkMaxLength(textField: UITextField) {
        guard let prospectiveText = self.text,
            prospectiveText.count > maxLength
            else {
                return
        }

        let selection = selectedTextRange

        let indexEndOfText = prospectiveText.index(prospectiveText.startIndex, offsetBy: maxLength)
        let substring = prospectiveText[..<indexEndOfText]
        text = String(substring)

        selectedTextRange = selection
    }
}

संपादित करें: स्मृति रिसाव मुद्दा तय हो गया।

यहाँ छवि विवरण दर्ज करें


महान विचार Frouo! मैंने अपने उत्तर में इसका विस्तार अधिकतम स्ट्रिंग ट्रिमिंग को स्ट्रिंग एक्सटेंशन में स्थानांतरित करने के लिए किया, ताकि इसका उपयोग UITextView इंस्टेंस जैसी चीजों के लिए भी किया जा सके और UITextextield एक्सटेंशन में इन स्ट्रिंग एक्सटेंशन का लाभ उठाने के लिए एक सुविधा फ़ंक्शन को जोड़ा जा सके।
स्कॉट गार्डनर

1
क्या यह वैश्विक चर स्मृति लीक नहीं बनाता है, जो सभी पाठ्यपुस्तकों (जो रूट-अप तक के पर्यवेक्षण को संदर्भित करता है) का संदर्भ लेकर
Ixx

3
@ XXX मैंने आपके द्वारा इंगित की गई मेमोरी लीक समस्या को ठीक करने के लिए संपादित किया है + स्विफ्ट 3. धन्यवाद
frouo

1
इसे प्राप्त करने का सबसे सुंदर तरीका! धन्यवाद
विक्टर चोय

क्या कोई मुझे इसका उद्देश्य संस्करण प्रदान कर सकता है
MRizwan33

56

धन्यवाद! ( पोस्ट )

यह वह कोड है जो मैंने काम किया है:

#define MAX_LENGTH 20

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
    if (textField.text.length >= MAX_LENGTH && range.length == 0)
    {
        return NO; // return NO to not change text
    }
    else
    {return YES;}
}

19
दुर्भाग्य से, यह समाधान उपयोगकर्ताओं को पाठ क्षेत्र में कॉपी-पेस्ट करने से रोकने में विफल रहता है, इसलिए उन्हें सीमा को बायपास करने की अनुमति देता है। सिकापे का जवाब इस स्थिति का सही ढंग से सामना करता है।
चींटी

5
NO या YES को वापस करने के लिए एक if स्टेटमेंट वाले लोगों के साथ क्या है? इसे आज़माएँ: वापसी! (TextField.text.length> = MAX_LENGTH && range.length == 0);
मैट पार्किंस

या यहreturn textField.text.length < MAX_LENGTH || range.length != 0;
igrek

22

अगस्त उत्तर को पूरा करने के लिए, प्रस्तावित फ़ंक्शन का एक संभावित कार्यान्वयन ( UITextField के प्रतिनिधि देखें )।

मैंने वर्चस्व कोड का परीक्षण नहीं किया , लेकिन उपयोगकर्ता द्वारा सीमा तक पहुंचने पर मेरा अटकना नहीं है, और यह एक नए स्ट्रिंग के साथ संगत है जो एक छोटे या बराबर की जगह आता है।

-(BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string {
    //limit the size :
    int limit = 20;
    return !([textField.text length]>limit && [string length] > range.length);
}

17

आप इसे सीधे नहीं कर सकते - UITextFieldकोई अधिकतम गति नहीं है, लेकिन आप UITextField'sप्रतिनिधि को सेट कर सकते हैं , फिर उपयोग कर सकते हैं:

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

5
मैं सहमत हूं, यह सबसे अच्छा तरीका है, लेकिन यह थोड़ा हैक रहता है। Apple को एक बग रिपोर्ट सबमिट करें जो आप पाठ की लंबाई के लिए एक संपत्ति देखना चाहते हैं। मैं निश्चित रूप से इस में दिलचस्पी है।
एवोकैड

5
@avocade, यह हैक नहीं है: यह एक उदाहरण है जहां आपको बुनियादी ढांचा कोड करना पड़ता है जो कि Apple को आपके लिए करना चाहिए था। IOS SDK में इसके कई उदाहरण हैं।
डेन रोसेनस्टार्क

13

अक्सर आपके पास एक अलग लंबाई के साथ कई इनपुट फ़ील्ड होते हैं।

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string {
    int allowedLength;
    switch(textField.tag) {
        case 1: 
            allowedLength = MAXLENGTHNAME;      // triggered for input fields with tag = 1
            break;
        case 2:
            allowedLength = MAXLENGTHADDRESS;   // triggered for input fields with tag = 2
            break;
        default:
            allowedLength = MAXLENGTHDEFAULT;   // length default when no tag (=0) value =255
            break;
    }

    if (textField.text.length >= allowedLength && range.length == 0) {
        return NO; // Change not allowed
    } else {
        return YES; // Change allowed
    }
}

12

सबसे अच्छा तरीका यह होगा कि आप पाठ बदलने पर एक अधिसूचना स्थापित करें। अपने में -awakeFromNibआपके विचार नियंत्रक विधि की आप चाहेंगे:

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(limitTextField:) name:@"UITextFieldTextDidChangeNotification" object:myTextField];

फिर उसी वर्ग में जोड़ें:

- (void)limitTextField:(NSNotification *)note {
    int limit = 20;
    if ([[myTextField stringValue] length] > limit) {
        [myTextField setStringValue:[[myTextField stringValue] substringToIndex:limit]];
    }
}

फिर आउटलेट myTextFieldको अपने ऊपर लिंक करें UITextFieldऔर यह आपको सीमा को हिट करने के बाद किसी भी अधिक वर्ण जोड़ने की अनुमति नहीं देगा। इसे अपने टैकलोक विधि में अवश्य जोड़ें:

[[NSNotificationCenter defaultCenter] removeObserver:self name:@"UITextFieldTextDidChangeNotification" object:myTextField];

हालाँकि मैंने त्रुटियों को दूर करने के लिए ऐसा किया था> myTextField.text = [myTextField.text substringToIndex: limit];
ल्यूक

11

मैंने यह UITextFieldLimit उपवर्ग बनाया :

  • एकाधिक टेक्स्ट फ़ील्ड का समर्थन किया
  • पाठ की लंबाई सीमा निर्धारित करें
  • पेस्ट की रोकथाम
  • टेक्स्टफ़ील्ड के अंदर बाएं अक्षरों का एक लेबल प्रदर्शित करता है, जब आप संपादन रोकते हैं तो छिप जाते हैं।
  • जब कोई वर्ण शेष न हो तो एनीमेशन को हिलाएं।

पकड़ो UITextFieldLimit.hऔर UITextFieldLimit.mइस GitHub भंडार से:

https://github.com/JonathanGurebo/UITextFieldLimit

और परीक्षण करना शुरू करें!

अपने स्टोरीबोर्ड-निर्मित UITextField को चिह्नित करें और पहचान उप निरीक्षक का उपयोग करके इसे मेरे उपवर्ग से लिंक करें:

पहचान इंस्पेक्टर

फिर आप इसे IBOutlet से लिंक कर सकते हैं और सीमा निर्धारित कर सकते हैं (डिफ़ॉल्ट 10 है)।


आपकी ViewController.h फ़ाइल में सम्‍मिलित होना चाहिए: (यदि आप सेटिंग को संशोधित करना चाहते हैं, तो सीमा की तरह)

#import "UITextFieldLimit.h"

/.../

@property (weak, nonatomic) IBOutlet UITextFieldLimit *textFieldLimit; // <--Your IBOutlet

आपकी ViewController.m फ़ाइल चाहिए @synthesize textFieldLimit


अपनी ViewController.m फ़ाइल में पाठ की लंबाई सीमा निर्धारित करें:

- (void)viewDidLoad
{
    [super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.

    [textFieldLimit setLimit:25];// <-- and you won't be able to put more than 25 characters in the TextField.
}

आशा है कि वर्ग आपकी मदद करेगा। सौभाग्य!


चरित्र सीमा की छोटी सी जरूरत के लिए, मुझे लगता है कि आपकी कक्षा को जोड़ने से बस ओवरकिल हो जाएगा।
डोमिनेंस

फिर भी प्रयास की सराहना की।
रीपर

11

यह समस्या को हल करने के लिए पर्याप्त होना चाहिए (यू 4 की सीमा से 4 को बदलें)। बस आईबी में प्रतिनिधि जोड़ना सुनिश्चित करें।

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
     NSString *newString = [textField.text stringByReplacingCharactersInRange:range withString:string];
     return (newString.length<=4);
}

9

एक की अधिकतम वर्ण सीमा निर्धारित करने के लिए विस्तार से नीचे का प्रयोग करें UITextFieldऔर UITextView

स्विफ्ट 4.0

    private var kAssociationKeyMaxLength: Int = 0
    private var kAssociationKeyMaxLengthTextView: Int = 0
    extension UITextField {


        @IBInspectable var maxLength: Int {
            get {
                if let length = objc_getAssociatedObject(self, &kAssociationKeyMaxLength) as? Int {
                    return length
                } else {
                    return Int.max
                }
            }
            set {
                objc_setAssociatedObject(self, &kAssociationKeyMaxLength, newValue, .OBJC_ASSOCIATION_RETAIN)
                addTarget(self, action: #selector(checkMaxLength), for: .editingChanged)
            }
        }

        @objc func checkMaxLength(textField: UITextField) {
            guard let prospectiveText = self.text,
                prospectiveText.count > maxLength
                else {
                    return
            }

            let selection = selectedTextRange

            let indexEndOfText = prospectiveText.index(prospectiveText.startIndex, offsetBy: maxLength)
            let substring = prospectiveText[..<indexEndOfText]
            text = String(substring)

            selectedTextRange = selection
        }
    }

UITextView

extension UITextView:UITextViewDelegate {


        @IBInspectable var maxLength: Int {
            get {
                if let length = objc_getAssociatedObject(self, &kAssociationKeyMaxLengthTextView) as? Int {
                    return length
                } else {
                    return Int.max
                }
            }
            set {
                self.delegate = self

                objc_setAssociatedObject(self, &kAssociationKeyMaxLengthTextView, newValue, .OBJC_ASSOCIATION_RETAIN)
            }
        }

        public func textViewDidChange(_ textView: UITextView) {
            checkMaxLength(textField: self)
        }
        @objc func checkMaxLength(textField: UITextView) {
            guard let prospectiveText = self.text,
                prospectiveText.count > maxLength
                else {
                    return
            }

            let selection = selectedTextRange

            let indexEndOfText = prospectiveText.index(prospectiveText.startIndex, offsetBy: maxLength)
            let substring = prospectiveText[..<indexEndOfText]
            text = String(substring)

            selectedTextRange = selection
        }
    }

आप नीचे सीमा निर्धारित कर सकते हैं।

यहाँ छवि विवरण दर्ज करें


अब तक का सबसे अच्छा जवाब ,,, एक बहुत बढ़िया समाधान धन्यवाद जब कई
टेक्स्टफिल्ड हैं जिनकी

Textfield और textview नियंत्रण चरित्र इनपुट सीमा के लिए वास्तव में महान समाधान। डेवलपर के लिए इसकी सेव कोड लाइन्स और समय भी ... :)
संदीप पटेल - SM

यह मेरे द्वारा पाए गए अन्य समाधानों की तुलना में बेहतर काम करता है। उदाहरण के लिए, यदि आपके टेक्स्टफील्ड में इमोजी हैं, तो मुझे मिलने वाले अन्य एक्सटेंशन एडिट करते समय लाइन के अंत तक चले जाएंगे। लेकिन आपका कोड ऐसा नहीं करता है। धन्यवाद!
फोंटेन जुड

7

मैं वास्तविक स्ट्रिंग प्रतिस्थापन की नकल करता हूं जो कि भविष्य की स्ट्रिंग की लंबाई की गणना करने के लिए होने वाला है:

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

    NSString *newString = [textField.text stringByReplacingCharactersInRange:range withString:string];

    if([newString length] > maxLength)
       return NO;

    return YES;
}

7

स्विफ्ट 3 संस्करण // ***** यह स्विफ्ट 2.x के साथ काम नहीं करेगा! ***** //

पहले एक नई स्विफ्ट फ़ाइल बनाएँ: TextFieldMaxLength.swift, और फिर नीचे दिया गया कोड जोड़ें:

import UIKit

private var maxLengths = [UITextField: Int]()

extension UITextField {

   @IBInspectable var maxLength: Int {

      get {

          guard let length = maxLengths[self] 
             else {
                return Int.max
      }
      return length
   }
   set {
      maxLengths[self] = newValue
      addTarget(
         self,
         action: #selector(limitLength),
         for: UIControlEvents.editingChanged
      )
   }
}
func limitLength(textField: UITextField) {
    guard let prospectiveText = textField.text,
        prospectiveText.characters.count > maxLength
    else {
        return
    }

   let selection = selectedTextRange
   let maxCharIndex = prospectiveText.index(prospectiveText.startIndex, offsetBy: maxLength)
   text = prospectiveText.substring(to: maxCharIndex)
   selectedTextRange = selection
   }
}

और तब आप Storyboard एक नया क्षेत्र (अधिकतम लंबाई) देखेंगे जब आप किसी भी TextField का चयन करेंगे

यदि आपके पास अभी भी अधिक प्रश्न हैं, तो इस लिंक को देखें: http://www.globalnerdy.com/2016/05/18/ios-programming-trick-how-to-use-xcode-to-set-a-text-fields -maximum-लंबाई-विजुअल स्टूडियो शैली /


चेतावनी, यह वैश्विक चर सभी पाठों के संदर्भों को पकड़कर, मेमोरी लीक बनाता है।
फूरो

6

इंटरफ़ेस बिल्डर का उपयोग करके आप अपने किसी भी फंक्शन में "एडिटिंग चेंज" के लिए घटना को लिंक और प्राप्त कर सकते हैं। अब वहां आप लंबाई की जांच कर सकते हैं

- (IBAction)onValueChange:(id)sender 
{
    NSString *text = nil;
    int MAX_LENGTH = 20;
    switch ([sender tag] ) 
    {
        case 1: 
        {
            text = myEditField.text;
            if (MAX_LENGTH < [text length]) {
                myEditField.text = [text substringToIndex:MAX_LENGTH];
            }
        }
            break;
        default:
            break;
    }

}

6

निम्न कोड सिकलप के उत्तर के समान है, लेकिन कॉपी-पेस्ट संचालन को सही ढंग से संभालता है। यदि आप किसी ऐसे पाठ को चिपकाने की कोशिश करते हैं जो सीमा से अधिक लंबा है, तो निम्न कोड पूरी तरह से पेस्ट ऑपरेशन से इनकार करने के बजाय सीमा को फिट करने के लिए पाठ को काट देगा।

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string {
    static const NSUInteger limit = 70; // we limit to 70 characters
    NSUInteger allowedLength = limit - [textField.text length] + range.length;
    if (string.length > allowedLength) {
        if (string.length > 1) {
            // get at least the part of the new string that fits
            NSString *limitedString = [string substringToIndex:allowedLength];
            NSMutableString *newString = [textField.text mutableCopy];
            [newString replaceCharactersInRange:range withString:limitedString];
            textField.text = newString;
        }
        return NO;
    } else {
        return YES;
    }
}

6

नहीं है सामान्य समाधान स्विफ्ट में अधिकतम लंबाई की स्थापना के लिए। IBInspectable द्वारा आप Xcode विशेषता निरीक्षक में नए गुण जोड़ सकते हैं।यहाँ छवि विवरण दर्ज करें

import UIKit
private var maxLengths = [UITextField: Int]()
extension UITextField {

    @IBInspectable var maxLength: Int {
        get {
            guard let length = maxLengths[self]
            else {
                return Int.max
            }
            return length
        }
        set {
            maxLengths[self] = newValue
            addTarget(
                self,
                action: Selector("limitLength:"),
                forControlEvents: UIControlEvents.EditingChanged
            )
        }
    }

    func limitLength(textField: UITextField) {
        guard let prospectiveText = textField.text
            where prospectiveText.characters.count > maxLength else {
                return
        }
        let selection = selectedTextRange
        text = prospectiveText.substringWithRange(
            Range<String.Index>(prospectiveText.startIndex ..< prospectiveText.startIndex.advancedBy(maxLength))
        )
        selectedTextRange = selection
    }

}

स्वच्छ और सही समाधान
एडुआर्डो

एक वैश्विक क्षेत्र में एक UITextField को होल्ड करने के बाद भी UIViewController को खारिज करने के बाद उन्हें मेमोरी में बनाए रखा जाएगा। यह एक मेमोरी लीक है। इस विधि का उपयोग न करें।
गुंजन

5

किसी भी लम्बाई के तारों के कट और पेस्ट के साथ इसे काम करने के लिए, मैं सुझाव दूंगा कि फ़ंक्शन को कुछ इस तरह से बदला जाए:

#define MAX_LENGTH 20

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
    {
        NSInteger insertDelta = string.length - range.length;

        if (textField.text.length + insertDelta > MAX_LENGTH)
        {
           return NO; // the new string would be longer than MAX_LENGTH
        }
        else {
            return YES;
        }
    }

4

स्विफ्ट 4

func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
    guard let text = textField.text else { return true }
    let newLength = text.count + string.count - range.length
    return newLength <= 10
}

क्यों guard?
विषमकाल

जांचें कि क्या पाठ शून्य है, यदि आप चाहें, तो आप @oddRaven
Shan Ye

3

स्विफ्ट 2.0 +

सबसे पहले इस प्रक्रिया के लिए एक वर्ग बनाएं। इसे StringValidator.swift कहते हैं।

फिर बस इसके अंदर निम्न कोड पेस्ट करें।

import Foundation

extension String {

func containsCharactersIn(matchCharacters: String) -> Bool {
let characterSet = NSCharacterSet(charactersInString: matchCharacters)
return self.rangeOfCharacterFromSet(characterSet) != nil
}

func containsOnlyCharactersIn(matchCharacters: String) -> Bool {
let disallowedCharacterSet = NSCharacterSet(charactersInString: matchCharacters).invertedSet
return self.rangeOfCharacterFromSet(disallowedCharacterSet) == nil
}


func doesNotContainCharactersIn(matchCharacters: String) -> Bool {
let characterSet = NSCharacterSet(charactersInString: matchCharacters)
return self.rangeOfCharacterFromSet(characterSet) == nil
}

func isNumeric() -> Bool
{
let scanner = NSScanner(string: self)
scanner.locale = NSLocale.currentLocale()

return scanner.scanDecimal(nil) && scanner.atEnd
}

}

अब क्लास बचाओ .....

प्रयोग ..

अब गोटो अपने viewController.swift वर्ग और अपने textfield के आउटलेट के रूप में ..

@IBOutlet weak var contactEntryTxtFld: UITextField! //First textfield
@IBOutlet weak var contactEntryTxtFld2: UITextField!   //Second textfield

अब टेक्स्टो के मूल्‍यों को बदल दें।

func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
    if string.characters.count == 0 {
        return true
    }
    let latestText = textField.text ?? ""
    let checkAbleText = (latestText as NSString).stringByReplacingCharactersInRange(range, withString: string)


    switch textField {

    case contactEntryTxtFld:
        return checkAbleText.containsOnlyCharactersIn("0123456789") && prospectiveText.characters.count <= 5

    case contactEntryTxtFld2:
        return checkAbleText.containsOnlyCharactersIn("0123456789") && prospectiveText.characters.count <= 5

    default:
        return true
    }

}

टेक्स्टफ़िल्ड के प्रतिनिधि प्रोटोकॉल / विधियों को सेट करना न भूलें।

मुझे इसके बारे में समझाएं ... मैं स्ट्रिंग की सरल विस्तार प्रक्रिया का उपयोग कर रहा हूं जो मैंने एक अन्य वर्ग के अंदर लिखा था। अब मैं सिर्फ दूसरी कक्षा से उन विस्तार विधियों को बुला रहा हूं जहां मुझे चेक और अधिकतम मूल्य जोड़कर उनकी आवश्यकता है।

विशेषताएं...

  1. यह एक विशेष टेक्स्टफील्ड की अधिकतम सीमा निर्धारित करेगा।
  2. यह विशेष टेक्स्टफील्ड के लिए स्वीकृत कुंजी का प्रकार सेट करेगा।

प्रकार ...

होते हैंOnlyCharactersIn // केवल वर्ण स्वीकार करता है।

शामिल हैं। अक्षर / // वर्णों के संयोजन को स्वीकार करता है

doesNotContainsCharactersIn // वर्ण स्वीकार नहीं करेगा

उम्मीद है कि इस मदद की .... धन्यवाद ..


3

तेजी से 3.0

यह कोड तब ठीक काम कर रहा है जब आप अपने चरित्र की सीमाओं से अधिक पेस्ट स्ट्रिंग कर रहे हैं।

func textView(_ textView: UITextView, shouldChangeTextIn range: NSRange, replacementText text: String) -> Bool {
        let str = (textView.text + text)
        if str.characters.count <= 10 {
            return true
        }
        textView.text = str.substring(to: str.index(str.startIndex, offsetBy: 10))
        return false
    }

आपके वोटों के लिए धन्यवाद। :)


2
UITextField, UITextView नहीं।
जोनी

3

मैं @ पूरक के आधार पर एक पूरक उत्तर देता हूं। मुझे लगता है कि उनका जवाब सबसे सुंदर तरीका है। Beuase यह एक सामान्य नियंत्रण है जिसका हम पुन: उपयोग कर सकते हैं।

private var kAssociationKeyMaxLength: Int = 0

extension UITextField {

    @IBInspectable var maxLength: Int {
        get {
            if let length = objc_getAssociatedObject(self, &kAssociationKeyMaxLength) as? Int {
                return length
            } else {
                return Int.max
            }
        }
        set {
            objc_setAssociatedObject(self, &kAssociationKeyMaxLength, newValue, .OBJC_ASSOCIATION_RETAIN)
            self.addTarget(self, action: #selector(checkMaxLength), for: .editingChanged)
        }
    }

    func checkMaxLength(textField: UITextField) {

        guard !self.isInputMethod(), let prospectiveText = self.text,
            prospectiveText.count > maxLength
            else {
                return
        }

        let selection = selectedTextRange
        let maxCharIndex = prospectiveText.index(prospectiveText.startIndex, offsetBy: maxLength)
        text = prospectiveText.substring(to: maxCharIndex)
        selectedTextRange = selection
    }

    //The method is used to cancel the check when use Chinese Pinyin input method.
    //Becuase the alphabet also appears in the textfield when inputting, we should cancel the check.
    func isInputMethod() -> Bool {
        if let positionRange = self.markedTextRange {
            if let _ = self.position(from: positionRange.start, offset: 0) {
                return true
            }
        }
        return false
    }

}

2

यह UITextField पर अधिकतम लंबाई को संभालने का सही तरीका है, यह पाठ कुंजी को पहले उत्तरदाता के रूप में टेक्स्टफील्ड से बाहर निकलने की अनुमति देता है और उपयोगकर्ता को सीमा तक पहुंचने पर बैकस्पेस देता है

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string {
int MAX_LENGHT = 5;
    if([string isEqualToString:@"\n"])
    {
        [textField resignFirstResponder];
        return FALSE;
    }
    else if(textField.text.length > MAX_LENGHT-1)
    {
        if([string isEqualToString:@""] && range.length == 1)
        {
            return TRUE;
        }
        else
        {
            return FALSE;
        }
    }
    else
    {
        return TRUE;
    }
}

2

इस सरल दृष्टिकोण के बारे में क्या। इसका काम करना मेरे लिए ठीक है।

extension UITextField {

    func  charactersLimit(to:Int) {

        if (self.text!.count > to) {
            self.deleteBackward()
        }
    }
}

फिर:

someTextField.charactersLimit(to:16)

1

अन्य उत्तर उस मामले को नहीं संभालते हैं जहां उपयोगकर्ता क्लिपबोर्ड से एक लंबी स्ट्रिंग पेस्ट कर सकता है। यदि मैं एक लंबी स्ट्रिंग चिपकाता हूं तो इसे केवल छोटा किया जाना चाहिए लेकिन दिखाया गया है। इसे अपने प्रतिनिधि में उपयोग करें:

static const NSUInteger maxNoOfCharacters = 5;

-(IBAction)textdidChange:(UITextField * )textField
{
NSString * text = textField.text;

if(text.length > maxNoOfCharacters)
{
    text = [text substringWithRange:NSMakeRange(0, maxNoOfCharacters)];
    textField.text = text;
}

// use 'text'

}

1

इसे कोड की 1 पंक्ति के नीचे मिला :)

अपने पाठ दृश्य के प्रतिनिधि को "स्वयं" पर सेट करें। फिर <UITextViewDelegate>अपने .h और निम्न कोड को अपने .m में जोड़ें .... आप "मैक्सिमम" संख्या को समायोजित कर सकते हैं कि जो भी आप चाहते हैं कि आपका मैक्सिमम अक्षर हो।

-(BOOL)textView:(UITextView *)a shouldChangeTextInRange:(NSRange)b replacementText:(NSString *)c {
    return ((a.text.length+c.length<=7)+(c.length<1)+(b.length>=c.length)>0);
}

यह कोड नए वर्ण टाइप करने, वर्णों को हटाने, वर्णों का चयन करने या फिर हटाने, वर्णों का चयन करने और काटने, सामान्य रूप से चिपकाने और वर्णों का चयन करने के लिए होता है।

किया हुआ!






वैकल्पिक रूप से, इस कोड को बिट-ऑपरेशन के साथ लिखने का एक और अच्छा तरीका होगा

-(BOOL)textView:(UITextView *)a shouldChangeTextInRange:(NSRange)b replacementText:(NSString *)c {
    return 0^((a.text.length+c.length<=7)+(c.length<1)+(b.length>=c.length));
}


1

अब कितने वर्ण u केवल मान देना चाहते हैं

 - (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range   replacementString:(NSString *)string {
     NSUInteger newLength = [textField.text length] + [string length] - range.length;
     return (newLength > 25) ? NO : YES;
  }

1

यहां इस कोड का उपयोग करें RESTRICTED_LENGTH वह लंबाई है जिसे आप टेक्स्टफील्ड के लिए प्रतिबंधित करना चाहते हैं।

   - (BOOL)textField:(UITextField *)textField     shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
    if (textField == nameTF) {
    int limit = RESTRICTED_LENGTH - 1;
    return !([textField.text length]>limit && [string length] > range.length);
    }
   else
   {
    return YES;
   }

return NO;

}

1

मैंने एक नंबर पैड का उपयोग करते समय 8 कैरेक्टर लिमिट के लिए स्विफ्ट में ऐसा किया था।

func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
    return !(textField.text?.characters.count == MAX_LENGTH && string != "")
}

मुझे डिलीट बटन को नंबर पैड पर काम करने की अनुमति देने के लिए स्ट्रिंग के लिए परीक्षण करना होगा! = "", अन्यथा इसके अधिकतम तक पहुंचने के बाद पाठ क्षेत्र में वर्णों को हटाने की अनुमति नहीं होगी।


1

ज़मारिन के लिए:

YourTextField.ShouldChangeCharacters = 
delegate(UITextField textField, NSRange range, string replacementString)
        {
            return (range.Location + replacementString.Length) <= 4; // MaxLength == 4
        };

1

मैंने एक मैक्सलिफ्ट प्रॉपर्टी को इसमें जोड़ने के लिए एक UITextField Extension लागू किया है।

यह Xcode 6 IBInspectables पर आधारित है, इसलिए आप इंटरफ़ेस बिल्डर पर अधिकतम गति निर्धारित कर सकते हैं।

यहाँ कार्यान्वयन है:

UITextField + MaxLength.h

#import <UIKit/UIKit.h>

@interface UITextField_MaxLength : UITextField<UITextFieldDelegate>

@property (nonatomic)IBInspectable int textMaxLength;
@end

UITextField + MaxLength.m

#import "UITextField+MaxLength.h"

@interface UITextField_MaxLength()

@property (nonatomic, assign) id <UITextFieldDelegate> superDelegate;

@end

@implementation UITextField_MaxLength

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

    //validate the length, only if it's set to a non zero value
    if (self.textMaxLength>0) {
        if(range.length + range.location > textField.text.length)
            return NO;

        if (textField.text.length+string.length - range.length>self.textMaxLength) {
            return NO;
        }
    }

    //if length validation was passed, query the super class to see if the delegate method is implemented there
    if (self.superDelegate && [self.superDelegate respondsToSelector:@selector(textField:shouldChangeCharactersInRange:replacementString:)]) {
        return [self.superDelegate textField:textField shouldChangeCharactersInRange:range replacementString:string];
    }
    else{
        //if the super class does not implement the delegate method, simply return YES as the length validation was passed
        return YES;
    }
}

- (void)setDelegate:(id<UITextFieldDelegate>)delegate {
    if (delegate == self)
        return;
    self.superDelegate = delegate;
    [super setDelegate:self];
}

//forward all non overriden delegate methods
- (id)forwardingTargetForSelector:(SEL)aSelector {
    if ([self.superDelegate  respondsToSelector:aSelector])
        return self.superDelegate;

    return [super forwardingTargetForSelector:aSelector];
}

- (BOOL)respondsToSelector:(SEL)aSelector {
    if ([self.superDelegate respondsToSelector:aSelector])
        return YES;

    return [super respondsToSelector:aSelector];
}
@end
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.