96 votes

Générer des couleurs RGB distinctes dans les graphiques

Lors de la génération de graphiques et l'affichage de différents ensembles de données, il est généralement judicieux de différencier les ensembles par couleur. Ainsi, une ligne est rouge et la suivante est verte, et ainsi de suite. Le problème est alors que lorsque le nombre d'ensembles de données est inconnu, il est nécessaire de générer ces couleurs de manière aléatoire et souvent elles se retrouvent très proches les unes des autres (par exemple vert, vert clair).

Avez-vous des idées sur la façon dont cela pourrait être résolu et comment il serait possible de générer des couleurs nettement différentes?

Il serait utile que des exemples soient en C# et basés sur des couleurs RGB.

1 votes

136voto

Sam Meldrum Points 7405

Vous avez trois canaux de couleur 0 à 255 R, G et B.

Passez d'abord par

0, 0, 255
0, 255, 0
255, 0, 0

Puis passez par

0, 255, 255
255, 0, 255
255, 255, 0

Ensuite divisez par 2 => 128 et recommencez :

0, 0, 128
0, 128, 0
128, 0, 0
0, 128, 128
128, 0, 128
128, 128, 0

Divisez par 2 => 64

La prochaine fois, ajoutez 64 à 128 => 192

suivez le modèle.

Facile à programmer et vous donne des couleurs assez distinctes.

EDIT : Demande de code d'exemple

Aussi - en ajoutant le motif supplémentaire ci-dessous si le gris est une couleur acceptable :

255, 255, 255
128, 128, 128

Il existe plusieurs façons de générer ces couleurs en code.

La méthode facile

Si vous pouvez garantir que vous n'aurez jamais besoin de plus d'un nombre fixe de couleurs, générez simplement un tableau de couleurs suivant ce modèle et utilisez-les :

    static string[] ColourValues = new string[] { 
        "FF0000", "00FF00", "0000FF", "FFFF00", "FF00FF", "00FFFF", "000000", 
        "800000", "008000", "000080", "808000", "800080", "008080", "808080", 
        "C00000", "00C000", "0000C0", "C0C000", "C000C0", "00C0C0", "C0C0C0", 
        "400000", "004000", "000040", "404000", "400040", "004040", "404040", 
        "200000", "002000", "000020", "202000", "200020", "002020", "202020", 
        "600000", "006000", "000060", "606000", "600060", "006060", "606060", 
        "A00000", "00A000", "0000A0", "A0A000", "A000A0", "00A0A0", "A0A0A0", 
        "E00000", "00E000", "0000E0", "E0E000", "E000E0", "00E0E0", "E0E0E0", 
    };

La méthode difficile

Si vous ne savez pas combien de couleurs vous allez avoir besoin, le code ci-dessous générera jusqu'à 896 couleurs en utilisant ce modèle. (896 = 256 * 7 / 2) 256 est l'espace de couleur par canal, nous avons 7 modèles et nous arrêtons avant d'atteindre des couleurs séparées par une seule valeur de couleur.

J'ai probablement rendu ce code plus compliqué que nécessaire. Tout d'abord, il y a un générateur d'intensité qui commence à 255, puis génère les valeurs selon le modèle décrit ci-dessus. Le générateur de motif fait simplement une boucle à travers les sept modèles de couleur.

using System;

class Program {
    static void Main(string[] args) {
        ColourGenerator generator = new ColourGenerator();
        for (int i = 0; i < 896; i++) {
            Console.WriteLine(string.Format("{0}: {1}", i, generator.NextColour()));
        }
    }
}

public class ColourGenerator {

    private int index = 0;
    private IntensityGenerator intensityGenerator = new IntensityGenerator();

    public string NextColour() {
        string colour = string.Format(PatternGenerator.NextPattern(index),
            intensityGenerator.NextIntensity(index));
        index++;
        return colour;
    }
}

