CSS color-mix()

Adam Argyle
Adam Argyle

CSS の color-mix() 関数を使用すると、サポートされている任意の色空間で、CSS から直接色を混ぜることができます。

対応ブラウザ

  • Chrome: 111.
  • Edge: 111.
  • Firefox: 113。
  • Safari: 16.2。

ソース

color-mix() より前は、色を暗くしたり、明るくしたり、彩度を下げたりするために、デベロッパーは CSS プリプロセッサまたは色チャネルの calc() を使用していました。

SCSS を使用した前
.color-mixing-with-sass {
  /* Sass: equally mix red with white */
  --red-white-mix: color.mix(red, white);
}

Sass は、カラーの CSS 仕様を先取りして優れた成果を上げています。ただし、CSS で色を混ぜる方法はありませんでした。近づけるには、部分的な色値の計算を行う必要があります。以下は、CSS でミキシングをシミュレートする方法の簡略化した例です。

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() により、CSS で色を混ぜ合わせることができます。デベロッパーは、混合するカラースペースと、混合における各色の優先度を選択できます。

変更後
.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);
}

これらを兼ね備えた人材を、Google は求めています。柔軟性、パワー、フル機能を備えた API。Love it.

CSS で色を混ぜる

CSS は複数の色空間と色域の世界に存在するため、混合する色空間を指定することは必須です。さらに、色空間が異なると、ミックスの結果が大幅に変わる可能性があります。そのため、色空間の効果を理解しておくと、必要な結果を得やすくなります。

インタラクティブな紹介については、こちらの color-mix() ツールをお試しください。 - 各カラースペースの効果を確認できます。 - 円筒形のカラー空間(lchoklchhslhwb)で混色する際の色相補間の効果を確認します。 - 上部の 2 つのカラーボックスのいずれかをクリックして、混色する色を変更します。- スライダーを使用して混合比率を変更します。- 生成された color-mix() CSS コードが下部に表示されます。

さまざまな色空間での混色

混合(およびグラデーション)のデフォルトの色空間は oklab です。一貫した結果が得られます。別のカラースペースを指定して、必要に応じてミックスを調整することもできます。

たとえば、blackwhite の場合、混ぜる色空間が違っても、それほど大きな違いは出ないはずです。これは間違いです。

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);
7 つの色空間(srgb、linear-srgb、lch、oklch、lab、oklab、xyz)で、白と黒を混ぜた結果がそれぞれ示されます。約 5 種類の色合いが表示され、各色空間でグレーに混ざる色が異なることが示されます。
デモを試す

大きな影響があります。

別の例として、bluewhite について考えてみましょう。色空間の形状が結果に影響する可能性がある場合であるため、この例を選びました。この場合、ほとんどの色空間は白から青に移動する際に紫色になります。また、oklab が混色に信頼できる色空間であることも示しています。白と青を混ぜた場合、ほとんどの人が期待する色(紫色ではない)に最も近い色空間です。

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);
7 つの色空間(srgb、linear-srgb、lch、oklch、lab、oklab、xyz)がそれぞれ異なる結果を示しています。多くの場合、ピンクや紫色で、実際に青色のままであるものはほとんどありません。
デモを試す

color-mix() で色空間の効果を学ぶことは、グラデーションを作成する際にも役立ちます。カラー 4 構文では、グラデーションにカラースペースを指定することもできます。グラデーションは、空間の領域にわたる混合を示します。

.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);
}
異なる色空間での黒から白へのグラデーション。
デモを試す

どの色空間が「最適」なのかと疑問に思うかもしれませんが、最適な色空間はありません。そのため、さまざまなオプションが用意されています。また、新しい色空間が開発されることもありません(oklchoklab を参照)。各カラースペースには、輝く独自の瞬間があり、適切な選択肢になる場合があります。

たとえば、鮮やかな混合結果が必要な場合は、hsl または hwb を使用します。次のデモでは、2 つの鮮やかな色(マゼンタとライム)を混ぜ合わせています。hsl と hwb はどちらも鮮やかな結果を生成しますが、srgb と oklab は彩度の低い色を生成します。

前段落で説明したミックス結果。
デモを試す

一貫性と繊細さを重視する場合は、oklab を使用します。次のデモでは、青と黒を混ぜ合わせています。hsl と hwb では、鮮やかすぎる色と色相がシフトした色が生成されますが、srgb と oklab では、より濃い青が生成されます。

前段落で説明したミックス結果。
デモを試す

