UILabel avec texte de deux couleurs différentes


109

Je veux afficher une chaîne comme celle-ci dans un UILabel:

Il y a 5 résultats.

Où le numéro 5 est de couleur rouge et le reste de la chaîne est noir.

Comment puis-je faire cela dans le code?


6
@EmptyStack Ce n'est certainement pas le cas puisque iOS 4 prend en charge NSAttributedString. Voir ma réponse ci-dessous.
Mic Pringle

Réponses:


223

La façon de le faire est d'utiliser NSAttributedStringcomme ceci:

NSMutableAttributedString *text = 
 [[NSMutableAttributedString alloc] 
   initWithAttributedString: label.attributedText];

[text addAttribute:NSForegroundColorAttributeName 
             value:[UIColor redColor] 
             range:NSMakeRange(10, 1)];
[label setAttributedText: text];

J'ai créé une UILabel extension pour le faire .


Puis-je y ajouter des cibles. Thnaks
UserDev

Je viens d'ajouter votre extension à mon projet! THX!
Zeb

Belle catégorie pour UILabel. Merci beaucoup. Cela devrait être la réponse acceptée.
Pradeep Reddy Kypa

63

J'ai fait cela en créant un categorypourNSMutableAttributedString

-(void)setColorForText:(NSString*) textToFind withColor:(UIColor*) color
{
    NSRange range = [self.mutableString rangeOfString:textToFind options:NSCaseInsensitiveSearch];

    if (range.location != NSNotFound) {
        [self addAttribute:NSForegroundColorAttributeName value:color range:range];
    }
}

Utilisez-le comme

- (void) setColoredLabel
{
    NSMutableAttributedString *string = [[NSMutableAttributedString alloc] initWithString:@"Here is a red blue and green text"];
    [string setColorForText:@"red" withColor:[UIColor redColor]];
    [string setColorForText:@"blue" withColor:[UIColor blueColor]];
    [string setColorForText:@"green" withColor:[UIColor greenColor]];
    mylabel.attributedText = string;
}

SWIFT 3

extension NSMutableAttributedString{
    func setColorForText(_ textToFind: String, with color: UIColor) {
        let range = self.mutableString.range(of: textToFind, options: .caseInsensitive)
        if range.location != NSNotFound {
            addAttribute(NSForegroundColorAttributeName, value: color, range: range)
        }
    }
}

USAGE

