IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C++Builder Discussion :

comment avoir differentes couleurs de caractere dans une cellule d'un StringGrid


Sujet :

C++Builder

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Rédacteur
    Avatar de blondelle
    Homme Profil pro
    Inscrit en
    Mars 2006
    Messages
    2 738
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Mars 2006
    Messages : 2 738
    Par défaut comment avoir differentes couleurs de caractere dans une cellule d'un StringGrid
    A la suite de recherches sur le Net j'ai trouve une source Delphi qui permet d'avoir differentes couleurs sur la chaine de caractere qui s'affiche dans une cellule, ce n'est juste qu'un essai qui demande a etre complete
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
     
    void __fastcall TForm1::StringGrid1DrawCell(TObject *Sender, int ACol,
          int ARow, TRect &Rect, TGridDrawState State)
    {
            if (State.Contains(gdFocused))
            {
    // decalage qui evite le chevauchement des caracteres
    const CharOffset = 8;
    // 1er lettre de couleur bleu
    StringGrid1->Canvas->Font->Color = clBlue;
    StringGrid1->Canvas->TextOutA(Rect.left + CharOffset, Rect.top + CharOffset, "C");
    // 2em lettre de couleur rouge
    StringGrid1->Canvas->Font->Color = clRed;
    StringGrid1->Canvas->TextOutA(Rect.left + CharOffset + StringGrid1->Canvas->TextWidth("L"), Rect.top + CharOffset, "D");
    // reste du texte de couleur verte
    StringGrid1->Canvas->Font->Color = clGreen;
    StringGrid1->Canvas->TextOutA(Rect.left + CharOffset + CharOffset + StringGrid1->Canvas->TextWidth("L"), Rect.top + CharOffset, "Essai");
            }
    }

  2. #2
    Membre Expert

    Profil pro
    Inscrit en
    Juin 2002
    Messages
    1 407
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2002
    Messages : 1 407
    Par défaut
    Salut !

    On pourrait éventuellement aussi le penser comme ceci (chaque lettre a une couleur différente de ses voisines immédiates):

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    TColor Colors[MaxColors]= {...};
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
     
    int j, x, y;
    AnsiString A = " ";
    Ansistring N = ...Strings[..]
     
    y = (R.Top + R.Bottom - Canvas->TextHeight("W")) / 2;
     
    x = ;// selon que... 
     
    for(j=1; j <= N->Length(); j++)
        {
        Canvas->Font->Color = Colors[(j-1) % MaxColors];
        A[1] = N[j];
        Canvas->TextOut(x,y, A);
        x = x + Canvas->TextWidth(A);
        }
    En ce qui concerne le calcul de l'index de la couleur dans le tableau ou le calcul de la couleur elle-meme (via la macro RGB par exemple), il n'y a bien que l'imagination qui soit une limite à ce que l'on peut faire !

    A plus !

  3. #3
    Rédacteur
    Avatar de blondelle
    Homme Profil pro
    Inscrit en
    Mars 2006
    Messages
    2 738
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Mars 2006
    Messages : 2 738
    Par défaut
    Salut henderson
    Merci pour ta reponse, voici comment j'ai teste ton code
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
     
    void __fastcall TForm1::StringGrid1DrawCell(TObject *Sender, int ACol,
          int ARow, TRect &Rect, TGridDrawState State)
    {
            if (State.Contains(gdFocused))
            {
    int MaxColors = 255;
    TColor Colors[5] = {RGB(50,50,50),RGB(100,100,100),RGB(150,150,150),RGB(200,200,200),RGB(250,250,250)};
    int j;
    int x;
    int y;
    AnsiString A = " ";
    AnsiString N = "Chaine d'essai";
    y = (Rect.top + Rect.bottom - StringGrid1->Canvas->TextHeight("W")) / 2;
    x = (Rect.left + StringGrid1->Canvas->TextWidth("W"));
    for(j = 1; j <= N.Length(); j++)
        {
        StringGrid1->Canvas->Font->Color = Colors[(j-1) % MaxColors];
        A[1] = N[j];
        StringGrid1->Canvas->TextOut(x,y, A);
        x = x + StringGrid1->Canvas->TextWidth(A);
        }
        }
    }
    Je ne sais pas si l'ecriture de ces deux lignes est comme tu l'avais pense
    int MaxColors = 255;
    TColor Colors[5] = {RGB(50,50,50),RGB(100,100,100),RGB(150,150,150),RGB(200,200,200),RGB(250,250,250)};

  4. #4
    Membre Expert

    Profil pro
    Inscrit en
    Juin 2002
    Messages
    1 407
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2002
    Messages : 1 407
    Par défaut
    Salut !

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    //Pour fixer la dimension du tableau
    #define MaxColors 5
     
    TColor Colors[MaxColors]=  {...initialisation...};
    On est donc dans un contexte où l'on impose (pour une compilation donnée) une règle : MaxColors ni plus ni moins !
    Le modulo qui est appliqué dans la formule [ (j-1) % MaxColors ] sert à ne pas déborder du tableau.
    Il est clair que si j > MaxColors alors on obtient un cycle dû à l'accès circulaire dans le tableau.

    On peut envisager tout plein de solutions (entends par là plein d'effets).
    Par exemple, on peut calculer les teintes sous forme d'une progression, du premier au dernier caractère sans utiliser de tableau et uniquement en travaillant avec RGB, en partant d'une teinte connue pour arriver à une autre teinte connue.
    Ca fonctionne très bien (et facilement) dans un contexte à niveaux de Rouge, Vert, Bleu ou Gris...

    MaxColors pourrait aussi valoir 26 ou 16 !

    Et pour cette dernière valeur (donc un tableau de 16 teintes) :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    Canvas->Font->Color = Colors[ A[1] & 0xF ];
    A plus !

  5. #5
    Membre Expert

    Profil pro
    Inscrit en
    Juin 2002
    Messages
    1 407
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2002
    Messages : 1 407
    Par défaut
    Salut !

    Voici un modèle pour faire des dégradés :
    Comme c'est un simple test, j'utilise une TPaintBox (256 * 17) pour faire écho.
    Ici je fais un dégradé de couleur d'arrière plan avec un dégradé de couleur différent pour le texte.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
     
    class jRgb
    {
    public :
    Byte b;
    Byte g;
    Byte r;
    };
     
    void __fastcall TForm1::PaintBox1Paint(TObject *Sender)
    {
    AnsiString N = "Hello...bla bla bla . That's all folks!";
    int we = PaintBox1->Width;
    int he = PaintBox1->Height;
    Graphics::TBitmap *A = new Graphics::TBitmap;
    A->PixelFormat = pf24bit;
    A->Width = we;
    A->Height = he;
     
    A->Canvas->Brush->Style = bsSolid;
    A->Canvas->Brush->Color = clBlack;
    A->Canvas->FillRect(Rect(0,0,we, he));
     
    A->Canvas->Font->Style = A->Canvas->Font->Style << fsBold;
    int y = (he - A->Canvas->TextHeight(N)) / 2;
    int x = (we - A->Canvas->TextWidth(N)) / 2;
     
    A->Canvas->Font->Color = (TColor)0xC0C040;
    A->Canvas->TextOut(x, y, N);
     
    jRgb *P;
    for(y = 0; y < he; y++)
        {
        P = (jRgb*)A->ScanLine[y];
        for(x = 0; x < we; x++)
            {
            P[x].b = (Byte)(P[x].b | x);
            P[x].g = (Byte)(P[x].g ^ x);
            P[x].r = (Byte)(P[x].r & x);
            }
        }
     
    PaintBox1->Canvas->Draw(0, 0, A);
    delete A;
    }

    La partie ...
    P[x].b = (Byte)(P[x].b | x);
    P[x].g = (Byte)(P[x].g ^ x);
    P[x].r = (Byte)(P[x].r & x);
    ... montre qu'il ne faut pas avoir peur de tester tout et n'importe quoi !


    Si on veut seulement un dégradé de couleur dans le texte (sur fond blanc) :
    - au niveau du bitmap on remplit avec du blanc et on écrit le texte en noir.
    - on traite chaque pixel du texte en prenant, la encore, la précaution d'utiliser ScanLine pour une question de rapidité d'exécution :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
     
    for(y = 0; y < he; y++)
        {
        P = (jRgb*)A->ScanLine[y];
        for(x = 0; x < we; x++)
            {
            if( (P[x].b + P[x].g + (P[x].r) == 0) // << si noir donc texte
                {
                P[x].b = (Byte)(P[x].b | x);
                P[x].g = (Byte)(P[x].g ^ x);
                P[x].r = (Byte)(P[x].r & x);
                }
            }
        }
    Puis pour imiter un problème d'imprimante :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    P[x].b = (Byte)(P[x].b | x);
    P[x].g = (Byte)((P[x].g ^ x) * y);
    P[x].r = (Byte)(P[x].r & x);
    Sans oublier tous les algos de traitement d'image...
    Bref !


    Sinon pour le sujet qui était initialement proposé, à savoir :
    - dessiner le premier caractère d'une chaîne avec une couleur
    - puis le deuxième avec une deuxième couleur
    - et le reste de la chaîne avec une troisième couleur
    Il faudrait ajouter des tests, pour l'appliquer sur le contenu renvoyé par Cells :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
     
    int x ...
    int Y ...
    AnsiString A = " ";
    AnsiString N = ...->Cells[ACol][ARow];
    int le = N.Length();
    if(le >= 1)
        {
        A[1] = N[1];
        Canvas->Font->Color = ...;
        Canvas->TextOut(x,y, A);
        x = x + Canvas->TextWidth(A);
        if(le >= 2)
            {
            A[1] = N[2];
            Canvas->Font->Color = ...;
            Canvas->TextOut(x,y, A);
            x = x + Canvas->TextWidth(A);
            if(le >= 3)
                {
                Canvas->Font->Color = ...;
                Canvas->TextOut( x,y, N.SubString(3, le) ); 
                }
            }
        }
    A plus !

Discussions similaires

  1. [LibreOffice][Tableur] Comment copier la couleur de fond d'une cellule existante dans une autre ?
    Par elfasys dans le forum OpenOffice & LibreOffice
    Réponses: 2
    Dernier message: 28/02/2014, 21h28
  2. comment avoir plus de 4000 Char dans une variable CLOB?
    Par makohsarah dans le forum PL/SQL
    Réponses: 11
    Dernier message: 29/04/2010, 14h40
  3. comment avoir le nbr de caracteres dans un JTextField
    Par naazih dans le forum Composants
    Réponses: 3
    Dernier message: 25/03/2007, 11h47
  4. Réponses: 2
    Dernier message: 02/03/2007, 22h20
  5. [VBA-E] Insérez le caractere " dans une cellule
    Par Ania dans le forum Macros et VBA Excel
    Réponses: 2
    Dernier message: 22/09/2006, 16h20

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo