forked from MapComplete/MapComplete
		
	
		
			
	
	
		
			70 lines
		
	
	
	
		
			2.4 KiB
		
	
	
	
		
			Svelte
		
	
	
	
	
	
		
		
			
		
	
	
			70 lines
		
	
	
	
		
			2.4 KiB
		
	
	
	
		
			Svelte
		
	
	
	
	
	
| 
								 | 
							
								<script lang="ts">
							 | 
						||
| 
								 | 
							
								    /**
							 | 
						||
| 
								 | 
							
								     * The overlay map is a bit a weird map:
							 | 
						||
| 
								 | 
							
								     * it is a HTML-component which is intended to be placed _over_ another map.
							 | 
						||
| 
								 | 
							
								     * It will align itself in order to seamlessly show the same location; but possibly in a different style
							 | 
						||
| 
								 | 
							
								     */
							 | 
						||
| 
								 | 
							
								    import MaplibreMap from "./MaplibreMap.svelte";
							 | 
						||
| 
								 | 
							
								    import {Store, UIEventSource} from "../../Logic/UIEventSource";
							 | 
						||
| 
								 | 
							
								    import {Map as MlMap} from "maplibre-gl";
							 | 
						||
| 
								 | 
							
								    import {MapLibreAdaptor} from "./MapLibreAdaptor";
							 | 
						||
| 
								 | 
							
								    import type {MapProperties} from "../../Models/MapProperties";
							 | 
						||
| 
								 | 
							
								    import {onDestroy} from "svelte";
							 | 
						||
| 
								 | 
							
								    import type {RasterLayerPolygon} from "../../Models/RasterLayers";
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    export let placedOverMapProperties: MapProperties
							 | 
						||
| 
								 | 
							
								    export let placedOverMap: UIEventSource<MlMap>
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    export let rasterLayer: UIEventSource<RasterLayerPolygon>
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    export let visible: Store<boolean> = undefined
							 | 
						||
| 
								 | 
							
								    let altmap: UIEventSource<MlMap> = new UIEventSource(undefined)
							 | 
						||
| 
								 | 
							
								    let altproperties = new MapLibreAdaptor(altmap, {
							 | 
						||
| 
								 | 
							
								        rasterLayer,
							 | 
						||
| 
								 | 
							
								        zoom: UIEventSource.feedFrom(placedOverMapProperties.zoom)
							 | 
						||
| 
								 | 
							
								    })
							 | 
						||
| 
								 | 
							
								    altproperties.allowMoving.setData(false)
							 | 
						||
| 
								 | 
							
								    altproperties.allowZooming.setData(false)
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    function pixelCenterOf(map: UIEventSource<MlMap>): [number, number] {
							 | 
						||
| 
								 | 
							
								        const rect = map?.data?.getCanvas()?.getBoundingClientRect()
							 | 
						||
| 
								 | 
							
								        if (!rect) {
							 | 
						||
| 
								 | 
							
								            return undefined
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								        const x = (rect.left + rect.right) / 2
							 | 
						||
| 
								 | 
							
								        const y = (rect.top + rect.bottom) / 2
							 | 
						||
| 
								 | 
							
								        return [x, y]
							 | 
						||
| 
								 | 
							
								    }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    function updateLocation() {
							 | 
						||
| 
								 | 
							
								        if (!placedOverMap.data || !altmap.data) {
							 | 
						||
| 
								 | 
							
								            return
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								        altmap.data.resize()
							 | 
						||
| 
								 | 
							
								        const {lon, lat} = placedOverMapProperties.location.data
							 | 
						||
| 
								 | 
							
								        const altMapCenter = pixelCenterOf(altmap)
							 | 
						||
| 
								 | 
							
								        const c = placedOverMap.data.unproject(altMapCenter)
							 | 
						||
| 
								 | 
							
								        altproperties.location.setData({lon: c.lng, lat: c.lat})
							 | 
						||
| 
								 | 
							
								    }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    onDestroy(placedOverMapProperties.location.addCallbackAndRunD(updateLocation))
							 | 
						||
| 
								 | 
							
								    updateLocation()
							 | 
						||
| 
								 | 
							
								    window.setTimeout(updateLocation, 150)
							 | 
						||
| 
								 | 
							
								    window.setTimeout(updateLocation, 500)
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    if (visible) {
							 | 
						||
| 
								 | 
							
								        onDestroy(visible?.addCallbackAndRunD(v => {
							 | 
						||
| 
								 | 
							
								            if (!v) {
							 | 
						||
| 
								 | 
							
								                return
							 | 
						||
| 
								 | 
							
								            }
							 | 
						||
| 
								 | 
							
								            updateLocation()
							 | 
						||
| 
								 | 
							
								            window.setTimeout(updateLocation, 150)
							 | 
						||
| 
								 | 
							
								            window.setTimeout(updateLocation, 500)
							 | 
						||
| 
								 | 
							
								        }))
							 | 
						||
| 
								 | 
							
								    }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								</script>
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								<MaplibreMap map={altmap}/>
							 |