CSS-Only dark mode in 15 lines of code

I'm a fan of dark UIs, and since Apple created the "dark mode" trend it's really easy to implement it. I built a quick implementation for my small RSS reader, and thought I could share how simple it is, because there are tons of articles with loads of code and Javascript and whatnot, but things can still be simple:

  • No Javascript required (this means no toggle functionality, but not a big deal)
  • No complex CSS rules or queries
  • Not a pure black + pure white colors selection
  • Good practices: remember hyperlinks & set a default almost-white image bg (because almost nobody remembers transparent images, except AWS blog posts)
  • Good trick: apply a slight grayscale filter to images, so they aren't that bright
  • Extra: A nice border color (I use Bootstrap at my RSS reader, so for the button and panel borders is nice)

All in 15 lines of code (12 if you don't want the border rule). Also, if the filter is not supported in your browser, will simply render the image normally, so the fallback is original behaviour instead of a degraded experience.

First, the director's cut commented version:

/* Works with Javascript-disabled, and if your browser doesn't supports media queries, it's way too old */
@media (prefers-color-scheme:dark) {
    /* A light-grey-but-not-white and a dark-but-not-pure-black, both stolen from Firefox's dark theme colors */
    body {
        color: #DCD8D9;
        background-color: #2A2A2E;
    }

    /* because browsers usually allow to customize default hyperlink colors */
    a {
        color: #DCD8D9;
    }

    img {
         /* subtle but easier on the eyes instead of full bright */
        filter: grayscale(30%);
         /* good practice: bg color for transparent images, diagrams, etc. */
        background-color: #EEE;
    }

    /* sample of something that has a border */
    div.panel-default {
        border-color: #4C4C4E;
    }
}

And the comment-less 15 lines version:

@media (prefers-color-scheme:dark) {
    body {
        color: #DCD8D9;
        background-color: #2A2A2E;
    }
    a {
        color: #DCD8D9;
    }
    img {
        filter: grayscale(30%);
        background-color: #EEE;
    }
    div.panel-default {
        border-color: #4C4C4E;
    }
}

And that's pretty much it.

2021-04-12

Comments? Share via Twitter Share via Linkedin Share via Mastodon