perf: code-split maplibre-gl in AboutPage
This commit is contained in:
@@ -0,0 +1,107 @@
|
|||||||
|
import { useEffect, useState } from 'react'
|
||||||
|
import Box from '@mui/material/Box'
|
||||||
|
import CircularProgress from '@mui/material/CircularProgress'
|
||||||
|
import Map, { Marker } from 'react-map-gl/maplibre'
|
||||||
|
import type * as maplibregl from 'maplibre-gl'
|
||||||
|
|
||||||
|
let maplibreglPromise: Promise<typeof maplibregl> | null = null
|
||||||
|
|
||||||
|
function loadMaplibre() {
|
||||||
|
if (!maplibreglPromise) {
|
||||||
|
maplibreglPromise = Promise.all([
|
||||||
|
import('maplibre-gl'),
|
||||||
|
import('maplibre-gl/dist/maplibre-gl.css'),
|
||||||
|
]).then(([mod]) => mod)
|
||||||
|
}
|
||||||
|
return maplibreglPromise
|
||||||
|
}
|
||||||
|
|
||||||
|
const rasterStyle = {
|
||||||
|
version: 8 as const,
|
||||||
|
sources: {
|
||||||
|
osm: {
|
||||||
|
type: 'raster' as const,
|
||||||
|
tiles: ['https://tile.openstreetmap.org/{z}/{x}/{y}.png'],
|
||||||
|
tileSize: 256,
|
||||||
|
attribution: '© OpenStreetMap contributors',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
layers: [{ id: 'osm', type: 'raster' as const, source: 'osm' }],
|
||||||
|
}
|
||||||
|
|
||||||
|
type AboutMapProps = {
|
||||||
|
lat: number
|
||||||
|
lng: number
|
||||||
|
}
|
||||||
|
|
||||||
|
export function AboutMap({ lat, lng }: AboutMapProps) {
|
||||||
|
const [maplibre, setMaplibre] = useState<typeof maplibregl | null>(null)
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
let cancelled = false
|
||||||
|
loadMaplibre().then((mod) => {
|
||||||
|
if (!cancelled) setMaplibre(mod)
|
||||||
|
})
|
||||||
|
return () => {
|
||||||
|
cancelled = true
|
||||||
|
}
|
||||||
|
}, [])
|
||||||
|
|
||||||
|
if (!maplibre) {
|
||||||
|
return (
|
||||||
|
<Box
|
||||||
|
sx={{
|
||||||
|
height: 380,
|
||||||
|
borderRadius: 2,
|
||||||
|
border: 1,
|
||||||
|
borderColor: 'divider',
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
justifyContent: 'center',
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<CircularProgress size={24} />
|
||||||
|
</Box>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Box
|
||||||
|
sx={{
|
||||||
|
height: 380,
|
||||||
|
borderRadius: 2,
|
||||||
|
overflow: 'hidden',
|
||||||
|
border: 1,
|
||||||
|
borderColor: 'divider',
|
||||||
|
position: 'relative',
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Map
|
||||||
|
mapLib={maplibre}
|
||||||
|
initialViewState={{ latitude: lat, longitude: lng, zoom: 15 }}
|
||||||
|
style={{ width: '100%', height: 380 }}
|
||||||
|
mapStyle={rasterStyle}
|
||||||
|
scrollZoom={false}
|
||||||
|
dragRotate={false}
|
||||||
|
dragPan={false}
|
||||||
|
doubleClickZoom={false}
|
||||||
|
keyboard={false}
|
||||||
|
touchZoomRotate={false}
|
||||||
|
>
|
||||||
|
<Marker longitude={lng} latitude={lat} anchor="bottom">
|
||||||
|
<Box
|
||||||
|
sx={{
|
||||||
|
width: 20,
|
||||||
|
height: 20,
|
||||||
|
bgcolor: 'primary.main',
|
||||||
|
borderRadius: '50%',
|
||||||
|
border: 2,
|
||||||
|
borderColor: 'background.paper',
|
||||||
|
boxShadow: 3,
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
</Marker>
|
||||||
|
</Map>
|
||||||
|
</Box>
|
||||||
|
)
|
||||||
|
}
|
||||||
@@ -3,24 +3,10 @@ import Link from '@mui/material/Link'
|
|||||||
import Paper from '@mui/material/Paper'
|
import Paper from '@mui/material/Paper'
|
||||||
import Stack from '@mui/material/Stack'
|
import Stack from '@mui/material/Stack'
|
||||||
import Typography from '@mui/material/Typography'
|
import Typography from '@mui/material/Typography'
|
||||||
import * as maplibregl from 'maplibre-gl'
|
|
||||||
import Map, { Marker } from 'react-map-gl/maplibre'
|
|
||||||
import { STORE_EMAIL, STORE_PHONE, VK_URL } from '@/shared/config'
|
import { STORE_EMAIL, STORE_PHONE, VK_URL } from '@/shared/config'
|
||||||
import { PICKUP_ADDRESS_FULL, PICKUP_COORDINATES } from '@/shared/constants/pickup-point'
|
import { PICKUP_ADDRESS_FULL, PICKUP_COORDINATES } from '@/shared/constants/pickup-point'
|
||||||
import { usePageTitle } from '@/shared/lib/use-page-title'
|
import { usePageTitle } from '@/shared/lib/use-page-title'
|
||||||
|
import { AboutMap } from './AboutMap'
|
||||||
const rasterStyle = {
|
|
||||||
version: 8 as const,
|
|
||||||
sources: {
|
|
||||||
osm: {
|
|
||||||
type: 'raster' as const,
|
|
||||||
tiles: ['https://tile.openstreetmap.org/{z}/{x}/{y}.png'],
|
|
||||||
tileSize: 256,
|
|
||||||
attribution: '© OpenStreetMap contributors',
|
|
||||||
},
|
|
||||||
},
|
|
||||||
layers: [{ id: 'osm', type: 'raster' as const, source: 'osm' }],
|
|
||||||
}
|
|
||||||
|
|
||||||
export function AboutPage() {
|
export function AboutPage() {
|
||||||
usePageTitle('О нас')
|
usePageTitle('О нас')
|
||||||
@@ -63,43 +49,7 @@ export function AboutPage() {
|
|||||||
</Typography>
|
</Typography>
|
||||||
</Paper>
|
</Paper>
|
||||||
|
|
||||||
<Box
|
<AboutMap lat={lat} lng={lng} />
|
||||||
sx={{
|
|
||||||
height: 380,
|
|
||||||
borderRadius: 2,
|
|
||||||
overflow: 'hidden',
|
|
||||||
border: 1,
|
|
||||||
borderColor: 'divider',
|
|
||||||
position: 'relative',
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<Map
|
|
||||||
mapLib={maplibregl}
|
|
||||||
initialViewState={{ latitude: lat, longitude: lng, zoom: 15 }}
|
|
||||||
style={{ width: '100%', height: 380 }}
|
|
||||||
mapStyle={rasterStyle}
|
|
||||||
scrollZoom={false}
|
|
||||||
dragRotate={false}
|
|
||||||
dragPan={false}
|
|
||||||
doubleClickZoom={false}
|
|
||||||
keyboard={false}
|
|
||||||
touchZoomRotate={false}
|
|
||||||
>
|
|
||||||
<Marker longitude={lng} latitude={lat} anchor="bottom">
|
|
||||||
<Box
|
|
||||||
sx={{
|
|
||||||
width: 20,
|
|
||||||
height: 20,
|
|
||||||
bgcolor: 'primary.main',
|
|
||||||
borderRadius: '50%',
|
|
||||||
border: 2,
|
|
||||||
borderColor: 'background.paper',
|
|
||||||
boxShadow: 3,
|
|
||||||
}}
|
|
||||||
/>
|
|
||||||
</Marker>
|
|
||||||
</Map>
|
|
||||||
</Box>
|
|
||||||
</Stack>
|
</Stack>
|
||||||
</Box>
|
</Box>
|
||||||
)
|
)
|
||||||
|
|||||||
Reference in New Issue
Block a user