UNPKG

@react-native-ohos/react-native-unistyles

Version:
131 lines (100 loc) 4.34 kB
import type { UnistylesBridge, UnistylesConfig, UnistylesPlugin } from '../types' import type { UnistylesBreakpoints, UnistylesThemes } from '../global' import { isAndroid, isDev, isWeb, UnistylesError } from '../common' import { cssMediaQueriesPlugin, normalizeWebStylesPlugin } from '../plugins' export class UnistyleRegistry { public config: UnistylesConfig = {} public plugins: Array<UnistylesPlugin> = isWeb ? [normalizeWebStylesPlugin] : [] public themeNames: Array<keyof UnistylesThemes> = [] public themes: UnistylesThemes = {} as UnistylesThemes public breakpoints: UnistylesBreakpoints = {} as UnistylesBreakpoints public sortedBreakpointPairs: Array<[keyof UnistylesBreakpoints, UnistylesBreakpoints[keyof UnistylesBreakpoints]]> = [] constructor(private unistylesBridge: UnistylesBridge) {} public addThemes = (themes: UnistylesThemes) => { this.themes = themes const keys = Object.keys(themes) as Array<keyof UnistylesThemes> this.unistylesBridge.themes = keys this.themeNames = keys return { addBreakpoints: this.addBreakpoints, addConfig: this.addConfig } } public addBreakpoints = (breakpoints: UnistylesBreakpoints) => { this.breakpoints = breakpoints this.unistylesBridge.useBreakpoints(breakpoints) this.sortedBreakpointPairs = this.unistylesBridge.sortedBreakpointPairs return { addThemes: this.addThemes, addConfig: this.addConfig } } public addConfig = (config: UnistylesConfig) => { this.config = config if (config.adaptiveThemes) { this.unistylesBridge.useAdaptiveThemes(config.adaptiveThemes) } if (config.plugins) { config.plugins.forEach(plugin => this.addPlugin(plugin, false)) } if (config.initialTheme) { this.unistylesBridge.useTheme(config.initialTheme) } if (config.experimentalCSSMediaQueries) { this.plugins = [cssMediaQueriesPlugin].concat(this.plugins) this.unistylesBridge.addPlugin(cssMediaQueriesPlugin.name, false) } if (isWeb && config.windowResizeDebounceTimeMs !== undefined) { this.unistylesBridge.setWindowResizeDebounceTimeMs(config.windowResizeDebounceTimeMs) } if (isAndroid && config.disableAnimatedInsets) { this.unistylesBridge.disableAnimatedInsets() } return { addBreakpoints: this.addBreakpoints, addThemes: this.addThemes } } public getTheme = (forName: keyof UnistylesThemes) => { if (this.themeNames.length === 0) { return {} as UnistylesThemes[keyof UnistylesThemes] } if (this.hasTheme(forName)) { return this.themes[forName] } if (this.unistylesBridge.themeName) { throw new Error(UnistylesError.ThemeNotFound) } throw new Error(UnistylesError.ThemeNotSelected) } public addPlugin = (plugin: UnistylesPlugin, notify: boolean = true) => { if (plugin.name.startsWith('__unistyles')) { throw new Error(UnistylesError.InvalidPluginName) } const isAlreadyRegistered = this.plugins.some(({ name }) => name === plugin.name) if (!isAlreadyRegistered) { this.plugins = [plugin].concat(this.plugins) this.unistylesBridge.addPlugin(plugin.name, notify) return } if (!isDev) { throw new Error(UnistylesError.DuplicatePluginName) } } public removePlugin = (plugin: UnistylesPlugin) => { if (plugin.name.startsWith('__unistyles')) { throw new Error(UnistylesError.CantRemoveInternalPlugin) } this.plugins = this.plugins.filter(({ name }) => name !== plugin.name) this.unistylesBridge.removePlugin(plugin.name) } public updateTheme = (name: keyof UnistylesThemes, theme: UnistylesThemes[keyof UnistylesThemes]) => { this.themes[name] = theme if (this.unistylesBridge.themeName === name) { this.unistylesBridge.updateTheme(name) } } public hasTheme = (name: keyof UnistylesThemes) => name in this.themes }