public class PatternGenerator {
    public static string NextPattern(int index) {
        switch (index % 7) {
        case 0: return "{0}0000";
        case 1: return "00{0}00";
        case 2: return "0000{0}";
        case 3: return "{0}{0}00";
        case 4: return "{0}00{0}";
        case 5: return "00{0}{0}";
        case 6: return "{0}{0}{0}";
        default: throw new Exception("Erreur mathématique");
        }
    }
}

public class IntensityGenerator {
    private IntensityValueWalker walker;
    private int current;

    public string NextIntensity(int index) {
        if (index == 0) {
            current = 255;
        }
        else if (index % 7 == 0) {
            if (walker == null) {
                walker = new IntensityValueWalker();
            }
            else {
                walker.MoveNext();
            }
            current = walker.Current.Value;
        }
        string currentText = current.ToString("X");
        if (currentText.Length == 1) currentText = "0" + currentText;
        return currentText;
    }
}

public class IntensityValue {

    private IntensityValue mChildA;
    private IntensityValue mChildB;

    public IntensityValue(IntensityValue parent, int value, int level) {
        if (level > 7) throw new Exception("Il ne reste plus de couleurs");
        Value = value;
        Parent = parent;
        Level = level;
    }

    public int Level { get; set; }
    public int Value { get; set; }
    public IntensityValue Parent { get; set; }

    public IntensityValue ChildA {
        get {
            return mChildA ?? (mChildA = new IntensityValue(this, this.Value - (1<<(7-Level)), Level+1));
        }
    }

    public IntensityValue ChildB {
        get {
            return mChildB ?? (mChildB = new IntensityValue(this, Value + (1<<(7-Level)), Level+1));
        }
    }
}

public class IntensityValueWalker {

    public IntensityValueWalker() {
        Current = new IntensityValue(null, 1<<7, 1);
    }

    public IntensityValue Current { get; set; }

    public void MoveNext() {
        if (Current.Parent == null) {
            Current = Current.ChildA;
        }
        else if (Current.Parent.ChildA == Current) {
            Current = Current.Parent.ChildB;
        }
        else {
            int levelsUp = 1;
            Current = Current.Parent;
            while (Current.Parent != null && Current == Current.Parent.ChildB) {
                Current = Current.Parent;
                levelsUp++;
            }
            if (Current.Parent != null) {
                Current = Current.Parent.ChildB;
            }
            else {
                levelsUp++;
            }
            for (int i = 0; i < levelsUp; i++) {
                Current = Current.ChildA;
            }

        }
    }
}

0 votes

Je ne suis pas entièrement l'exemple. Est-ce que quelqu'un peut fournir un exemple en C# pour cela?

0 votes

J'espère que cet exemple de code vous aide - il y a probablement une manière beaucoup plus propre de parcourir l'arbre des valeurs d'intensité, mais c'était une première tentative qui a bien fonctionné. Cheers.

4 votes

Notez que cet algorithme produira quelques paires de couleurs qui sont TRÈS similaires (particulièrement dans des régions très sombres ou claires, de faible saturation). Il fait un bon travail pour commencer dans des régions de haute saturation et de luminosité, mais rate beaucoup de couleurs subtiles qui restent visuellement distinctes.

99voto

Tatarize Points 490

Pour mettre en œuvre une variation de liste où par vos couleurs vont, 255 ensuite utiliser toutes les possibilités de cette place, puis ajouter 0 et tous les modèles RVB avec ces deux valeurs. Puis ajouter 128 et toutes les combinaisons RVB avec ceux-ci. 64. Ensuite, 192. Etc.

En Java,

public Color getColor(int i) {
    return new Color(getRGB(i));
}

public int getRGB(int index) {
    int[] p = getPattern(index);
    return getElement(p[0]) << 16 | getElement(p[1]) << 8 | getElement(p[2]);
}

public int getElement(int index) {
    int value = index - 1;
    int v = 0;
    for (int i = 0; i < 8; i++) {
        v = v | (value & 1);
        v <<= 1;
        value >>= 1;
    }
    v >>= 1;
    return v & 0xFF;
}

