2015-08-07 19 views
24

Ho un'app in cui l'utente deve digitare un codice pin di quattro cifre. Tutte le cifre devono essere a una distanza prestabilita l'una dall'altra.Come impostare la spaziatura delle lettere di UITextField

C'è un modo per farlo se lo PinTextField è una sottoclasse di UIView? So che in un ViewController è possibile utilizzare UITextFieldTextDidChangeNotification e impostare il testo attribuito per ogni modifica. Le notifiche non sembrano funzionare in un UIView.

Inoltre, mi chiedevo se non c'è un modo più semplice di creare una stringa attribuita per ogni aggiornamento se si desidera impostare la spaziatura delle lettere di un testo UITextField?

corretta spaziatura:

TextField with correct spacing

spaziatura Sbagliato:

TextField with wrong spacing

+0

per cominciare *** è necessario utilizzare un carattere a spaziatura fissa ** !!!!! – Fattie

+0

Per chiunque su Google, questo è cambiato radicalmente da questa vecchia domanda. *** NON FARE, usa il testo attribuito. La soluzione è semplice: guarda la risposta di @iOSer qui sotto. – Fattie

risposta

8

Questo è quello che alla fine ha lavorato per impostare il Kern per ogni cambio

textField.addTarget(self, action: "textFieldDidChange", forControlEvents: .EditingChanged) 

    func textFieldDidChange() {  
     let attributedString = NSMutableAttributedString(string: textField.text) 
     attributedString.addAttribute(NSKernAttributeName, value: 5, range: NSMakeRange(0, count(textField.text))) 
     attributedString.addAttribute(NSFontAttributeName, value: font, range: NSMakeRange(0, count(textField.text))) 
     attributedString.addAttribute(NSForegroundColorAttributeName, value: UIColor.blackColor(), range: NSMakeRange(0, count(textField.text))) 

     textField.attributedText = attributedString 
    } 

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

     if count(textField.text) < 4 { 
      return true 
      // Else if 4 and delete is allowed 
     }else if count(string) == 0 { 
      return true 
      // Else limit reached 
     }else{ 
      return false 
     } 
    } 

Il problema resta però perché i numeri diversi hanno diverse larghezze, mi limiterò a ricorrere di nuovo a fare un UITextField per ogni cifra.

+0

La soluzione corretta è usare il carattere monospace. – Jurasic

0

Non proprio sicuro di qualsiasi altra soluzione invece di utilizzare stringhe attribuito.

Ma per la parte di notifica, è possibile impostare il delegato textFields su UIView e definire sotto il metodo nella vista.

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

Il metodo precedente viene chiamato ogni volta che il testo immesso nel campo di testo cambia.

0

Prova questo codice Dopo aver impostato il delegato sul campo di testo. Sperare che funzioni.

- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string 
{ 
    NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] initWithString:textField.text]; 
    [attributedString addAttribute:NSKernAttributeName 
          value:@(5.4) 
          range:NSMakeRange(0, textField.text.length)]; 
    textField.attributedText = attributedString; 
    return YES; 
} 
+0

'shouldChangeCharactersInRange' non funziona per la prima lettera, ma appare solo dopo aver inserito il secondo. – KMV

+1

controlla questo link per la prima lettera, potrebbe aiutarti: http://stackoverflow.com/questions/7010547/uitextfield-text-change-event – Vishnuvardhan

0

Questo funziona perfettamente in Swift 2.2. Spero che questo vi aiuterà per la spaziatura tra lettere nel campo di testo

override func viewDidLoad() { 
// Do any additional setup after loading the view. 
     NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(SignupVC.limitTextField(_:)), name: "UITextFieldTextDidChangeNotification", object: txtContactNumber) 
} 
func limitTextField(Notif:NSNotification) { 

    let limit=10; 

    let attributedString = NSMutableAttributedString(string: txtContactNumber.text!) 
    attributedString.addAttribute(NSKernAttributeName, value: 7, range: NSMakeRange(0, (txtContactNumber.text?.characters.count)!)) 
    // attributedString.addAttribute(NSFontAttributeName, value: font, range: NSMakeRange(0, count(textField.text))) 
    attributedString.addAttribute(NSForegroundColorAttributeName, value: UIColor.blackColor(), range: NSMakeRange(0,(txtContactNumber.text?.characters.count)!)) 

    txtContactNumber.attributedText = attributedString 
    if(txtContactNumber.text?.characters.count>limit) 
    { 
     txtContactNumber.text=txtContactNumber.text?.substringToIndex(limit) 
    } 
} 
2

utilizzare la proprietà defaultTextAttributes di UITextField. Gestirà la conversione in NSAttributedString per te e applicherà gli attributi impostati. Per esempio:

NSMutableDictionary *attrs = [self.textField.defaultTextAttributes mutableCopy]; 
[attrs addEntriesFromDictionary:@{ 
    NSKernAttributeName: @18, 
    NSUnderlineColorAttributeName: [UIColor grayColor], 
    NSUnderlineStyleAttributeName: @(NSUnderlineStyleSingle | NSUnderlinePatternDash) 
}]; 
self.textField.defaultTextAttributes = attrs; 
4

Non c'è bisogno di andare per attributedText, che a dire il vero, è stato un disastro esecutive per la spaziatura modificata. Ogni volta che chiudevo la tastiera, la spaziatura spariva, il che mi spinse a scavare ulteriormente.

Ogni UITextField ha una proprietà chiamata defaultTextAttributes, che secondo Apple "restituisce un dizionario di attributi di testo con valori di default.".Il Apple document dice anche che "questa proprietà si applica gli attributi specificati per l'intero testo del campo di testo"

solo trovare un luogo adatto nel codice, di solito dove il campo di testo viene inizializzato e quindi copiare e incollare il seguente .

risolta in Swift 3,0

textfield.defaultTextAttributes.updateValue(spacing, forKey: NSKernAttributeName) 

cui spaziatura è un CGFloat. Ad esempio 2.0.

Questo funziona anche per diversi tipi di carattere.

Saluti !!


L'ultima sintassi sembra essere:

yourField.defaultTextAttributes 
    .updateValue(20.0, forKey: NSAttributedStringKey.kern.rawValue) 
+1

@Fattie grazie per aver aggiunto l'ultima sintassi e anche per il commento. :) – iOSer

Problemi correlati