@ -2,58 +2,39 @@
var toggle _theme = document . getElementById ( 'toggle_theme' ) ;
toggle _theme . href = 'javascript:void(0)' ;
toggle _theme . addEventListener ( 'click' , function ( ) {
var dark _mode = document . body . classList . contains ( 'light-theme' ) ;
set _mode ( dark _mode ) ;
helpers . storage . set ( 'dark_mode' , dark _mode ? 'dark' : 'light' ) ;
const STORAGE _KEY _THEME = 'dark_mode' ;
const THEME _DARK = 'dark' ;
const THEME _LIGHT = 'light' ;
const THEME _SYSTEM = '' ;
// TODO: theme state controlled by system
toggle _theme . addEventListener ( 'click' , function ( ) {
const isDarkTheme = helpers . storage . get ( STORAGE _KEY _THEME ) === THEME _DARK ;
setTheme ( isDarkTheme ? THEME _LIGHT : THEME _DARK ) ;
helpers . xhr ( 'GET' , '/toggle_theme?redirect=false' , { } , { } ) ;
} ) ;
// Handles theme change event caused by other tab
addEventListener ( 'storage' , function ( e ) {
if ( e . key === 'dark_mode' ) {
update _mode ( e . newValue ) ;
}
} ) ;
addEventListener ( 'DOMContentLoaded' , function ( ) {
const dark _mode = document . getElementById ( 'dark_mode_pref' ) . textContent ;
// Update storage if dark mode preference changed on preferences page
helpers . storage . set ( 'dark_mode' , dark _mode ) ;
update _mode ( dark _mode ) ;
// Ask system about dark theme
var systemDarkTheme = matchMedia ( '(prefers-color-scheme: dark)' ) ;
systemDarkTheme . addListener ( function ( ) {
// Ignore system events if theme set manually
if ( ! helpers . storage . get ( STORAGE _KEY _THEME ) )
setTheme ( THEME _SYSTEM ) ;
} ) ;
var darkScheme = matchMedia ( '(prefers-color-scheme: dark)' ) ;
var lightScheme = matchMedia ( '(prefers-color-scheme: light)' ) ;
darkScheme . addListener ( scheme _switch ) ;
lightScheme . addListener ( scheme _switch ) ;
function scheme _switch ( e ) {
// ignore this method if we have a preference set
if ( helpers . storage . get ( 'dark_mode' ) ) return ;
if ( ! e . matches ) return ;
if ( e . media . includes ( 'dark' ) ) {
set _mode ( true ) ;
} else if ( e . media . includes ( 'light' ) ) {
set _mode ( false ) ;
}
}
/** @param {THEME_DARK|THEME_LIGHT|THEME_SYSTEM} theme */
function setTheme ( theme ) {
if ( theme !== THEME _SYSTEM )
helpers . storage . set ( STORAGE _KEY _THEME , theme ) ;
function set _mode ( bool ) {
if ( bool ) {
// dark
if ( theme === THEME _DARK || ( theme === THEME _SYSTEM && systemDarkTheme . matches ) ) {
toggle _theme . children [ 0 ] . setAttribute ( 'class' , 'icon ion-ios-sunny' ) ;
document . body . classList . remove ( 'no-theme' ) ;
document . body . classList . remove ( 'light-theme' ) ;
document . body . classList . add ( 'dark-theme' ) ;
} else {
// light
toggle _theme . children [ 0 ] . setAttribute ( 'class' , 'icon ion-ios-moon' ) ;
document . body . classList . remove ( 'no-theme' ) ;
document . body . classList . remove ( 'dark-theme' ) ;
@ -61,18 +42,13 @@ function set_mode (bool) {
}
}
function update _mode ( mode ) {
if ( mode === 'true' /* for backwards compatibility */ || mode === 'dark' ) {
// If preference for dark mode indicated
set _mode ( true ) ;
}
else if ( mode === 'false' /* for backwards compatibility */ || mode === 'light' ) {
// If preference for light mode indicated
set _mode ( false ) ;
}
else if ( document . getElementById ( 'dark_mode_pref' ) . textContent === '' && matchMedia ( '(prefers-color-scheme: dark)' ) . matches ) {
// If no preference indicated here and no preference indicated on the preferences page (backend), but the browser tells us that the operating system has a dark theme
set _mode ( true ) ;
}
// else do nothing, falling back to the mode defined by the `dark_mode` preference on the preferences page (backend)
}
// Handles theme change event caused by other tab
addEventListener ( 'storage' , function ( e ) {
if ( e . key === STORAGE _KEY _THEME ) setTheme ( e . newValue ) ;
} ) ;
// Set theme from preferences on page load
addEventListener ( 'DOMContentLoaded' , function ( ) {
const prefTheme = document . getElementById ( 'dark_mode_pref' ) . textContent ;
setTheme ( prefTheme ) ;
} ) ;