public int[] getPattern(int index) {
    int n = (int)Math.cbrt(index);
    index -= (n*n*n);
    int[] p = new int[3];
    Arrays.fill(p,n);
    if (index == 0) {
        return p;
    }
    index--;
    int v = index % 3;
    index = index / 3;
    if (index < n) {
        p[v] = index % n;
        return p;
    }
    index -= n;
    p[v      ] = index / n;
    p[++v % 3] = index % n;
    return p;
}

Cela permettra de produire des modèles de ce type à l'infini (2^24) dans le futur. Cependant, après une centaine de spots vous n'aurez probablement pas voir beaucoup de différence entre une couleur avec 0 ou 32 dans le bleu.

Vous pourriez être mieux de normaliser ce dans un autre espace colorimétrique. Espace couleur LAB par exemple, le L,A,B les valeurs normalisées et les convertis. Donc, la distinction de la couleur est poussé par quelque chose de plus proche de l'œil humain.

getElement() annule la endian de 8 bits, et commence à compter à partir de -1 au lieu de 0 (masquage à 255). Donc, il va 255,0,127,192,64,... comme le nombre croît, il se déplace de moins en moins de bits significatifs, de subdiviser le nombre.

getPattern() détermine l'élément le plus significatif dans le modèle devrait être (c'est la racine cubique). Puis continue à briser les 3N2+3N+1-différents modèles qui impliquent que la plupart élément significatif.

