170 lines
4.9 KiB
JavaScript
170 lines
4.9 KiB
JavaScript
import AsyncStorage from '@react-native-async-storage/async-storage'
|
|
import { useCallback, useMemo, useState } from 'react'
|
|
import { Image, StyleSheet, Text, TouchableOpacity, View } from 'react-native'
|
|
import { background, icons, videos } from '../assets'
|
|
import FullscreenIntroVideo from '../components/FullscreenIntroVideo'
|
|
import Page from '../layouts/Page'
|
|
import { Routes } from '../navigation'
|
|
import { navigate, reset } from '../navigation/NavigationService'
|
|
import { useUser } from '../providers/UserDataProvider'
|
|
import { Palette } from '../styles'
|
|
import { FONT_FAMILY } from '../styles/Fonts'
|
|
|
|
const LANGUAGE_STORAGE_KEY = 'preferredLanguage'
|
|
const FLOW_PHASE = {
|
|
JINGLE: 'jingle',
|
|
LANGUAGE: 'language',
|
|
WELCOME_VIDEO: 'welcomeVideo',
|
|
}
|
|
|
|
export default function LandingPage({ route }) {
|
|
const { currentUID } = useUser()
|
|
const [phase, setPhase] = useState(() =>
|
|
route?.params?.startAtLanguage ? FLOW_PHASE.LANGUAGE : FLOW_PHASE.JINGLE
|
|
)
|
|
const [selectedLanguage, setSelectedLanguage] = useState(null)
|
|
const isAuthenticated = !!currentUID
|
|
|
|
const openRegistration = useCallback(() => {
|
|
navigate(Routes.Register)
|
|
}, [])
|
|
|
|
const openMainMenu = useCallback(() => {
|
|
reset({
|
|
index: 0,
|
|
routes: [
|
|
{
|
|
name: Routes.BottomTab,
|
|
params: {
|
|
screen: Routes.HomeStack,
|
|
params: { screen: Routes.Home },
|
|
},
|
|
},
|
|
],
|
|
})
|
|
}, [])
|
|
|
|
const handleJingleClose = useCallback(() => {
|
|
if (isAuthenticated) {
|
|
openMainMenu()
|
|
return
|
|
}
|
|
setPhase(FLOW_PHASE.LANGUAGE)
|
|
}, [isAuthenticated, openMainMenu])
|
|
|
|
const handleSelectLanguage = useCallback(async (language) => {
|
|
try {
|
|
await AsyncStorage.setItem(LANGUAGE_STORAGE_KEY, language)
|
|
} catch (error) {
|
|
console.warn('LandingPage: failed to persist language', error)
|
|
}
|
|
setSelectedLanguage(language)
|
|
setPhase(FLOW_PHASE.WELCOME_VIDEO)
|
|
}, [])
|
|
|
|
const handleWelcomeVideoClose = useCallback(() => {
|
|
setSelectedLanguage(null)
|
|
setPhase(FLOW_PHASE.LANGUAGE)
|
|
requestAnimationFrame(openRegistration)
|
|
}, [openRegistration])
|
|
|
|
const activeVideo = useMemo(() => {
|
|
if (phase === FLOW_PHASE.JINGLE) return videos.entryJingle
|
|
if (phase !== FLOW_PHASE.WELCOME_VIDEO) return null
|
|
return selectedLanguage === 'en' ? videos.welcomeEn : videos.welcomeFr
|
|
}, [phase, selectedLanguage])
|
|
|
|
const activeVideoClose = phase === FLOW_PHASE.JINGLE ? handleJingleClose : handleWelcomeVideoClose
|
|
const isJingle = phase === FLOW_PHASE.JINGLE
|
|
const skipLabel = selectedLanguage === 'en' ? 'Skip video' : 'Passer la vidéo'
|
|
const playLabel = isJingle
|
|
? 'Activer le son / Enable sound'
|
|
: selectedLanguage === 'en'
|
|
? 'Play video with sound'
|
|
: 'Lire la vidéo avec le son'
|
|
|
|
return (
|
|
<>
|
|
<Page title="Landing Page" backgroundImg={background.homeBGWeb}>
|
|
<View
|
|
style={{
|
|
flex: 1,
|
|
justifyContent: 'center',
|
|
alignItems: 'center',
|
|
}}
|
|
>
|
|
<View style={styles.content}>
|
|
{phase === FLOW_PHASE.LANGUAGE ? (
|
|
<View style={styles.languageRow}>
|
|
<TouchableOpacity
|
|
style={[styles.languageButton]}
|
|
onPress={() => handleSelectLanguage('fr')}
|
|
>
|
|
<Image source={icons.frenchFlag} style={styles.flagIcon} />
|
|
<Text style={styles.languageText}>Français</Text>
|
|
</TouchableOpacity>
|
|
<TouchableOpacity
|
|
style={[styles.languageButton]}
|
|
onPress={() => handleSelectLanguage('en')}
|
|
>
|
|
<Image source={icons.englishFlag} style={styles.flagIcon} />
|
|
<Text style={styles.languageText}>English</Text>
|
|
</TouchableOpacity>
|
|
</View>
|
|
) : null}
|
|
</View>
|
|
</View>
|
|
</Page>
|
|
{activeVideo ? (
|
|
<FullscreenIntroVideo
|
|
key={phase}
|
|
url={activeVideo}
|
|
visible
|
|
onClose={activeVideoClose}
|
|
contentFit="contain"
|
|
allowSkip={!isJingle}
|
|
requireAudio={!isJingle}
|
|
offerSoundActivation={isJingle}
|
|
skipLabel={skipLabel}
|
|
playLabel={playLabel}
|
|
/>
|
|
) : null}
|
|
</>
|
|
)
|
|
}
|
|
|
|
const styles = StyleSheet.create({
|
|
content: {
|
|
width: '100%',
|
|
maxWidth: 360,
|
|
alignItems: 'center',
|
|
gap: 32,
|
|
},
|
|
languageRow: {
|
|
flexDirection: 'row',
|
|
gap: 16,
|
|
justifyContent: 'center',
|
|
},
|
|
languageButton: {
|
|
borderRadius: 14,
|
|
borderWidth: 1,
|
|
borderColor: Palette.ultraLightWhite,
|
|
backgroundColor: Palette.ultraLightWhite,
|
|
paddingVertical: 12,
|
|
paddingHorizontal: 18,
|
|
minWidth: 140,
|
|
alignItems: 'center',
|
|
flexDirection: 'row',
|
|
gap: 8,
|
|
},
|
|
flagIcon: {
|
|
width: 24,
|
|
height: 18,
|
|
},
|
|
languageText: {
|
|
fontSize: 16,
|
|
color: Palette.white,
|
|
fontFamily: FONT_FAMILY.InterSemiBold,
|
|
},
|
|
})
|