DEV Community

Discussion on: 🌙 How to implement darkmode with a Vue.js component

Collapse
 
violacase profile image
violacase • Edited

That being said... getMediaPreference() is not a good idea for lots of reasons.
Simply replace it with a get from localStorage with f.i.:

getTheme() {
this.setTheme(localStorage.getItem("user-theme"))
},

Collapse
 
tqbit profile image
tq-bit

Thank you for your reply. & you got a valid point. I'll add your suggestion here & in the code sandbox. Will keep the getMediaPreference() as a default tho

Thread Thread
 
violacase profile image
violacase

Why keep it as a default? It really is BAD. My solution is SIMPLE, easy to implement and last but not least: secure and without any issues on all kind of browsers. My 2 pennies.

Thread Thread
 
tqbit profile image
tq-bit

With default, I meant as much as 'if there's no previous user preference in localStorage, use the result from getUserPreference. Please pick me up though on what's bad about reading out "(prefers-color-scheme: dark)" (besides missing support for IE11). I've seen it in other implementations and never had any issues using it.

Thread Thread
 
violacase profile image
violacase • Edited

Oké. I was in error. Nothing wrong with getUserPreference. Thanks and good luck with all your work.:-)

BTW: for just toggling between two color themes you can also do it with plain CSS. See developer.mozilla.org/en-US/docs/W...

Thread Thread
 
tqbit profile image
tq-bit

Mh, how would you do this? prefers-color-scheme is a read-only attribute in the browser's context.

In another project (w/o Vue), I'm using a different approach with SASS though, creating a function & a few mixins to apply themes

In a styles/state.scss file:

:root {
  --light-bg-color: #{$color-light-white};
  --light-text-color: #{$color-dark-grey};
  --bg-color: #{$color-white};
  --text-color: #{$color-black};
  --dark-bg-color: #{$color-light-white};
  --dark-text-color: #{$color-dark-grey};
}

:root.dark-theme {
  --light-bg-color: #{$color-dark-grey};
  --light-text-color: #{$color-light-white};
  --bg-color: #{$color-grey};
  --text-color: #{$color-white};
  --dark-bg-color: #{$color-dark-grey};
  --dark-text-color: #{$color-white};
}

@function theme-color($for) {
  @return var(--#{$for}-color);
}

@mixin theme-colors {
  background-color: theme-color('bg');
  color: theme-color('text');
  fill: theme-color('text');
}

@mixin light-theme-colors {
  background-color: theme-color('light-bg');
  color: theme-color('light-text');
  fill: theme-color('light-text');
}

@mixin dark-theme-colors {
  background-color: theme-color('dark-bg');
  color: theme-color('dark-text');
  fill: theme-color('dark-text');
}
Enter fullscreen mode Exit fullscreen mode

To apply it to the whole HTML - site: in styles/index.scss:

@import './state.scss';
html {
  @include dark-theme-colors;
}
Enter fullscreen mode Exit fullscreen mode

The JS code is quite similar to the one in the article as well

Thread Thread
 
violacase profile image
violacase

Right now I'm working on a multi themes setup. I'll come back to you later when a demo project has been finished. Will take me a couple of days (in my spare time).