Cet algorithme se produire (d'abord 128 valeurs):

#FFFFFF 
#000000 
#FF0000 
#00FF00 
#0000FF 
#FFFF00 
#00FFFF 
#FF00FF 
#808080 
#FF8080 
#80FF80 
#8080FF 
#008080 
#800080 
#808000 
#FFFF80 
#80FFFF 
#FF80FF 
#FF0080 
#80FF00 
#0080FF 
#00FF80 
#8000FF 
#FF8000 
#000080 
#800000 
#008000 
#404040 
#FF4040 
#40FF40 
#4040FF 
#004040 
#400040 
#404000 
#804040 
#408040 
#404080 
#FFFF40 
#40FFFF 
#FF40FF 
#FF0040 
#40FF00 
#0040FF 
#FF8040 
#40FF80 
#8040FF 
#00FF40 
#4000FF 
#FF4000 
#000040 
#400000 
#004000 
#008040 
#400080 
#804000 
#80FF40 
#4080FF 
#FF4080 
#800040 
#408000 
#004080 
#808040 
#408080 
#804080 
#C0C0C0 
#FFC0C0 
#C0FFC0 
#C0C0FF 
#00C0C0 
#C000C0 
#C0C000 
#80C0C0 
#C080C0 
#C0C080 
#40C0C0 
#C040C0 
#C0C040 
#FFFFC0 
#C0FFFF 
#FFC0FF 
#FF00C0 
#C0FF00 
#00C0FF 
#FF80C0 
#C0FF80 
#80C0FF 
#FF40C0 
#C0FF40 
#40C0FF 
#00FFC0 
#C000FF 
#FFC000 
#0000C0 
#C00000 
#00C000 
#0080C0 
#C00080 
#80C000 
#0040C0 
#C00040 
#40C000 
#80FFC0 
#C080FF 
#FFC080 
#8000C0 
#C08000 
#00C080 
#8080C0 
#C08080 
#80C080 
#8040C0 
#C08040 
#40C080 
#40FFC0 
#C040FF 
#FFC040 
#4000C0 
#C04000 
#00C040 
#4080C0 
#C04080 
#80C040 
#4040C0 
#C04040 
#40C040 
#202020 
#FF2020 
#20FF20 

Lire de gauche à droite, de haut en bas. 729 couleurs (93). Donc, tous les modèles jusqu'à n = 9. Vous remarquerez que la vitesse à laquelle ils commencent à se heurter. Il ya seulement tellement de WRGBCYMK variations. Et cette solution, alors que intelligent fondamentalement seulement les différentes nuances de couleurs primaires.

Color Grid, 729 16x16

Beaucoup de confrontations est en raison de vert et de façon similaire, la plupart des greens look pour la plupart des gens. La demande que chaque être au maximum de différent au début plutôt que suffisamment différents pour ne pas être de la même couleur. De base et des défauts dans l'idée qui en résulte dans les couleurs primaires, les schémas et les mêmes teintes.


À l'aide de CIELab2000 Couleur de l'Espace et de la Distance de la Routine, de sélectionner au hasard et essayer de 10k de couleurs différentes et de trouver le maximum distance minimum-distance entre les couleurs précédentes (à peu près la définition de la demande) permet d'éviter les collisions de plus que la solution ci-dessus:

Max Color Distance

Ce qui pourrait être appelé une liste statique de la Manière la plus Facile. Il a fallu une heure et demi pour générer 729 entrées:

#9BC4E5
#310106
#04640D
#FEFB0A
#FB5514
#E115C0
#00587F
#0BC582
#FEB8C8
#9E8317
#01190F
#847D81
#58018B
#B70639
#703B01
#F7F1DF
#118B8A
#4AFEFA
#FCB164
#796EE6
#000D2C
#53495F
#F95475
#61FC03
#5D9608
#DE98FD
#98A088
#4F584E
#248AD0
#5C5300
#9F6551
#BCFEC6
#932C70
#2B1B04
#B5AFC4
#D4C67A
#AE7AA1
#C2A393
#0232FD
#6A3A35
#BA6801
#168E5C
#16C0D0
#C62100
#014347
#233809
#42083B
#82785D
#023087
#B7DAD2
#196956
#8C41BB
#ECEDFE
#2B2D32
#94C661
#F8907D
#895E6B
#788E95
#FB6AB8
#576094
#DB1474
#8489AE
#860E04
#FBC206
#6EAB9B
#F2CDFE
#645341
#760035
#647A41
#496E76
#E3F894
#F9D7CD
#876128
#A1A711
#01FB92
#FD0F31
#BE8485
#C660FB
#120104
#D48958
#05AEE8
#C3C1BE
#9F98F8
#1167D9
#D19012
#B7D802
#826392
#5E7A6A
#B29869
#1D0051
#8BE7FC
#76E0C1
#BACFA7
#11BA09
#462C36
#65407D
#491803
#F5D2A8
#03422C
#72A46E
#128EAC
#47545E
#B95C69
#A14D12
#C4C8FA
#372A55
#3F3610
#D3A2C6
#719FFA
#0D841A
#4C5B32
#9DB3B7
#B14F8F
#747103
#9F816D
#D26A5B
#8B934B
#F98500
#002935
#D7F3FE
#FCB899
#1C0720
#6B5F61
#F98A9D
#9B72C2
#A6919D
#2C3729
#D7C70B
#9F9992
#EFFBD0
#FDE2F1
#923A52
#5140A7
#BC14FD
#6D706C
#0007C4
#C6A62F
#000C14
#904431
#600013
#1C1B08
#693955
#5E7C99
#6C6E82
#D0AFB3
#493B36
#AC93CE
#C4BA9C
#09C4B8
#69A5B8
#374869
#F868ED
#E70850
#C04841
#C36333
#700366
#8A7A93
#52351D
#B503A2
#D17190
#A0F086
#7B41FC
#0EA64F
#017499
#08A882
#7300CD
#A9B074
#4E6301
#AB7E41
#547FF4
#134DAC
#FDEC87
#056164
#FE12A0
#C264BA
#939DAD
#0BCDFA
#277442
#1BDE4A
#826958
#977678
#BAFCE8
#7D8475
#8CCF95
#726638
#FEA8EB
#EAFEF0
#6B9279
#C2FE4B
#304041
#1EA6A7
#022403
#062A47
#054B17
#F4C673
#02FEC7
#9DBAA8
#775551
#835536
#565BCC
#80D7D2
#7AD607
#696F54
#87089A
#664B19
#242235
#7DB00D
#BFC7D6
#D5A97E
#433F31
#311A18
#FDB2AB
#D586C9
#7A5FB1
#32544A
#EFE3AF
#859D96
#2B8570
#8B282D
#E16A07
#4B0125
#021083
#114558
#F707F9
#C78571
#7FB9BC
#FC7F4B
#8D4A92
#6B3119
#884F74
#994E4F
#9DA9D3
#867B40
#CED5C4
#1CA2FE
#D9C5B4
#FEAA00
#507B01
#A7D0DB
#53858D
#588F4A
#FBEEEC
#FC93C1
#D7CCD4
#3E4A02
#C8B1E2
#7A8B62
#9A5AE2
#896C04
#B1121C
#402D7D
#858701
#D498A6
#B484EF
#5C474C
#067881
#C0F9FC
#726075
#8D3101
#6C93B2
#A26B3F
#AA6582
#4F4C4F
#5A563D
#E83005
#32492D
#FC7272
#B9C457
#552A5B
#B50464
#616E79
#DCE2E4
#CF8028
#0AE2F0
#4F1E24
#FD5E46
#4B694E
#C5DEFC
#5DC262
#022D26
#7776B8
#FD9F66
#B049B8
#988F73
#BE385A
#2B2126
#54805A
#141B55
#67C09B
#456989
#DDC1D9
#166175
#C1E29C
#A397B5
#2E2922
#ABDBBE
#B4A6A8
#A06B07
#A99949
#0A0618
#B14E2E
#60557D
#D4A556
#82A752
#4A005B
#3C404F
#6E6657
#7E8BD5
#1275B8
#D79E92
#230735
#661849
#7A8391
#FE0F7B
#B0B6A9
#629591
#D05591
#97B68A
#97939A
#035E38
#53E19E
#DFD7F9
#02436C
#525A72
#059A0E
#3E736C
#AC8E87
#D10C92
#B9906E
#66BDFD
#C0ABFD
#0734BC
#341224
#8AAAC1
#0E0B03
#414522
#6A2F3E
#2D9A8A
#4568FD
#FDE6D2
#FEE007
#9A003C
#AC8190
#DCDD58
#B7903D
#1F2927
#9B02E6
#827A71
#878B8A
#8F724F
#AC4B70
#37233B
#385559
#F347C7
#9DB4FE
#D57179
#DE505A
#37F7DD
#503500
#1C2401
#DD0323
#00A4BA
#955602
#FA5B94
#AA766C
#B8E067
#6A807E
#4D2E27
#73BED7
#D7BC8A
#614539
#526861
#716D96
#829A17
#210109
#436C2D
#784955
#987BAB
#8F0152
#0452FA
#B67757
#A1659F
#D4F8D8
#48416F
#DEBAAF
#A5A9AA
#8C6B83
#403740
#70872B
#D9744D
#151E2C
#5C5E5E
#B47C02
#F4CBD0
#E49D7D
#DD9954
#B0A18B
#2B5308
#EDFD64
#9D72FC
#2A3351
#68496C
#C94801
#EED05E
#826F6D
#E0D6BB
#5B6DB4
#662F98
#0C97CA
#C1CA89
#755A03
#DFA619
#CD70A8
#BBC9C7
#F6BCE3
#A16462
#01D0AA
#87C6B3
#E7B2FA
#D85379
#643AD5
#D18AAE
#13FD5E
#B3E3FD
#C977DB
#C1A7BB
#9286CB
#A19B6A
#8FFED7
#6B1F17
#DF503A
#10DDD7
#9A8457
#60672F
#7D327D
#DD8782
#59AC42
#82FDB8
#FC8AE7
#909F6F
#B691AE
#B811CD
#BCB24E
#CB4BD9
#2B2304
#AA9501
#5D5096
#403221
#F9FAB4
#3990FC
#70DE7F
#95857F
#84A385
#50996F
#797B53
#7B6142
#81D5FE
#9CC428
#0B0438
#3E2005
#4B7C91
#523854
#005EA9
#F0C7AD
#ACB799
#FAC08E
#502239
#BFAB6A
#2B3C48
#0EB5D8
#8A5647
#49AF74
#067AE9
#F19509
#554628
#4426A4
#7352C9
#3F4287
#8B655E
#B480BF
#9BA74C
#5F514C
#CC9BDC
#BA7942
#1C4138
#3C3C3A
#29B09C
#02923F
#701D2B
#36577C
#3F00EA
#3D959E
#440601
#8AEFF3
#6D442A
#BEB1A8
#A11C02
#8383FE
#A73839
#DBDE8A
#0283B3
#888597
#32592E
#F5FDFA
#01191B
#AC707A
#B6BD03
#027B59
#7B4F08
#957737
#83727D
#035543
#6F7E64
#C39999
#52847A
#925AAC
#77CEDA
#516369
#E0D7D0
#FCDD97
#555424
#96E6B6
#85BB74
#5E2074
#BD5E48
#9BEE53
#1A351E
#3148CD
#71575F
#69A6D0
#391A62
#E79EA0
#1C0F03
#1B1636
#D20C39
#765396
#7402FE
#447F3E
#CFD0A8
#3A2600
#685AFC
#A4B3C6
#534302
#9AA097
#FD5154
#9B0085
#403956
#80A1A7
#6E7A9A
#605E6A
#86F0E2
#5A2B01
#7E3D43
#ED823B
#32331B
#424837
#40755E
#524F48
#B75807
#B40080
#5B8CA1
#FDCFE5
#CCFEAC
#755847
#CAB296
#C0D6E3
#2D7100
#D5E4DE
#362823
#69C63C
#AC3801
#163132
#4750A6
#61B8B2
#FCC4B5
#DEBA2E
#FE0449
#737930
#8470AB
#687D87
#D7B760
#6AAB86
#8398B8
#B7B6BF
#92C4A1
#B6084F
#853B5E
#D0BCBA
#92826D
#C6DDC6
#BE5F5A
#280021
#435743
#874514
#63675A
#E97963
#8F9C9E
#985262
#909081
#023508
#DDADBF
#D78493
#363900
#5B0120
#603C47
#C3955D
#AC61CB
#FD7BA7
#716C74
#8D895B
#071001
#82B4F2
#B6BBD8
#71887A
#8B9FE3
#997158
#65A6AB
#2E3067
#321301
#FEECCB
#3B5E72
#C8FE85
#A1DCDF
#CB49A6
#B1C5E4
#3E5EB0
#88AEA7
#04504C
#975232
#6786B9
#068797
#9A98C4
#A1C3C2
#1C3967
#DBEA07
#789658
#E7E7C6
#A6C886
#957F89
#752E62
#171518
#A75648
#01D26F
#0F535D
#047E76
#C54754
#5D6E88
#AB9483
#803B99
#FA9C48
#4A8A22
#654A5C
#965F86
#9D0CBB
#A0E8A0
#D3DBFA
#FD908F
#AEAB85
#A13B89
#F1B350
#066898
#948A42
#C8BEDE
#19252C
#7046AA
#E1EEFC
#3E6557
#CD3F26
#2B1925
#DDAD94
#C0B109
#37DFFE
#039676
#907468
#9E86A5
#3A1B49
#BEE5B7
#C29501
#9E3645
#DC580A
#645631
#444B4B
#FD1A63
#DDE5AE
#887800
#36006F
#3A6260
#784637
#FEA0B7
#A3E0D2
#6D6316
#5F7172
#B99EC7
#777A7E
#E0FEFD
#E16DC5
#01344B
#F8F8FC
#9F9FB5
#182617
#FE3D21
#7D0017
#822F21
#EFD9DC
#6E68C4
#35473E
#007523
#767667
#A6825D
#83DC5F
#227285
#A95E34
#526172
#979730
#756F6D
#716259
#E8B2B5
#B6C9BB
#9078DA
#4F326E
#B2387B
#888C6F
#314B5F
#E5B678
#38A3C6
#586148
#5C515B
#CDCCE1
#C8977F

Utilisant la force brute pour (tester tous les 16,777,216 couleurs RVB par CIELab Delta2000 / de Départ avec le noir) produit une série. Qui commence à se heurter à de 26 ans, mais pourrait le faire à 30 ou 40 avec contrôle visuel et manuel de tomber (ce qui ne peut être fait avec un ordinateur). Ce faisant, le maximum absolu on peut par programme ne fait que quelques dizaines de couleurs distinctes. Un discret liste est votre meilleur pari. Vous obtiendrez plus de couleurs discrètes avec une liste que vous le feriez par programmation. Le plus simple est la meilleure solution, commencez à mélanger et assortir avec d'autres façons de modifier vos données que la couleur.

Maximally Different

#000000
#00FF00
#0000FF
#FF0000
#01FFFE
#FFA6FE
#FFDB66
#006401
#010067
#95003A
#007DB5
#FF00F6
#FFEEE8
#774D00
#90FB92
#0076FF
#D5FF00
#FF937E
#6A826C
#FF029D
#FE8900
#7A4782
#7E2DD2
#85A900
#FF0056
#A42400
#00AE7E
#683D3B
#BDC6FF
#263400
#BDD393
#00B917
#9E008E
#001544
#C28C9F
#FF74A3
#01D0FF
#004754
#E56FFE
#788231
#0E4CA1
#91D0CB
#BE9970
#968AE8
#BB8800
#43002C
#DEFF74
#00FFC6
#FFE502
#620E00
#008F9C
#98FF52
#7544B1
#B500FF
#00FF78
#FF6E41
#005F39
#6B6882
#5FAD4E
#A75740
#A5FFD2
#FFB167
#009BFF
#E85EBE

11 votes

IMHO beaucoup mieux que la réponse acceptée. Et +1 pour les exemples visuels et les listes précalculées!

1 votes

J'ai également effectué une recherche exhaustive pour maximiser le CIEDE2000 entre la couleur ajoutée et les couleurs déjà présentes dans l'ensemble, avec le noir et le blanc comme couleurs prédéfinies. Comme vous, j'ai obtenu très tôt deux "tons de peau" : #ff9d25 (tendance vers l'orange) et #ffb46c (tendance vers le rose). Je trouve qu'ils se ressemblent beaucoup, donc peut-être que le CIEDE2000 n'est pas une mesure aussi efficace de la différence de couleur. Pour l'instant, il n'y a rien de mieux disponible. Il est tentant de commencer à faire mes propres expériences de différence à peine perceptible, peut-être d'abord avec une grille sRGB de 16x16x16...

