CSS color-mix()

Adam Argyle
Adam Argyle

La fonction CSS color-mix() vous permet de mélanger les couleurs, dans n'importe quel espace colorimétrique compatible, directement à partir de votre CSS.

Navigateurs pris en charge

  • 111
  • 111
  • 113
  • 16.2

Source

Avant color-mix(), pour assombrir, éclaircir ou désaturer une couleur, les développeurs utilisaient des préprocesseurs CSS ou calc() sur les canaux de couleur.

Avant avec SCSS
.color-mixing-with-sass {
  /* Sass: equally mix red with white */
  --red-white-mix: color.mix(red, white);
}

Sass a fait un excellent travail pour garder une longueur d'avance sur la spécification CSS de couleur. Toutefois, il n'y a pas eu de véritable moyen de mélanger les couleurs en CSS. Pour vous rapprocher, vous devez effectuer des calculs sur les valeurs de couleur partielles. Voici un exemple réduit de la façon dont le CSS peut simuler le mixage aujourd'hui:

Avant avec HSL
.color-mixing-with-vanilla-css-before {
  --lightness: 50%;
  --red: hsl(0 50% var(--lightness));

  /* add "white" to red
     by adding 25% to the lightness channel
  */
  --lightred: hsl(0 50% calc(var(--lightness) + 25%);
}

color-mix() permet de mélanger les couleurs au CSS. Les développeurs peuvent choisir l'espace colorimétrique et la prédominance de chaque couleur.

Après
.color-mixing-after {
  /* equally mix red with white */
  --red-white-mix: color-mix(in oklab, red, white);

  /* equally mix red with white in srgb */
  --red-white-mix-srgb: color-mix(in srgb, red, white);
}

C'est ce que nous voulons. Flexibilité, puissance et API complètes. Aimez.

Mélanger des couleurs en CSS

Le CSS existe dans un univers avec plusieurs espaces colorimétriques et gammes de couleurs multiples. De ce fait, il n'est pas facultatif de spécifier l'espace colorimétrique pour le mélange. De plus, différents espaces de couleur peuvent modifier considérablement les résultats d'un mixage. Par conséquent, connaître les effets d'un espace de couleur vous aidera à obtenir les résultats dont vous avez besoin.

Pour une introduction interactive, essayez cet outil color-mix() : - Explorez les effets de chaque espace de couleur. - Explorez les effets de l'interpolation des teintes lors du mélange dans un espace colorimétrique cylindrique (lch, oklch, hsl et hwb). - Modifiez les couleurs mélangées en cliquant sur l'une des deux cases de couleur supérieures. - Utilisez le curseur pour modifier le ratio de mélange. - Code CSS color-mix() généré disponible en bas de l'écran.

Mélanger les différents espaces de couleurs

L'espace colorimétrique par défaut pour le mélange (et les dégradés) est oklab. Les résultats sont cohérents. Vous pouvez également spécifier d'autres espaces de couleur pour adapter le mixage à vos besoins.

Prenons l'exemple de black et white. L'espace de couleur qu'ils se mélangent ne fera pas une grande différence, n'est-ce pas ? Impossible.

color-mix(in srgb, black, white);
color-mix(in srgb-linear, black, white);
color-mix(in lch, black, white);
color-mix(in oklch, black, white);
color-mix(in lab, black, white);
color-mix(in oklab, black, white);
color-mix(in xyz, black, white);
Sept espaces colorimétriques (srgb, linear-srgb, lch, oklch, lab, oklab, xyz) affichent chacun le résultat du mélange noir et blanc. Environ cinq nuances différentes sont affichées, ce qui démontre que chaque espace colorimétrique peut même se mélanger au gris différemment.
Essayer la version de démonstration

L'effet est considérable !

Prenons blue et white comme autre exemple. J'ai choisi cette option spécifiquement parce que c'est un cas où la forme d'un espace colorimétrique peut affecter les résultats. Dans ce cas, c'est que la plupart des espaces de couleur passent en violet lorsqu'ils passent du blanc au bleu. Cela montre également que oklab est un espace de couleurs si fiable pour le mélange, qu'il est le plus proche des attentes de la plupart des utilisateurs en mélangeant blanc et bleu (pas de violet).

color-mix(in srgb, blue, white);
color-mix(in srgb-linear, blue, white);
color-mix(in lch, blue, white);
color-mix(in oklch, blue, white);
color-mix(in lab, blue, white);
color-mix(in oklab, blue, white);
color-mix(in xyz, blue, white);
Sept espaces colorimétriques (srgb, linear-srgb, lch, oklch, lab, oklab, xyz) et en afficher chacun un résultat différent. Beaucoup sont roses ou violets, quelques-uns sont encore bleus.
Essayer la version de démonstration

Apprendre les effets d'un espace colorimétrique avec color-mix() est également une excellente connaissance pour créer des dégradés. La syntaxe Color 4 permet également aux dégradés de spécifier l'espace colorimétrique, un dégradé représentant le mélange sur une zone d'espace.

.black-to-white-gradient-in-each-space {
  --srgb: linear-gradient(to right in srgb, black, white);
  --srgb-linear: linear-gradient(to right in srgb-linear, black, white);
  --lab: linear-gradient(to right in lab, black, white);
  --oklab: linear-gradient(to right in oklab, black, white);
  --lch: linear-gradient(to right in lch, black, white);
  --oklch: linear-gradient(to right in oklch, black, white);
  --hsl: linear-gradient(to right in hsl, black, white);
  --hwb: linear-gradient(to right in hwb, black, white);
  --xyz: linear-gradient(to right in xyz, black, white);
  --xyz-d50: linear-gradient(to right in xyz-d50, black, white);
  --xzy-d65: linear-gradient(to right in xyz-d65, black, white);
}
Dégradés noirs à blancs dans différents espaces de couleurs.
Essayer la version de démonstration

Si vous vous demandez quel espace colorimétrique est « le meilleur », il n'y en a pas. C'est pourquoi il y a tant d'options ! De plus, de nouveaux espaces de couleur ne seront pas inventés (voir oklch et oklab), si l'un était "le meilleur". Chaque espace de couleur peut offrir un moment unique de brillance et de pertinence.

Par exemple, pour obtenir un mix dynamique, utilisez hsl ou hwb. Dans la démonstration suivante, deux couleurs vives (magenta et citron vert) sont mélangées. Les couleurs RH et HWB produisent tous deux un résultat éclatant, tandis que srgb et oklab produisent des couleurs insaturées.

Les résultats du mix sont décrits dans le paragraphe précédent.
Essayer la version de démonstration

Si vous recherchez de la cohérence et de la subtilité, utilisez oklab. Dans la démonstration suivante, qui mélange le bleu et le noir, les couleurs HSM et HWB produisent des couleurs très vives et des couleurs différentes, tandis que srgb et oklab produisent un bleu plus foncé.

Les résultats du mix sont décrits dans le paragraphe précédent.
Essayer la version de démonstration

Passez cinq minutes sur color-mix() Playground, testez différentes couleurs et espaces, et vous commencerez à vous faire une idée des avantages de chaque espace. Attendez-vous également à davantage de conseils sur les espaces de couleur à mesure que nous nous adaptons tous à leur potentiel dans nos interfaces utilisateur.

Ajuster la méthode d'interpolation de teinte

Si vous avez choisi de mélanger un espace colorimétrique cylindrique, essentiellement tout espace colorimétrique avec un canal de teinte h qui accepte un angle, vous pouvez spécifier si l'interpolation va shorter, longer, decreasing et increasing. Pour en savoir plus, consultez ce guide des couleurs HD.

Voici le même exemple de mélange bleu-blanc, mais cette fois, ce n'est que dans les espaces cylindriques avec des méthodes d'interpolation de teinte différentes.

Les résultats du mix sont décrits dans le paragraphe précédent.
Essayer la version de démonstration

Voici un autre codepen que j'ai créé pour aider à visualiser l'interpolation de la teinte, mais en particulier pour les gradients. Je pense que cela vous aidera à comprendre comment chaque espace de couleur produit son résultat de mélange lorsque l'interpolation de teinte est spécifiée, donnez-lui une étude !

Mélange avec différentes syntaxes de couleurs

Jusqu'à présent, nous avons principalement utilisé des styles CSS nommés de couleurs, comme blue et white. Le mélange de couleurs CSS est prêt à mélanger des couleurs provenant de deux espaces de couleurs différents. Il est également essentiel de spécifier l'espace colorimétrique pour le mélange, car il définit l'espace commun lorsque les deux couleurs ne sont pas dans le même espace.

color-mix(in oklch, hsl(200deg 50% 50%), color(display-p3 .5 0 .5));

Dans l'exemple précédent, hsl et display-p3 ont été convertis en oklch, puis mélangés. Plutôt cool et flexible.

Ajuster les ratios de mélange

Il est peu probable que, chaque fois que vous mélangez, vous ayez besoin d'une partie égale de chaque couleur, comme l'ont montré la plupart des exemples jusqu'à présent. Bonne nouvelle, il existe une syntaxe permettant d'articuler la quantité de chaque couleur à voir dans le mélange obtenu.

Pour commencer, voici quelques mix qui sont tous équivalents (et disponibles dans les spécifications):

.ratios-syntax-examples {
  /* omit the percentage for equal mixes */
  color: color-mix(in lch, purple, plum);
  color: color-mix(in lch, plum, purple);

  /* percentage can go on either side of the color */
  color: color-mix(in lch, purple 50%, plum 50%);
  color: color-mix(in lch, 50% purple, 50% plum);

  /* percentage on just one color? other color gets the remainder */
  color: color-mix(in lch, purple 50%, plum);
  color: color-mix(in lch, purple, plum 50%);

  /* percentages > 100% are equally clamped */
  color: color-mix(in lch, purple 80%, plum 80%);
  /* above mix is clamped to this */
  color: color-mix(in lch, purple 50%, plum 50%);
}

Je trouve que ces exemples mettent bien en lumière les cas limites. Le premier ensemble d'exemples montre que 50% n'est pas obligatoire, mais peut être spécifié de manière facultative. Le dernier exemple montre un cas intéressant lorsque les ratios dépassent 100% lorsqu'ils sont additionnés, et que leur total est également limité à 100%.

Notez également que si une seule couleur spécifie un rapport, l'autre est supposée être le reste à 100%. Voici quelques exemples supplémentaires pour illustrer ce comportement.

color-mix(in lch, purple 40%, plum) /* plum assigned 60% */
color-mix(in lch, purple, 60% plum) /* purple assigned 40% */
color-mix(in lch, purple 40%, plum 60%) /* no auto assignments */

Ces exemples illustrent deux règles : 1. Lorsque les ratios dépassent 100%, ils sont limités et répartis équitablement. 1. Lorsqu'un seul ratio est fourni, l'autre couleur est définie sur 100 moins ce ratio.

La dernière règle est un peu moins évidente : que se passe-t-il si des pourcentages sont fournis pour les deux couleurs et que leur somme totale n'est pas égale à 100%?

color-mix(in lch, purple 20%, plum 20%)

Cette combinaison d'un color-mix() se traduit par une transparence et une transparence 40%. Lorsque la somme des rapports n'est pas égale à 100%, le mixage obtenu n'est pas opaque. Aucune des couleurs ne sera complètement mélangée.

Imbrication de color-mix()

Comme tout CSS, l'imbrication est gérée correctement et comme prévu. Les fonctions internes seront résolues en premier et renvoient leurs valeurs au contexte parent.

color-mix(in lch, purple 40%, color-mix(plum, white))

N'hésitez pas à imbriquer autant d'éléments que nécessaire pour obtenir le résultat souhaité.

Créer un jeu de couleurs clair et sombre

Créons des jeux de couleurs avec color-mix().

Un jeu de couleurs de base

Dans le code CSS suivant, un thème clair et un thème sombre sont créés en fonction d'une couleur hexadécimale de la marque. Le thème clair crée deux couleurs de texte bleu foncé et une couleur de surface blanche très claire à l'arrière-plan. Ensuite, dans une requête multimédia de préférence sombre, de nouvelles couleurs sont attribuées aux propriétés personnalisées afin que l'arrière-plan soit sombre et que les couleurs du texte soient claires.

:root {
  /* a base brand color */
  --brand: #0af;

  /* very dark brand blue */
  --text1: color-mix(in oklab, var(--brand) 25%, black);
  --text2: color-mix(in oklab, var(--brand) 40%, black);

  /* very bright brand white */
  --surface1: color-mix(in oklab, var(--brand) 5%, white);
}

@media (prefers-color-scheme: dark) {
  :root {
    --text1: color-mix(in oklab, var(--brand) 15%, white);
    --text2: color-mix(in oklab, var(--brand) 40%, white);
    --surface1: color-mix(in oklab, var(--brand) 5%, black);
  }
}

Tout cela est accompli en mélangeant le blanc ou le noir dans une couleur de marque.

Jeu de couleurs intermédiaire

Vous pouvez aller plus loin en ajoutant d'autres thèmes que les thèmes clair et sombre. Dans la démonstration suivante, les modifications apportées au groupe d'options mettent à jour un attribut au niveau de la balise HTML [color-scheme="auto"], ce qui permet ensuite aux sélecteurs d'appliquer un thème de couleur de manière conditionnelle.

Cette démonstration intermédiaire présente également une technique de thématisation des couleurs dans laquelle toutes les couleurs de thème sont répertoriées dans :root. Cela les rend faciles à voir tous ensemble et à ajuster si nécessaire. Vous pourrez utiliser les variables telles qu'elles sont définies dans la feuille de style. Cela vous évite de parcourir la feuille de style à la recherche de manipulations de couleurs, car elles sont toutes contenues dans le bloc :root initial.

Cas d'utilisation plus intéressants

Ana Tudor propose une démonstration de qualité avec quelques cas d'utilisation à étudier:

Déboguer color-mix() avec les Outils de développement

Les outils pour les développeurs Chrome sont parfaitement compatibles avec color-mix(). Il reconnaît et met en surbrillance la syntaxe, crée un aperçu du mixage juste à côté du style dans le volet "Styles" et permet de choisir d'autres couleurs.

Les outils de développement se présentent comme suit:

Capture d'écran des outils pour les développeurs Chrome inspectant la syntaxe du mélange de couleurs

Bon mix !