aboutsummaryrefslogtreecommitdiff
path: root/src/map/MapRoutePoints.js
diff options
context:
space:
mode:
Diffstat (limited to 'src/map/MapRoutePoints.js')
-rw-r--r--src/map/MapRoutePoints.js77
1 files changed, 77 insertions, 0 deletions
diff --git a/src/map/MapRoutePoints.js b/src/map/MapRoutePoints.js
new file mode 100644
index 00000000..e329da81
--- /dev/null
+++ b/src/map/MapRoutePoints.js
@@ -0,0 +1,77 @@
+import { useId, useCallback, useEffect } from 'react';
+import { map } from './core/MapView';
+
+const MapRoutePoints = ({ positions, onClick }) => {
+ const id = useId();
+
+ const onMouseEnter = () => map.getCanvas().style.cursor = 'pointer';
+ const onMouseLeave = () => map.getCanvas().style.cursor = '';
+
+ const onMarkerClick = useCallback((event) => {
+ event.preventDefault();
+ const feature = event.features[0];
+ if (onClick) {
+ onClick(feature.properties.id, feature.properties.index);
+ }
+ }, [onClick]);
+
+ useEffect(() => {
+ map.addSource(id, {
+ type: 'geojson',
+ data: {
+ type: 'FeatureCollection',
+ features: [],
+ },
+ });
+ map.addLayer({
+ id,
+ type: 'symbol',
+ source: id,
+ layout: {
+ 'icon-image': 'arrow',
+ 'icon-allow-overlap': true,
+ 'icon-rotate': ['get', 'rotation'],
+ 'icon-rotation-alignment': 'map',
+ },
+ });
+
+ map.on('mouseenter', id, onMouseEnter);
+ map.on('mouseleave', id, onMouseLeave);
+ map.on('click', id, onMarkerClick);
+
+ return () => {
+ map.off('mouseenter', id, onMouseEnter);
+ map.off('mouseleave', id, onMouseLeave);
+ map.off('click', id, onMarkerClick);
+
+ if (map.getLayer(id)) {
+ map.removeLayer(id);
+ }
+ if (map.getSource(id)) {
+ map.removeSource(id);
+ }
+ };
+ }, [onMarkerClick]);
+
+ useEffect(() => {
+ map.getSource(id)?.setData({
+ type: 'FeatureCollection',
+ features: positions.map((position, index) => ({
+ type: 'Feature',
+ geometry: {
+ type: 'Point',
+ coordinates: [position.longitude, position.latitude],
+ },
+ properties: {
+ index,
+ id: position.id,
+ rotation: position.course,
+ },
+ })),
+ });
+ }, [onMarkerClick, positions]);
+
+ return null;
+};
+
+export default MapRoutePoints;