【Vue.js】ダークモード切り替えの実装|ユーザーのテーマに合わせた表示対応

【Vue.js】ダークモード切り替えの実装|ユーザーのテーマに合わせた表示対応 Vue.js

最近のWebアプリでは、ユーザーが好みに応じて「ライトモード」「ダークモード」を切り替えられることが標準的になりつつあります。Vue.jsを使えば、簡単にダークモード対応を実装できます。本記事では、ユーザーのOSテーマ設定を自動で検出する方法と、手動での切り替えボタンを設置する方法、さらにその設定をローカルストレージに保存する仕組みまで紹介します。

ダークモードの実装方針

基本的な実装方針は以下の通りです:

  1. prefers-color-scheme でOSのテーマ設定を検出
  2. 手動切り替え用のボタンを設置
  3. 選択状態をlocalStorageに保存して再読み込み時に反映

CSSでダークテーマを定義する

まずはCSSレベルでライト・ダークの切り替えに対応させます。


body.light {
  background-color: #ffffff;
  color: #000000;
}

body.dark {
  background-color: #1e1e1e;
  color: #ffffff;
}

アプリ起動時に該当クラスをbodyに付与することで、テーマが切り替わる仕組みです。

OSのテーマを初期状態に反映する

<script setup>
import { onMounted } from 'vue'

onMounted(() => {
  const savedTheme = localStorage.getItem('theme')
  if (savedTheme) {
    document.body.className = savedTheme
  } else {
    const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches
    document.body.className = prefersDark ? 'dark' : 'light'
  }
})
</script>

切り替えボタンの実装

<template>
  <button @click="toggleTheme">
    テーマ切り替え(現在: {{ currentTheme }})
  </button>
</template>

<script setup>
import { ref, onMounted } from 'vue'

const currentTheme = ref('light')

onMounted(() => {
  currentTheme.value = document.body.className || 'light'
})

const toggleTheme = () => {
  currentTheme.value = currentTheme.value === 'light' ? 'dark' : 'light'
  document.body.className = currentTheme.value
  localStorage.setItem('theme', currentTheme.value)
}
</script>

この仕組みにより、ボタンを押すとテーマがトグルで切り替わり、設定はローカルストレージに保存されます。

ダークモード対応のポイント

  • コンポーネント単位ではなく、全体(bodyhtml)にテーマクラスを適用する
  • VuexやPiniaでテーマ状態をグローバル管理することも可能
  • Tailwind CSSを使用している場合は、dark:クラスやdarkMode: 'class'設定が有効

まとめ

Vue.jsでのダークモード対応は非常にシンプルかつ柔軟です。OSのテーマ自動検出、手動切り替え、状態保存の3点を押さえることで、ユーザーの視認性や操作感を大幅に改善できます。アプリの第一印象やアクセシビリティを高める手段として、ぜひ導入を検討してみてください。