forked from MapComplete/MapComplete
		
	Do not zoom to location if it is out of the map bounds
This commit is contained in:
		
							parent
							
								
									8aa830f15e
								
							
						
					
					
						commit
						6763c682ab
					
				
					 2 changed files with 59 additions and 40 deletions
				
			
		| 
						 | 
					@ -85,30 +85,30 @@ export class InitUiElements {
 | 
				
			||||||
        function updateFavs() {
 | 
					        function updateFavs() {
 | 
				
			||||||
            // This is purely for the personal theme to load the layers there
 | 
					            // This is purely for the personal theme to load the layers there
 | 
				
			||||||
            const favs = State.state.favouriteLayers.data ?? [];
 | 
					            const favs = State.state.favouriteLayers.data ?? [];
 | 
				
			||||||
            
 | 
					
 | 
				
			||||||
            const neededLayers = new Set<LayerConfig>();
 | 
					            const neededLayers = new Set<LayerConfig>();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
            console.log("Favourites are: ", favs)
 | 
					            console.log("Favourites are: ", favs)
 | 
				
			||||||
            layoutToUse.layers.splice(0, layoutToUse.layers.length);
 | 
					            layoutToUse.layers.splice(0, layoutToUse.layers.length);
 | 
				
			||||||
            let somethingChanged = false;
 | 
					            let somethingChanged = false;
 | 
				
			||||||
            for (const fav of favs) {
 | 
					            for (const fav of favs) {
 | 
				
			||||||
                
 | 
					
 | 
				
			||||||
                if(AllKnownLayers.sharedLayers.has(fav)){
 | 
					                if (AllKnownLayers.sharedLayers.has(fav)) {
 | 
				
			||||||
                    const layer = AllKnownLayers.sharedLayers.get(fav)
 | 
					                    const layer = AllKnownLayers.sharedLayers.get(fav)
 | 
				
			||||||
                    if(!neededLayers.has(layer)){
 | 
					                    if (!neededLayers.has(layer)) {
 | 
				
			||||||
                        neededLayers.add(layer)
 | 
					                        neededLayers.add(layer)
 | 
				
			||||||
                        somethingChanged = true;
 | 
					                        somethingChanged = true;
 | 
				
			||||||
                    }
 | 
					                    }
 | 
				
			||||||
                }
 | 
					                }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
                
 | 
					
 | 
				
			||||||
                for (const layouts of State.state.installedThemes.data) {
 | 
					                for (const layouts of State.state.installedThemes.data) {
 | 
				
			||||||
                    for (const layer of layouts.layout.layers) {
 | 
					                    for (const layer of layouts.layout.layers) {
 | 
				
			||||||
                        if (typeof layer === "string") {
 | 
					                        if (typeof layer === "string") {
 | 
				
			||||||
                            continue;
 | 
					                            continue;
 | 
				
			||||||
                        }
 | 
					                        }
 | 
				
			||||||
                        if (layer.id === fav) {
 | 
					                        if (layer.id === fav) {
 | 
				
			||||||
                            if(!neededLayers.has(layer)){
 | 
					                            if (!neededLayers.has(layer)) {
 | 
				
			||||||
                                neededLayers.add(layer)
 | 
					                                neededLayers.add(layer)
 | 
				
			||||||
                                somethingChanged = true;
 | 
					                                somethingChanged = true;
 | 
				
			||||||
                            }
 | 
					                            }
 | 
				
			||||||
| 
						 | 
					@ -116,13 +116,13 @@ export class InitUiElements {
 | 
				
			||||||
                    }
 | 
					                    }
 | 
				
			||||||
                }
 | 
					                }
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
            if(somethingChanged){
 | 
					            if (somethingChanged) {
 | 
				
			||||||
                console.log("layoutToUse.layers:", layoutToUse.layers)
 | 
					                console.log("layoutToUse.layers:", layoutToUse.layers)
 | 
				
			||||||
                State.state.layoutToUse.data.layers = Array.from(neededLayers);
 | 
					                State.state.layoutToUse.data.layers = Array.from(neededLayers);
 | 
				
			||||||
                State.state.layoutToUse.ping();
 | 
					                State.state.layoutToUse.ping();
 | 
				
			||||||
                State.state.layerUpdater?.ForceRefresh();
 | 
					                State.state.layerUpdater?.ForceRefresh();
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
            
 | 
					
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -174,7 +174,8 @@ export class InitUiElements {
 | 
				
			||||||
            new MapControlButton(
 | 
					            new MapControlButton(
 | 
				
			||||||
                new GeoLocationHandler(
 | 
					                new GeoLocationHandler(
 | 
				
			||||||
                    State.state.currentGPSLocation,
 | 
					                    State.state.currentGPSLocation,
 | 
				
			||||||
                    State.state.leafletMap
 | 
					                    State.state.leafletMap,
 | 
				
			||||||
 | 
					                    State.state.layoutToUse
 | 
				
			||||||
                )),
 | 
					                )),
 | 
				
			||||||
            State.state.featureSwitchGeolocation);
 | 
					            State.state.featureSwitchGeolocation);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -381,23 +382,25 @@ export class InitUiElements {
 | 
				
			||||||
        State.state.leafletMap.setData(bm.map);
 | 
					        State.state.leafletMap.setData(bm.map);
 | 
				
			||||||
        const layout = State.state.layoutToUse.data
 | 
					        const layout = State.state.layoutToUse.data
 | 
				
			||||||
        if (layout.lockLocation) {
 | 
					        if (layout.lockLocation) {
 | 
				
			||||||
            const tile = Utils.embedded_tile(layout.startLat, layout.startLon, layout.startZoom - 1)
 | 
					
 | 
				
			||||||
            const bounds = Utils.tile_bounds(tile.z, tile.x, tile.y)
 | 
					            if (layout.lockLocation === true) {
 | 
				
			||||||
            // We use the bounds to get a sense of distance for this zoom level
 | 
					                const tile = Utils.embedded_tile(layout.startLat, layout.startLon, layout.startZoom - 1)
 | 
				
			||||||
            const latDiff = bounds[0][0] - bounds[1][0]
 | 
					                const bounds = Utils.tile_bounds(tile.z, tile.x, tile.y)
 | 
				
			||||||
            const lonDiff = bounds[0][1] - bounds[1][1]
 | 
					                // We use the bounds to get a sense of distance for this zoom level
 | 
				
			||||||
            console.warn("Locking the bounds to ", bounds)
 | 
					                const latDiff = bounds[0][0] - bounds[1][0]
 | 
				
			||||||
            bm.map.setMaxBounds(
 | 
					                const lonDiff = bounds[0][1] - bounds[1][1]
 | 
				
			||||||
                [[layout.startLat - latDiff, layout.startLon - lonDiff],
 | 
					                layout.lockLocation = [[layout.startLat - latDiff, layout.startLon - lonDiff],
 | 
				
			||||||
                    [layout.startLat + latDiff, layout.startLon + lonDiff],
 | 
					                    [layout.startLat + latDiff, layout.startLon + lonDiff],
 | 
				
			||||||
                ]
 | 
					                ];
 | 
				
			||||||
            );
 | 
					            }
 | 
				
			||||||
 | 
					            console.warn("Locking the bounds to ", layout.lockLocation)
 | 
				
			||||||
 | 
					            bm.map.setMaxBounds(layout.lockLocation);
 | 
				
			||||||
            bm.map.setMinZoom(layout.startZoom)
 | 
					            bm.map.setMinZoom(layout.startZoom)
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    private static InitLayers() : FeatureSource{
 | 
					    private static InitLayers(): FeatureSource {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        const state = State.state;
 | 
					        const state = State.state;
 | 
				
			||||||
| 
						 | 
					@ -420,13 +423,12 @@ export class InitUiElements {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        const updater = new LoadFromOverpass(state.locationControl, state.layoutToUse, state.leafletMap);
 | 
					        const updater = new LoadFromOverpass(state.locationControl, state.layoutToUse, state.leafletMap);
 | 
				
			||||||
        State.state.layerUpdater = updater;
 | 
					        State.state.layerUpdater = updater;
 | 
				
			||||||
        
 | 
					
 | 
				
			||||||
        
 | 
					
 | 
				
			||||||
        
 | 
					        const source = new FeaturePipeline(state.filteredLayers,
 | 
				
			||||||
        const source = new FeaturePipeline(state.filteredLayers, 
 | 
					            updater,
 | 
				
			||||||
            updater, 
 | 
					            state.osmApiFeatureSource,
 | 
				
			||||||
            state.osmApiFeatureSource, 
 | 
					            state.layoutToUse,
 | 
				
			||||||
            state.layoutToUse, 
 | 
					 | 
				
			||||||
            state.changes,
 | 
					            state.changes,
 | 
				
			||||||
            state.locationControl,
 | 
					            state.locationControl,
 | 
				
			||||||
            state.selectedElement);
 | 
					            state.selectedElement);
 | 
				
			||||||
| 
						 | 
					@ -442,7 +444,7 @@ export class InitUiElements {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        // ------------- Setup the layers -------------------------------
 | 
					        // ------------- Setup the layers -------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
       const source =  InitUiElements.InitLayers();
 | 
					        const source = InitUiElements.InitLayers();
 | 
				
			||||||
        InitUiElements.InitLayerSelection(source);
 | 
					        InitUiElements.InitLayerSelection(source);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -5,6 +5,7 @@ import {Utils} from "../../Utils";
 | 
				
			||||||
import Svg from "../../Svg";
 | 
					import Svg from "../../Svg";
 | 
				
			||||||
import Img from "../../UI/Base/Img";
 | 
					import Img from "../../UI/Base/Img";
 | 
				
			||||||
import {LocalStorageSource} from "../Web/LocalStorageSource";
 | 
					import {LocalStorageSource} from "../Web/LocalStorageSource";
 | 
				
			||||||
 | 
					import LayoutConfig from "../../Customizations/JSON/LayoutConfig";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export default class GeoLocationHandler extends UIElement {
 | 
					export default class GeoLocationHandler extends UIElement {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -49,12 +50,15 @@ export default class GeoLocationHandler extends UIElement {
 | 
				
			||||||
     * @private
 | 
					     * @private
 | 
				
			||||||
     */
 | 
					     */
 | 
				
			||||||
    private readonly _previousLocationGrant: UIEventSource<string> = LocalStorageSource.Get("geolocation-permissions");
 | 
					    private readonly _previousLocationGrant: UIEventSource<string> = LocalStorageSource.Get("geolocation-permissions");
 | 
				
			||||||
 | 
					    private readonly _layoutToUse: UIEventSource<LayoutConfig>;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    constructor(currentGPSLocation: UIEventSource<{ latlng: any; accuracy: number }>,
 | 
					    constructor(currentGPSLocation: UIEventSource<{ latlng: any; accuracy: number }>,
 | 
				
			||||||
                leafletMap: UIEventSource<L.Map>) {
 | 
					                leafletMap: UIEventSource<L.Map>,
 | 
				
			||||||
 | 
					                layoutToUse: UIEventSource<LayoutConfig>) {
 | 
				
			||||||
        super(undefined);
 | 
					        super(undefined);
 | 
				
			||||||
        this._currentGPSLocation = currentGPSLocation;
 | 
					        this._currentGPSLocation = currentGPSLocation;
 | 
				
			||||||
        this._leafletMap = leafletMap;
 | 
					        this._leafletMap = leafletMap;
 | 
				
			||||||
 | 
					        this._layoutToUse = layoutToUse;
 | 
				
			||||||
        this._hasLocation = currentGPSLocation.map((location) => location !== undefined);
 | 
					        this._hasLocation = currentGPSLocation.map((location) => location !== undefined);
 | 
				
			||||||
        this.dumbMode = false;
 | 
					        this.dumbMode = false;
 | 
				
			||||||
        const self = this;
 | 
					        const self = this;
 | 
				
			||||||
| 
						 | 
					@ -90,11 +94,11 @@ export default class GeoLocationHandler extends UIElement {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        const self = this;
 | 
					        const self = this;
 | 
				
			||||||
        htmlElement.onclick = function () {
 | 
					        htmlElement.onclick = function () {
 | 
				
			||||||
            self.StartGeolocating(19);
 | 
					            self.StartGeolocating();
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        htmlElement.oncontextmenu = function (e) {
 | 
					        htmlElement.oncontextmenu = function (e) {
 | 
				
			||||||
            self.StartGeolocating(15);
 | 
					            self.StartGeolocating();
 | 
				
			||||||
            e.preventDefault();
 | 
					            e.preventDefault();
 | 
				
			||||||
            return false;
 | 
					            return false;
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
| 
						 | 
					@ -133,9 +137,24 @@ export default class GeoLocationHandler extends UIElement {
 | 
				
			||||||
            const timeSinceRequest = (new Date().getTime() - (self._lastUserRequest?.getTime() ?? 0)) / 1000;
 | 
					            const timeSinceRequest = (new Date().getTime() - (self._lastUserRequest?.getTime() ?? 0)) / 1000;
 | 
				
			||||||
            if (timeSinceRequest < 30) {
 | 
					            if (timeSinceRequest < 30) {
 | 
				
			||||||
                self._lastUserRequest = undefined;
 | 
					                self._lastUserRequest = undefined;
 | 
				
			||||||
                this._leafletMap.data.setView(
 | 
					
 | 
				
			||||||
                    this._currentGPSLocation.data.latlng, this._leafletMap.data.getZoom()
 | 
					                // We use the layout location
 | 
				
			||||||
                );
 | 
					                const b = this._layoutToUse.data.lockLocation
 | 
				
			||||||
 | 
					                let inRange = true;
 | 
				
			||||||
 | 
					                if(b){
 | 
				
			||||||
 | 
					                    if(b!== true){
 | 
				
			||||||
 | 
					                        // B is an array with our locklocation
 | 
				
			||||||
 | 
					                        inRange = b[0][0] <= location.latlng[0] && location.latlng[0] <= b[1][0] &&
 | 
				
			||||||
 | 
					                            b[0][1] <= location.latlng[1] && location.latlng[1] <= b[1][1];
 | 
				
			||||||
 | 
					                    }
 | 
				
			||||||
 | 
					                }
 | 
				
			||||||
 | 
					                if (!inRange) {
 | 
				
			||||||
 | 
					                    console.log("Not zooming to GPS location: out of bounds", b, location.latlng)
 | 
				
			||||||
 | 
					                } else {
 | 
				
			||||||
 | 
					                    this._leafletMap.data.setView(
 | 
				
			||||||
 | 
					                        location.latlng, this._leafletMap.data.getZoom()
 | 
				
			||||||
 | 
					                    );
 | 
				
			||||||
 | 
					                }
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
            let color = "#1111cc";
 | 
					            let color = "#1111cc";
 | 
				
			||||||
| 
						 | 
					@ -166,7 +185,7 @@ export default class GeoLocationHandler extends UIElement {
 | 
				
			||||||
                ?.then(function (status) {
 | 
					                ?.then(function (status) {
 | 
				
			||||||
                    console.log("Geolocation is already", status)
 | 
					                    console.log("Geolocation is already", status)
 | 
				
			||||||
                    if (status.state === "granted") {
 | 
					                    if (status.state === "granted") {
 | 
				
			||||||
                        self.StartGeolocating(19, false);
 | 
					                        self.StartGeolocating(false);
 | 
				
			||||||
                    }
 | 
					                    }
 | 
				
			||||||
                    self._permission.setData(status.state);
 | 
					                    self._permission.setData(status.state);
 | 
				
			||||||
                    status.onchange = function () {
 | 
					                    status.onchange = function () {
 | 
				
			||||||
| 
						 | 
					@ -179,7 +198,7 @@ export default class GeoLocationHandler extends UIElement {
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
        if (this._previousLocationGrant.data === "granted") {
 | 
					        if (this._previousLocationGrant.data === "granted") {
 | 
				
			||||||
            this._previousLocationGrant.setData("");
 | 
					            this._previousLocationGrant.setData("");
 | 
				
			||||||
            self.StartGeolocating();
 | 
					            self.StartGeolocating(false);
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        this.HideOnEmpty(true);
 | 
					        this.HideOnEmpty(true);
 | 
				
			||||||
| 
						 | 
					@ -207,7 +226,7 @@ export default class GeoLocationHandler extends UIElement {
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    private StartGeolocating(zoomlevel = 19, zoomToGPS = true) {
 | 
					    private StartGeolocating(zoomToGPS = true) {
 | 
				
			||||||
        const self = this;
 | 
					        const self = this;
 | 
				
			||||||
        console.log("Starting geolocation")
 | 
					        console.log("Starting geolocation")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -217,9 +236,7 @@ export default class GeoLocationHandler extends UIElement {
 | 
				
			||||||
            return "";
 | 
					            return "";
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
        if (this._currentGPSLocation.data !== undefined) {
 | 
					        if (this._currentGPSLocation.data !== undefined) {
 | 
				
			||||||
            this._leafletMap.data.setView(
 | 
					            this._currentGPSLocation.ping()
 | 
				
			||||||
                this._currentGPSLocation.data.latlng, zoomlevel
 | 
					 | 
				
			||||||
            );
 | 
					 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue