# js-cookieでウェブサイトのダークモード表示設定をユーザーごとに保存しておく方法 URL: https://webrandum.net/cookie-js-darkmode/ 公開日: 2020-07-03 更新日: 2020-07-01 カテゴリー: コーディング タグ: JavaScript, PHP 出典: Webrandum(著者: サイトウ マサカズ) 少し前にブログを[リニューアル](https://webrandum.net/renewal-3/)して、そのときに一緒にダークモードの対応を行いました。 [![](https://www.google.com/s2/favicons?domain=webrandum.net)Webrandum![](//webrandum.net/mskz/wp-content/uploads/2020/04/eyecatch-10.jpg)ブログをリニューアルして、ダークモードに対応しました(2020年版)https://webrandum.net/renewal-32020年3月中頃から4月15日まで、主にブログのリニューアルを行っていたため、新規の記事の投稿は控えていました。それがようやく落ち着いてきたので、新規記事の執筆を再開します。日々新しい記事を書くことを考えていると、なかなか大規模なリニューアルや機能追加が難しいので、年に1回はこうした期間を設けるのもよさそうです。今回のリニューアルの経緯今回リニューアルを思い立ったきっかけは「今後のブログ運用の目的って何だろう?」をふと考えたことです。もともとこのブログは、管理人であるサイトウマサカズ(@31mskz10)が...](https://webrandum.net/renewal-3) ただ、人によっては「システム環境設定に依存しないで、常にダークモードの方がいい!」人や「逆にライトモードの方が見やすい!」という人もいると思い、個別に設定できるように変更してみました。 今後デザインは変えていく予定ですが、メニュー右上の「表示設定」をクリックすると設定モーダルが表示されます。 ![ダークモード設定変更のモーダル](https://webrandum.net/mskz/wp-content/uploads/2020/07/image_1.png) このラジオボタンを選択すると、それぞれのモードに固定されます。 - ライト - ダーク - ナイト - システム設定に合わせる(デフォルト) ちなみに「ライトモード」と「ダークモード」以外に「ナイトモード」という表示も追加していて、これは深夜暗い部屋でも見やすいように、色を全体的に暗くして画像の輝度も下がります。 今回はこれの実装方法についてまとめておきます。 ダークモード自体の実装方法は有名ですが、それを保存する方法についてはあまり見かけなかったので、ぜひ参考にしてください。 ## ダークモードの対応 そもそもまずはダークモードの対応が必要です。 CSS変数を利用して、ライトモード(通常)時と`@media (prefers-color-scheme: dark) {}`を使って、ダークモード時の色を設定します。 ``` :root{ --c-primary: #0076b5; --c-secondary: #17C2C7; --c-background-base: #F7F9FB; --c-background-primary: #FFF; --c-background-secondary: #F0F2F5; --c-text-base: #555; --c-text-lighter: #676767; --c-text-link: #0076b5; } @media (prefers-color-scheme: dark) { :root{ --c-primary: #EBCB1A; --c-secondary: #FF178D; --c-background-base: #2B2B2B; --c-background-primary: #313131; --c-background-secondary: #242424; --c-text-base: #EAEAEA; --c-text-lighter: #B7B7B7; --c-text-link: #0076b5; } } ``` これでライトモードとダークモードの指定はできましたが、このままだとメディアクエリでのみの設定になるので、`body`に特定classが付いたときにも変数が変わるようにしておきます。 ``` body.dark-mode{ --c-primary: #0076b5; --c-secondary: #17C2C7; --c-background-base: #F7F9FB; --c-background-primary: #FFF; --c-background-secondary: #F0F2F5; --c-text-base: #555; --c-text-lighter: #676767; --c-text-link: #0076b5; } ``` ## js-cookieの導入 [![](https://www.google.com/s2/favicons?domain=github.com)GitHub![](//webrandum.net/mskz/wp-content/uploads/pz-linkcard/cache/698e2b2bfc63fe7b0166cb2af717cf0790a1ae8f40344e70f35c64fd094acb45.webp)js-cookie/js-cookiehttps://github.com/js-cookie/js-cookieA simple, lightweight JavaScript API for handling browser cookies - js-cookie/js-cookie](https://github.com/js-cookie/js-cookie) js-cookieを使うと、JavaScriptでCookieの登録や取得が簡単にできます。こちらから読み込みます。 ### js-cookieでCookieの登録 Cookieを登録したい場合は`Cookies.set('Cookie名', 値);`で登録できます。 ``` Cookies.set('darkmode', darkModeVal); ``` Cookieを取得したい場合は`Cookies.get('Cookie名');`で取得できます。 ``` Cookies.get('darkmode'); ``` あとはラジオボタンでどこがチェックされているのかを判定するのと、判定に応じて`body`にclassを追加するだけです。 ``` let getDarkModeVal = function () { let radios = document.getElementsByName('darkmode'); for (let i = 0; i < radios.length; i++) { if (radios[i].checked) { return radios[i].id; } } } let setDarkModeVal = () => { let darkModeVal = getDarkModeVal(); switch (darkModeVal) { case 'light': document.body.classList.add("light-theme"); document.body.classList.remove("dark-theme"); document.body.classList.remove("night-theme"); break; case 'dark': document.body.classList.remove("light-theme"); document.body.classList.add("dark-theme"); document.body.classList.remove("night-theme"); break; case 'night': document.body.classList.remove("light-theme"); document.body.classList.remove("dark-theme"); document.body.classList.add("night-theme"); break; default: document.body.classList.remove("light-theme"); document.body.classList.remove("dark-theme"); document.body.classList.remove("night-theme"); break; } Cookies.set('darkmode', darkModeVal); } const darkMode = Cookies.get('darkmode'); if (darkMode) { document.getElementById(darkMode).checked = true; } else { document.getElementById('system').checked = true; } // チェックした時の挙動 let radios = document.getElementsByName('darkmode'); for (let i = 0; i < radios.length; i++) { radios[i].addEventListener('change', () => { setDarkModeVal(); }); } ``` ### PHPでCookieに合わせてclassを追加する いまのままだと、ページが表示された後にJavaScriptが読み込まれてclassが付くまでの間はライトモードが表示されてしまいます。 一瞬ライトモードが表示されて、そのあとダークモードになったりするのはむしろ目がチカチカしてしまうので、Cookieが設定されてある場合はPHPで最初からclassを付けておくようにしましょう。 PHPでやることはCookieの取得のみで、`isset( $_COOKIE['Cookie名'] )`で取得ができるので、取得したあとは条件分岐でclassの中身を設定します。 ``` ``` これで、ダークモードのCookieが設定されてある場合は最初からダークモードのclassが付いた状態で表示されます。