web-dev-qa-db-fra.com

Est-il possible de changer la couleur d'un seul mot dans UITextView et UITextField

Est-il possible de changer la couleur d'un seul mot dans UITextView et UITextField?

Si j'ai tapé un mot avec un symbole devant (par exemple: @Word), sa couleur peut-elle être changée?

30
Nithin M Keloth

Oui, vous devez utiliser NSAttributedString pour cela, recherchez le RunningAppHere .

Parcourez le mot, repérez la plage de votre mot et changez sa couleur.

MODIFIER:

- (IBAction)colorWord:(id)sender {
    NSMutableAttributedString * string = [[NSMutableAttributedString alloc]initWithString:self.text.text];

    NSArray *words=[self.text.text componentsSeparatedByString:@" "];

    for (NSString *Word in words) {        
        if ([Word hasPrefix:@"@"]) {
            NSRange range=[self.text.text rangeOfString:Word];
            [string addAttribute:NSForegroundColorAttributeName value:[UIColor redColor] range:range];           
        }
    }
    [self.text setAttributedText:string];
}

EDIT 2: voir la capture d'écran enter image description here

64
Anoop Vaidya

La réponse modifiée de @ fareed pour Swift 2.0 et cela fonctionne (testé dans un terrain de jeu):

func getColoredText(text: String) -> NSMutableAttributedString {
    let string:NSMutableAttributedString = NSMutableAttributedString(string: text)
    let words:[String] = text.componentsSeparatedByString(" ")
    var w = ""

    for Word in words {
        if (Word.hasPrefix("{|") && Word.hasSuffix("|}")) {
            let range:NSRange = (string.string as NSString).rangeOfString(Word)
            string.addAttribute(NSForegroundColorAttributeName, value: UIColor.redColor(), range: range)
            w = Word.stringByReplacingOccurrencesOfString("{|", withString: "")
            w = w.stringByReplacingOccurrencesOfString("|}", withString: "")
            string.replaceCharactersInRange(range, withString: w)
        }
    }
    return string
}

getColoredText("i {|love|} this!")
5
chapani

ceci est une implémentation Swift de @Anoop Vaidya answer, cette fonction détecte tout mot compris entre {| myword |}, colorie ces mots en rouge et supprime les caractères spéciaux. J'espère que cela pourra aider quelqu'un d'autre:

 func getColoredText(text:String) -> NSMutableAttributedString{
    var string:NSMutableAttributedString = NSMutableAttributedString(string: text)
    var words:[NSString] = text.componentsSeparatedByString(" ")

    for (var Word:NSString) in words {
        if (Word.hasPrefix("{|") && Word.hasSuffix("|}")) {
            var range:NSRange = (string.string as NSString).rangeOfString(Word)
            string.addAttribute(NSForegroundColorAttributeName, value: UIColor.redColor(), range: range)
            Word = Word.stringByReplacingOccurrencesOfString("{|", withString: "")
            Word = Word.stringByReplacingOccurrencesOfString("|}", withString: "")
            string.replaceCharactersInRange(range, withString: Word)
        }
    }
    return string
}

vous pouvez l'utiliser comme ceci:

self.msgText.attributedText = self.getColoredText("i {|love|} this!")
5

@fareed namrouti implémentation réécrite dans Swift 3

func getColoredText(text: String) -> NSMutableAttributedString {
    let string:NSMutableAttributedString = NSMutableAttributedString(string: text)
    let words:[String] = text.components(separatedBy:" ")
    var w = ""

    for Word in words {
        if (Word.hasPrefix("{|") && Word.hasSuffix("|}")) {
            let range:NSRange = (string.string as NSString).range(of: Word)
            string.addAttribute(NSForegroundColorAttributeName, value: UIColor.red, range: range)
            w = Word.replacingOccurrences(of: "{|", with: "")
            w = w.replacingOccurrences(of:"|}", with: "")
            string.replaceCharacters(in: range, with: w)
        }
    }
    return string
}
3
Eugene Gordin
-(void)colorHashtag
{
NSMutableAttributedString * string = [[NSMutableAttributedString alloc]initWithString:textView.text];

NSString *str = textView.text;
NSError *error = nil;

//I Use regex to detect the pattern I want to change color
NSRegularExpression *regex = [NSRegularExpression regularExpressionWithPattern:@"#(\\w+)" options:0 error:&error];



NSArray *matches = [regex matchesInString:textView.text options:0 range:NSMakeRange(0, textView.text.length)];

for (NSTextCheckingResult *match in matches) {
    NSRange wordRange = [match rangeAtIndex:0];
    [string addAttribute:NSForegroundColorAttributeName value:[UIColor redColor] range:wordRange]; 
}

[textView setAttributedText:string];
}
1
skittle

Après avoir défini un texte attribué, vous pouvez définir typingAttributes of UITextView avec les valeurs souhaitées pour le champ de saisie.

NSDictionary *attribs = @{
    NSForegroundColorAttributeName:[UIColor colorWithHex:kUsernameColor],
    NSFontAttributeName:[UIFont robotoRegularWithSize:40]
};
self.textView.typingAttributes = attribs;
0
Andrei Boleac

