UNPKG

react-map-gl

Version:

React components for MapLibre GL JS and Mapbox GL JS

84 lines 3.06 kB
/* global document */ import * as React from 'react'; import { createPortal } from 'react-dom'; import { useImperativeHandle, useEffect, useMemo, useRef, useContext, forwardRef, memo } from 'react'; import { applyReactStyle } from "../utils/apply-react-style.js"; import { MapContext } from "./map.js"; import { arePointsEqual } from "../utils/deep-equal.js"; /* eslint-disable complexity,max-statements */ export const Marker = memo(forwardRef((props, ref) => { const { map, mapLib } = useContext(MapContext); const thisRef = useRef({ props }); thisRef.current.props = props; const marker = useMemo(() => { let hasChildren = false; React.Children.forEach(props.children, el => { if (el) { hasChildren = true; } }); const options = { ...props, element: hasChildren ? document.createElement('div') : null }; const mk = new mapLib.Marker(options); mk.setLngLat([props.longitude, props.latitude]); mk.getElement().addEventListener('click', (e) => { thisRef.current.props.onClick?.({ type: 'click', target: mk, originalEvent: e }); }); mk.on('dragstart', e => { const evt = e; evt.lngLat = marker.getLngLat(); thisRef.current.props.onDragStart?.(evt); }); mk.on('drag', e => { const evt = e; evt.lngLat = marker.getLngLat(); thisRef.current.props.onDrag?.(evt); }); mk.on('dragend', e => { const evt = e; evt.lngLat = marker.getLngLat(); thisRef.current.props.onDragEnd?.(evt); }); return mk; }, []); useEffect(() => { marker.addTo(map.getMap()); return () => { marker.remove(); }; }, []); const { longitude, latitude, offset, style, draggable = false, popup = null, rotation = 0, rotationAlignment = 'auto', pitchAlignment = 'auto' } = props; useEffect(() => { applyReactStyle(marker.getElement(), style); }, [style]); useImperativeHandle(ref, () => marker, []); if (marker.getLngLat().lng !== longitude || marker.getLngLat().lat !== latitude) { marker.setLngLat([longitude, latitude]); } if (offset && !arePointsEqual(marker.getOffset(), offset)) { marker.setOffset(offset); } if (marker.isDraggable() !== draggable) { marker.setDraggable(draggable); } if (marker.getRotation() !== rotation) { marker.setRotation(rotation); } if (marker.getRotationAlignment() !== rotationAlignment) { marker.setRotationAlignment(rotationAlignment); } if (marker.getPitchAlignment() !== pitchAlignment) { marker.setPitchAlignment(pitchAlignment); } if (marker.getPopup() !== popup) { marker.setPopup(popup); } return createPortal(props.children, marker.getElement()); })); //# sourceMappingURL=marker.js.map