color-mix() プレイグラウンドで 5 分ほど過ごして、さまざまな色とスペースを試すと、各スペースのメリットを把握できるようになります。また、ユーザー インターフェースでの可能性に慣れていくにつれて、カラースペースに関するガイダンスも増えていく予定です。

色相補間方法の調整

円筒形のカラースペース(角度を受け入れる h 色相チャネルを持つ任意のカラースペース)で混合する場合は、補間が shorterlongerdecreasingincreasing のいずれになるかを指定できます。詳しくは、HD カラーガイドをご覧ください。

同じ青から白への混合の例を示します。ただし、今回は、色相補間方法が異なる円筒空間のみです。

前段落で説明したミックス結果。
デモを試す

色相補間の可視化に役立つ別の Codepen を作成しました。これは特にグラデーション用です。色相補間が指定された場合に、各カラースペースがどのように混合結果を生成するかを理解するのに役立つと思います。ぜひご確認ください。

さまざまな色の構文を使用した混色

ここまでは、bluewhite などの CSS の名前付きの色を主に使用してきました。CSS の色の混合では、2 つの異なる色空間の色を混合できます。これは、2 つの色が同じ空間にない場合に共通の空間を設定することから、混合の色空間を指定することが重要であるもう 1 つの理由です。

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

上の例では、hsldisplay-p3oklch に変換されてから混合されます。かなりクールで柔軟です。

混合比の調整

これまでのほとんどの例で示されているように、混ぜるたびに各色を同量にすることはあまりありません。幸い、結果のミックスに各色をどの程度表示するかを指定するための構文があります。

このトピックの始めに、すべて同等の(仕様から)ミックスのサンプルを示します。

.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%);
}

これらの例は、エッジケースを明確に示しています。最初の例は、50% は必須ではないが、必要に応じて指定できることを示しています。最後の例は、比率を合計したときに 100% を超える場合に、合計が 100% になるように均等にクランプされるという興味深いケースを示しています。

また、1 色のみに比率を指定した場合、残りの色は 100% と見なされます。以下に、この動作を示す例をいくつか示します。

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 */

次の例は、2 つのルールを示しています。比率が 100% を超えると、その比率はクランプされ、均等に分配されます。1. 比率を 1 つだけ指定した場合、もう一方の色は、その比率を 100 から引いた値に設定されます。

最後のルールは少しわかりにくいかもしれません。両方の色に割合を指定して、合計が 100% にならない場合はどうなりますか?

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

この color-mix() の組み合わせにより、透明性、40% 透明性が得られます。比率の合計が 100% に満たない場合、結果の混合は不透明になりません。どちらの色も完全に混ざり合うことはありません。

ネスト color-mix()

他の CSS と同様に、ネストも期待どおりに適切に処理されます。内部関数は最初に解決され、その値が親コンテキストに返されます。

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

目的の結果を得るために、必要なだけネストしてください。

ライトとダークのカラーパターンを作成する

color-mix() を使用して配色を作成しましょう。

基本的なカラーパターン

次の CSS では、ブランドの 16 進数カラーに基づいてライトモードとダークモードが作成されています。ライトモードでは、2 つの濃い青色のテキスト色と非常に明るい白色の背景サーフェス色が作成されます。次に、ダークモードの設定のメディアクエリで、カスタム プロパティに新しい色が割り当てられ、背景が暗く、テキストの色が明るくなります。

: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);
  }
}

これらはすべて、ブランドカラーに白または黒を混ぜることで実現できます。

中級のカラーパターン

さらに一歩進めて、ライトモードとダークモード以外のテーマを追加することもできます。次のデモでは、ラジオ グループの変更によって HTML タグ [color-scheme="auto"] の属性が更新され、セレクタがカラーテーマを条件付きで適用できるようになります。

この中級者向けデモでは、すべてのテーマカラーが :root にリストされるカラーテーマ設定手法も示しています。これにより、すべてをまとめて確認し、必要に応じて調整できます。スタイルシートの後半で、定義した変数を使用できます。色の操作はすべて最初の :root ブロックに含まれているため、スタイルシートを探して色を操作する必要がなくなります。

その他の興味深いユースケース

Ana Tudor による、学習用のユースケースをいくつか含む優れたデモがあります。

DevTools を使用した color-mix() のデバッグ

Chrome DevTools は color-mix() を十分にサポートしています。構文を認識してハイライト表示し、[スタイル] ペインでスタイルのすぐ横に混合のプレビューを作成し、代替の色を選択できるようにします。

DevTools では次のようになります。

色の混合構文を検査している Chrome DevTools のスクリーンショット。

楽しいミキシングを!