/* * Copyright (c) 2019 - 2020 Arnaud Vergnet. * * This file is part of Campus INSAT. * * Campus INSAT is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * Campus INSAT is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with Campus INSAT. If not, see . */ import React, { useState } from 'react'; import { Linking, StyleSheet, View } from 'react-native'; import { Avatar, Button, Card, Chip, Paragraph, useTheme, } from 'react-native-paper'; import i18n from 'i18n-js'; import CustomHTML from '../../../components/Overrides/CustomHTML'; import { TAB_BAR_HEIGHT } from '../../../components/Tabbar/CustomTabBar'; import type { ClubCategoryType, ClubType } from './ClubListScreen'; import CollapsibleScrollView from '../../../components/Collapsible/CollapsibleScrollView'; import ImageGalleryButton from '../../../components/Media/ImageGalleryButton'; import RequestScreen from '../../../components/Screens/RequestScreen'; import { useFocusEffect } from '@react-navigation/core'; import { useCallback } from 'react'; import { useNavigation } from '@react-navigation/native'; import { useAuthenticatedRequest } from '../../../context/loginContext'; type Props = { route: { params?: { data?: ClubType; categories?: Array; clubId?: number; }; }; }; type ResponseType = ClubType; const AMICALE_MAIL = 'clubs@amicale-insat.fr'; const styles = StyleSheet.create({ category: { marginRight: 5, }, categoryContainer: { flexDirection: 'row', marginTop: 5, }, card: { marginTop: 10, }, icon: { backgroundColor: 'transparent', }, emailButton: { marginLeft: 'auto', }, scroll: { paddingLeft: 5, paddingRight: 5, }, imageButton: { width: 300, height: 300, marginLeft: 'auto', marginRight: 'auto', marginTop: 10, marginBottom: 10, }, }); /** * Class defining a club event information page. * If called with data and categories navigation parameters, will use those to display the data. * If called with clubId parameter, will fetch the information on the server */ function ClubDisplayScreen(props: Props) { const navigation = useNavigation(); const theme = useTheme(); const [displayData, setDisplayData] = useState(); const [categories, setCategories] = useState | undefined>(); const [clubId, setClubId] = useState(); useFocusEffect( useCallback(() => { if (props.route.params?.data && props.route.params?.categories) { setDisplayData(props.route.params.data); setCategories(props.route.params.categories); setClubId(props.route.params.data.id); } else { const id = props.route.params?.clubId; setClubId(id ? id : 0); } }, [props.route.params]) ); /** * Gets the name of the category with the given ID * * @param id The category's ID * @returns {string|*} */ const getCategoryName = (id: number): string => { let categoryName = ''; if (categories) { categories.forEach((item: ClubCategoryType) => { if (id === item.id) { categoryName = item.name; } }); } return categoryName; }; /** * Gets the view for rendering categories * * @param categories The categories to display (max 2) * @returns {null|*} */ const getCategoriesRender = (c: Array) => { if (!categories) { return null; } const final: Array = []; c.forEach((cat: number | null) => { if (cat != null) { final.push( {getCategoryName(cat)} ); } }); return {final}; }; /** * Gets the view for rendering club managers if any * * @param managers The list of manager names * @param email The club contact email * @returns {*} */ const getManagersRender = (managers: Array, email: string | null) => { const managersListView: Array = []; managers.forEach((item: string) => { managersListView.push({item}); }); const hasManagers = managers.length > 0; return ( ( )} /> {managersListView} {getEmailButton(email, hasManagers)} ); }; /** * Gets the email button to contact the club, or the amicale if the club does not have any managers * * @param email The club contact email * @param hasManagers True if the club has managers * @returns {*} */ const getEmailButton = (email: string | null, hasManagers: boolean) => { const destinationEmail = email != null && hasManagers ? email : AMICALE_MAIL; const text = email != null && hasManagers ? i18n.t('screens.clubs.clubContact') : i18n.t('screens.clubs.amicaleContact'); return ( ); }; const getScreen = (data: ResponseType | undefined) => { if (data) { updateHeaderTitle(data); return ( {getCategoriesRender(data.category)} {data.logo !== null ? ( ) : ( )} {data.description !== null ? ( // Surround description with div to allow text styling if the description is not html ) : ( )} {getManagersRender(data.responsibles, data.email)} ); } return ; }; /** * Updates the header title to match the given club * * @param data The club data */ const updateHeaderTitle = (data: ClubType) => { navigation.setOptions({ title: data.name }); }; const request = useAuthenticatedRequest('clubs/info', { id: clubId, }); return ( ); } export default ClubDisplayScreen;