UNPKG

react-native-reanimated

Version:

More powerful alternative to Animated library for React Native.

94 lines (79 loc) 2.83 kB
'use strict'; import { createPropsBuilder } from '../../style'; import type { PlainStyle, UnknownRecord } from '../../types'; import { hasValueProcessor, isConfigPropertyAlias, isDefined, kebabizeCamelCase, maybeAddSuffix, } from '../../utils'; import { isRuleBuilder } from '../utils'; import { PROPERTIES_CONFIG } from './config'; import type { PropsBuilderConfig, RuleBuilder } from './types'; type WebPropsBuilderConfig<P extends UnknownRecord = UnknownRecord> = PropsBuilderConfig<P>; export function createWebPropsBuilder<TProps extends UnknownRecord>( config: WebPropsBuilderConfig<TProps> ) { const usedRuleBuilders = new Set<RuleBuilder<TProps>>(); const propsBuilder = createPropsBuilder({ config, processConfigValue(configValue, propertyKey) { // Handle true - include unchanged if (configValue === true) { return true; } // Handle false - exclude property if (configValue === false) { return; } // Handle suffix (e.g., 'px') if (typeof configValue === 'string') { return (value) => maybeAddSuffix(value, configValue); } // Handle property alias if (isConfigPropertyAlias<TProps>(configValue)) { return config[configValue.as]; } // Handle rule builders - store reference and return marker if (isRuleBuilder<TProps>(configValue)) { // Return a processor that feeds values to the rule builder and returns undefined // so the property doesn't appear in the regular processed props (only the result // of the rule builder will appear in the final style) return (value) => { usedRuleBuilders.add(configValue); configValue.add(propertyKey, value as TProps[keyof TProps]); return; }; } // Handle value processor if (hasValueProcessor(configValue)) { return configValue.process; } }, }); return { build(props: Partial<TProps>): string | null { usedRuleBuilders.clear(); // Build props - rule builders are fed during processing const processedProps = propsBuilder.build(props); // Build only used rule builders and merge their results for (const builder of usedRuleBuilders) { Object.assign(processedProps, builder.build()); } // Convert to CSS string const cssString = Object.entries(processedProps) .reduce<string[]>((acc, [key, value]) => { if (isDefined(value)) { acc.push(`${kebabizeCamelCase(key)}: ${value as string}`); } return acc; }, []) .join('; '); return cssString || null; // Return null if cssString is empty }, }; } export const webPropsBuilder = createWebPropsBuilder<PlainStyle>(PROPERTIES_CONFIG);