Oui c'est possible. Cependant, j'ai constaté qu'il peut s'agir d'un mal de tête en essayant d'utiliser NSMutableAttributesString avec un Swift Range. Le code ci-dessous vous évitera de devoir utiliser la classe Range et vous renverra une chaîne attribuée avec les mots mis en surbrillance d'une couleur différente.

extension String {
    func getRanges(of string: String) -> [NSRange] {
        var ranges:[NSRange] = []
        if contains(string) {
            let words = self.components(separatedBy: " ")
            var position:Int = 0
            for Word in words {
                if Word.lowercased() == string.lowercased() {
                    let startIndex = position
                    let endIndex = Word.characters.count
                    let range = NSMakeRange(startIndex, endIndex)
                    ranges.append(range)
                }
                position += (Word.characters.count + 1) // +1 for space
            }
        }
        return ranges
    }
    func highlight(_ words: [String], this color: UIColor) -> NSMutableAttributedString {
        let attributedString = NSMutableAttributedString(string: self)
        for Word in words {
            let ranges = getRanges(of: Word)
            for range in ranges {
                attributedString.addAttributes([NSForegroundColorAttributeName: color], range: range)
            }
        }
        return attributedString
    }
}

Usage:

// The strings you're interested in
let string = "The dog ran after the cat"
let words = ["the", "ran"]

// Highlight words and get back attributed string
let attributedString = string.highlight(words, this: .yellow)

// Set attributed string
textView.attributedText = attributedString
0
Brandon A

Pour expliquer la réponse de Jamal Kharrat et la réécrire dans Swift, voici comment procéder dans un UITextView:

  1. Définissez votre UITextView sur "Attribué" dans le storyboard
  2. Cliquez avec le bouton droit de la souris et faites glisser l’icône ViewController en haut de la vue (XC 6), puis définissez le délégué.
  3. Créez un IBOutlet pour votre UITextView (nous l'appellerons "textView")
  4. Rendre votre classe conforme à UITextViewDelegate

Voici la fonction de Jamal écrite en Swift:

func colorHastag(){
    var string:NSMutableAttributedString = NSMutableAttributedString(string: textView.text)
    var str:NSString = textView.text
    var error:NSError?
    var match:NSTextCheckingResult?

    var regEx:NSRegularExpression = NSRegularExpression(pattern: "#(\\w+)", options: nil, error: &error)!
    var matches:NSArray = regEx.matchesInString(textView.text, options: nil, range: NSMakeRange(0, countElements(textView.text)))

    for (match) in matches {
        var wordRange:NSRange = match.rangeAtIndex(0)
        string.addAttribute(NSForegroundColorAttributeName, value: UIColor.blueColor(), range: wordRange)
    }

    textView.attributedText = string
}

Maintenant, vous aurez besoin d'appeler cette fonction. Pour ce faire, chaque fois que l'utilisateur tape un caractère, vous pouvez utiliser:

func textView(textView: UITextView, shouldChangeTextInRange range: NSRange, replacementText text: String) -> Bool {
    self.colorHastag()
    return true
}

Vous remarquerez que j'ai changé la couleur en bleu. Vous pouvez le définir sur n'importe quelle couleur. En outre, vous pouvez supprimer le: Type pour chaque variable. Vous voudrez également définir devenFirstResponder () et gérer également resignFirstResponder () pour une bonne expérience utilisateur. Vous pouvez également ajouter un peu de gestion des erreurs. Cela convertira uniquement les hashtags en bleu. Vous devrez modifier ou ajouter un regEx pour gérer le @.

0
AlphaCodaSeven

La solution est la suivante:

NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] init];

NSArray *words=[txtDescription.text componentsSeparatedByString:@" "];

for (NSString *Word in words)
{
    if ([Word hasPrefix:@"@"] || [Word hasPrefix:@"#"])
    {
        [attributedString appendAttributedString:[[NSAttributedString alloc] initWithString:[NSString stringWithFormat:@"%@ ", Word]
                                                                                 attributes:@{NSFontAttributeName: [UIFont fontWithName:FONT_LIGHT size:15],
                                                                                              NSForegroundColorAttributeName: [ImageToolbox colorWithHexString:@"f64d5a"]}]];
    }
    else // normal text
    {
        [attributedString appendAttributedString:[[NSAttributedString alloc] initWithString:[NSString stringWithFormat:@"%@ ", Word]
                                                                                 attributes:@{NSFontAttributeName: [UIFont fontWithName:FONT_LIGHT size:15],
                                                                                              NSForegroundColorAttributeName: [ImageToolbox colorWithHexString:@"3C2023"]}]];
    }
}

if([[attributedString string] hasSuffix:@" "]) // loose the last space
{
    NSRange lastCharRange;
    lastCharRange.location=0;
    lastCharRange.length=[attributedString string].length-1;

    attributedString=[[NSMutableAttributedString alloc] initWithAttributedString:[attributedString attributedSubstringFromRange:lastCharRange]];
}

[txtDescription setAttributedText:attributedString];
0
Catalin