UNPKG

@umituz/react-native-design-system-theme

Version:

Theme management system for React Native apps - Colors, design tokens, and theme state management

421 lines (392 loc) 8.38 kB
/** * BASE TOKENS - Static Design Tokens * * SINGLE SOURCE OF TRUTH for all static design tokens * These tokens don't change with theme (light/dark) * Used by TokenFactory to create complete DesignTokens * Material Design 3 compliant * * @module BaseTokens */ import { TextStyle, ViewStyle } from 'react-native'; // ============================================================================= // TYPE DEFINITIONS // ============================================================================= export type Spacing = { // Base Spacing Scale xs: number; sm: number; md: number; lg: number; xl: number; xxl: number; xxxl: number; // Semantic Spacing screenPadding: number; cardPadding: number; buttonPadding: number; inputPadding: number; sectionSpacing: number; // Icon Sizes iconSizeSmall: number; iconSizeMedium: number; iconSizeLarge: number; iconSizeXLarge: number; iconSizeHero: number; // Component Heights buttonHeight: number; inputHeight: number; appBarHeight: number; tabBarHeight: number; }; export type Typography = { displayLarge: TextStyle; displayMedium: TextStyle; displaySmall: TextStyle; headlineLarge: TextStyle; headlineMedium: TextStyle; headlineSmall: TextStyle; titleLarge: TextStyle; titleMedium: TextStyle; titleSmall: TextStyle; bodyLarge: TextStyle; bodyMedium: TextStyle; bodySmall: TextStyle; labelLarge: TextStyle; labelMedium: TextStyle; labelSmall: TextStyle; button: TextStyle; caption: TextStyle; overline: TextStyle; // Legacy compatibility headingLarge: TextStyle; headingMedium: TextStyle; headingSmall: TextStyle; // Font weight helpers (for inline fontWeight usage) semibold: '600'; medium: '500'; bold: '700'; }; export type Borders = { radius: { none: number; xs: number; sm: number; md: number; lg: number; xl: number; xxl: number; full: number; }; width: { none: number; thin: number; medium: number; thick: number; }; button: ViewStyle; card: ViewStyle; input: ViewStyle; pill: ViewStyle; }; export type IconSizes = { xs: number; sm: number; md: number; lg: number; xl: number; xxl: number; hero: number; }; export type Opacity = { disabled: number; inactive: number; subtle: number; medium: number; full: number; }; export type AvatarSizes = { xs: number; sm: number; md: number; lg: number; xl: number; xxl: number; }; export type ComponentSizes = { touchTarget: number; progressBar: { normal: number; thick: number; }; dot: { active: number; inactive: number; }; buttonHeight: { sm: number; md: number; lg: number; }; }; export type BaseTokens = { spacing: Spacing; typography: Typography; borders: Borders; iconSizes: IconSizes; opacity: Opacity; avatarSizes: AvatarSizes; sizes: ComponentSizes; }; // ============================================================================= // BASE TOKENS IMPLEMENTATION // ============================================================================= /** * BASE_TOKENS - Static design tokens * These values don't change with theme (light/dark) */ export const BASE_TOKENS: BaseTokens = { spacing: { // Base Spacing Scale (4px base unit) xs: 4, sm: 8, md: 16, lg: 24, xl: 32, xxl: 48, xxxl: 64, // Semantic Spacing screenPadding: 20, cardPadding: 16, buttonPadding: 16, inputPadding: 12, sectionSpacing: 24, // Icon Sizes iconSizeSmall: 16, iconSizeMedium: 20, iconSizeLarge: 24, iconSizeXLarge: 32, iconSizeHero: 64, // Component Heights buttonHeight: 48, inputHeight: 48, appBarHeight: 56, tabBarHeight: 60, }, typography: { displayLarge: { fontSize: 57, fontWeight: '400', lineHeight: 64, letterSpacing: -0.25, } as TextStyle, displayMedium: { fontSize: 45, fontWeight: '400', lineHeight: 52, letterSpacing: 0, } as TextStyle, displaySmall: { fontSize: 36, fontWeight: '400', lineHeight: 44, letterSpacing: 0, } as TextStyle, headlineLarge: { fontSize: 32, fontWeight: '400', lineHeight: 40, letterSpacing: 0, } as TextStyle, headlineMedium: { fontSize: 28, fontWeight: '400', lineHeight: 36, letterSpacing: 0, } as TextStyle, headlineSmall: { fontSize: 24, fontWeight: '400', lineHeight: 32, letterSpacing: 0, } as TextStyle, titleLarge: { fontSize: 22, fontWeight: '500', lineHeight: 28, letterSpacing: 0, } as TextStyle, titleMedium: { fontSize: 16, fontWeight: '500', lineHeight: 24, letterSpacing: 0.15, } as TextStyle, titleSmall: { fontSize: 14, fontWeight: '500', lineHeight: 20, letterSpacing: 0.1, } as TextStyle, bodyLarge: { fontSize: 16, fontWeight: '400', lineHeight: 24, letterSpacing: 0.5, } as TextStyle, bodyMedium: { fontSize: 14, fontWeight: '400', lineHeight: 20, letterSpacing: 0.25, } as TextStyle, bodySmall: { fontSize: 12, fontWeight: '400', lineHeight: 16, letterSpacing: 0.4, } as TextStyle, labelLarge: { fontSize: 14, fontWeight: '500', lineHeight: 20, letterSpacing: 0.1, } as TextStyle, labelMedium: { fontSize: 12, fontWeight: '500', lineHeight: 16, letterSpacing: 0.5, } as TextStyle, labelSmall: { fontSize: 11, fontWeight: '500', lineHeight: 16, letterSpacing: 0.5, } as TextStyle, button: { fontSize: 14, fontWeight: '500', lineHeight: 20, letterSpacing: 0.1, } as TextStyle, caption: { fontSize: 12, fontWeight: '400', lineHeight: 16, letterSpacing: 0.4, } as TextStyle, overline: { fontSize: 10, fontWeight: '500', lineHeight: 16, letterSpacing: 1.5, textTransform: 'uppercase', } as TextStyle, // Legacy compatibility aliases headingLarge: { fontSize: 32, fontWeight: '700', lineHeight: 40, letterSpacing: 0, } as TextStyle, headingMedium: { fontSize: 24, fontWeight: '600', lineHeight: 32, letterSpacing: 0, } as TextStyle, headingSmall: { fontSize: 20, fontWeight: '600', lineHeight: 28, letterSpacing: 0, } as TextStyle, // Font weight helpers (for inline fontWeight usage) semibold: '600' as const, medium: '500' as const, bold: '700' as const, }, borders: { radius: { none: 0, xs: 2, sm: 4, md: 8, lg: 12, xl: 16, xxl: 24, full: 9999, }, width: { none: 0, thin: 1, medium: 2, thick: 4, }, button: { borderRadius: 12, borderWidth: 0, } as ViewStyle, card: { borderRadius: 16, borderWidth: 1, } as ViewStyle, input: { borderRadius: 8, borderWidth: 1, } as ViewStyle, pill: { borderRadius: 9999, borderWidth: 0, } as ViewStyle, }, iconSizes: { xs: 16, sm: 20, md: 24, lg: 32, xl: 40, xxl: 48, hero: 64, }, opacity: { disabled: 0.6, inactive: 0.7, subtle: 0.8, medium: 0.9, full: 1.0, }, avatarSizes: { xs: 24, sm: 32, md: 40, lg: 48, xl: 64, xxl: 80, }, sizes: { touchTarget: 44, // Minimum touch target size (iOS/Android guidelines) progressBar: { normal: 4, thick: 8, }, dot: { active: 12, inactive: 8, }, buttonHeight: { sm: 40, md: 48, lg: 56, }, }, }; // ============================================================================= // CONVENIENCE EXPORTS // ============================================================================= export const spacing = BASE_TOKENS.spacing; export const typography = BASE_TOKENS.typography; export const borders = BASE_TOKENS.borders; // STATIC_TOKENS is an alias for BASE_TOKENS (backward compatibility) export const STATIC_TOKENS = BASE_TOKENS;