ダークモードの実装
CSS, JavaScriptダークモード
Mac OS の Mojave(10.14 以降)には、ダークモード(Dark Mode)が搭載されている。
配色を暗めにして、ユーザーの目の負担を抑えたりする機能のこと。
従来の画面は、ライトモード(Light Mode)として区別される。
多くのネイティブアプリで対応が進んでいて、現在では一部の Web ページも対応している。
メディアクエリの 1 つで、ユーザーの操作などに応じて、CSS のスタイルを切り替えるもの。
ボタンでの実装
一部のページでは、トグル式、またはラジオボタンを用意して手動で切り替える。
また、localstorage に状態を保存するページもある。
How I added Dark Mode to my website
上記ページでは、.dark クラスの付け外しで対応している。
prefers-color-schemeでの実装
prefers-color-scheme
は、Media Queries Level 5
のメディアクエリ。
ユーザーがライトモード、ダークモードどちらの配色を指定しているのかを判定する。
モダンブラウザで使用できる。
値は、no-preference(設定なし) | light | dark
の 3 種類から指定できる。
CSS Variables と併せて、すでに一部のサイトに取り入れられている。
CSS
// ライトモードの時
@media (prefers-color-scheme: light) {
:root {
--main-bg-color: #fff;
--main-text-color: #000;
}
}
// ダークモードの時
@media (prefers-color-scheme: dark) {
:root {
--main-bg-color: #1e1e1e;
--main-text-color: #fff;
}
}
body {
background-color: var(--main-bg-color);
color: var(--main-text-color);
}
草案
"Can I use..." より対応バージョン
近づくダークモード対応の足音 | フロントエンド Blog | ミツエーリンクス
prefers-color-scheme を用いた Dark Mode 対応と User Preference Media Features | blog.jxck.io
matchmediaで分岐させる
prefers-color-scheme はメディアクエリなので、matchMedia
を用いた対応が可能。
返ってきた MediaQueryList オブジェクトから matches
で判定する。
JavaScript
const isDark = window.matchMedia('(prefers-color-scheme: dark)').matches;
また、Listener を設定できる。
JavaScript
window
.matchMedia('(prefers-color-scheme: dark)')
.addListener(({ matches }) => {
if (matches) {
// ダークモードの時の処理
}
});
ライトモードとダークモードでコンテンツを出し分ける、というのをやった。
あくまでユーザー支援の位置付けなので、演出として用いるのは問題だけど…。
(雲のイラストはこちらからお借りした: https://codepen.io/Mark_Bowley/pen/xEbuI)
対策
単に配色を置き換えるだけでなく、何箇所か対応が必要。
色
ダークモードの背景色には、#282c2f
や #1e1e1e
などの黒に近いグレーが搭載されることが多い。
#000
と文字 #fff
の組み合わせはコントラストが高く、あまり採用されない。
テキストサイトェ…。
文字や背景にピュアブラックを使ってはいけない理由 | UX MILK
(元記事: Why You Should Never Use Pure Black for Text or Backgrounds)
文字
背景色が変わると、文字の印象も異なる。
下記リンク先の Stuff & Nonsense は、配色を変えるだけでなく、文章の line-height
や word-spacing
も調整している。
Redesigning your product and website for dark mode — Stuff & Nonsense
画像
その実態は CSS いじりということで、画像へのフォローも必要になる。
特に白地の背景だと辛くなってしまうので、透過 png や、SVG を検討した方が良いかもしれない。
一応、picture 要素のメディアクエリで画像を出し分けることは可能。
HTML
<picture>
<source srcset="dark.jpg" media="(prefers-color-scheme: dark)">
<img src="light.jpg">
</picture>
box-shadow
CSS
@media (prefers-color-scheme: dark) {
* {
box-shadow: none !important;
}
}
あとは、SNS サイトなどのシェアアイコンで色を変えるのは、ライセンス違反の恐れがあるので確認が必須。