Modo Oscuro en Tailwind
Tailwind CSS incluye soporte integrado para modo oscuro que te permite estilizar tu sitio de forma diferente cuando el modo oscuro está habilitado.
Habilitar Modo Oscuro
Configura la estrategia de modo oscuro en tu configuración:
// tailwind.config.js
module.exports = {
darkMode: 'class', // o 'media'
// ...
}
Estrategias de Modo Oscuro
- media - Usa la media query prefers-color-scheme (preferencia del sistema)
- class - Control manual con una clase 'dark' en el elemento html
Usando el Modificador Dark
<!-- Estilo básico de modo oscuro -->
<div class="bg-white dark:bg-gray-900">
<h1 class="text-gray-900 dark:text-white">Hello World</h1>
<p class="text-gray-600 dark:text-gray-400">Some text content</p>
</div>
<!-- Card con modo oscuro -->
<div class="bg-white dark:bg-gray-800 rounded-lg shadow-lg dark:shadow-gray-900/50 p-6">
<h2 class="text-xl font-bold text-gray-900 dark:text-white mb-2">
Card Title
</h2>
<p class="text-gray-600 dark:text-gray-300">
This card adapts to dark mode.
</p>
</div>
Modo Oscuro con Estrategia de Clase
<!-- Alterna modo oscuro agregando/quitar la clase 'dark' en html -->
<html class="dark">
<body class="bg-white dark:bg-gray-900">
<!-- Contenido -->
</body>
</html>
// JavaScript para alternar modo oscuro
function toggleDarkMode() {
document.documentElement.classList.toggle('dark');
}
// O con persistencia en localStorage
function toggleDarkMode() {
const isDark = document.documentElement.classList.toggle('dark');
localStorage.setItem('darkMode', isDark ? 'dark' : 'light');
}
// Al cargar la página, revisar preferencia
if (localStorage.getItem('darkMode') === 'dark' ||
(!localStorage.getItem('darkMode') &&
window.matchMedia('(prefers-color-scheme: dark)').matches)) {
document.documentElement.classList.add('dark');
}
Toggle de Modo Oscuro en React
import { useState, useEffect } from 'react';
function DarkModeToggle() {
const [isDark, setIsDark] = useState(false);
useEffect(() => {
// Check initial preference
const darkMode = localStorage.getItem('darkMode') === 'dark' ||
(!localStorage.getItem('darkMode') &&
window.matchMedia('(prefers-color-scheme: dark)').matches);
setIsDark(darkMode);
document.documentElement.classList.toggle('dark', darkMode);
}, []);
const toggle = () => {
const newValue = !isDark;
setIsDark(newValue);
document.documentElement.classList.toggle('dark', newValue);
localStorage.setItem('darkMode', newValue ? 'dark' : 'light');
};
return (
<button
onClick={toggle}
className="p-2 rounded-lg bg-gray-200 dark:bg-gray-700 transition-colors"
>
{isDark ? '☀️' : '🌙'}
</button>
);
}
Patrones Comunes de Modo Oscuro
<!-- Navegación -->
<nav class="bg-white dark:bg-gray-900 border-b border-gray-200 dark:border-gray-700">
<a href="#" class="text-gray-700 dark:text-gray-200 hover:text-blue-600 dark:hover:text-blue-400">
Link
</a>
</nav>
<!-- Inputs de formulario -->
<input
type="text"
class="
bg-white dark:bg-gray-800
border border-gray-300 dark:border-gray-600
text-gray-900 dark:text-white
placeholder-gray-400 dark:placeholder-gray-500
focus:ring-blue-500 dark:focus:ring-blue-400
focus:border-blue-500 dark:focus:border-blue-400
rounded-lg px-4 py-2
"
placeholder="Enter text..."
>
<!-- Botón -->
<button class="
bg-blue-600 dark:bg-blue-500
hover:bg-blue-700 dark:hover:bg-blue-600
text-white
px-4 py-2 rounded-lg
">
Submit
</button>
<!-- Bloque de código -->
<pre class="bg-gray-100 dark:bg-gray-800 text-gray-800 dark:text-gray-200 p-4 rounded-lg overflow-x-auto">
<code>const hello = "world";</code>
</pre>
Paleta de Colores para Modo Oscuro
<!-- Mapeos recomendados de color -->
<!--
Modo claro Modo oscuro
bg-white → bg-gray-900 or bg-gray-950
bg-gray-50 → bg-gray-800
bg-gray-100 → bg-gray-700
text-gray-900 → text-white or text-gray-100
text-gray-700 → text-gray-200
text-gray-600 → text-gray-300
text-gray-500 → text-gray-400
border-gray-200 → border-gray-700
border-gray-300 → border-gray-600
-->
<!-- Ejemplo de página completa -->
<div class="min-h-screen bg-gray-50 dark:bg-gray-900 transition-colors">
<header class="bg-white dark:bg-gray-800 shadow">
<nav class="max-w-7xl mx-auto px-4 py-4">
<span class="text-xl font-bold text-gray-900 dark:text-white">
My App
</span>
</nav>
</header>
<main class="max-w-7xl mx-auto px-4 py-8">
<div class="bg-white dark:bg-gray-800 rounded-lg shadow p-6">
<h1 class="text-2xl font-bold text-gray-900 dark:text-white mb-4">
Welcome
</h1>
<p class="text-gray-600 dark:text-gray-300">
This page supports dark mode.
</p>
</div>
</main>
</div>
Modo Oscuro con Otros Estados
<!-- Modo oscuro combinado con hover -->
<button class="
bg-gray-100 hover:bg-gray-200
dark:bg-gray-800 dark:hover:bg-gray-700
text-gray-900 dark:text-white
">
Button
</button>
<!-- Modo oscuro con responsive -->
<div class="
bg-white dark:bg-gray-900
md:bg-gray-50 md:dark:bg-gray-800
">
Responsive dark mode
</div>