import React from 'react'; import { Pressable, Text, ActivityIndicator, StyleSheet, ViewStyle, StyleProp, } from 'react-native'; import { Colors, Spacing, BorderRadius, FontSize, Animation } from '@/constants/theme'; type ButtonVariant = 'primary' | 'secondary' | 'outline' | 'text'; type ButtonSize = 'small' | 'medium' | 'large'; interface ButtonProps { title: string; onPress: () => void; variant?: ButtonVariant; size?: ButtonSize; disabled?: boolean; loading?: boolean; fullWidth?: boolean; icon?: React.ReactNode; style?: StyleProp; } const config = { variants: { primary: { backgroundColor: Colors.brand.primary, borderWidth: 0, borderColor: 'transparent', textColor: '#FFFFFF', }, secondary: { backgroundColor: Colors.brand.secondary, borderWidth: 0, borderColor: 'transparent', textColor: '#FFFFFF', }, outline: { backgroundColor: 'transparent', borderWidth: 1, borderColor: Colors.brand.primary, textColor: Colors.brand.primary, }, text: { backgroundColor: 'transparent', borderWidth: 0, borderColor: 'transparent', textColor: Colors.brand.primary, }, }, sizes: { small: { height: 36, paddingHorizontal: Spacing.md, fontSize: FontSize.sm, }, medium: { height: 48, paddingHorizontal: Spacing.xl, fontSize: FontSize.md, }, large: { height: 56, paddingHorizontal: Spacing.xxl, fontSize: FontSize.lg, }, }, }; export const Button: React.FC = ({ title, onPress, variant = 'primary', size = 'medium', disabled = false, loading = false, fullWidth = false, icon, style, }) => { const variantConfig = config.variants[variant]; const sizeConfig = config.sizes[size]; const isInteractive = !disabled && !loading; const buttonStyle = [ styles.base, { height: sizeConfig.height, paddingHorizontal: sizeConfig.paddingHorizontal, }, { backgroundColor: variantConfig.backgroundColor, borderWidth: variantConfig.borderWidth, borderColor: variantConfig.borderColor, opacity: disabled ? 0.5 : 1, }, fullWidth && styles.fullWidth, style, ]; const textStyle = [ styles.text, { color: variantConfig.textColor, fontSize: sizeConfig.fontSize, }, ]; const indicatorColor = variant === 'outline' || variant === 'text' ? '#007AFF' : '#FFFFFF'; return ( [ buttonStyle, isInteractive && pressed && styles.pressed, ]} > <>{icon} {loading ? ( ) : ( {title} )} ); }; const styles = StyleSheet.create({ base: { flexDirection: 'row', alignItems: 'center', justifyContent: 'center', borderRadius: BorderRadius.full, fontWeight: '600', }, fullWidth: { width: '100%', }, pressed: { transform: [{ scale: Animation.scale.pressed }], }, text: { fontWeight: '600', textAlign: 'center', }, }); export default Button;