← All @molecule/* packages · App templates
@molecule/app-themeCore interface · theme · App (browser) · v1.0.1 · Apache-2.0
Theme system with dark/light mode
npm install @molecule/app-theme@molecule/app-theme is the theme core interface on the app (browser) side: the API your app calls, with no vendor inside.
Choose the implementation by bonding one of its 2 providers: @molecule/app-theme-css-variables, @molecule/app-theme-css-variables-liquid-glass.
import { getProvider } from '@molecule/app-theme'
const theme = getProvider() // null until a bond is wired at startup
theme?.toggleMode() // light <-> dark
const unsubscribe = theme?.subscribe((t) => applyBranding(t))Providers (2): @molecule/app-theme-css-variables, @molecule/app-theme-css-variables-liquid-glass
Works with: @molecule/app-bond
Auto-generated, AI-first package reference for the molecule.dev ecosystem. It is written to be read by coding agents as much as by people, and is generated from this package's source — edit
src/index.tsJSDoc, not this file.
Theme interface and utilities for molecule.dev.
Framework-agnostic theme contract — a {@link Theme} (colors, spacing,
typography, radii, shadows, z-index) plus a {@link ThemeProvider} bond for
reading/switching themes, dark/light toggling, and change subscriptions.
Bond a provider (e.g. @molecule/app-theme-css-variables, which applies the
palette as CSS variables) at startup; {@link lightTheme}/{@link darkTheme}
are the base defaults.
import { getProvider } from '@molecule/app-theme'
const theme = getProvider() // null until a bond is wired at startup
theme?.toggleMode() // light <-> dark
const unsubscribe = theme?.subscribe((t) => applyBranding(t))
core
npm install @molecule/app-theme @molecule/app-bond
ThemeComplete theme definition.
interface Theme {
name: string
mode: 'light' | 'dark'
colors: ThemeColors
breakpoints: ThemeBreakpoints
spacing: ThemeSpacing
typography: ThemeTypography
borderRadius: ThemeBorderRadius
shadows: ThemeShadows
transitions: ThemeTransitions
zIndex: ThemeZIndex
}
ThemeBorderRadiusBorder radius scale.
interface ThemeBorderRadius {
none: string
sm: string
md: string
lg: string
xl: string
full: string
}
ThemeBreakpointsResponsive viewport breakpoints from mobileS (320px) to desktop (2560px).
interface ThemeBreakpoints {
mobileS: string // 320px
mobileM: string // 375px
mobileL: string // 425px
tablet: string // 768px
laptop: string // 1024px
laptopL: string // 1440px
desktop: string // 2560px
}
ThemeColorsColor palette definition.
interface ThemeColors {
// Base colors
background: string
backgroundSecondary: string
backgroundTertiary: string
surface: string
surfaceSecondary: string
inputBackground: string
// Text colors
text: string
textSecondary: string
textTertiary: string
textInverse: string
// Brand colors
primary: string
primaryLight: string
primaryDark: string
secondary: string
secondaryLight: string
secondaryDark: string
// Semantic colors
success: string
successLight: string
warning: string
warningLight: string
error: string
errorLight: string
info: string
infoLight: string
// Border colors
border: string
borderSecondary: string
borderFocus: string
// Other
overlay: string
shadow: string
}
ThemeProviderManages theme state including the active theme, mode toggling, and change subscriptions.
interface ThemeProvider {
/**
* Returns the currently active theme.
*/
getTheme(): Theme
/**
* Sets the active theme by reference or by name.
*
* @param theme - A `Theme` object or a theme name string to activate.
*/
setTheme(theme: Theme | string): void
/**
* Toggles between light and dark mode for the active theme.
*/
toggleMode(): void
/**
* Subscribes to theme changes. The callback fires whenever
* `setTheme()` or `toggleMode()` is called.
*
* @param callback - Invoked with the new theme after each change.
* @returns An unsubscribe function.
*/
subscribe(callback: (theme: Theme) => void): () => void
/**
* Returns all registered themes. Optional — not all providers
* support multiple themes.
*/
getThemes?(): Theme[]
}
ThemeShadowsBox-shadow scale from none to xl for elevation levels.
interface ThemeShadows {
none: string
sm: string
md: string
lg: string
xl: string
}
ThemeSpacingTheme spacing scale mapping size tokens (xs–3xl) to CSS values (e.g. '4px', '16px').
interface ThemeSpacing {
xs: string // 4px
sm: string // 8px
md: string // 16px
lg: string // 24px
xl: string // 32px
xxl: string // 48px
xxxl: string // 64px
}
ThemeTransitionsCSS transition duration presets (fast, normal, slow).
interface ThemeTransitions {
fast: string
normal: string
slow: string
}
ThemeTypographyTypography scale (font families, sizes, weights, and line heights).
interface ThemeTypography {
fontFamily: {
sans: string
serif: string
mono: string
}
fontSize: {
xs: string // 12px
sm: string // 14px
base: string // 16px
lg: string // 18px
xl: string // 20px
'2xl': string // 24px
'3xl': string // 30px
'4xl': string // 36px
'5xl': string // 48px
}
fontWeight: {
light: number
normal: number
medium: number
semibold: number
bold: number
}
lineHeight: {
tight: number
normal: number
relaxed: number
}
}
ThemeZIndexTheme z-index scale for layering UI elements (dropdowns, modals, toasts, etc.).
interface ThemeZIndex {
hide: number
base: number
dropdown: number
sticky: number
fixed: number
modal: number
popover: number
tooltip: number
toast: number
}
createDarkTheme(overrides)Creates a dark theme by merging default dark-mode tokens with optional overrides for colors, spacing, typography, etc.
function createDarkTheme(overrides?: Partial<Theme>): Theme
overrides — Partial theme tokens to merge over the defaults.Returns: A complete Theme object with mode: 'dark'.
createLightTheme(overrides)Creates a light theme by merging default light-mode tokens with optional overrides for colors, spacing, typography, etc.
function createLightTheme(overrides?: Partial<Theme>): Theme
overrides — Partial theme tokens to merge over the defaults.Returns: A complete Theme object with mode: 'light'.
getProvider()Retrieves the bonded theme provider, or null if none is configured.
function getProvider(): ThemeProvider | null
Returns: The bonded theme provider, or null.
hasProvider()Checks whether a theme provider is currently bonded.
function hasProvider(): boolean
Returns: true if a theme provider is bonded.
setProvider(provider)Registers a theme provider as the active singleton.
function setProvider(provider: ThemeProvider): void
provider — The theme provider implementation to bond.darkColorsDefault dark theme colors.
const darkColors: ThemeColors
darkThemeDefault dark theme.
const darkTheme: Theme
defaultBorderRadiusDefault border radius.
const defaultBorderRadius: ThemeBorderRadius
defaultBreakpointsDefault responsive breakpoints (320px mobileS → 2560px desktop).
const defaultBreakpoints: ThemeBreakpoints
defaultShadowsDefault box-shadow scale (none → xl, rgba-based).
const defaultShadows: ThemeShadows
defaultSpacingDefault spacing scale (4px xs → 64px xxxl).
const defaultSpacing: ThemeSpacing
defaultTransitionsDefault CSS transition durations (150ms fast, 250ms normal, 350ms slow).
const defaultTransitions: ThemeTransitions
defaultTypographyDefault typography scale (system font stacks, rem-based sizes, weight/line-height presets).
const defaultTypography: ThemeTypography
defaultZIndexDefault z-index scale.
const defaultZIndex: ThemeZIndex
lightColorsDefault light theme colors.
const lightColors: ThemeColors
lightThemeDefault light theme.
const lightTheme: Theme
| Provider | Package |
|---|---|
| CSS Variables | @molecule/app-theme-css-variables |
| Liquid Glass | @molecule/app-theme-css-variables-liquid-glass |
Peer dependencies:
@molecule/app-bond ^1.0.1@molecule/app-bond
Recoloring: find the REAL source of truth first. Apps scaffolded from a
template ship a per-app stylesheet (e.g. app/src/theme.css) that
hardcodes the --color-* variables and loads AFTER the bond — its values
win, and editing this package's Theme objects (or the bond's palette) has
NO visible effect there. Precedence: per-app theme stylesheet > theme
bond > base defaults. Recolor by editing whichever file actually defines
the variables; the bond's Theme palette applies only when no per-app
stylesheet defines colors.
Read theme values through the provider or the CSS variables it emits — never hardcode hex values in components; surfaces and status colors come from the theme so light AND dark both work.
{@link getProvider} returns null when nothing is bonded — theme switching
is optional; guard rather than throw.