10aa46aa9e
* prevent flash of wrong theme on startup * move bg color to #root * Update and use existing system * Darken slightly, better contrast --------- Co-authored-by: Eric Bailey <git@esb.lol>
68 lines
1.8 KiB
TypeScript
68 lines
1.8 KiB
TypeScript
import React from 'react'
|
|
import {type ColorSchemeName, useColorScheme} from 'react-native'
|
|
import {type ThemeName} from '@bsky.app/alf'
|
|
|
|
import {isWeb} from '#/platform/detection'
|
|
import {useThemePrefs} from '#/state/shell'
|
|
import {dark, dim, light} from '#/alf/themes'
|
|
|
|
export function useColorModeTheme(): ThemeName {
|
|
const theme = useThemeName()
|
|
|
|
React.useLayoutEffect(() => {
|
|
updateDocument(theme)
|
|
}, [theme])
|
|
|
|
return theme
|
|
}
|
|
|
|
export function useThemeName(): ThemeName {
|
|
const colorScheme = useColorScheme()
|
|
const {colorMode, darkTheme} = useThemePrefs()
|
|
|
|
return getThemeName(colorScheme, colorMode, darkTheme)
|
|
}
|
|
|
|
function getThemeName(
|
|
colorScheme: ColorSchemeName,
|
|
colorMode: 'system' | 'light' | 'dark',
|
|
darkTheme?: ThemeName,
|
|
) {
|
|
if (
|
|
(colorMode === 'system' && colorScheme === 'light') ||
|
|
colorMode === 'light'
|
|
) {
|
|
return 'light'
|
|
} else {
|
|
return darkTheme ?? 'dim'
|
|
}
|
|
}
|
|
|
|
function updateDocument(theme: ThemeName) {
|
|
// @ts-ignore web only
|
|
if (isWeb && typeof window !== 'undefined') {
|
|
// @ts-ignore web only
|
|
const html = window.document.documentElement
|
|
// @ts-ignore web only
|
|
const meta = window.document.querySelector('meta[name="theme-color"]')
|
|
|
|
// remove any other color mode classes
|
|
html.className = html.className.replace(/(theme)--\w+/g, '')
|
|
html.classList.add(`theme--${theme}`)
|
|
// set color to 'theme-color' meta tag
|
|
meta?.setAttribute('content', getBackgroundColor(theme))
|
|
window.localStorage.setItem('ALF_THEME', theme)
|
|
}
|
|
}
|
|
|
|
export function getBackgroundColor(theme: ThemeName): string {
|
|
switch (theme) {
|
|
case 'light':
|
|
return light.atoms.bg.backgroundColor
|
|
case 'dark':
|
|
return dark.atoms.bg.backgroundColor
|
|
case 'dim':
|
|
return dim.atoms.bg.backgroundColor
|
|
}
|
|
}
|