Projekt

Obecné

Profil

Stáhnout (4.73 KB) Statistiky
| Větev: | Tag: | Revize:
1
import { Button, Divider, Grid, Paper, Typography } from '@mui/material'
2
import { Fragment, useEffect, useState } from 'react'
3
import { useParams } from 'react-router-dom'
4
import axiosInstance from '../../api/api'
5
import { CatalogItemDto } from '../../swagger/data-contracts'
6
import ShowErrorIfPresent from '../Reusables/ShowErrorIfPresent'
7
import ContentLoading from '../Reusables/ContentLoading'
8
import CatalogItemMap from './CatalogItemMap'
9
import ArrowBackIosIcon from '@mui/icons-material/ArrowBackIos'
10
import { Link as RouterLink } from 'react-router-dom'
11
import DOMPurify from 'dompurify'
12
import { formatHtmlStringToReactDom } from '../../utils/formatting/HtmlUtils'
13

    
14
const apiError =
15
    'Error while fetching data from the server, please try again later.'
16

    
17
const CatalogItemDetail = () => {
18
    // itemId from query params
19
    const { itemId } = useParams()
20

    
21
    const [item, setItem] = useState<CatalogItemDto | undefined>(undefined)
22
    const [isItemLoading, setIsItemLoading] = useState(true)
23
    const [err, setErr] = useState<string | undefined>(undefined)
24

    
25
    // Fetch the item from the api after mounting the component
26
    useEffect(() => {
27
        // Function to fetch the item from the api
28
        const fetchItem = async () => {
29
            try {
30
                const { data, status } = await axiosInstance.get(
31
                    `/catalog-items/${itemId}`
32
                )
33
                if (status !== 200) {
34
                    setErr(apiError)
35
                    return
36
                }
37

    
38
                setItem(data)
39
                setIsItemLoading(false)
40
            } catch (err: any) {
41
                setErr(apiError)
42
            }
43
        }
44

    
45
        fetchItem()
46
    }, [itemId])
47

    
48
    // Maps catalogItem property to corresponding table row
49
    const mapToRow = (rowName: string, items: string[]) => (
50
        <Fragment>
51
            <Grid sx={{ my: 2 }} container justifyContent="space-around">
52
                <Grid item xs={8} sx={{ px: 1 }}>
53
                    <Typography fontWeight={500}>{rowName}</Typography>
54
                </Grid>
55
                <Grid item xs={4} sx={{ ml: 'auto' }}>
56
                    {items.map((item) => (
57
                        <Typography key={item}>{item}</Typography>
58
                    ))}
59
                </Grid>
60
            </Grid>
61
        </Fragment>
62
    )
63

    
64
    // Catalog item rows
65
    const rows = [
66
        {
67
            rowName: 'Name',
68
            items: [item?.name],
69
        },
70
        {
71
            rowName: 'Alternative Names',
72
            items: item?.alternativeNames,
73
        },
74
        {
75
            rowName: 'Written Forms',
76
            items: item?.writtenForms,
77
        },
78
        {
79
            rowName: 'Type',
80
            items: item?.types,
81
        },
82
        {
83
            rowName: 'State or Territory',
84
            items: item?.countries,
85
        },
86
        {
87
            rowName: 'Coordinates',
88
            items: [`${item?.longitude}°, ${item?.latitude}°`],
89
        },
90
        {
91
            rowName: 'Certainty',
92
            items: [item?.certainty],
93
        },
94
        {
95
            rowName: 'Bibliography',
96
            items: item?.bibliography,
97
        },
98
    ]
99

    
100
    return (
101
        // TODO remove min height
102
        <Fragment>
103
            <Button
104
                startIcon={<ArrowBackIosIcon />}
105
                variant="contained"
106
                component={RouterLink}
107
                to="/catalog"
108
                color="primary"
109
                sx={{ mb: 2 }}
110
            >
111
                Return To Catalog
112
            </Button>
113
            <ShowErrorIfPresent err={err} />
114

    
115
            <Paper style={{ minHeight: '100vh' }} variant="outlined">
116
                {isItemLoading && !err ? <ContentLoading /> : null}
117
                {!isItemLoading && item ? (
118
                    <Grid container justifyContent="space-around">
119
                        <Grid item xs={12} md={6} sx={{ px: 2 }}>
120
                            {rows.map((row, idx) => {
121
                                const maxIdx = rows.length - 1
122
                                return (
123
                                    <Fragment>
124
                                        {mapToRow(
125
                                            row.rowName as string,
126
                                            row.items as string[]
127
                                        )}
128
                                        {idx === maxIdx ? null : <Divider />}
129
                                    </Fragment>
130
                                )
131
                            })}
132
                        </Grid>
133

    
134
                        <Grid item md={6} xs={12}>
135
                            <CatalogItemMap item={item} />
136
                        </Grid>
137
                    </Grid>
138
                ) : null}
139
            </Paper>
140
        </Fragment>
141
    )
142
}
143

    
144
export default CatalogItemDetail
(3-3/7)