# Dark Mode ## 1. Saving/Loading state **LocalStorage** Saving/Loading the current theme in LocalStorage is quite easy on the frontend it works for static apps that do not have a server. But it only works when Javascript is enabled and it can take a second to load the current theme which may cause some flickering. **Cookie Session** If you have a server rendering the webpage this is the better approach imho, because we can inject a `````` into the html and this causes the current theme to be immediately available on the client. ## 2. Applying the Theme From mind there are two methods of changing the colors. **File based** We can create two files ```theme-light.css``` and ```theme-dark.css``` and decide which one to load based on the current theme. The advantage of this is that we can put anything we want into these files and even change layout based on the theme. This is also a disadvantage as we need to always keep two css files in sync with our html markup. **Variable based** CSS Variables are now widely [available in all browser](https://caniuse.com/css-variables). We can use this to our advantage because we can avoid duplicating our css styles by injecting the theme variables into the markup. ```css :root { /* primary */ --primary-source: rgb(255, 142, 60); } body { } body.theme-dark { --text-color: var(--) } ``` ## 3. Detecting user preferences We can also detect if the user prefers a light or dark theme using ```prefers-color-scheme```. This API is available in css: ```css .theme-a { background: #dca; color: #731; } @media (prefers-color-scheme: dark) { .theme-a.adaptive { background: #753; color: #dcb; outline: 5px dashed #000; } } ``` ```javascript window.matchMedia('(prefers-color-scheme: dark)').addEventListener('change', event => { const newColorScheme = event.matches ? "dark" : "light"; }); ```