123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247 |
- import React, { useCallback, useEffect, useState } from 'react';
- import { View, Text, TouchableOpacity, ScrollView, FlatList, Platform } from 'react-native';
- import ReactModal from 'react-native-modal';
- import * as Progress from 'react-native-progress';
- import { useFocusEffect, useNavigation } from '@react-navigation/native';
- import CountryItem from '../Components/CountryItem';
- import EditModal from '../Components/EditSlowModal';
- import { Header, Input, PageWrapper, WarningModal } from 'src/components';
- import { useGetSlowQuery, usePostSetSlowMutation } from '@api/countries';
- import { StoreType, storage } from 'src/storage';
- import { SlowData } from '../utils/types';
- import { Colors } from 'src/theme';
- import { styles } from './styles';
- import ChevronIcon from 'assets/icons/travels-screens/down-arrow.svg';
- import IngoSvg from 'assets/icons/travels-screens/info.svg';
- import SearchIcon from '../../../../../assets/icons/search.svg';
- import InfoIcon from 'assets/icons/info-solid.svg';
- import { NAVIGATION_PAGES } from 'src/types';
- import { useRegion } from 'src/contexts/RegionContext';
- const CountriesScreen = () => {
- const token = storage.get('token', StoreType.STRING) as string;
- const { data, refetch } = useGetSlowQuery(String(token));
- const [megaSelectorVisible, setMegaSelectorVisible] = useState(false);
- const [selectedMega, setSelectedMega] = useState<{ name: string; id: number }>({
- name: 'ALL MEGAREGIONS',
- id: -1
- });
- const [total, setTotal] = useState({ slow: 0, visited: 0 });
- const [isEditModalVisible, setIsEditModalVisible] = useState(false);
- const [currentItem, setCurrentItem] = useState<SlowData | null>(null);
- const [infoModalVisible, setInfoModalVisible] = useState(false);
- const [search, setSearch] = useState<string>('');
- const [filteredSlow, setFilteredSlow] = useState<SlowData[] | null>(null);
- const navigation = useNavigation();
- const { handleUpdateSlowList: handleUpdateSlow, slow, setSlow, setUserData } = useRegion();
- const handleOpenEditModal = (item: SlowData) => {
- setCurrentItem(item);
- setIsEditModalVisible(true);
- };
- useEffect(() => {
- if (slow && slow.length) {
- token && calcTotalScore();
- let newSlowData = slow;
- if (search) {
- newSlowData =
- slow?.filter((item: any) => {
- const itemData = item.country ? item.country.toLowerCase() : ''.toLowerCase();
- const textData = search.toLowerCase();
- return itemData.indexOf(textData) > -1;
- }) ?? [];
- }
- setFilteredSlow(newSlowData);
- }
- }, [slow]);
- useEffect(() => {
- const refetchData = async () => {
- await refetch().then((res) => {
- if (res.data) {
- setSlow(res.data.slow);
- }
- });
- };
- if (data && data.result === 'OK') {
- setSearch('');
- if (selectedMega.id === -1) {
- refetchData();
- } else {
- setSlow(data?.slow?.filter((item) => item.mega.includes(selectedMega.id)));
- }
- }
- }, [selectedMega]);
- useEffect(() => {
- if (data && data.result === 'OK') {
- setSlow(data?.slow);
- }
- }, [data]);
- const searchFilter = (text: string) => {
- if (text) {
- const newData: SlowData[] | null =
- slow?.filter((item: any) => {
- const itemData = item.country ? item.country.toLowerCase() : ''.toLowerCase();
- const textData = text.toLowerCase();
- return itemData.indexOf(textData) > -1;
- }) ?? [];
- setFilteredSlow(newData);
- setSearch(text);
- } else {
- setFilteredSlow(slow);
- setSearch(text);
- }
- };
- const calcTotalScore = () => {
- let visited = 0;
- let slow11 = 0;
- let slow31 = 0;
- let slow101 = 0;
- slow?.forEach((item: SlowData) => {
- visited += item.visited;
- slow11 += item.slow11;
- slow31 += item.slow31;
- slow101 += item.slow101;
- });
- setTotal({ slow: slow11 + slow31 + slow101, visited });
- };
- const renderCountryItem = ({ item }: { item: SlowData }) => (
- <CountryItem
- item={item}
- updateSlow={handleUpdateSlow}
- openEditModal={handleOpenEditModal}
- token={token}
- setUserData={setUserData}
- navigation={navigation}
- />
- );
- return (
- <PageWrapper>
- <Header
- label="Countries"
- // rightElement={
- // <TouchableOpacity
- // onPress={() => navigation.navigate(NAVIGATION_PAGES.COUNTRIES_INFO as never)}
- // style={{ width: 30 }}
- // >
- // <InfoIcon />
- // </TouchableOpacity>
- // }
- />
- <TouchableOpacity style={styles.megaSelector} onPress={() => setMegaSelectorVisible(true)}>
- <Text style={styles.megaButtonText}>{selectedMega.name}</Text>
- <ChevronIcon width={18} height={18} />
- </TouchableOpacity>
- <View style={{ marginBottom: 16 }}>
- <Input
- inputMode={'search'}
- placeholder={'Search'}
- onChange={(text) => searchFilter(text)}
- value={search}
- icon={<SearchIcon fill={'#C8C8C8'} width={14} height={14} />}
- height={34}
- />
- </View>
- <View style={styles.progressHeader}>
- <Text style={styles.visitedCountriesCount}>Visited countries</Text>
- <Text style={styles.visitedCountriesCount}>
- {slow?.length
- ? `${total.visited}/${slow.length} • ${((total.visited * 100) / slow.length).toFixed(2)}%`
- : '0/0 • 100%'}
- </Text>
- </View>
- <Progress.Bar
- progress={slow?.length ? total.visited / slow.length : 1}
- width={null}
- height={4}
- color={Colors.DARK_BLUE}
- borderWidth={0}
- borderRadius={5}
- unfilledColor={Colors.FILL_LIGHT}
- />
- <View style={styles.slowScoreSection}>
- <Text style={styles.visitedCountriesCount}>SLOW score: {total.slow}</Text>
- <TouchableOpacity style={styles.infoBtn} onPress={() => setInfoModalVisible(true)}>
- <IngoSvg />
- </TouchableOpacity>
- </View>
- {filteredSlow && filteredSlow?.length ? (
- <FlatList
- data={filteredSlow}
- renderItem={renderCountryItem}
- keyExtractor={(item) => item.country_id.toString()}
- showsVerticalScrollIndicator={false}
- style={{ paddingTop: 8 }}
- />
- ) : null}
- <ReactModal
- isVisible={megaSelectorVisible}
- onBackdropPress={() => setMegaSelectorVisible(false)}
- style={styles.modal}
- statusBarTranslucent={true}
- presentationStyle="overFullScreen"
- >
- <View style={styles.wrapper}>
- <ScrollView style={{ paddingBottom: 16 }} showsVerticalScrollIndicator={false}>
- <TouchableOpacity
- style={styles.btnOption}
- onPress={() => {
- setMegaSelectorVisible(false);
- setSelectedMega({ name: 'ALL MEGAREGIONS', id: -1 });
- }}
- >
- <Text style={styles.btnOptionText}>ALL MEGAREGIONS</Text>
- </TouchableOpacity>
- {data?.megaregions?.map((mega) => (
- <TouchableOpacity
- key={mega.id}
- style={styles.btnOption}
- onPress={() => {
- setMegaSelectorVisible(false);
- setSelectedMega(mega);
- }}
- >
- <Text style={styles.btnOptionText}>{mega.name}</Text>
- </TouchableOpacity>
- ))}
- </ScrollView>
- </View>
- </ReactModal>
- {currentItem && (
- <EditModal
- isVisible={isEditModalVisible}
- onClose={() => setIsEditModalVisible(false)}
- item={currentItem}
- updateSlow={(id, v, s11, s31, s101) => handleUpdateSlow(id, v, s11, s31, s101)}
- />
- )}
- <WarningModal
- isVisible={infoModalVisible}
- onClose={() => setInfoModalVisible(false)}
- type="success"
- title="SLOW score"
- message={`Mark countries as visited.\nTell us if you stayed longer (7, 31, 101) days, this will increase your SLOW score, each longer stay should include at least 7 days countinuous stay in a country.`}
- />
- </PageWrapper>
- );
- };
- export default CountriesScreen;
|