func setColoredLabel() {
    let string = NSMutableAttributedString(string: "Here is a red blue and green text")
    string.setColorForText("red", with: #colorLiteral(red: 0.9254902005, green: 0.2352941185, blue: 0.1019607857, alpha: 1))
    string.setColorForText("blue", with: #colorLiteral(red: 0.2392156869, green: 0.6745098233, blue: 0.9686274529, alpha: 1))
    string.setColorForText("green", with: #colorLiteral(red: 0.3411764801, green: 0.6235294342, blue: 0.1686274558, alpha: 1))
    mylabel.attributedText = string
}

SWIFT 4 @ kj13 Merci de l'avoir notifié

// If no text is send, then the style will be applied to full text
func setColorForText(_ textToFind: String?, with color: UIColor) {

    let range:NSRange?
    if let text = textToFind{
        range = self.mutableString.range(of: text, options: .caseInsensitive)
    }else{
        range = NSMakeRange(0, self.length)
    }
    if range!.location != NSNotFound {
        addAttribute(NSAttributedStringKey.foregroundColor, value: color, range: range!)
    }
}

J'ai fait plus d'expériences avec les attributs et ci-dessous sont les résultats, voici le SOURCECODE

Voici le résultat

modes


2
Vous devez créer une nouvelle catégorie pour NSMutableAttributedString avec la méthode ... de toute façon, j'ai ajouté cet exemple à github, vous pouvez le récupérer et le vérifier github.com/anoop4real/NSMutableAttributedString-Color
anoop4real

Mais j'ai besoin de définir la couleur de tous les alphabets avec incasensitive dans une chaîne .... comme tous les "e" dans la couleur rouge de la chaîne entière
Ravi Ojha

Aucune @interface visible pour 'NSMutableAttributedString' déclare le sélecteur 'setColorForText: withColor:'
ekashking

1
J'ai eu l'erreur «Utilisation de l'identificateur non résolu« NSForegroundColorAttributeName »avec Swift4.1, mais je remplace« NSForegroundColorAttributeName »par« NSAttributedStringKey.foregroundColor »et je construis correctement.
kj13

1
@ kj13 Merci d'avoir averti, j'ai mis à jour la réponse et ajouté quelques styles supplémentaires
anoop4real

25

Voici

NSMutableAttributedString * string = [[NSMutableAttributedString alloc] initWithString:lblTemp.text];
[string addAttribute:NSForegroundColorAttributeName value:[UIColor redColor] range:NSMakeRange(0,5)];
[string addAttribute:NSForegroundColorAttributeName value:[UIColor greenColor] range:NSMakeRange(5,6)];
[string addAttribute:NSForegroundColorAttributeName value:[UIColor blueColor] range:NSMakeRange(11,5)];
lblTemp.attributedText = string;

20

Swift 4

// An attributed string extension to achieve colors on text.
extension NSMutableAttributedString {

    func setColor(color: UIColor, forText stringValue: String) {
       let range: NSRange = self.mutableString.range(of: stringValue, options: .caseInsensitive)
       self.addAttribute(NSAttributedStringKey.foregroundColor, value: color, range: range)
    }

}

// Try it with label
let label = UILabel()
label.frame = CGRect(x: 70, y: 100, width: 260, height: 30)
let stringValue = "There are 5 results."
let attributedString: NSMutableAttributedString = NSMutableAttributedString(string: stringValue)
attributedString.setColor(color: UIColor.red, forText: "5")
label.font = UIFont.systemFont(ofSize: 26)
label.attributedText = attributedString
self.view.addSubview(label)

Résultat

entrez la description de l'image ici


Swift 3

func setColoredLabel() {
        var string: NSMutableAttributedString = NSMutableAttributedString(string: "redgreenblue")
        string.setColor(color: UIColor.redColor(), forText: "red")
        string.setColor(color: UIColor.greenColor(), forText: "green")
        string.setColor(color: UIColor.blueColor(, forText: "blue")
        mylabel.attributedText = string
    }


func setColor(color: UIColor, forText stringValue: String) {
        var range: NSRange = self.mutableString.rangeOfString(stringValue, options: NSCaseInsensitiveSearch)
        if range != nil {
            self.addAttribute(NSForegroundColorAttributeName, value: color, range: range)
        }
    }

Résultat:

entrez la description de l'image ici


12
//NSString *myString = @"I have to replace text 'Dr Andrew Murphy, John Smith' ";
NSString *myString = @"Not a member?signin";

//Create mutable string from original one
NSMutableAttributedString *attString = [[NSMutableAttributedString alloc] initWithString:myString];

//Fing range of the string you want to change colour
//If you need to change colour in more that one place just repeat it
NSRange range = [myString rangeOfString:@"signin"];
[attString addAttribute:NSForegroundColorAttributeName value:[UIColor colorWithRed:(63/255.0) green:(163/255.0) blue:(158/255.0) alpha:1.0] range:range];

//Add it to the label - notice its not text property but it's attributeText
_label.attributedText = attString;

6

Depuis iOS 6 , UIKit prend en charge le dessin de chaînes attribuées, aucune extension ou remplacement n'est donc nécessaire.

De UILabel:

@property(nonatomic, copy) NSAttributedString *attributedText;

Il vous suffit de créer votre fichier NSAttributedString. Il existe essentiellement deux façons:

  1. Ajoutez des morceaux de texte avec les mêmes attributs - pour chaque partie, créez une NSAttributedStringinstance et ajoutez-les à uneNSMutableAttributedString

  2. Créez un texte attribué à partir d'une chaîne simple, puis ajoutez un attribut pour des plages données - trouvez la plage de votre numéro (ou autre) et appliquez un attribut de couleur différent à cela.


6

Anups répond rapidement. Peut être réutilisé à partir de n'importe quelle classe.

Dans le fichier rapide

extension NSMutableAttributedString {

    func setColorForStr(textToFind: String, color: UIColor) {

        let range = self.mutableString.rangeOfString(textToFind, options:NSStringCompareOptions.CaseInsensitiveSearch);
        if range.location != NSNotFound {
            self.addAttribute(NSForegroundColorAttributeName, value: color, range: range);
        }

    }
}

Dans certains contrôleur de vue

let attributedString: NSMutableAttributedString = NSMutableAttributedString(string: self.labelShopInYourNetwork.text!);
attributedString.setColorForStr("YOUR NETWORK", color: UIColor(red: 0.039, green: 0.020, blue: 0.490, alpha: 1.0));
self.labelShopInYourNetwork.attributedText = attributedString;

4

Avoir un UIWebView ou plus d'un UILabel pourrait être considéré comme excessif pour cette situation.

Ma suggestion serait d'utiliser TTTAttributedLabel, qui remplace UILabel qui prend en charge NSAttributedString . Cela signifie que vous pouvez très facilement appliquer différents styles à différentes plages d'une chaîne.




3

JTAttributedLabel (par mystcolor) vous permet d'utiliser le support des chaînes attribuées dans UILabel sous iOS 6 et en même temps sa classe JTAttributedLabel sous iOS 5 via son JTAutoLabel.


2

Il existe une solution Swift 3.0

extension UILabel{


    func setSubTextColor(pSubString : String, pColor : UIColor){
        let attributedString: NSMutableAttributedString = NSMutableAttributedString(string: self.text!);
        let range = attributedString.mutableString.range(of: pSubString, options:NSString.CompareOptions.caseInsensitive)
        if range.location != NSNotFound {
            attributedString.addAttribute(NSForegroundColorAttributeName, value: pColor, range: range);
        }
        self.attributedText = attributedString

    }
}

Et il y a un exemple d'appel:

let colorString = " (string in red)"
self.mLabel.text = "classic color" + colorString
self.mLabel.setSubTextColor(pSubString: colorString, pColor: UIColor.red)

Salut, comment puis-je faire cela si je veux ajouter deux colorStrings différents? J'ai essayé d'utiliser votre exemple et d'en ajouter un autre, mais cela ne colore que l'un d'entre eux.
Erik Auranaune

Essayez ceci: let colorString = "(string in red)" let colorStringGreen = "(string in green)" self.mLabel.text = "classic color" + colorString + colorStringGreen self.mLabel.setSubTextColor (pSubString: colorString, pColor: UIColor .red) self.mLabel.setSubTextColor (pSubString: colorStringGreen, pColor: UIColor.green)
Kevin ABRIOUX

C'est étrange, cela ne change toujours pas les deux: s24.postimg.org/ds0rpyyut/… .
Erik Auranaune

Un problème est que si les deux chaînes sont identiques, cela ne colore qu'une seule d'entre elles, regardez ici: pastebin.com/FJZJTpp3 . Vous avez une solution pour cela aussi?
Erik Auranaune

2

Swift 4 et supérieur: Inspiré de la solution anoop4real , voici une extension String qui peut être utilisée pour générer du texte avec 2 couleurs différentes.

extension String {

    func attributedStringForPartiallyColoredText(_ textToFind: String, with color: UIColor) -> NSMutableAttributedString {
        let mutableAttributedstring = NSMutableAttributedString(string: self)
        let range = mutableAttributedstring.mutableString.range(of: textToFind, options: .caseInsensitive)
        if range.location != NSNotFound {
            mutableAttributedstring.addAttribute(NSAttributedStringKey.foregroundColor, value: color, range: range)
        }
        return mutableAttributedstring
    }
}

L'exemple suivant change la couleur de l'astérisque en rouge tout en conservant la couleur de l'étiquette d'origine pour le texte restant.

label.attributedText = "Enter username *".attributedStringForPartiallyColoredText("*", with: #colorLiteral(red: 1, green: 0, blue: 0, alpha: 1))

2

Ma réponse a également la possibilité de colorer toutes les occurrences d'un texte non seulement une occurrence de celui-ci: "wa ba wa ba dubdub", vous pouvez colorier toutes les occurrences de wa non seulement la première occurrence comme la réponse acceptée.

extension NSMutableAttributedString{
    func setColorForText(_ textToFind: String, with color: UIColor) {
        let range = self.mutableString.range(of: textToFind, options: .caseInsensitive)
        if range.location != NSNotFound {
            addAttribute(NSForegroundColorAttributeName, value: color, range: range)
        }
    }

    func setColorForAllOccuranceOfText(_ textToFind: String, with color: UIColor) {
        let inputLength = self.string.count
        let searchLength = textToFind.count
        var range = NSRange(location: 0, length: self.length)

        while (range.location != NSNotFound) {
            range = (self.string as NSString).range(of: textToFind, options: [], range: range)
            if (range.location != NSNotFound) {
                self.addAttribute(NSForegroundColorAttributeName, value: color, range: NSRange(location: range.location, length: searchLength))
                range = NSRange(location: range.location + range.length, length: inputLength - (range.location + range.length))
            }
        }
    }
}

Vous pouvez maintenant faire ceci:

let message = NSMutableAttributedString(string: "wa ba wa ba dubdub")
message.setColorForText(subtitle, with: UIColor.red) 
// or the below one if you want all the occurrence to be colored 
message.setColorForAllOccuranceOfText("wa", with: UIColor.red) 
// then you set this attributed string to your label :
lblMessage.attributedText = message

Et comment puis-je l'utiliser?
pableiros

1
Mis à jour ma réponse, passez une bonne journée :)
compilateur Alsh

1

Pour les utilisateurs de Xamarin , j'ai un C # statique méthode laquelle je passe un tableau de chaînes, un tableau d'UIColours et un tableau d'UIFont (ils devront correspondre en longueur). La chaîne attribuée est ensuite renvoyée.

voir:

public static NSMutableAttributedString GetFormattedText(string[] texts, UIColor[] colors, UIFont[] fonts)
    {

        NSMutableAttributedString attrString = new NSMutableAttributedString(string.Join("", texts));
        int position = 0;

        for (int i = 0; i < texts.Length; i++)
        {
            attrString.AddAttribute(new NSString("NSForegroundColorAttributeName"), colors[i], new NSRange(position, texts[i].Length));

            var fontAttribute = new UIStringAttributes
            {
                Font = fonts[i]
            };

            attrString.AddAttributes(fontAttribute, new NSRange(position, texts[i].Length));

            position += texts[i].Length;
        }

        return attrString;

    }

1

Dans mon cas, j'utilise Xcode 10.1. Il existe une option permettant de basculer entre le texte brut et le texte attribué dans le texte d'étiquette dans Interface Builder

entrez la description de l'image ici

J'espère que cela peut aider quelqu'un d'autre ..!


2
Il semble que XCode 11.0 a cassé l'éditeur de texte attribué. J'ai donc essayé d'utiliser TextEdit pour créer le texte, puis je l'ai collé dans Xcode et cela a étonnamment bien fonctionné.
Brainware

0
extension UILabel{

    func setSubTextColor(pSubString : String, pColor : UIColor){


        let attributedString: NSMutableAttributedString = self.attributedText != nil ? NSMutableAttributedString(attributedString: self.attributedText!) : NSMutableAttributedString(string: self.text!);


        let range = attributedString.mutableString.range(of: pSubString, options:NSString.CompareOptions.caseInsensitive)
        if range.location != NSNotFound {
            attributedString.addAttribute(NSForegroundColorAttributeName, value: pColor, range: range);
        }
        self.attributedText = attributedString

    }
}

0

Ma propre solution a été créée une méthode comme la suivante:

-(void)setColorForText:(NSString*) textToFind originalText:(NSString *)originalString withColor:(UIColor*)color andLabel:(UILabel *)label{

NSMutableAttributedString *attString = [[NSMutableAttributedString alloc] initWithString:originalString];
NSRange range = [originalString rangeOfString:textToFind];

[attString addAttribute:NSForegroundColorAttributeName value:color range:range];

label.attributedText = attString;

if (range.location != NSNotFound) {
    [attString addAttribute:NSForegroundColorAttributeName value:color range:range];
}
label.attributedText = attString; }

Cela fonctionnait avec une seule couleur différente dans le même texte, mais vous pouvez l'adapter facilement à plusieurs couleurs dans la même phrase.


0

En utilisant le code ci-dessous, vous pouvez définir plusieurs couleurs en fonction du mot.

NSMutableArray * array = [[NSMutableArray alloc] initWithObjects:@"1 ball",@"2 ball",@"3 ball",@"4 ball", nil];    
NSMutableAttributedString *attStr = [[NSMutableAttributedString alloc] init];
for (NSString * str in array)
 {
    NSMutableAttributedString * textstr = [[NSMutableAttributedString alloc] initWithString:[NSString stringWithFormat:@"%@ ,",str] attributes:@{NSForegroundColorAttributeName :[self getRandomColor]}];
     [attStr appendAttributedString:textstr];
  }
UILabel *lab = [[UILabel alloc] initWithFrame:CGRectMake(10, 300, 300, 30)];
lab.attributedText = attStr;
[self.view addSubview:lab];

-(UIColor *) getRandomColor
{
   CGFloat redcolor = arc4random() % 255 / 255.0;
   CGFloat greencolor = arc4random() % 255 / 255.0;
   CGFloat bluencolor = arc4random() % 255 / 255.0;
   return  [UIColor colorWithRed:redcolor green:greencolor blue:bluencolor alpha:1.0];
}

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.