UNPKG

@oxyhq/services

Version:

Reusable OxyHQ module to handle authentication, user management, karma system, device-based session management and more 🚀

365 lines (363 loc) • 9.73 kB
"use strict"; import { View, Text, TouchableOpacity, StyleSheet, Platform } from 'react-native'; import { Ionicons } from '@expo/vector-icons'; import OxyIcon from './icon/OxyIcon'; import { fontFamilies } from '../styles/fonts'; import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime"; const Header = ({ title, subtitle, onBack, onClose, rightAction, rightActions, theme, showBackButton = true, showCloseButton = false, variant = 'default', elevation = 'subtle', subtitleVariant = 'default', titleAlignment = 'left' }) => { const isDarkTheme = theme === 'dark'; // Modern color palette const colors = { background: isDarkTheme ? '#1C1C1E' : '#FFFFFF', surface: isDarkTheme ? '#2C2C2E' : '#F8F9FA', primary: '#007AFF', secondary: isDarkTheme ? '#8E8E93' : '#6C757D', text: { primary: isDarkTheme ? '#FFFFFF' : '#1A1A1A', secondary: isDarkTheme ? '#8E8E93' : '#6C757D', tertiary: isDarkTheme ? '#636366' : '#ADB5BD' }, border: isDarkTheme ? '#38383A' : '#E9ECEF', accent: '#5856D6', success: '#34C759', warning: '#FF9500', error: '#FF3B30' }; const renderBackButton = () => { if (!showBackButton || !onBack) return null; return /*#__PURE__*/_jsx(TouchableOpacity, { style: [styles.backButton, { backgroundColor: colors.surface }], onPress: onBack, activeOpacity: 0.7, children: /*#__PURE__*/_jsx(OxyIcon, { name: "chevron-back", size: 18, color: colors.primary }) }); }; const renderCloseButton = () => { if (!showCloseButton || !onClose) return null; return /*#__PURE__*/_jsx(TouchableOpacity, { style: [styles.closeButton, { backgroundColor: colors.surface }], onPress: onClose, activeOpacity: 0.7, children: /*#__PURE__*/_jsx(Ionicons, { name: "close", size: 18, color: colors.text.primary }) }); }; const renderRightActionButton = (action, idx) => { const isTextAction = action.text; return /*#__PURE__*/_jsx(TouchableOpacity, { style: [styles.rightActionButton, isTextAction ? styles.textActionButton : styles.iconActionButton, { backgroundColor: isTextAction ? colors.primary : colors.surface, opacity: action.disabled ? 0.5 : 1 }], onPress: action.onPress, disabled: action.disabled || action.loading, activeOpacity: 0.7, children: action.loading ? /*#__PURE__*/_jsxs(View, { style: styles.loadingContainer, children: [/*#__PURE__*/_jsx(View, { style: [styles.loadingDot, { backgroundColor: isTextAction ? '#FFFFFF' : colors.primary }] }), /*#__PURE__*/_jsx(View, { style: [styles.loadingDot, { backgroundColor: isTextAction ? '#FFFFFF' : colors.primary }] }), /*#__PURE__*/_jsx(View, { style: [styles.loadingDot, { backgroundColor: isTextAction ? '#FFFFFF' : colors.primary }] })] }) : isTextAction ? /*#__PURE__*/_jsx(Text, { style: [styles.actionText, { color: '#FFFFFF' }], children: action.text }) : /*#__PURE__*/_jsx(Ionicons, { name: action.icon, size: 18, color: colors.primary }) }, action.key || idx); }; const renderRightActions = () => { if (rightActions?.length) { return /*#__PURE__*/_jsx(View, { style: styles.rightActionsRow, children: rightActions.map((a, i) => renderRightActionButton(a, i)) }); } if (rightAction) return renderRightActionButton(rightAction, 0); return null; }; const renderTitle = () => { const titleStyle = variant === 'large' ? styles.titleLarge : variant === 'minimal' ? styles.titleMinimal : styles.titleDefault; const subtitleStyle = variant === 'large' ? styles.subtitleLarge : variant === 'minimal' ? styles.subtitleMinimal : subtitleVariant === 'small' ? styles.subtitleSmall : subtitleVariant === 'large' ? styles.subtitleLarge : subtitleVariant === 'muted' ? styles.subtitleMuted : styles.subtitleDefault; const getTitleAlignment = () => { switch (titleAlignment) { case 'center': return styles.titleContainerCenter; case 'right': return styles.titleContainerRight; default: return styles.titleContainerLeft; } }; return /*#__PURE__*/_jsxs(View, { style: [styles.titleContainer, getTitleAlignment(), variant === 'minimal' && styles.titleContainerMinimal], children: [/*#__PURE__*/_jsx(Text, { style: [titleStyle, { color: colors.text.primary }], children: title }), subtitle && /*#__PURE__*/_jsx(Text, { style: [subtitleStyle, { color: colors.text.secondary }], children: subtitle })] }); }; const getElevationStyle = () => { switch (elevation) { case 'none': return {}; case 'subtle': return Platform.select({ web: { boxShadow: isDarkTheme ? '0 1px 3px rgba(0,0,0,0.3)' : '0 1px 3px rgba(0,0,0,0.1)' }, default: { shadowColor: '#000000', shadowOffset: { width: 0, height: 1 }, shadowOpacity: isDarkTheme ? 0.3 : 0.1, shadowRadius: 3, elevation: 2 } }); case 'prominent': return Platform.select({ web: { boxShadow: isDarkTheme ? '0 4px 12px rgba(0,0,0,0.4)' : '0 4px 12px rgba(0,0,0,0.15)' }, default: { shadowColor: '#000000', shadowOffset: { width: 0, height: 4 }, shadowOpacity: isDarkTheme ? 0.4 : 0.15, shadowRadius: 12, elevation: 8 } }); default: return {}; } }; const getBackgroundStyle = () => { if (variant === 'gradient') { return { backgroundColor: isDarkTheme ? '#1C1C1E' : '#FFFFFF', // Add gradient overlay effect borderBottomWidth: 1, borderBottomColor: colors.border }; } return { backgroundColor: colors.background, borderBottomWidth: elevation === 'none' ? 0 : 1, borderBottomColor: colors.border }; }; return /*#__PURE__*/_jsx(View, { style: [styles.container, getBackgroundStyle(), getElevationStyle()], children: /*#__PURE__*/_jsxs(View, { style: [styles.content, variant === 'minimal' && styles.contentMinimal], children: [renderBackButton(), renderTitle(), renderRightActions(), renderCloseButton()] }) }); }; const styles = StyleSheet.create({ container: { paddingTop: Platform.OS === 'ios' ? 50 : 16, paddingBottom: 12, top: 0, left: 0, right: 0, zIndex: 1000, ...Platform.select({ web: { position: 'sticky' }, default: { position: 'absolute' } }) }, content: { flexDirection: 'row', alignItems: 'center', paddingHorizontal: 16, position: 'relative', minHeight: 40 }, contentMinimal: { paddingHorizontal: 12, minHeight: 36 }, backButton: { width: 32, height: 32, borderRadius: 16, alignItems: 'center', justifyContent: 'center', marginRight: 10 }, closeButton: { width: 32, height: 32, borderRadius: 16, alignItems: 'center', justifyContent: 'center', marginLeft: 10 }, titleContainer: { flex: 1, alignItems: 'flex-start', justifyContent: 'center' }, titleContainerLeft: { alignItems: 'flex-start' }, titleContainerCenter: { alignItems: 'center' }, titleContainerRight: { alignItems: 'flex-end' }, titleContainerMinimal: { alignItems: 'center', marginHorizontal: 16 }, titleDefault: { fontSize: 18, fontWeight: '700', fontFamily: fontFamilies.phuduBold, letterSpacing: -0.5, lineHeight: 22 }, titleLarge: { fontSize: 28, fontWeight: '800', fontFamily: fontFamilies.phuduExtraBold, letterSpacing: -1, lineHeight: 34, marginBottom: 3 }, titleMinimal: { fontSize: 16, fontWeight: '600', fontFamily: fontFamilies.phuduSemiBold, letterSpacing: -0.3, lineHeight: 20 }, subtitleDefault: { fontSize: 14, fontWeight: '400', lineHeight: 17, marginTop: 1 }, subtitleLarge: { fontSize: 16, fontWeight: '400', lineHeight: 19, marginTop: 3 }, subtitleMinimal: { fontSize: 13, fontWeight: '400', lineHeight: 15, marginTop: 1 }, subtitleSmall: { fontSize: 12, fontWeight: '400', lineHeight: 14, marginTop: 0 }, subtitleMuted: { fontSize: 14, fontWeight: '400', lineHeight: 17, marginTop: 1, opacity: 0.7 }, rightActionButton: { alignItems: 'center', justifyContent: 'center', marginLeft: 10 }, iconActionButton: { width: 32, height: 32, borderRadius: 16 }, textActionButton: { paddingHorizontal: 14, paddingVertical: 6, borderRadius: 18, minWidth: 56 }, actionText: { fontSize: 14, fontWeight: '600', fontFamily: fontFamilies.phuduSemiBold, letterSpacing: -0.2 }, loadingContainer: { flexDirection: 'row', alignItems: 'center', justifyContent: 'center', gap: 2 }, loadingDot: { width: 4, height: 4, borderRadius: 2, opacity: 0.6 }, rightActionsRow: { flexDirection: 'row', alignItems: 'center' } }); export default Header; //# sourceMappingURL=Header.js.map