Multiples couleurs sur un UILabel incluant plusieurs NSString

Bonjour,


J'utilise actuellement un label qui comprend 3 NSString différents, voici le code :



NSString *sentenceActivity = [object objectForKey:@sentence];
NSString *commentActivity = [object objectForKey:@comment];
NSString *username = [userfriend objectForKey:@username];

UILabel *colorLabel = (UILabel*) [cell viewWithTag:101];
[colorLabel setText:[NSString stringWithFormat:@%@ %@ : '%@'", username,sentenceActivity,commentActivity]];

Pour des raisons de lisibilité je souhaiterais que chaque NSString soit affiché dans une couleur, voire une police différente. Par exemple


username en rouge


sentenceActivity en noir


commentActivity en noir gras


 


En faisant des recherches j'ai pu comprendre qu'un NSString ne pouvait pas changer de couleur, il faudrait a priori passer par un "NSAttributedString"


 


J'ai utilisé l'exemple ci-dessous, qui fonctionne : le username s'affiche bien en rouge.


Ma question : Est-il possible d'associer cet NSAttributedString avec mes 3 NSString pour que mon label puisse être composé des trois couleurs différentes ?



UIColor *color = [UIColor redColor]; // select needed color
NSDictionary *attrs = @{ NSForegroundColorAttributeName : color };
NSAttributedString *attrStr = [[NSAttributedString alloc] initWithString:username attributes:attrs];
colorLabel.attributedText = attrStr;

si vous avez une petite idée merci par avance pour votre aide


 


 


Mots clés:
«1

Réponses

  • LarmeLarme Membre
    février 2017 modifié #2

    Utilises la version mutable : NSMutableAttributedString pour ça. Tu peux faire des append et autre.


     


    Pour simplifier/résumer la différence entre NSString & NSAttributedString :


    Le NSString ne peut pas changer la couleur, car le NSString n'est pour simplifier qu'une suite de caractères, la couleur, c'est au UILabel de la gérer, le NSString se fout complètement de l'UI.


    Le NSAttributedString lui rajoute des propriétés de couleurs et autres au NSString, afin de dire quand il sera affiché, qu'il préférerait que ses propriétés additionnelles soient interprétées par le Label.


  • OK Larme merci beaucoup


    Je trouve peu d'exemples pouvant m'aider à  construire mon code il me faudrait un truc dans cette logique je suppose :



    NSMutableAttributedString *string = [[NSMutableAttributedString alloc] initWithString:@%@ %@ : '%@'"];
    [string ---- ajouter la couleur [UIColor redColor] sur :username];
    [string ---- ajouter la couleur [UIColor blackColor] sur :commentActivity];
    [string ---- ajouter la couleur [UIColor greenColor] sur :sentenceActivity];

    UILabel *colorLabel = (UILabel*) [cell viewWithTag:101];
    colorLabel.attributedText = string;

    suis-je sur la bonne voie ?

  • LarmeLarme Membre
    février 2017 modifié #4

    Exemple :



    NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] init];
    NSAttributedString *userNameAttr = [[NSAttributedString alloc] initWithString:userName attributes:@{NSForegroundAttributeName:[UIColor redColor]}];
    [attrAttr appendAttributedString:userNameAttr];
    NSAttributedString *commentAttr = [[NSAttributedString alloc] initWithString:commentActivity attributes:@{NSForegroundAttributeName:[UIColor blackColor]}];
    [attrAttr appendAttributedString:commentAttr];
    NSAttributedString *sentenceAttr = [[NSAttributedString alloc] initWithString:sentenceActivity attributes:@{NSForegroundAttributeName:[UIColor greenColor]}];
    [attrAttr appendAttributedString:sentenceAttr];
    colorLabel.attributedText = attrStr;

    Je n'ai pas mis les espaces et autres caractères comme les deux points, mais tu peux avoir ton idée là -dessus pour les rajouter, ne sachant pas ce que tu veux comme attributes (police/taille/couleur, etc).


     


    Maintenant, comme c'est parfois un peu long à  faire, tu peux passer par des convertisseurs, en embarquant ça dans du HTML, ou autre. Il y a des libs sur le net pour faciliter le tout.


  • Merci beaucoup pour l'exemple !


    Du coup comment l'associer au "string" initial ci-dessous ?



    [colorLabel setText:[NSString stringWithFormat:@%@ %@ : '%@'", username,sentenceActivity,commentActivity]];

    J'ai tenté ceci en vain ça ne fonctionne pas :



    NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] initWithString:@%@ %@ : '%@'"];
    NSAttributedString *userNameAttr = [[NSAttributedString alloc] initWithString:username attributes:@{NSForegroundColorAttributeName:[UIColor redColor]}];
    [attrStr appendAttributedString:userNameAttr];
    NSAttributedString *commentAttr = [[NSAttributedString alloc] initWithString:commentActivity attributes:@{NSForegroundColorAttributeName:[UIColor blackColor]}];
    [attrStr appendAttributedString:commentAttr];
    NSAttributedString *sentenceAttr = [[NSAttributedString alloc] initWithString:sentenceActivity attributes:@{NSForegroundColorAttributeName:[UIColor greenColor]}];
    [attrStr appendAttributedString:sentenceAttr];
    colorLabel.attributedText = attrStr;

  • Il n'y a pas de attributedStringWithFormat équivalent dans NSAttributedString.


     


    Il faut que tu fasses toi-même le format.




  • Il n'y a pas de attributedStringWithFormat équivalent dans NSAttributedString.


     


    Il faut que tu fasses toi-même le format.




    gloups ... aurais-tu un petit exemple de format pour que je puisse en suivre la construction et l'adapter à  mon projet ?


  • NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] init];

    sera mieux !


     


    Je ne vois pas a priori d'autre erreur potentielle dans ton code.




  • NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] init];

    sera mieux !


     


    Je ne vois pas a priori d'autre erreur potentielle dans ton code.


     




    Oui Larme m'a bien aidé là  dessus, maintenant ma difficulté est de l'inclure dans mon UILabel

  • Un truc comme çà  peut-être...



    NSMutableAttributedString *theString = [[NSMutableAttributedString alloc] initWithString:oneString];

    [theString beginEditing];
    NSRange selectedRange = NSMakeRange(0, 14);
    int fontSizeText=14;
    [theString addAttribute:NSFontAttributeName
    value:[UIFont italicSystemFontOfSize:fontSizeText+1]
    range:selectedRange];
    selectedRange = NSMakeRange(2, 5);
    [theString addAttribute:NSFontAttributeName
    value:[UIFont italicSystemFontOfSize:fontSizeText-1]
    range:selectedRange];
    selectedRange=NSMakeRange(8, 5);
    [theString addAttribute:NSFontAttributeName
    value:[UIFont italicSystemFontOfSize:fontSizeText-1]
    range:selectedRange];
    selectedRange = NSMakeRange(20, 7);
    [theString addAttribute:NSFontAttributeName
    value:[UIFont italicSystemFontOfSize:fontSizeText-3]
    range:selectedRange];
    [theString endEditing];


    Bien sûr les "selectedRange" sont définis en dur, mais il faut éviter çà ... A toi d'adapter à  ton cas...




  • Un truc comme çà  peut-être...



    NSMutableAttributedString *theString = [[NSMutableAttributedString alloc] initWithString:oneString];

    [theString beginEditing];
    NSRange selectedRange = NSMakeRange(0, 14);
    int fontSizeText=14;
    [theString addAttribute:NSFontAttributeName
    value:[UIFont italicSystemFontOfSize:fontSizeText+1]
    range:selectedRange];
    selectedRange = NSMakeRange(2, 5);
    [theString addAttribute:NSFontAttributeName
    value:[UIFont italicSystemFontOfSize:fontSizeText-1]
    range:selectedRange];
    selectedRange=NSMakeRange(8, 5);
    [theString addAttribute:NSFontAttributeName
    value:[UIFont italicSystemFontOfSize:fontSizeText-1]
    range:selectedRange];
    selectedRange = NSMakeRange(20, 7);
    [theString addAttribute:NSFontAttributeName
    value:[UIFont italicSystemFontOfSize:fontSizeText-3]
    range:selectedRange];
    [theString endEditing];


    Bien sûr les "selectedRange" sont définis en dur, mais il faut éviter çà ... A toi d'adapter à  ton cas...




    Merci, oui le problème avec les "range" c'est que dans mon cas il n'y a pas de longueur identique , c'est là  où à  présent je rame ...

  • colas_colas_ Membre
    février 2017 modifié #12

    colorLabel.attributedText = attrStr;

    me semble nickel.


     


    Si tu mets un point d'arrêt, tu peux inspecter ton attributedString pour voir s'il a les bonnes couleurs, déjà .


     


    Quel est le problème ?


    Qu'est-ce qui ne marche pas ?


     


    à‰ventuellement, dans IB, tu peux dire si le label accepte ou non des attributedString mais normalement si tu passes par le code ensuite, cette valeur de IB n'a pas d'importance.


     


    PS qui n'a rien à  voir mais pourra t'intéresser : tu peux transformer un ficher RTF en NSAttributedString


    PPS : ne t'embête pas avec les range. Append est suffisant.




  • Merci, oui le problème avec les "range" c'est que dans mon cas il n'y a pas de longueur identique , c'est là  où à  présent je rame ...




     


    Désolée, j'ai mis un exemple avec des tailles de police différentes mais tu peux t'en inspirer pour les couleurs. Concernant la définition des ranges, il te suffit de les définir avec la longueur de tes différentes strings 


    en utilisant :



    [sentenceActivity lenght]
    [commentActivity lenght]

    comme longueur des ranges...

  • Manière bateau :


    On construit petit à  petit la chaà®ne.



    NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] init];
    NSAttributedString *userNameAttr = [[NSAttributedString alloc] initWithString:userName attributes:@{NSForegroundAttributeName:[UIColor redColor]}];
    [attrAttr appendAttributedString:userNameAttr];
    NSAttributedString *f1 = [[NSAttributedString alloc] initWithString:@ ];
    [attrAttr appendAttributedString:f1];
    NSAttributedString *commentAttr = [[NSAttributedString alloc] initWithString:commentActivity attributes:@{NSForegroundAttributeName:[UIColor blackColor]}];
    [attrAttr appendAttributedString:commentAttr];
    NSAttributedString *f2 = [[NSAttributedString alloc] initWithString:@: '];
    [attrAttr appendAttributedString:f2];
    NSAttributedString *sentenceAttr = [[NSAttributedString alloc] initWithString:sentenceActivity attributes:@{NSForegroundAttributeName:[UIColor greenColor]}];
    [attrAttr appendAttributedString:sentenceAttr];
    NSAttributedString *f3 = [[NSAttributedString alloc] initWithString:@'];
    [attrAttr appendAttributedString:f3];
    colorLabel.attributedText = attrStr;

    Manière un peu différente avec des placeholders manuels :



    NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] initWithString:@<PlaceHolder1> : <PlaceHolder2> '<PlaceHolder3>'];
    NSAttributedString *userNameAttr = [[NSAttributedString alloc] initWithString:userName attributes:@{NSForegroundAttributeName:[UIColor redColor]}];
    [attrStr replaceCharactersInRange:[attrStr.String rangeOfString:@<PlaceHolder1>] withAttributedString:userNameAttr];
    NSAttributedString *commentAttr = [[NSAttributedString alloc] initWithString:commentActivity attributes:@{NSForegroundAttributeName:[UIColor blackColor]}];
    [attrStr replaceCharactersInRange:[attrStr.String rangeOfString:@<PlaceHolder2>] withAttributedString:commentAttr];
    NSAttributedString *sentenceAttr = [[NSAttributedString alloc] initWithString:sentenceActivity attributes:@{NSForegroundAttributeName:[UIColor greenColor]}];
    [attrStr replaceCharactersInRange:[attrStr.String rangeOfString:@<PlaceHolder3>] withAttributedString:sentenceAttr];

    Problème : Si userName, commentActivity ou sentenceActivity contiennent <PlaceHolder1>, <PlaceHolder2> ou <PlaceHolder3>...


    En bref, le soucis de "rangeOfString:", c'est qu'il retourne la première occurence trouvée, et si y'en a plusieurs et que tu ne voulais pas la première...


     


     


    Je t'invite à  créer un nouveau projet avec un unique UIViewController et un UILabel et de jouer avec les NSAttributedString pour comprendre comment cela fonctionne.




  • Manière un peu différente avec des placeholders manuels :



    NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] initWithString:@<PlaceHolder1> : <PlaceHolder2> '<PlaceHolder3>'];
    NSAttributedString *userNameAttr = [[NSAttributedString alloc] initWithString:userName attributes:@{NSForegroundAttributeName:[UIColor redColor]}];
    [attrStr replaceCharactersInRange:[attrStr.String rangeOfString:@<PlaceHolder1>] withAttributedString:userNameAttr];
    NSAttributedString *commentAttr = [[NSAttributedString alloc] initWithString:commentActivity attributes:@{NSForegroundAttributeName:[UIColor blackColor]}];
    [attrStr replaceCharactersInRange:[attrStr.String rangeOfString:@<PlaceHolder2>] withAttributedString:commentAttr];
    NSAttributedString *sentenceAttr = [[NSAttributedString alloc] initWithString:sentenceActivity attributes:@{NSForegroundAttributeName:[UIColor greenColor]}];
    [attrStr replaceCharactersInRange:[attrStr.String rangeOfString:@<PlaceHolder3>] withAttributedString:sentenceAttr];

    merci beaucoup à  tous pour l'entraide ! ... pour le moment ça coince :



    *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'NSConcreteAttributedString initWithString:: nil value'


    voici le code sur mon projet :



    PFUser *userfriend = [object objectForKey:@fromUser];
    NSString *sentenceActivity = [object objectForKey:@sentence];
    NSString *commentActivity = [object objectForKey:@comment];
    NSString *username = [userfriend objectForKey:@username];

    UILabel *colorLabel = (UILabel*) [cell viewWithTag:99];

    NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] initWithString:@<PlaceHolder1> : <PlaceHolder2> '<PlaceHolder3>'];

    NSAttributedString *userNameAttr = [[NSAttributedString alloc] initWithString:username attributes:@{NSForegroundColorAttributeName:[UIColor redColor]}];
    [attrStr replaceCharactersInRange:[attrStr.string rangeOfString:@<PlaceHolder1>] withAttributedString:userNameAttr];

    NSAttributedString *commentAttr = [[NSAttributedString alloc] initWithString:commentActivity attributes:@{NSForegroundColorAttributeName:[UIColor blackColor]}];
    [attrStr replaceCharactersInRange:[attrStr.string rangeOfString:@<PlaceHolder2>] withAttributedString:commentAttr];

    NSAttributedString *sentenceAttr = [[NSAttributedString alloc] initWithString:sentenceActivity attributes:@{NSForegroundColorAttributeName:[UIColor greenColor]}];
    [attrStr replaceCharactersInRange:[attrStr.string rangeOfString:@<PlaceHolder3>] withAttributedString:sentenceAttr];
    colorLabel.attributedText = attrStr;


  • DrakenDraken Membre
    février 2017 modifié #16

    Moi j'aurais écrit des fonctions génériques pour mettre en forme les NSAttributedString, et concaténer les chaà®nes à  la fin. Et je l'aurais réalisé en Swift, ma religion interdisant l'Obj-C.



    func changerFont (texte:NSMutableAttributedString, font:UIFont)
    {
    texte.addAttribute(NSFontAttributeName,
    value: font,
    range:NSRange(location:0, length:texte.length))
    }

    func changerCouleur(texte:NSMutableAttributedString, couleur:UIColor) {
    texte.addAttribute(NSForegroundColorAttributeName,
    value: couleur,
    range:NSRange(location:0, length:texte.length))
    }


    Mise en pratique :



    // Création du label pour affichage
    let monLabel = UILabel(frame: CGRect(x: 0, y: 0, width: 400, height: 50))
    monLabel.textAlignment = .center
    monLabel.center = self.view.center
    self.view.addSubview(monLabel)

    let dico = ["sentence":"Démission",
    "comment":"Bien fait pour lui",
    "username":"Donald Trump"]

    // Lecture infos
    // et ajout de la présentation
    // (Tous ces ! => Pas très propre pour du Swift)
    let strSenteceActivity = dico["sentence"]! + " "
    let strCommentActivity = dico["comment"]! + " : "
    let strUsername = dico["username"]!

    // Création des NSMutableAttributedString
    let sentenceActivity = NSMutableAttributedString(string: strSenteceActivity)
    let commentActivity = NSMutableAttributedString(string: strCommentActivity)
    let username = NSMutableAttributedString(string: strUsername)

    // Colorisation du texte
    self.changerCouleur(texte: sentenceActivity, couleur: UIColor.red)
    self.changerCouleur(texte: commentActivity, couleur: UIColor.black)
    self.changerCouleur(texte: username, couleur: UIColor.green)

    // Concaténation des textes
    let monTexte = NSMutableAttributedString()
    monTexte.append(sentenceActivity)
    monTexte.append(commentActivity)
    monTexte.append(username)

    // Affichage
    monLabel.attributedText = monTexte


    EDIT :


    J'ai tapé ce code pour te donner une idée de la manière comment faire. Si je l'avais écris pour moi, j'aurais utilisé certaines fonctionnalités du Swift non traduisible en Obj-C.


     


    Copie d'écran du résultat :


  • Le même, avec plusieurs Fonts :



    // Création du label pour affichage
    let monLabel = UILabel(frame: CGRect(x: 0, y: 0, width: 400, height: 50))
    monLabel.textAlignment = .center
    monLabel.center = self.view.center
    self.view.addSubview(monLabel)

    let dico = ["sentence":"Démission",
    "comment":"bien fait pour lui",
    "username":"Donald Trump"]

    // Polices de caractéres
    let fontSize:CGFloat = 14
    let fontNormal = UIFont.systemFont(ofSize: fontSize)
    let fontGras = UIFont.boldSystemFont(ofSize: fontSize + 5.0)
    let fontItalic = UIFont.italicSystemFont(ofSize: fontSize)

    // Lecture infos
    // et ajout de la présentation
    // (Tous ces ! => Pas très propre pour du Swift)
    let strSenteceActivity = dico["sentence"]! + " "
    let strCommentActivity = dico["comment"]! + " : "
    let strUsername = dico["username"]!

    // Création des NSMutableAttributedString
    let sentenceActivity = NSMutableAttributedString(string: strSenteceActivity)
    let commentActivity = NSMutableAttributedString(string: strCommentActivity)
    let username = NSMutableAttributedString(string: strUsername)

    // Colorisation du texte
    self.changerCouleur(texte: sentenceActivity, couleur: UIColor.red)
    self.changerFont(texte: sentenceActivity, font: fontGras)

    self.changerCouleur(texte: commentActivity, couleur: UIColor.black)
    self.changerFont(texte: commentActivity, font: fontNormal)

    self.changerCouleur(texte: username, couleur: UIColor.green)
    self.changerFont(texte: username, font: fontItalic)

    // Concaténation des textes
    let monTexte = NSMutableAttributedString()
    monTexte.append(sentenceActivity)
    monTexte.append(commentActivity)
    monTexte.append(username)

    // Affichage
    monLabel.attributedText = monTexte
     

    En image :


     


     


     


  • Draken tout ça me fait bien envie (surtout la démission de D Trump), malheureusement je suis un vieux réac 'old school' qui ne s'est pas encore suffisamment adapté au Swift ...
  • DrakenDraken Membre
    février 2017 modifié #19

    C'est bien dommage (surtout l'élection de D Trump).


    Mais je pense que tu peux reprendre la même logique en Obj-C.



  • Le même, avec plusieurs Fonts :



    // Création du label pour affichage
    let monLabel = UILabel(frame: CGRect(x: 0, y: 0, width: 400, height: 50))
    monLabel.textAlignment = .center
    monLabel.center = self.view.center
    self.view.addSubview(monLabel)

    let dico = ["sentence":"Démission",
    "comment":"bien fait pour lui",
    "username":"Donald Trump"]

    // Polices de caractéres
    let fontSize:CGFloat = 14
    let fontNormal = UIFont.systemFont(ofSize: fontSize)
    let fontGras = UIFont.boldSystemFont(ofSize: fontSize + 5.0)
    let fontItalic = UIFont.italicSystemFont(ofSize: fontSize)

    // Lecture infos
    // et ajout de la présentation
    // (Tous ces ! => Pas très propre pour du Swift)
    let strSenteceActivity = dico["sentence"]! + " "
    let strCommentActivity = dico["comment"]! + " : "
    let strUsername = dico["username"]!

    // Création des NSMutableAttributedString
    let sentenceActivity = NSMutableAttributedString(string: strSenteceActivity)
    let commentActivity = NSMutableAttributedString(string: strCommentActivity)
    let username = NSMutableAttributedString(string: strUsername)

    // Colorisation du texte
    self.changerCouleur(texte: sentenceActivity, couleur: UIColor.red)
    self.changerFont(texte: sentenceActivity, font: fontGras)

    self.changerCouleur(texte: commentActivity, couleur: UIColor.black)
    self.changerFont(texte: commentActivity, font: fontNormal)

    self.changerCouleur(texte: username, couleur: UIColor.green)
    self.changerFont(texte: username, font: fontItalic)

    // Concaténation des textes
    let monTexte = NSMutableAttributedString()
    monTexte.append(sentenceActivity)
    monTexte.append(commentActivity)
    monTexte.append(username)

    // Affichage
    monLabel.attributedText = monTexte
     



    Help... please .... petite traduction en Obj-C  ? ... :'(

  • Joanna CarterJoanna Carter Membre, Modérateur
    février 2017 modifié #21

    Autre possibilité, peut-être plus facile à  gérer :


     


  • DrakenDraken Membre
    février 2017 modifié #22


     


    Trois UILabels, avec de l'espace entre eux, quE autolayout gérera automatiquement.




    Note pour Jopaone : Joanna est anglaise. On l'aide à  parfaire sa (considérable) maitrise du français en lui signalant de petites erreurs ici et là .

  • Joanna CarterJoanna Carter Membre, Modérateur


     


    Trois UILabels, avec de l'espace entre eux, qu'autolayout gérera automatiquement.




    :o

  • ::)


  • Du coup, c'est quoi la bonne orthographe ?


    "que autolayout" ou "qu'autolayout" ?




  • Autre possibilité, peut-être plus facile à  gérer :


     


    attachicon.gifLabels.png


     


    Trois UILabels, avec de l'espace entre eux, qu'autolayout gérera automatiquement.


     


    Ou, on peut les mettre dans un UIStackView


     


    attachicon.gifStackView.png




    Enorme !! Tellement évident ...



  • Du coup, c'est quoi la bonne orthographe ?


    "que autolayout" ou "qu'autolayout" ?




    Je dirais "qu'autolayout" mais je suis moi-même franglais ...

  • DrakenDraken Membre
    février 2017 modifié #28


    Du coup, c'est quoi la bonne orthographe ?


    "que autolayout" ou "qu'autolayout" ?




    Si mes souvenirs sont bon, on ne doit pas utiliser "qu'" devant un nom. Reste à  savoir si autolayout est une chose ou le nom d'une chose. Ce n'est pas clair.


     


    Joanna n'avait pas tapé "qu'" ou "que" mais .. autre chose. Elle a corrigé son post depuis.


     


    EDIT : après recherche on doit toujours mettre "qu'" devant une voyelle (A, E, I, O, U, et Y). 


    C'est donc "qu'autolayout"


  • LarmeLarme Membre
    février 2017 modifié #29


     



    Manière un peu différente avec des placeholders manuels :



    NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] initWithString:@<PlaceHolder1> : <PlaceHolder2> '<PlaceHolder3>'];
    NSAttributedString *userNameAttr = [[NSAttributedString alloc] initWithString:userName attributes:@{NSForegroundAttributeName:[UIColor redColor]}];
    [attrStr replaceCharactersInRange:[attrStr.String rangeOfString:@<PlaceHolder1>] withAttributedString:userNameAttr];
    NSAttributedString *commentAttr = [[NSAttributedString alloc] initWithString:commentActivity attributes:@{NSForegroundAttributeName:[UIColor blackColor]}];
    [attrStr replaceCharactersInRange:[attrStr.String rangeOfString:@<PlaceHolder2>] withAttributedString:commentAttr];
    NSAttributedString *sentenceAttr = [[NSAttributedString alloc] initWithString:sentenceActivity attributes:@{NSForegroundAttributeName:[UIColor greenColor]}];
    [attrStr replaceCharactersInRange:[attrStr.String rangeOfString:@<PlaceHolder3>] withAttributedString:sentenceAttr];

    merci beaucoup à  tous pour l'entraide ! ... pour le moment ça coince :



    *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'NSConcreteAttributedString initWithString:: nil value'


    voici le code sur mon projet :



    PFUser *userfriend = [object objectForKey:@fromUser];
    NSString *sentenceActivity = [object objectForKey:@sentence];
    NSString *commentActivity = [object objectForKey:@comment];
    NSString *username = [userfriend objectForKey:@username];

    UILabel *colorLabel = (UILabel*) [cell viewWithTag:99];

    NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] initWithString:@<PlaceHolder1> : <PlaceHolder2> '<PlaceHolder3>'];

    NSAttributedString *userNameAttr = [[NSAttributedString alloc] initWithString:username attributes:@{NSForegroundColorAttributeName:[UIColor redColor]}];
    [attrStr replaceCharactersInRange:[attrStr.string rangeOfString:@<PlaceHolder1>] withAttributedString:userNameAttr];

    NSAttributedString *commentAttr = [[NSAttributedString alloc] initWithString:commentActivity attributes:@{NSForegroundColorAttributeName:[UIColor blackColor]}];
    [attrStr replaceCharactersInRange:[attrStr.string rangeOfString:@<PlaceHolder2>] withAttributedString:commentAttr];

    NSAttributedString *sentenceAttr = [[NSAttributedString alloc] initWithString:sentenceActivity attributes:@{NSForegroundColorAttributeName:[UIColor greenColor]}];
    [attrStr replaceCharactersInRange:[attrStr.string rangeOfString:@<PlaceHolder3>] withAttributedString:sentenceAttr];
    colorLabel.attributedText = attrStr;



     




    ça veut dire qu'à  un moment donné, il y a NSString qui est nilsentenceActivity? commentActivity? userName ?


    Mais je t'ai donné ce qu'il fallait faire grosso-modo, c'est à  toi aussi de débugguer de ton côté.


    C'est un conseil qui pourra t'aider plus tard :


    Ne jamais prendre à  100% pour argent comptant un code que tu peux trouver sur Internet. 


    Si le code semble "correct", ne pas hésiter à  y trouver ses limites, cas non-gérés (comme c'est le cas ici avec ton crash). Ce sont souvent des indications de code qui fonctionnent dans le meilleur des cas.


     


    En remplaçant initWithString:username avec initWithString:[NSString stringWithFormat:@%@", userName] pour les 3 cas, tu l'éviteras, mais tu devrais voir (null) à  la place. 


    Donc plutôt :


    initWithString:username avec initWithString:userName?userName:@UserName inconnu


    initWithString:commentActivity avec initWithString:commentActivity?commentActivity:@Pas de commentaire


    initWithString:sentenceActivity avec initWithString:sentenceActivity?sentenceActivity:@Pas de phrase


    Ce sont des idées, rien de plus.



  • ça veut dire qu'à  un moment donné, il y a NSString qui est nilsentenceActivity? commentActivity? userName ?


    Mais je t'ai donné ce qu'il fallait faire grosso-modo, c'est à  toi aussi de débugguer de ton côté.


    C'est un conseil qui pourra t'aider plus tard :


    Ne jamais prendre à  100% pour argent comptant un code que tu peux trouver sur Internet. 


    Si le code semble "correct", ne pas hésiter à  y trouver ses limites, cas non-gérés (comme c'est le cas ici avec ton crash). Ce sont souvent des indications de code qui fonctionnent dans le meilleur des cas.


     


    En remplaçant initWithString:username avec initWithString:[NSString stringWithFormat:@%@", userName] pour les 3 cas, tu l'éviteras, mais tu devrais voir (null) à  la place. 


    Donc plutôt :


    initWithString:username avec initWithString:userName?userName:@UserName inconnu


    initWithString:commentActivity avec initWithString:commentActivity?commentActivity:@Pas de commentaire


    initWithString:sentenceActivity avec initWithString:sentenceActivity?sentenceActivity:@Pas de phrase


    Ce sont des idées, rien de plus.




    Oui merci beaucoup c'est débuggué et ça fonctionne nickel !

  • JopaoneJopaone Membre
    février 2017 modifié #31

    Encore merci à  tous et bravo pour cette aide très collective


Connectez-vous ou Inscrivez-vous pour répondre.