0 votes

Je suis monté jusqu'à 1024 mais cela m'a pris plus d'un mois. Vous pouvez également exécuter ceci avec d'autres ensembles de couleurs, j'en ai une grande variété allant du spectre complet. Et vraiment CIEDE2000 est en fait le meilleur. Une des corrections dans dE2k concerne la couleur de la peau, elles nous paraissent plus différentes et ont plus d'importance pour de nombreuses fonctions. La dE standard les rend plus différentes qu'elles ne devraient l'être. L'abricot et le jaune terne semblent assez différents. godsnotwheregodsnot.blogspot.com/2012/09/…

28voto

Phrogz Points 112337

J'ai mis en ligne une page pour générer de manière procédurale des couleurs visuellement distinctes :
http://phrogz.net/css/distinct-colors.html

Contrairement aux autres réponses qui se concentrent sur les espaces RGB ou HSV (où il existe une relation non linéaire entre les valeurs des axes et les différences perceptuelles), ma page utilise l'algorithme standard de distance de couleur CMI(I:c) pour éviter que deux couleurs soient trop proches visuellement.

L'onglet final de la page vous permet de trier les valeurs de plusieurs manières, puis de les entrelacer (mélange ordonné) afin d'obtenir des couleurs très distinctes placées côte à côte.

