import { useEffect, useRef, useState } from 'react'; import { useMediaQuery } from 'react-responsive'; import ArcGISMap from '@arcgis/core/Map'; import Extent from '@arcgis/core/geometry/Extent'; import MapView from '@arcgis/core/views/MapView'; import Basemap from '@arcgis/core/Basemap'; import MapImageLayer from '@arcgis/core/layers/MapImageLayer'; import WMTSLayer from '@arcgis/core/layers/WMTSLayer'; import SpatialReference from '@arcgis/core/geometry/SpatialReference'; import Search from '@arcgis/core/widgets/Search'; import ScaleBar from '@arcgis/core/widgets/ScaleBar'; import GraphicsLayer from '@arcgis/core/layers/GraphicsLayer'; import Graphic from '@arcgis/core/Graphic'; import LayerList from '@arcgis/core/widgets/LayerList'; import Zoom from '@arcgis/core/widgets/Zoom'; import Legend from '@arcgis/core/widgets/Legend'; import FeatureLayer from '@arcgis/core/layers/FeatureLayer'; import Polygon from '@arcgis/core/geometry/Polygon'; import esriConfig from '@arcgis/core/config'; import { watch } from '@arcgis/core/core/reactiveUtils'; import SimpleFillSymbol from '@arcgis/core/symbols/SimpleFillSymbol'; import './esri-ui-grundlagenkarte.css'; import { Vienna, Austria } from '@/public/borders-vienna-austria'; import { BASEMAP_AT_URL, AMPEL_GWWP_URL, RESOURCES_GWWP_URL, SRS } from '@/app/config/config'; import getAddress from '@/app/utils/getAddress'; import identifyAllLayers from '@/app/utils/identify'; import takeScreenshot from '@/app/utils/screenshot'; import { useAppDispatch } from '@/redux/hooks'; import PanelGrundlagenkarte from './panel-grundlagenkarte-gwwp'; // set path for local assets esriConfig.assetsPath = '/assets'; export default function MapComponent() { const dispatch = useAppDispatch(); const isMobile = useMediaQuery({ maxWidth: 480 }); const mapDiv = useRef(null); const [address, setAddress] = useState([]); useEffect(() => { let view: MapView; let handle: IHandle; if (mapDiv.current) { view = new MapView({ container: mapDiv.current, extent: new Extent({ xmin: -19000, ymin: 325000, xmax: 29000, ymax: 360000, spatialReference: new SpatialReference({ wkid: SRS }), }), popupEnabled: false, }); let viennaGraphic = new Graphic({ geometry: new Polygon({ rings: [Austria, Vienna], spatialReference: { wkid: SRS } }), symbol: { type: 'simple-fill', color: [209, 213, 219, 0.65], style: 'solid', outline: { color: 'white', width: 0, }, } as unknown as SimpleFillSymbol, }); // graphic layers let viennaGraphicsLayer = new GraphicsLayer({ title: 'Wien', listMode: 'hide' }); viennaGraphicsLayer.add(viennaGraphic); const ampelkarte_gwwp = new FeatureLayer({ url: AMPEL_GWWP_URL + '/0', title: 'Mögliche Einschränkungen', visible: false, listMode: 'show', opacity: 0.5, }); const resources_gwwp = new MapImageLayer({ title: 'Ressourcen', url: RESOURCES_GWWP_URL, visible: false, listMode: 'show', opacity: 0.5, }); // basemap in Viennese coordinate system due to tranformation inaccuracies from MGI to WGS84 // default transformation in ArcGIS API from MGI to WGS84 is 1306 // transformation 1618 is recommended const basemap_at = new WMTSLayer({ url: BASEMAP_AT_URL, listMode: 'hide', }); let basemap = new Basemap({ baseLayers: [basemap_at], title: 'basemap.at', id: 'basemap.at', spatialReference: { wkid: SRS }, }); let arcgisMap = new ArcGISMap({ basemap: basemap, layers: [resources_gwwp, ampelkarte_gwwp, viennaGraphicsLayer], }); const layerList = new LayerList({ view, }); const search = new Search({ view, popupEnabled: true, }); const scaleBar = new ScaleBar({ view: view, unit: 'metric', }); const zoom = new Zoom({ view, layout: 'horizontal', }); const legend = new Legend({ view, }); // register event handler for mouse clicks view.on('immediate-click', (event) => { if (setAddress) { takeScreenshot(view, event.mapPoint, dispatch, true); getAddress(event.mapPoint, setAddress); identifyAllLayers(view, event.mapPoint, dispatch, 'GWWP'); } }); // add map to view view.map = arcgisMap; // add UI components view.ui.components = []; if (!isMobile) { view.ui.add([zoom, search, layerList], 'top-left'); view.ui.add(scaleBar, 'bottom-left'); } view.when(() => { handle = watch( () => view.map?.layers?.map((layer) => layer.visible), () => { if (view.map?.layers?.some((layer) => layer.title !== 'Wien' && layer.visible === true)) { view.ui?.add(legend, 'top-left'); } else { view.ui?.remove(legend); } } ); }); } return () => { handle?.remove(); view?.destroy(); }; }, [dispatch, isMobile]); return (
); }