Theming & Dark Mode
@masumdev/rn-ui features a typed theme engine with built-in dark mode support, reactive hooks, dynamic style resolution, and storage hydration.
ThemeProvider API
| Prop | Type | Default | Description |
|---|---|---|---|
children | ReactNode | — | Application components wrapped by the provider. |
colorScheme | 'light' | 'dark' | 'system' | — | Controlled color scheme value. |
defaultColorScheme | 'light' | 'dark' | 'system' | 'system' | Uncontrolled initial color scheme preference. |
themes | { light?: ThemeInput; dark?: ThemeInput } | — | Custom light and dark theme object overrides. |
storage | { getItem: (key: string) => Promise<string | null>; setItem: (key: string, val: string) => Promise<void> } | — | Storage instance for persisting color scheme (e.g., SecureStore or AsyncStorage). |
storageKey | string | 'rn-ui-color-scheme' | Key name used in persistent storage. |
onColorSchemeChange | (colorScheme: ColorSchemePreference) => void | — | Callback triggered whenever the user updates the color scheme. |
Using the useTheme Hook
Access active theme colors, mode state, and toggle functions from any component:
import React from 'react';import { useTheme, Button, Text, Box } from '@masumdev/rn-ui';
export function ThemeToggleExample() { const { colors, colorScheme, isDark, toggleColorScheme, setColorScheme } = useTheme();
return ( <Box style={{ backgroundColor: colors.background, padding: 16 }}> <Text style={{ color: colors.text }}> Current Mode: {colorScheme} (Active: {isDark ? 'Dark' : 'Light'}) </Text> <Box row gap="sm" style={{ marginTop: 12 }}> <Button size="sm" tone="primary" onPress={toggleColorScheme}> Toggle Dark Mode </Button> <Button size="sm" variant="outline" onPress={() => setColorScheme('system')}> Use System </Button> </Box> </Box> );}Using the useThemeStyles Hook
Create type-safe, performance-optimized style objects driven by active theme tokens:
import React from 'react';import { View, Text } from 'react-native';import { useThemeStyles } from '@masumdev/rn-ui';
export function CustomStyledCard() { const styles = useStyles();
return ( <View style={styles.card}> <Text style={styles.title}>Type-Safe Theme Stylesheet</Text> </View> );}
function useStyles() { return useThemeStyles((theme) => ({ card: { backgroundColor: theme.colors.surface, borderRadius: theme.radii.xl, padding: theme.spacing.lg, borderWidth: 1, borderColor: theme.colors.border, }, title: { color: theme.colors.text, fontFamily: theme.fonts.bold, fontSize: 18, }, }));}Custom Themes & Font Customization
Pass custom ThemeInput definitions to ThemeProvider to change colors, fonts, spacing, or border radii:
import { ThemeProvider, type ThemeInput } from '@masumdev/rn-ui';
const customLight: ThemeInput = { colors: { primary: '#06B6D4', background: '#F6FBFC', surface: '#FFFFFF', text: '#06202A', border: '#B8D4DD', }, fonts: { regular: 'OutfitRegular', medium: 'OutfitMedium', bold: 'OutfitBold', },};
const customDark: ThemeInput = { colors: { primary: '#67E8F9', background: '#06141B', surface: '#0B202A', text: '#F2FBFD', border: '#2A5260', },};
export default function App() { return ( <ThemeProvider themes={{ light: customLight, dark: customDark }}> <RootNavigation /> </ThemeProvider> );}