| 
									
										
										
										
											2023-03-24 19:21:15 +01:00
										 |  |  | <script lang="ts"> | 
					
						
							| 
									
										
										
										
											2024-12-15 22:48:27 +01:00
										 |  |  |   import { ImmutableStore, Store, UIEventSource } from "../Logic/UIEventSource" | 
					
						
							| 
									
										
										
										
											2023-12-12 17:08:59 +01:00
										 |  |  |   import { Map as MlMap } from "maplibre-gl" | 
					
						
							|  |  |  |   import MaplibreMap from "./Map/MaplibreMap.svelte" | 
					
						
							|  |  |  |   import FeatureSwitchState from "../Logic/State/FeatureSwitchState" | 
					
						
							|  |  |  |   import MapControlButton from "./Base/MapControlButton.svelte" | 
					
						
							|  |  |  |   import ToSvelte from "./Base/ToSvelte.svelte" | 
					
						
							|  |  |  |   import If from "./Base/If.svelte" | 
					
						
							|  |  |  |   import type { Feature } from "geojson" | 
					
						
							|  |  |  |   import SelectedElementView from "./BigComponents/SelectedElementView.svelte" | 
					
						
							|  |  |  |   import LayerConfig from "../Models/ThemeConfig/LayerConfig" | 
					
						
							|  |  |  |   import ThemeViewState from "../Models/ThemeViewState" | 
					
						
							|  |  |  |   import type { MapProperties } from "../Models/MapProperties" | 
					
						
							|  |  |  |   import Translations from "./i18n/Translations" | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |   import { MenuIcon } from "@rgossiaux/svelte-heroicons/solid" | 
					
						
							| 
									
										
										
										
											2023-12-12 17:08:59 +01:00
										 |  |  |   import Tr from "./Base/Tr.svelte" | 
					
						
							|  |  |  |   import FloatOver from "./Base/FloatOver.svelte" | 
					
						
							|  |  |  |   import Constants from "../Models/Constants" | 
					
						
							|  |  |  |   import LoginToggle from "./Base/LoginToggle.svelte" | 
					
						
							|  |  |  |   import LevelSelector from "./BigComponents/LevelSelector.svelte" | 
					
						
							|  |  |  |   import type { RasterLayerPolygon } from "../Models/RasterLayers" | 
					
						
							|  |  |  |   import { AvailableRasterLayers } from "../Models/RasterLayers" | 
					
						
							|  |  |  |   import { onDestroy } from "svelte" | 
					
						
							|  |  |  |   import OpenBackgroundSelectorButton from "./BigComponents/OpenBackgroundSelectorButton.svelte" | 
					
						
							|  |  |  |   import StateIndicator from "./BigComponents/StateIndicator.svelte" | 
					
						
							|  |  |  |   import UploadingImageCounter from "./Image/UploadingImageCounter.svelte" | 
					
						
							|  |  |  |   import PendingChangesIndicator from "./BigComponents/PendingChangesIndicator.svelte" | 
					
						
							|  |  |  |   import Cross from "../assets/svg/Cross.svelte" | 
					
						
							|  |  |  |   import Min from "../assets/svg/Min.svelte" | 
					
						
							|  |  |  |   import Plus from "../assets/svg/Plus.svelte" | 
					
						
							|  |  |  |   import Filter from "../assets/svg/Filter.svelte" | 
					
						
							| 
									
										
										
										
											2023-12-15 01:46:01 +01:00
										 |  |  |   import VisualFeedbackPanel from "./BigComponents/VisualFeedbackPanel.svelte" | 
					
						
							| 
									
										
										
										
											2023-12-18 01:58:58 +01:00
										 |  |  |   import { Orientation } from "../Sensors/Orientation" | 
					
						
							| 
									
										
										
										
											2024-08-10 12:09:55 +02:00
										 |  |  |   import GeolocationIndicator from "./BigComponents/GeolocationIndicator.svelte" | 
					
						
							| 
									
										
										
										
											2023-12-18 01:30:02 +01:00
										 |  |  |   import Compass_arrow from "../assets/svg/Compass_arrow.svelte" | 
					
						
							| 
									
										
										
										
											2023-12-19 22:21:34 +01:00
										 |  |  |   import ReverseGeocoding from "./BigComponents/ReverseGeocoding.svelte" | 
					
						
							| 
									
										
										
										
											2023-12-20 02:50:08 +01:00
										 |  |  |   import { BBox } from "../Logic/BBox" | 
					
						
							| 
									
										
										
										
											2024-05-02 15:24:31 +02:00
										 |  |  |   import ExtraLinkButton from "./BigComponents/ExtraLinkButton.svelte" | 
					
						
							| 
									
										
										
										
											2024-06-19 01:56:19 +02:00
										 |  |  |   import Marker from "./Map/Marker.svelte" | 
					
						
							| 
									
										
										
										
											2024-07-22 17:24:30 +02:00
										 |  |  |   import SelectedElementPanel from "./Base/SelectedElementPanel.svelte" | 
					
						
							| 
									
										
										
										
											2024-08-29 02:46:51 +02:00
										 |  |  |   import MenuDrawer from "./BigComponents/MenuDrawer.svelte" | 
					
						
							|  |  |  |   import DrawerLeft from "./Base/DrawerLeft.svelte" | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |   import DrawerRight from "./Base/DrawerRight.svelte" | 
					
						
							|  |  |  |   import SearchResults from "./Search/SearchResults.svelte" | 
					
						
							| 
									
										
										
										
											2024-09-02 03:39:40 +02:00
										 |  |  |   import Hash from "../Logic/Web/Hash" | 
					
						
							| 
									
										
										
										
											2024-09-03 01:14:08 +02:00
										 |  |  |   import Searchbar from "./Base/Searchbar.svelte" | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |   import ChevronRight from "@babeard/svelte-heroicons/mini/ChevronRight" | 
					
						
							| 
									
										
										
										
											2024-09-04 01:08:14 +02:00
										 |  |  |   import { Drawer } from "flowbite-svelte" | 
					
						
							| 
									
										
										
										
											2024-09-16 15:12:05 +02:00
										 |  |  |   import { linear } from "svelte/easing" | 
					
						
							| 
									
										
										
										
											2023-12-05 18:35:18 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-12-12 17:08:59 +01:00
										 |  |  |   export let state: ThemeViewState | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-10-17 04:06:03 +02:00
										 |  |  |   let theme = state.theme | 
					
						
							| 
									
										
										
										
											2023-12-12 17:08:59 +01:00
										 |  |  |   let maplibremap: UIEventSource<MlMap> = state.map | 
					
						
							|  |  |  |   let selectedElement: UIEventSource<Feature> = new UIEventSource<Feature>(undefined) | 
					
						
							| 
									
										
										
										
											2023-12-16 01:29:42 +01:00
										 |  |  |   let compass = Orientation.singleton.alpha | 
					
						
							|  |  |  |   let compassLoaded = Orientation.singleton.gotMeasurement | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |   let hash = Hash.hash | 
					
						
							|  |  |  |   let addNewFeatureMode = state.userRelatedState.addNewFeatureMode | 
					
						
							|  |  |  |   let gpsAvailable = state.geolocation.geolocationState.gpsAvailable | 
					
						
							|  |  |  |   let gpsButtonAriaLabel = state.geolocation.geolocationState.gpsStateExplanation | 
					
						
							|  |  |  |   let debug = state.featureSwitches.featureSwitchIsDebugging | 
					
						
							|  |  |  |   let featureSwitches: FeatureSwitchState = state.featureSwitches | 
					
						
							| 
									
										
										
										
											2024-10-17 04:06:03 +02:00
										 |  |  |   let currentViewLayer: LayerConfig = theme.layers.find((l) => l.id === "current_view") | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |   let rasterLayer: Store<RasterLayerPolygon> = state.mapProperties.rasterLayer | 
					
						
							|  |  |  |   let currentZoom = state.mapProperties.zoom | 
					
						
							|  |  |  |   let showCrosshair = state.userRelatedState.showCrosshair | 
					
						
							|  |  |  |   let visualFeedback = state.visualFeedback | 
					
						
							|  |  |  |   let viewport: UIEventSource<HTMLDivElement> = new UIEventSource<HTMLDivElement>(undefined) | 
					
						
							|  |  |  |   let mapproperties: MapProperties = state.mapProperties | 
					
						
							|  |  |  |   let searchOpened = state.searchState.showSearchDrawer | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-12-16 01:42:45 +01:00
										 |  |  |   Orientation.singleton.startMeasurements() | 
					
						
							| 
									
										
										
										
											2023-12-19 23:02:02 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-09-04 01:50:34 +02:00
										 |  |  |   let slideDuration = 150 // ms | 
					
						
							|  |  |  |   state.selectedElement.addCallback((value) => { | 
					
						
							|  |  |  |     if (!value) { | 
					
						
							|  |  |  |       selectedElement.setData(undefined) | 
					
						
							| 
									
										
										
										
											2023-12-06 17:27:30 +01:00
										 |  |  |       return | 
					
						
							|  |  |  |     } | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |     if (!selectedElement.data) { | 
					
						
							| 
									
										
										
										
											2024-09-04 01:50:34 +02:00
										 |  |  |       // The store for this component doesn't have value right now, so we can simply set it | 
					
						
							|  |  |  |       selectedElement.set(value) | 
					
						
							|  |  |  |       return | 
					
						
							| 
									
										
										
										
											2023-12-06 17:27:30 +01:00
										 |  |  |     } | 
					
						
							| 
									
										
										
										
											2024-09-04 01:50:34 +02:00
										 |  |  |     // We first set the selected element to 'undefined' to force the popup to close... | 
					
						
							|  |  |  |     selectedElement.setData(undefined) | 
					
						
							|  |  |  |     // ... and we give svelte some time to update with requestAnimationFrame ... | 
					
						
							|  |  |  |     window.setTimeout(() => { | 
					
						
							|  |  |  |       window.requestAnimationFrame(() => { | 
					
						
							|  |  |  |         // ... and we force a fresh popup window | 
					
						
							|  |  |  |         selectedElement.setData(value) | 
					
						
							|  |  |  |       }) | 
					
						
							| 
									
										
										
										
											2024-11-05 00:25:40 +01:00
										 |  |  |     }, slideDuration * 2) | 
					
						
							| 
									
										
										
										
											2023-12-06 17:27:30 +01:00
										 |  |  |   }) | 
					
						
							| 
									
										
										
										
											2023-11-30 01:41:41 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |   state.mapProperties.installCustomKeyboardHandler(viewport) | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-11-18 21:38:30 +01:00
										 |  |  |   let selectedLayer: Store<LayerConfig> = selectedElement.mapD((element) => { | 
					
						
							| 
									
										
										
										
											2024-08-23 02:16:24 +02:00
										 |  |  |     if (element.properties.id.startsWith("current_view")) { | 
					
						
							| 
									
										
										
										
											2024-04-13 02:40:21 +02:00
										 |  |  |       return currentViewLayer | 
					
						
							| 
									
										
										
										
											2024-04-12 15:03:45 +02:00
										 |  |  |     } | 
					
						
							| 
									
										
										
										
											2024-08-23 02:16:24 +02:00
										 |  |  |     return state.getMatchingLayer(element.properties) | 
					
						
							| 
									
										
										
										
											2024-04-13 02:40:21 +02:00
										 |  |  |   }) | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-04-13 02:40:21 +02:00
										 |  |  |   let canZoomIn = mapproperties.maxzoom.map( | 
					
						
							|  |  |  |     (mz) => mapproperties.zoom.data < mz, | 
					
						
							| 
									
										
										
										
											2024-12-15 22:48:27 +01:00
										 |  |  |     [mapproperties.zoom], | 
					
						
							| 
									
										
										
										
											2024-04-13 02:40:21 +02:00
										 |  |  |   ) | 
					
						
							|  |  |  |   let canZoomOut = mapproperties.minzoom.map( | 
					
						
							|  |  |  |     (mz) => mapproperties.zoom.data > mz, | 
					
						
							| 
									
										
										
										
											2024-12-15 22:48:27 +01:00
										 |  |  |     [mapproperties.zoom], | 
					
						
							| 
									
										
										
										
											2024-04-13 02:40:21 +02:00
										 |  |  |   ) | 
					
						
							| 
									
										
										
										
											2024-04-12 15:03:45 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |   let rasterLayerName = | 
					
						
							|  |  |  |     rasterLayer.data?.properties?.name ?? | 
					
						
							|  |  |  |     AvailableRasterLayers.defaultBackgroundLayer.properties.name | 
					
						
							|  |  |  |   onDestroy( | 
					
						
							|  |  |  |     rasterLayer.addCallbackAndRunD((l) => { | 
					
						
							|  |  |  |       rasterLayerName = l.properties.name | 
					
						
							| 
									
										
										
										
											2024-12-15 22:48:27 +01:00
										 |  |  |     }), | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |   ) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   debug.addCallbackAndRun((dbg) => { | 
					
						
							|  |  |  |     if (dbg) { | 
					
						
							|  |  |  |       document.body.classList.add("debug") | 
					
						
							|  |  |  |     } else { | 
					
						
							|  |  |  |       document.body.classList.remove("debug") | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |   }) | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-12-21 17:36:43 +01:00
										 |  |  |   function updateViewport() { | 
					
						
							|  |  |  |     const rect = viewport.data?.getBoundingClientRect() | 
					
						
							|  |  |  |     if (!rect) { | 
					
						
							|  |  |  |       return | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     const mlmap = state.map.data | 
					
						
							|  |  |  |     if (!mlmap) { | 
					
						
							|  |  |  |       return undefined | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     const topLeft = mlmap.unproject([rect.left, rect.top]) | 
					
						
							|  |  |  |     const bottomRight = mlmap.unproject([rect.right, rect.bottom]) | 
					
						
							|  |  |  |     const bbox = new BBox([ | 
					
						
							|  |  |  |       [topLeft.lng, topLeft.lat], | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |       [bottomRight.lng, bottomRight.lat], | 
					
						
							| 
									
										
										
										
											2023-12-21 17:36:43 +01:00
										 |  |  |     ]) | 
					
						
							|  |  |  |     state.visualFeedbackViewportBounds.setData(bbox) | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-04-10 14:10:55 +02:00
										 |  |  |   viewport.addCallbackAndRunD(() => { | 
					
						
							| 
									
										
										
										
											2023-12-21 17:36:43 +01:00
										 |  |  |     updateViewport() | 
					
						
							|  |  |  |   }) | 
					
						
							| 
									
										
										
										
											2024-04-10 14:10:55 +02:00
										 |  |  |   mapproperties.bounds.addCallbackAndRunD(() => { | 
					
						
							| 
									
										
										
										
											2023-12-21 17:36:43 +01:00
										 |  |  |     updateViewport() | 
					
						
							| 
									
										
										
										
											2023-12-20 02:50:08 +01:00
										 |  |  |   }) | 
					
						
							| 
									
										
										
										
											2023-12-12 17:08:59 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  |   function forwardEventToMap(e: KeyboardEvent) { | 
					
						
							|  |  |  |     const mlmap = state.map.data | 
					
						
							| 
									
										
										
										
											2023-12-15 01:46:01 +01:00
										 |  |  |     if (!mlmap) { | 
					
						
							| 
									
										
										
										
											2023-12-12 17:08:59 +01:00
										 |  |  |       return | 
					
						
							|  |  |  |     } | 
					
						
							| 
									
										
										
										
											2023-12-15 01:46:01 +01:00
										 |  |  |     if (!mlmap.keyboard.isEnabled()) { | 
					
						
							| 
									
										
										
										
											2023-12-12 17:08:59 +01:00
										 |  |  |       return | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     const animation = mlmap.keyboard?.keydown(e) | 
					
						
							|  |  |  |     animation?.cameraAnimation(mlmap) | 
					
						
							|  |  |  |   } | 
					
						
							| 
									
										
										
										
											2024-12-15 22:48:27 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  |   let apiState = state?.osmConnection?.apiIsOnline ?? new ImmutableStore("online") | 
					
						
							| 
									
										
										
										
											2023-03-24 19:21:15 +01:00
										 |  |  | </script> | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-06-15 02:21:18 +02:00
										 |  |  | <main> | 
					
						
							| 
									
										
										
										
											2024-09-03 01:14:08 +02:00
										 |  |  |   <!-- Main map --> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |   <div class="absolute top-0 left-0 h-screen w-screen overflow-hidden"> | 
					
						
							| 
									
										
										
										
											2024-07-22 17:24:30 +02:00
										 |  |  |     <MaplibreMap map={maplibremap} mapProperties={mapproperties} autorecovery={true} /> | 
					
						
							| 
									
										
										
										
											2023-12-20 02:50:08 +01:00
										 |  |  |   </div> | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-12-15 22:48:27 +01:00
										 |  |  |   <LoginToggle ignoreLoading={true} silentFail {state}> | 
					
						
							| 
									
										
										
										
											2024-09-03 01:14:08 +02:00
										 |  |  |     {#if ($showCrosshair === "yes" && $currentZoom >= 17) || $showCrosshair === "always" || $visualFeedback} | 
					
						
							|  |  |  |       <!-- Don't use h-full: h-full does _not_ include the area under the URL-bar, which offsets the crosshair a bit --> | 
					
						
							|  |  |  |       <div | 
					
						
							|  |  |  |         class="pointer-events-none absolute top-0 left-0 flex w-full items-center justify-center" | 
					
						
							|  |  |  |         style="height: 100vh" | 
					
						
							|  |  |  |       > | 
					
						
							|  |  |  |         <Cross class="h-4 w-4" /> | 
					
						
							|  |  |  |       </div> | 
					
						
							|  |  |  |     {/if} | 
					
						
							|  |  |  |     <!-- Add in an empty container to remove error messages if login fails --> | 
					
						
							|  |  |  |     <svelte:fragment slot="error" /> | 
					
						
							|  |  |  |   </LoginToggle> | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |   {#if $visualFeedback} | 
					
						
							|  |  |  |     <div | 
					
						
							|  |  |  |       class="pointer-events-none absolute top-0 left-0 flex h-screen w-screen items-center justify-center overflow-hidden" | 
					
						
							| 
									
										
										
										
											2023-12-14 18:25:35 +01:00
										 |  |  |     > | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |       <div | 
					
						
							|  |  |  |         bind:this={$viewport} | 
					
						
							|  |  |  |         class:border={$visualFeedback} | 
					
						
							|  |  |  |         style="border: 2px solid #ff000044; width: 300px; height: 300px" | 
					
						
							|  |  |  |       /> | 
					
						
							|  |  |  |     </div> | 
					
						
							|  |  |  |   {/if} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-12-13 14:01:07 +01:00
										 |  |  |   <!-- bottom controls --> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |   <div class="pointer-events-none absolute bottom-0 left-0 mb-4 w-screen"> | 
					
						
							|  |  |  |     <div class="flex w-full items-end justify-between px-4"> | 
					
						
							|  |  |  |       <div class="flex flex-col"> | 
					
						
							|  |  |  |         <If condition={featureSwitches.featureSwitchEnableLogin}> | 
					
						
							| 
									
										
										
										
											2024-10-17 04:06:03 +02:00
										 |  |  |           {#if $addNewFeatureMode.indexOf("button") >= 0 && ((state.theme.hasPresets() && state.theme.enableAddNewPoints) || state.theme.hasNoteLayer())} | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |             <button | 
					
						
							|  |  |  |               class="low-interaction pointer-events-auto w-fit" | 
					
						
							|  |  |  |               class:disabled={$currentZoom < Constants.minZoomLevelToAddNewPoint} | 
					
						
							|  |  |  |               on:click={() => { | 
					
						
							|  |  |  |                 state.openNewDialog() | 
					
						
							|  |  |  |               }} | 
					
						
							|  |  |  |               on:keydown={forwardEventToMap} | 
					
						
							|  |  |  |             > | 
					
						
							|  |  |  |               {#if $currentZoom < Constants.minZoomLevelToAddNewPoint} | 
					
						
							|  |  |  |                 <Tr t={Translations.t.general.add.zoomInFurther} /> | 
					
						
							| 
									
										
										
										
											2024-10-17 04:06:03 +02:00
										 |  |  |               {:else if state.theme.hasPresets()} | 
					
						
							| 
									
										
										
										
											2024-12-15 22:48:27 +01:00
										 |  |  |                 ✨ | 
					
						
							|  |  |  |                 <Tr t={Translations.t.general.add.title} /> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |               {:else} | 
					
						
							| 
									
										
										
										
											2024-12-13 14:01:07 +01:00
										 |  |  |                 <Tr t={Translations.t.notes.createNote} /> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |               {/if} | 
					
						
							|  |  |  |             </button> | 
					
						
							|  |  |  |           {/if} | 
					
						
							|  |  |  |         </If> | 
					
						
							| 
									
										
										
										
											2023-06-15 16:12:46 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-06-17 04:27:08 +02:00
										 |  |  |         <div class="flex items-center"> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |           <!-- bottom left elements --> | 
					
						
							|  |  |  |           <If condition={state.featureSwitches.featureSwitchFilter}> | 
					
						
							|  |  |  |             <MapControlButton | 
					
						
							|  |  |  |               arialabel={Translations.t.general.labels.filter} | 
					
						
							|  |  |  |               on:click={() => state.guistate.openFilterView()} | 
					
						
							|  |  |  |               on:keydown={forwardEventToMap} | 
					
						
							|  |  |  |             > | 
					
						
							|  |  |  |               <Filter class="h-6 w-6" /> | 
					
						
							|  |  |  |             </MapControlButton> | 
					
						
							|  |  |  |           </If> | 
					
						
							|  |  |  |           <If condition={state.featureSwitches.featureSwitchBackgroundSelection}> | 
					
						
							| 
									
										
										
										
											2024-09-02 12:48:15 +02:00
										 |  |  |             <OpenBackgroundSelectorButton hideTooltip={true} {state} /> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |           </If> | 
					
						
							| 
									
										
										
										
											2024-08-29 02:46:51 +02:00
										 |  |  |           <button | 
					
						
							| 
									
										
										
										
											2024-08-29 12:16:35 +02:00
										 |  |  |             class="unstyled bg-black-transparent pointer-events-auto ml-1 h-fit max-h-12 cursor-pointer overflow-hidden rounded-2xl px-1 text-white opacity-50 hover:opacity-100" | 
					
						
							|  |  |  |             style="background: #00000088; padding: 0.25rem; border-radius: 2rem;" | 
					
						
							| 
									
										
										
										
											2024-09-02 12:48:15 +02:00
										 |  |  |             on:click={() => { | 
					
						
							|  |  |  |               state.guistate.pageStates.copyright.set(true) | 
					
						
							|  |  |  |             }} | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |           > | 
					
						
							| 
									
										
										
										
											2024-06-20 04:21:29 +02:00
										 |  |  |             © <span class="hidden sm:inline sm:pr-2"> | 
					
						
							|  |  |  |               OpenStreetMap | 
					
						
							|  |  |  |               <span class="hidden w-24 md:inline md:pr-2">, {rasterLayerName}</span> | 
					
						
							|  |  |  |             </span> | 
					
						
							| 
									
										
										
										
											2024-08-29 02:46:51 +02:00
										 |  |  |           </button> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |         </div> | 
					
						
							| 
									
										
										
										
											2023-06-15 16:12:46 +02:00
										 |  |  |       </div> | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |       <div class="flex flex-col items-end"> | 
					
						
							|  |  |  |         <!-- bottom right elements --> | 
					
						
							|  |  |  |         <If condition={state.floors.map((f) => f.length > 1)}> | 
					
						
							|  |  |  |           <div class="pointer-events-auto mr-0.5"> | 
					
						
							|  |  |  |             <LevelSelector | 
					
						
							|  |  |  |               floors={state.floors} | 
					
						
							|  |  |  |               layerState={state.layerState} | 
					
						
							|  |  |  |               zoom={state.mapProperties.zoom} | 
					
						
							|  |  |  |             /> | 
					
						
							|  |  |  |           </div> | 
					
						
							|  |  |  |         </If> | 
					
						
							|  |  |  |         <MapControlButton | 
					
						
							|  |  |  |           arialabel={Translations.t.general.labels.zoomIn} | 
					
						
							|  |  |  |           enabled={canZoomIn} | 
					
						
							|  |  |  |           on:click={() => mapproperties.zoom.update((z) => z + 1)} | 
					
						
							|  |  |  |           on:keydown={forwardEventToMap} | 
					
						
							|  |  |  |         > | 
					
						
							|  |  |  |           <Plus class="h-8 w-8" /> | 
					
						
							|  |  |  |         </MapControlButton> | 
					
						
							|  |  |  |         <MapControlButton | 
					
						
							|  |  |  |           enabled={canZoomOut} | 
					
						
							|  |  |  |           arialabel={Translations.t.general.labels.zoomOut} | 
					
						
							|  |  |  |           on:click={() => mapproperties.zoom.update((z) => z - 1)} | 
					
						
							|  |  |  |           on:keydown={forwardEventToMap} | 
					
						
							|  |  |  |         > | 
					
						
							|  |  |  |           <Min class="h-8 w-8" /> | 
					
						
							|  |  |  |         </MapControlButton> | 
					
						
							|  |  |  |         <If condition={featureSwitches.featureSwitchGeolocation}> | 
					
						
							|  |  |  |           <div class="relative m-0"> | 
					
						
							|  |  |  |             <MapControlButton | 
					
						
							| 
									
										
										
										
											2024-08-09 14:37:57 +02:00
										 |  |  |               enabled={gpsAvailable} | 
					
						
							| 
									
										
										
										
											2024-08-09 10:53:09 +02:00
										 |  |  |               arialabelDynamic={gpsButtonAriaLabel} | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |               on:click={() => state.geolocationControl.handleClick()} | 
					
						
							|  |  |  |               on:keydown={forwardEventToMap} | 
					
						
							|  |  |  |             > | 
					
						
							| 
									
										
										
										
											2024-08-10 12:09:55 +02:00
										 |  |  |               <GeolocationIndicator {state} /> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |               <!-- h-8 w-8 + p-0.5 sm:p-1 + 2px border => 9 sm: 10 in total--> | 
					
						
							|  |  |  |             </MapControlButton> | 
					
						
							|  |  |  |             {#if $compassLoaded} | 
					
						
							|  |  |  |               <div class="absolute top-0 left-0 m-0.5 h-0 w-0 sm:m-1"> | 
					
						
							|  |  |  |                 <Compass_arrow | 
					
						
							|  |  |  |                   class="compass_arrow" | 
					
						
							|  |  |  |                   style={`rotate: calc(${-$compass}deg + 45deg); transform-origin: 50% 50%;`} | 
					
						
							|  |  |  |                 /> | 
					
						
							|  |  |  |               </div> | 
					
						
							|  |  |  |             {/if} | 
					
						
							|  |  |  |           </div> | 
					
						
							|  |  |  |         </If> | 
					
						
							| 
									
										
										
										
											2024-09-12 01:53:47 +02:00
										 |  |  |         <If condition={state.mapProperties.showScale}> | 
					
						
							|  |  |  |           <div class="h-6"> | 
					
						
							|  |  |  |             <!-- Empty. We just provide some space for the maplibre scalecontrol --> | 
					
						
							|  |  |  |           </div> | 
					
						
							|  |  |  |         </If> | 
					
						
							| 
									
										
										
										
											2023-06-15 16:12:46 +02:00
										 |  |  |       </div> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |     </div> | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |   </div> | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-09-03 01:14:08 +02:00
										 |  |  |   <DrawerRight shown={state.searchState.showSearchDrawer}> | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |     <SearchResults {state} /> | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |   </DrawerRight> | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |   <!-- Top components --> | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |   <div class="z-4 pointer-events-none absolute top-0 left-0 w-full"> | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |     <div | 
					
						
							|  |  |  |       id="top-bar" | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |       class="bg-black-light-transparent pointer-events-auto flex flex-wrap items-center justify-between px-4 py-1" | 
					
						
							|  |  |  |     > | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |       <!-- Top bar with tools --> | 
					
						
							|  |  |  |       <div class="flex items-center"> | 
					
						
							|  |  |  |         <MapControlButton | 
					
						
							|  |  |  |           cls="m-0.5 p-0.5 sm:p-1" | 
					
						
							|  |  |  |           arialabel={Translations.t.general.labels.menu} | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |           on:click={() => { | 
					
						
							|  |  |  |             console.log("Opening....") | 
					
						
							|  |  |  |             state.guistate.pageStates.menu.setData(true) | 
					
						
							|  |  |  |           }} | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |           on:keydown={forwardEventToMap} | 
					
						
							|  |  |  |         > | 
					
						
							|  |  |  |           <MenuIcon class="h-6 w-6 cursor-pointer" /> | 
					
						
							|  |  |  |         </MapControlButton> | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         <MapControlButton | 
					
						
							|  |  |  |           on:click={() => state.guistate.pageStates.about_theme.set(true)} | 
					
						
							|  |  |  |           on:keydown={forwardEventToMap} | 
					
						
							|  |  |  |         > | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |           <div class="m-0.5 mx-1 mr-2 flex cursor-pointer items-center max-[480px]:w-full sm:mx-1"> | 
					
						
							| 
									
										
										
										
											2024-10-17 04:06:03 +02:00
										 |  |  |             <Marker icons={theme.icon} size="h-6 w-6 shrink-0 mr-0.5 sm:mr-1 md:mr-2" /> | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |             <b class="mr-1"> | 
					
						
							| 
									
										
										
										
											2024-10-17 04:06:03 +02:00
										 |  |  |               <Tr t={theme.title} /> | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |             </b> | 
					
						
							|  |  |  |           </div> | 
					
						
							|  |  |  |         </MapControlButton> | 
					
						
							|  |  |  |       </div> | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-09-03 01:14:08 +02:00
										 |  |  |       {#if $debug && $hash} | 
					
						
							|  |  |  |         <div class="alert"> | 
					
						
							|  |  |  |           {$hash} | 
					
						
							|  |  |  |         </div> | 
					
						
							|  |  |  |       {/if} | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |       <If condition={state.featureSwitches.featureSwitchSearch}> | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |         <div class="flex flex-grow items-center justify-end"> | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |           <div class="w-full sm:w-64"> | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |             <Searchbar | 
					
						
							|  |  |  |               value={state.searchState.searchTerm} | 
					
						
							|  |  |  |               isFocused={state.searchState.searchIsFocused} | 
					
						
							|  |  |  |             /> | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |           </div> | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |           <MapControlButton | 
					
						
							|  |  |  |             on:keydown={forwardEventToMap} | 
					
						
							|  |  |  |             on:click={() => { | 
					
						
							|  |  |  |               if (searchOpened.data) { | 
					
						
							|  |  |  |                 searchOpened.set(false) | 
					
						
							|  |  |  |               } else { | 
					
						
							|  |  |  |                 state.searchState.searchIsFocused.set(true) | 
					
						
							|  |  |  |               } | 
					
						
							|  |  |  |             }} | 
					
						
							|  |  |  |           > | 
					
						
							|  |  |  |             <ChevronRight | 
					
						
							|  |  |  |               class="m-0 h-7 w-7 p-0 transition-all" | 
					
						
							|  |  |  |               style={"rotate: " + ($searchOpened ? "0deg" : "180deg")} | 
					
						
							|  |  |  |             /> | 
					
						
							| 
									
										
										
										
											2024-09-05 02:25:03 +02:00
										 |  |  |           </MapControlButton> | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |         </div> | 
					
						
							|  |  |  |       </If> | 
					
						
							|  |  |  |     </div> | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     <div class="pointer-events-auto float-right mt-1 flex flex-col px-1 max-[480px]:w-full sm:m-2"> | 
					
						
							|  |  |  |       <If condition={state.visualFeedback}> | 
					
						
							|  |  |  |         {#if $selectedElement === undefined} | 
					
						
							|  |  |  |           <div class="w-fit"> | 
					
						
							|  |  |  |             <VisualFeedbackPanel {state} /> | 
					
						
							|  |  |  |           </div> | 
					
						
							|  |  |  |         {/if} | 
					
						
							|  |  |  |       </If> | 
					
						
							|  |  |  |     </div> | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-09-03 01:14:08 +02:00
										 |  |  |     <div class="float-left m-1 flex flex-col sm:mt-2"> | 
					
						
							|  |  |  |       <!-- Current view tools --> | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |       {#if currentViewLayer?.tagRenderings && currentViewLayer.defaultIcon()} | 
					
						
							|  |  |  |         <MapControlButton | 
					
						
							|  |  |  |           on:click={() => { | 
					
						
							|  |  |  |             state.selectCurrentView() | 
					
						
							|  |  |  |           }} | 
					
						
							|  |  |  |           on:keydown={forwardEventToMap} | 
					
						
							|  |  |  |         > | 
					
						
							|  |  |  |           <div class="h-8 w-8 cursor-pointer"> | 
					
						
							|  |  |  |             <ToSvelte construct={() => currentViewLayer.defaultIcon()} /> | 
					
						
							|  |  |  |           </div> | 
					
						
							|  |  |  |         </MapControlButton> | 
					
						
							|  |  |  |       {/if} | 
					
						
							| 
									
										
										
										
											2024-09-03 01:14:08 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |       <ExtraLinkButton {state} /> | 
					
						
							|  |  |  |       <UploadingImageCounter featureId="*" showThankYou={false} {state} /> | 
					
						
							|  |  |  |       <PendingChangesIndicator {state} /> | 
					
						
							|  |  |  |       <If condition={state.featureSwitchIsTesting}> | 
					
						
							|  |  |  |         <div class="alert w-fit">Testmode</div> | 
					
						
							|  |  |  |       </If> | 
					
						
							|  |  |  |       {#if state.osmConnection.Backend().startsWith("https://master.apis.dev.openstreetmap.org")} | 
					
						
							|  |  |  |         <div class="thanks">Testserver</div> | 
					
						
							|  |  |  |       {/if} | 
					
						
							|  |  |  |       <If condition={state.featureSwitches.featureSwitchFakeUser}> | 
					
						
							|  |  |  |         <div class="alert w-fit">Faking a user (Testmode)</div> | 
					
						
							|  |  |  |       </If> | 
					
						
							| 
									
										
										
										
											2024-12-15 22:48:27 +01:00
										 |  |  |       {#if $apiState !== "online"} | 
					
						
							|  |  |  |         <div class="alert w-fit">API is {$apiState}</div> | 
					
						
							|  |  |  |       {/if} | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |     </div> | 
					
						
							| 
									
										
										
										
											2024-09-03 01:14:08 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |     <div class="flex w-full flex-col items-center justify-center"> | 
					
						
							| 
									
										
										
										
											2024-08-30 02:18:29 +02:00
										 |  |  |       <!-- Flex and w-full are needed for the positioning --> | 
					
						
							|  |  |  |       <!-- Centermessage --> | 
					
						
							|  |  |  |       <StateIndicator {state} /> | 
					
						
							|  |  |  |       <ReverseGeocoding {state} /> | 
					
						
							|  |  |  |     </div> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |   </div> | 
					
						
							| 
									
										
										
										
											2023-06-15 16:12:46 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-12-15 22:48:27 +01:00
										 |  |  |   <div class="h-full overflow-hidden"> | 
					
						
							|  |  |  |     <DrawerLeft shown={state.guistate.pageStates.menu}> | 
					
						
							|  |  |  |       <div class="h-screen overflow-y-auto"> | 
					
						
							|  |  |  |         <MenuDrawer onlyLink={true} {state} /> | 
					
						
							|  |  |  |       </div> | 
					
						
							|  |  |  |     </DrawerLeft> | 
					
						
							|  |  |  |   </div> | 
					
						
							| 
									
										
										
										
											2024-08-29 02:46:51 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |   {#if $selectedElement !== undefined && $selectedLayer !== undefined && !$selectedLayer.popupInFloatover} | 
					
						
							|  |  |  |     <!-- right modal with the selected element view --> | 
					
						
							| 
									
										
										
										
											2024-09-04 01:08:14 +02:00
										 |  |  |     <Drawer | 
					
						
							|  |  |  |       placement="right" | 
					
						
							|  |  |  |       transitionType="fly" | 
					
						
							|  |  |  |       activateClickOutside={false} | 
					
						
							|  |  |  |       backdrop={false} | 
					
						
							|  |  |  |       id="drawer-right" | 
					
						
							|  |  |  |       width="w-full md:w-6/12 lg:w-5/12 xl:w-4/12" | 
					
						
							|  |  |  |       rightOffset="inset-y-0 right-0" | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |       transitionParams={{ | 
					
						
							|  |  |  |         x: 640, | 
					
						
							|  |  |  |         duration: slideDuration, | 
					
						
							|  |  |  |         easing: linear, | 
					
						
							|  |  |  |       }} | 
					
						
							| 
									
										
										
										
											2024-09-04 01:08:14 +02:00
										 |  |  |       divClass="overflow-y-auto z-50 " | 
					
						
							|  |  |  |       hidden={$selectedElement === undefined} | 
					
						
							| 
									
										
										
										
											2024-10-19 14:44:55 +02:00
										 |  |  |       on:close={() => { | 
					
						
							|  |  |  |         state.selectedElement.setData(undefined) | 
					
						
							|  |  |  |       }} | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |     > | 
					
						
							|  |  |  |       <div slot="close-button" /> | 
					
						
							| 
									
										
										
										
											2024-11-18 21:38:30 +01:00
										 |  |  |       <SelectedElementPanel {state} selected={$selectedElement} /> | 
					
						
							| 
									
										
										
										
											2024-09-04 01:08:14 +02:00
										 |  |  |     </Drawer> | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |   {/if} | 
					
						
							| 
									
										
										
										
											2023-06-15 16:12:46 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |   {#if $selectedElement !== undefined && $selectedLayer !== undefined && $selectedLayer.popupInFloatover} | 
					
						
							|  |  |  |     <!-- Floatover with the selected element, if applicable --> | 
					
						
							| 
									
										
										
										
											2024-07-22 17:24:30 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |     {#if $selectedLayer.popupInFloatover === "title"} | 
					
						
							|  |  |  |       <FloatOver | 
					
						
							|  |  |  |         on:close={() => { | 
					
						
							| 
									
										
										
										
											2024-08-09 16:55:08 +02:00
										 |  |  |           state.selectedElement.setData(undefined) | 
					
						
							|  |  |  |         }} | 
					
						
							| 
									
										
										
										
											2024-07-22 17:24:30 +02:00
										 |  |  |       > | 
					
						
							|  |  |  |         <span slot="close-button" /> | 
					
						
							| 
									
										
										
										
											2024-11-18 21:38:30 +01:00
										 |  |  |         <SelectedElementPanel absolute={false} {state} selected={$selectedElement} /> | 
					
						
							| 
									
										
										
										
											2024-07-22 17:24:30 +02:00
										 |  |  |       </FloatOver> | 
					
						
							|  |  |  |     {:else} | 
					
						
							|  |  |  |       <FloatOver | 
					
						
							|  |  |  |         on:close={() => { | 
					
						
							| 
									
										
										
										
											2024-08-09 16:55:08 +02:00
										 |  |  |           state.selectedElement.setData(undefined) | 
					
						
							|  |  |  |         }} | 
					
						
							| 
									
										
										
										
											2024-07-22 17:24:30 +02:00
										 |  |  |       > | 
					
						
							| 
									
										
										
										
											2024-11-28 12:00:23 +01:00
										 |  |  |         <SelectedElementView {state} layer={$selectedLayer} selectedElement={$selectedElement} /> | 
					
						
							| 
									
										
										
										
											2024-07-22 17:24:30 +02:00
										 |  |  |       </FloatOver> | 
					
						
							|  |  |  |     {/if} | 
					
						
							| 
									
										
										
										
											2024-06-16 16:41:57 +02:00
										 |  |  |   {/if} | 
					
						
							| 
									
										
										
										
											2023-06-15 16:12:46 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-09-16 15:12:05 +02:00
										 |  |  |   <MenuDrawer onlyLink={false} {state} /> | 
					
						
							| 
									
										
										
										
											2024-06-15 02:21:18 +02:00
										 |  |  | </main> |