Skip to content

Dark Mode & Theme Customization #240

@adriandarian

Description

@adriandarian

Description

Implement dark mode with automatic system preference detection, custom theme builder, and accessibility-compliant color schemes.


Requirements

  • Dark mode theme
  • Light mode theme (current)
  • System preference auto-detection
  • Manual theme toggle
  • Custom color schemes
  • Theme builder UI
  • Save user preferences
  • WCAG AAA contrast compliance
  • Smooth theme transitions
  • Persistent theme selection

Theme Options

Built-in Themes

  1. Light (Default) - Clean, professional white/gray
  2. Dark - Easy on eyes, OLED-friendly blacks
  3. High Contrast Light - Maximum readability
  4. High Contrast Dark - Accessibility focused
  5. Sepia - Reduced eye strain, warm tones
  6. Nord - Popular blue-gray palette
  7. Dracula - Developer favorite purple theme
  8. Custom - User-defined colors

Theme Customization

Color Palette Builder

┌────────────────────────────────────┐
│ 🎨 Customize Theme                 │
├────────────────────────────────────┤
│ Primary Color:    [🔵 #3B82F6]    │
│ Background:       [⚪ #FFFFFF]    │
│ Foreground:       [⚫ #1F2937]    │
│ Accent:           [🟢 #10B981]    │
│ Success:          [🟢 #22C55E]    │
│ Warning:          [🟡 #F59E0B]    │
│ Error:            [🔴 #EF4444]    │
│                                    │
│ [Preview]  [Save]  [Reset]         │
└────────────────────────────────────┘

Live Preview

  • See changes in real-time
  • Test on all UI components
  • Accessibility warnings
  • Export/import themes

UI Changes

Theme Switcher

┌────────────────────────────────────┐
│ ⚙️ Settings > Appearance           │
├────────────────────────────────────┤
│ Theme                              │
│ ◉ Light                            │
│ ○ Dark                             │
│ ○ System (Auto)                    │
│                                    │
│ Color Scheme:  [Default ▾]         │
│                                    │
│ [🎨 Customize Colors]              │
│                                    │
│ Options:                           │
│ ☑ Smooth transitions               │
│ ☑ Match system theme               │
│ ☐ Auto dark at night               │
│   From: [6:00 PM] To: [7:00 AM]    │
└────────────────────────────────────┘

Quick Toggle

  • Add theme toggle to header
  • Keyboard shortcut: Ctrl/Cmd + Shift + T
  • Smooth fade transition (200ms)

Color Schemes

Light Theme

--bg-primary: #FFFFFF;
--bg-secondary: #F3F4F6;
--text-primary: #1F2937;
--text-secondary: #6B7280;
--border: #E5E7EB;
--accent: #3B82F6;

Dark Theme

--bg-primary: #111827;
--bg-secondary: #1F2937;
--text-primary: #F9FAFB;
--text-secondary: #9CA3AF;
--border: #374151;
--accent: #60A5FA;

High Contrast Dark

--bg-primary: #000000;
--bg-secondary: #1A1A1A;
--text-primary: #FFFFFF;
--text-secondary: #CCCCCC;
--border: #4A4A4A;
--accent: #FFD700;

Technical Implementation

CSS Variables

:root {
  /* Light theme (default) */
  --color-bg-primary: #FFFFFF;
  --color-bg-secondary: #F3F4F6;
  /* ... */
}

[data-theme="dark"] {
  /* Dark theme overrides */
  --color-bg-primary: #111827;
  --color-bg-secondary: #1F2937;
  /* ... */
}

[data-theme="custom"] {
  /* User custom colors */
  --color-bg-primary: var(--custom-bg-primary);
  --color-bg-secondary: var(--custom-bg-secondary);
  /* ... */
}

Theme Store

interface ThemeSettings {
  mode: 'light' | 'dark' | 'system';
  scheme: 'default' | 'nord' | 'dracula' | 'custom';
  customColors?: Record<string, string>;
  smoothTransitions: boolean;
  autoNightMode: boolean;
  nightModeStart: string; // "18:00"
  nightModeEnd: string; // "07:00"
}

const useTheme = create<ThemeSettings>()(
  persist(
    (set) => ({
      mode: 'system',
      scheme: 'default',
      smoothTransitions: true,
      autoNightMode: false,
      // ...
    }),
    { name: 'theme-settings' }
  )
);

System Preference Detection

const getSystemTheme = () => {
  return window.matchMedia('(prefers-color-scheme: dark)').matches
    ? 'dark'
    : 'light';
};

// Listen for system theme changes
window.matchMedia('(prefers-color-scheme: dark)')
  .addEventListener('change', (e) => {
    if (themeMode === 'system') {
      applyTheme(e.matches ? 'dark' : 'light');
    }
  });

Accessibility

Contrast Ratios

All color combinations must meet:

  • WCAG AAA: 7:1 for normal text
  • WCAG AAA: 4.5:1 for large text
  • Auto-check and warn on violations

Focus Indicators

  • Visible focus rings in all themes
  • 3px solid border with high contrast
  • Consistent across all interactive elements

Reduced Motion

@media (prefers-reduced-motion: reduce) {
  * {
    animation-duration: 0.01ms !important;
    transition-duration: 0.01ms !important;
  }
}

Acceptance Criteria

  • Light and dark themes work
  • System preference detected
  • Manual toggle functional
  • Theme persists across sessions
  • All colors WCAG AAA compliant
  • Smooth transitions work
  • Custom themes can be created
  • No flash of wrong theme on load
  • Works across all pages

Additional Features

Theme Scheduling

  • Auto switch to dark at sunset
  • Use time-based rules
  • Location-based (optional)

Theme Presets

  • One-click theme installation
  • Import/export theme JSON
  • Share custom themes
  • Community theme gallery

Per-Page Themes

  • Override global theme for specific pages
  • Analytics → Dark (easier on eyes)
  • Forms → Light (better readability)

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

Projects

Status

No status

Relationships

None yet

Development

No branches or pull requests

Issue actions