Au moment où j'écris, cela fonctionne bien uniquement sur Chrome et Safari, avec un ajustement pour Firefox ; il utilise des curseurs d'entrée de plage HTML5 dans l'interface, que IE9 et Firefox ne prennent pas encore en charge nativement.

1 votes

C'est un excellent outil, merci de l'avoir créé. Je l'ai utilisé pour générer 145 couleurs distinctes et je suis très satisfait des résultats créés par ton outil de couleurs distinctes.

0 votes

L'idée semble bonne, mais je ne comprends pas comment fonctionne l'interface. Disons que je veux générer 64 couleurs éloignées dans l'espace L_a_b, quel paramètre dois-je utiliser? Je n'arrive pas à obtenir plus de 50 couleurs.

1 votes

@wil Les paramètres par défaut sur la page Lab commencent avec 480 couleurs parmi lesquelles choisir. Lorsque vous allez à l'onglet Affiner, ajustez le seuil pour voir plus ou moins d'échantillons.

9voto

aib Points 18608

Je pense que l'espace HSV (ou HSL) a plus d'opportunités ici. Si cela ne vous dérange pas la conversion supplémentaire, il est assez facile de passer par toutes les couleurs en faisant simplement tourner la valeur de la teinte. Si ce n'est pas suffisant, vous pouvez changer les valeurs de Saturation/Valeur/Luminosité et refaire la rotation. Ou, vous pouvez toujours décaler les valeurs de teinte ou changer votre angle de "pas" et faire tourner plus de fois.

