this repo has no description
at main 2.1 kB view raw
1import type { PropsWithChildren, ReactElement } from 'react'; 2import { StyleSheet } from 'react-native'; 3import Animated, { 4 interpolate, 5 useAnimatedRef, 6 useAnimatedStyle, 7 useScrollViewOffset, 8} from 'react-native-reanimated'; 9 10import { ThemedView } from '@/components/ThemedView'; 11import { useBottomTabOverflow } from '@/components/ui/TabBarBackground'; 12import { useColorScheme } from '@/hooks/useColorScheme'; 13 14const HEADER_HEIGHT = 250; 15 16type Props = PropsWithChildren<{ 17 headerImage: ReactElement; 18 headerBackgroundColor: { dark: string; light: string }; 19}>; 20 21export default function ParallaxScrollView({ 22 children, 23 headerImage, 24 headerBackgroundColor, 25}: Props) { 26 const colorScheme = useColorScheme() ?? 'light'; 27 const scrollRef = useAnimatedRef<Animated.ScrollView>(); 28 const scrollOffset = useScrollViewOffset(scrollRef); 29 const bottom = useBottomTabOverflow(); 30 const headerAnimatedStyle = useAnimatedStyle(() => { 31 return { 32 transform: [ 33 { 34 translateY: interpolate( 35 scrollOffset.value, 36 [-HEADER_HEIGHT, 0, HEADER_HEIGHT], 37 [-HEADER_HEIGHT / 2, 0, HEADER_HEIGHT * 0.75] 38 ), 39 }, 40 { 41 scale: interpolate(scrollOffset.value, [-HEADER_HEIGHT, 0, HEADER_HEIGHT], [2, 1, 1]), 42 }, 43 ], 44 }; 45 }); 46 47 return ( 48 <ThemedView style={styles.container}> 49 <Animated.ScrollView 50 ref={scrollRef} 51 scrollEventThrottle={16} 52 scrollIndicatorInsets={{ bottom }} 53 contentContainerStyle={{ paddingBottom: bottom }}> 54 <Animated.View 55 style={[ 56 styles.header, 57 { backgroundColor: headerBackgroundColor[colorScheme] }, 58 headerAnimatedStyle, 59 ]}> 60 {headerImage} 61 </Animated.View> 62 <ThemedView style={styles.content}>{children}</ThemedView> 63 </Animated.ScrollView> 64 </ThemedView> 65 ); 66} 67 68const styles = StyleSheet.create({ 69 container: { 70 flex: 1, 71 }, 72 header: { 73 height: HEADER_HEIGHT, 74 overflow: 'hidden', 75 }, 76 content: { 77 flex: 1, 78 padding: 32, 79 gap: 16, 80 overflow: 'hidden', 81 }, 82});