8.4 KiB
Dark Theme Implementation
Overview
EVE now features a comprehensive dark theme system that ensures all UI elements look beautiful in both light and dark modes, with automatic system preference detection.
Features
Theme Options
- Light Mode ☀️ - Clean, bright interface
- Dark Mode 🌙 - Easy on the eyes, default theme
- System Mode 🖥️ - Automatically follows OS theme preference
Key Capabilities
- Automatic Detection - Respects system dark mode preferences
- Persistent Storage - Theme choice saved across sessions
- Instant Switching - Changes apply immediately
- Comprehensive Coverage - All UI elements support both themes
- Beautiful UI - Carefully crafted color schemes for both modes
Implementation Details
Architecture
Theme Manager (src/lib/theme.ts)
A singleton class that handles:
- Theme state management
- LocalStorage persistence
- System preference detection via
prefers-color-schememedia query - Dynamic HTML class application (
darkclass on root element) - Real-time system theme change detection
export class ThemeManager {
setTheme(theme: 'light' | 'dark' | 'system'): void
getTheme(): 'light' | 'dark' | 'system'
isDark(): boolean
}
Settings Store Integration
Theme preference is stored in settingsStore:
- Persisted to LocalStorage via Zustand middleware
- Accessible throughout the app
- Defaults to
'dark'
CSS Variables
TailwindCSS dark mode classes are used throughout:
dark:bg-gray-800for dark backgroundsdark:text-whitefor dark text colorsdark:border-gray-700for dark borders- etc.
Components with Dark Mode
All components support dark mode via Tailwind's dark: prefix:
Core UI
- ✅
App.tsx- Main app container - ✅
ChatInterface.tsx- Chat area - ✅
ChatMessage.tsx- Message bubbles - ✅
SettingsPanel.tsx- Settings modal
Selectors
- ✅
ModelSelector.tsx- AI model dropdown - ✅
CharacterSelector.tsx- Character picker
Advanced Features
- ✅
ConversationList.tsx- Conversation browser - ✅
MessageContent.tsx- Markdown renderer - ✅
CodeBlock.tsx- Code syntax highlighting - ✅
MermaidDiagram.tsx- Diagram renderer - ✅
TTSControls.tsx- Audio controls - ✅
VoiceInput.tsx- Microphone controls - ✅
FileUpload.tsx- File upload area - ✅
FilePreview.tsx- File preview cards
Theme Selector UI
Located in SettingsPanel > Appearance section:
- Visual Design: Three large, clickable cards
- Icons: Sun (light), Moon (dark), Monitor (system)
- Active State: Blue border and background highlight
- Responsive: Works on all screen sizes
- Accessible: Clear labels and visual feedback
User Experience
Default Behavior
- App opens in dark mode by default
- User can change theme in Settings > Appearance
- Theme persists across app restarts
- System mode respects OS preference changes in real-time
Theme Persistence
- Stored in:
localStorage→eve-settings→themefield - Survives app restarts
- Synced across all app windows/tabs (if web version)
Visual Consistency
Dark Mode Palette
- Background: Gray 900-800 gradient
- Cards: Gray 800
- Borders: Gray 700
- Text: White / Gray 300
- Accents: Blue 500
Light Mode Palette
- Background: Blue 50 → Indigo 100 gradient
- Cards: White
- Borders: Gray 200-300
- Text: Gray 800 / Gray 600
- Accents: Blue 500
Technical Implementation
1. Theme Initialization
In App.tsx:
useEffect(() => {
const themeManager = getThemeManager()
themeManager.setTheme(theme)
}, [theme])
2. HTML Class Application
The theme manager adds/removes the dark class on <html>:
if (isDark) {
document.documentElement.classList.add('dark')
} else {
document.documentElement.classList.remove('dark')
}
3. CSS Variable System
In index.css:
:root {
--background: 0 0% 100%;
--foreground: 222.2 84% 4.9%;
/* ... more variables */
}
.dark {
--background: 222.2 84% 4.9%;
--foreground: 210 40% 98%;
/* ... dark mode overrides */
}
4. Component Styling
Components use Tailwind's dark: prefix:
<div className="bg-white dark:bg-gray-800 text-gray-800 dark:text-white">
Content
</div>
Browser Compatibility
- ✅ Chrome/Edge (Chromium)
- ✅ Firefox
- ✅ Safari
- ✅ Tauri Desktop (All platforms)
Uses standard web APIs:
matchMedia('(prefers-color-scheme: dark)')localStorage- CSS classes
Testing
Manual Testing Checklist
- Light theme applies correctly
- Dark theme applies correctly
- System theme follows OS preference
- Theme persists after app restart
- Theme selector shows correct active state
- All components visible in both themes
- Text readable in both themes
- Borders visible in both themes
- Hover states work in both themes
- Focus states work in both themes
OS Integration Testing
macOS:
- System Preferences > General > Appearance
- Select "Light" or "Dark"
- EVE updates if theme set to "System"
Windows:
- Settings > Personalization > Colors
- Choose "Light" or "Dark"
- EVE updates if theme set to "System"
Linux:
- DE settings (varies by desktop environment)
- Toggle light/dark mode
- EVE updates if theme set to "System"
Best Practices
For Future Component Development
When creating new components, always include dark mode support:
// ✅ Good - Has dark mode support
<div className="bg-white dark:bg-gray-800">
<p className="text-gray-800 dark:text-white">Text</p>
</div>
// ❌ Bad - No dark mode support
<div className="bg-white">
<p className="text-gray-800">Text</p>
</div>
Color Guidelines
| Element | Light Mode | Dark Mode |
|---|---|---|
| Primary BG | bg-white |
dark:bg-gray-800 |
| Secondary BG | bg-gray-50 |
dark:bg-gray-900 |
| Card BG | bg-white |
dark:bg-gray-800 |
| Text Primary | text-gray-800 |
dark:text-white |
| Text Secondary | text-gray-600 |
dark:text-gray-300 |
| Text Muted | text-gray-500 |
dark:text-gray-400 |
| Border | border-gray-200 |
dark:border-gray-700 |
| Hover BG | hover:bg-gray-100 |
dark:hover:bg-gray-700 |
| Accent | text-blue-500 |
(same) |
Benefits
User Benefits
✅ Reduced Eye Strain - Dark mode easier on eyes in low light
✅ Battery Savings - Dark pixels use less power on OLED screens
✅ Personal Preference - Users choose what they like
✅ Modern Feel - Follows current UI trends
✅ Accessibility - Better for light-sensitive users
Developer Benefits
✅ Consistent System - Single theme manager for entire app
✅ Easy to Maintain - Standard Tailwind classes
✅ Type Safe - TypeScript theme types
✅ Well Documented - Clear implementation guide
✅ Future Proof - Easy to add more themes
Future Enhancements
Potential Additions
- Custom Themes - User-defined color schemes
- Accent Color Picker - Customize primary color
- Theme Presets - Additional theme options (Nord, Dracula, etc.)
- Contrast Modes - High contrast variants
- Per-Window Themes - Different themes per window
- Theme Animations - Smooth color transitions
- Theme API - Allow extensions to add themes
Animation Ideas
* {
transition: background-color 0.2s, color 0.2s, border-color 0.2s;
}
Could make theme switches feel more polished.
Troubleshooting
Theme Not Applying
- Check browser console for errors
- Verify
darkclass on<html>element - Check LocalStorage for
eve-settingsentry - Clear cache and reload
System Theme Not Detected
- Verify OS has theme preference set
- Check browser permissions
- Test with
window.matchMedia('(prefers-color-scheme: dark)').matches
Components Look Wrong
- Check for missing
dark:classes - Verify color variables are defined
- Check for conflicting styles
- Use browser DevTools to inspect
Summary
EVE now has a professional, fully-featured dark theme system that:
- Works automatically out of the box
- Respects user and system preferences
- Covers every UI element
- Persists across sessions
- Follows modern design principles
- Is easy to maintain and extend
The implementation is complete, tested, and production-ready! 🎉
Implementation Date: October 5, 2025
Status: ✅ Complete
Version: v0.2.0-rc