2 votes

Notez cependant que même en marchant uniformément à travers la teinte produit une séparation perceptuelle sub-optimale.

4voto

deancutlet Points 91

Il y a une faille dans les solutions RGB précédentes. Elles ne tirent pas parti de tout l'espace colorimétrique car elles utilisent une valeur de couleur et 0 pour les canaux :

#006600
#330000
#FF00FF

À la place, elles devraient utiliser toutes les valeurs de couleur possibles pour générer des couleurs mixtes qui peuvent avoir jusqu'à 3 valeurs différentes à travers les canaux de couleur :

#336600
#FF0066
#33FF66

En utilisant tout l'espace colorimétrique, vous pouvez générer plus de couleurs distinctes. Par exemple, si vous avez 4 valeurs par canal, alors 4*4*4=64 couleurs peuvent être générées. Avec l'autre schéma, seules 4*7+1=29 couleurs peuvent être générées.

Si vous voulez N couleurs, alors le nombre de valeurs par canal requis est: ceil(cube_root(N))

Avec cela, vous pouvez ensuite déterminer les valeurs possibles (plage de 0 à 255) (en python) :

max = 255
segs = int(num**(Decimal("1.0")/3))
step = int(max/segs)
p = [(i*step) for i in xrange(segs)]
values = [max]
values.extend(p)

Ensuite, vous pouvez itérer sur les couleurs RGB (ceci n'est pas recommandé) :

total = 0
for red in values:
  for green in values:
    for blue in values:
      if total <= N:
        print color(red, green, blue)
      total += 1

Les boucles imbriquées fonctionneront, mais ne sont pas recommandées car elles favoriseront le canal bleu et les couleurs résultantes n'auront pas assez de rouge (N sera très probablement inférieur au nombre de toutes les valeurs de couleur possibles).

Vous pouvez créer un meilleur algorithme pour les boucles où chaque canal est traité de manière égale et les valeurs de couleur plus distinctes sont privilégiées aux petites.

J'ai une solution, mais je ne voulais pas la poster car elle n'est pas la plus facile à comprendre ou efficace. Mais, vous pouvez consulter la solution si vous le souhaitez vraiment.

Voici un exemple de 64 couleurs générées : 64 couleurs

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X