forked from MapComplete/MapComplete
		
	Streamline download buttons
This commit is contained in:
		
							parent
							
								
									0c760c8458
								
							
						
					
					
						commit
						b5eb569802
					
				
					 10 changed files with 222 additions and 193 deletions
				
			
		| 
						 | 
					@ -10,7 +10,6 @@ import SimpleAddUI from "./UI/BigComponents/SimpleAddUI";
 | 
				
			||||||
import CenterMessageBox from "./UI/CenterMessageBox";
 | 
					import CenterMessageBox from "./UI/CenterMessageBox";
 | 
				
			||||||
import UserBadge from "./UI/BigComponents/UserBadge";
 | 
					import UserBadge from "./UI/BigComponents/UserBadge";
 | 
				
			||||||
import SearchAndGo from "./UI/BigComponents/SearchAndGo";
 | 
					import SearchAndGo from "./UI/BigComponents/SearchAndGo";
 | 
				
			||||||
import GeoLocationHandler from "./Logic/Actors/GeoLocationHandler";
 | 
					 | 
				
			||||||
import {LocalStorageSource} from "./Logic/Web/LocalStorageSource";
 | 
					import {LocalStorageSource} from "./Logic/Web/LocalStorageSource";
 | 
				
			||||||
import {Utils} from "./Utils";
 | 
					import {Utils} from "./Utils";
 | 
				
			||||||
import Svg from "./Svg";
 | 
					import Svg from "./Svg";
 | 
				
			||||||
| 
						 | 
					@ -23,26 +22,22 @@ import UserDetails from "./Logic/Osm/OsmConnection";
 | 
				
			||||||
import Attribution from "./UI/BigComponents/Attribution";
 | 
					import Attribution from "./UI/BigComponents/Attribution";
 | 
				
			||||||
import LayerResetter from "./Logic/Actors/LayerResetter";
 | 
					import LayerResetter from "./Logic/Actors/LayerResetter";
 | 
				
			||||||
import FullWelcomePaneWithTabs from "./UI/BigComponents/FullWelcomePaneWithTabs";
 | 
					import FullWelcomePaneWithTabs from "./UI/BigComponents/FullWelcomePaneWithTabs";
 | 
				
			||||||
import LayerControlPanel from "./UI/BigComponents/LayerControlPanel";
 | 
					 | 
				
			||||||
import ShowDataLayer from "./UI/ShowDataLayer";
 | 
					import ShowDataLayer from "./UI/ShowDataLayer";
 | 
				
			||||||
import Hash from "./Logic/Web/Hash";
 | 
					import Hash from "./Logic/Web/Hash";
 | 
				
			||||||
import FeaturePipeline from "./Logic/FeatureSource/FeaturePipeline";
 | 
					import FeaturePipeline from "./Logic/FeatureSource/FeaturePipeline";
 | 
				
			||||||
import ScrollableFullScreen from "./UI/Base/ScrollableFullScreen";
 | 
					import ScrollableFullScreen from "./UI/Base/ScrollableFullScreen";
 | 
				
			||||||
import Translations from "./UI/i18n/Translations";
 | 
					import Translations from "./UI/i18n/Translations";
 | 
				
			||||||
import MapControlButton from "./UI/MapControlButton";
 | 
					import MapControlButton from "./UI/MapControlButton";
 | 
				
			||||||
import Combine from "./UI/Base/Combine";
 | 
					 | 
				
			||||||
import SelectedFeatureHandler from "./Logic/Actors/SelectedFeatureHandler";
 | 
					import SelectedFeatureHandler from "./Logic/Actors/SelectedFeatureHandler";
 | 
				
			||||||
import LZString from "lz-string";
 | 
					import LZString from "lz-string";
 | 
				
			||||||
import {LayoutConfigJson} from "./Customizations/JSON/LayoutConfigJson";
 | 
					import {LayoutConfigJson} from "./Customizations/JSON/LayoutConfigJson";
 | 
				
			||||||
import AttributionPanel from "./UI/BigComponents/AttributionPanel";
 | 
					 | 
				
			||||||
import ContributorCount from "./Logic/ContributorCount";
 | 
					 | 
				
			||||||
import FeatureSource from "./Logic/FeatureSource/FeatureSource";
 | 
					import FeatureSource from "./Logic/FeatureSource/FeatureSource";
 | 
				
			||||||
import AllKnownLayers from "./Customizations/AllKnownLayers";
 | 
					import AllKnownLayers from "./Customizations/AllKnownLayers";
 | 
				
			||||||
import LayerConfig from "./Customizations/JSON/LayerConfig";
 | 
					import LayerConfig from "./Customizations/JSON/LayerConfig";
 | 
				
			||||||
import AvailableBaseLayers from "./Logic/Actors/AvailableBaseLayers";
 | 
					import AvailableBaseLayers from "./Logic/Actors/AvailableBaseLayers";
 | 
				
			||||||
import {TagsFilter} from "./Logic/Tags/TagsFilter";
 | 
					import {TagsFilter} from "./Logic/Tags/TagsFilter";
 | 
				
			||||||
import FilterView from "./UI/BigComponents/FilterView";
 | 
					import LeftControls from "./UI/BigComponents/LeftControls";
 | 
				
			||||||
import ExportPDF from "./UI/ExportPDF";
 | 
					import RightControls from "./UI/BigComponents/RightControls";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export class InitUiElements {
 | 
					export class InitUiElements {
 | 
				
			||||||
    static InitAll(
 | 
					    static InitAll(
 | 
				
			||||||
| 
						 | 
					@ -191,42 +186,11 @@ export class InitUiElements {
 | 
				
			||||||
                marker.addTo(State.state.leafletMap.data);
 | 
					                marker.addTo(State.state.leafletMap.data);
 | 
				
			||||||
            });
 | 
					            });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        const geolocationButton = new Toggle(
 | 
					 | 
				
			||||||
            new MapControlButton(
 | 
					 | 
				
			||||||
                new GeoLocationHandler(
 | 
					 | 
				
			||||||
                    State.state.currentGPSLocation,
 | 
					 | 
				
			||||||
                    State.state.leafletMap,
 | 
					 | 
				
			||||||
                    State.state.layoutToUse
 | 
					 | 
				
			||||||
                ), {
 | 
					 | 
				
			||||||
                    dontStyle: true
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
            ),
 | 
					 | 
				
			||||||
            undefined,
 | 
					 | 
				
			||||||
            State.state.featureSwitchGeolocation
 | 
					 | 
				
			||||||
        );
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const plus = new MapControlButton(
 | 
					 | 
				
			||||||
            Svg.plus_zoom_svg()
 | 
					 | 
				
			||||||
        ).onClick(() => {
 | 
					 | 
				
			||||||
            State.state.locationControl.data.zoom++;
 | 
					 | 
				
			||||||
            State.state.locationControl.ping();
 | 
					 | 
				
			||||||
        });
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const min = new MapControlButton(
 | 
					 | 
				
			||||||
            Svg.min_zoom_svg()
 | 
					 | 
				
			||||||
        ).onClick(() => {
 | 
					 | 
				
			||||||
            State.state.locationControl.data.zoom--;
 | 
					 | 
				
			||||||
            State.state.locationControl.ping();
 | 
					 | 
				
			||||||
        });
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        new Combine([plus, min, geolocationButton].map(el => el.SetClass("m-0.5 md:m-1")))
 | 
					 | 
				
			||||||
            .SetClass("flex flex-col")
 | 
					 | 
				
			||||||
            .AttachTo("bottom-right");
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
        if (layoutToUse.id === personal.id) {
 | 
					        if (layoutToUse.id === personal.id) {
 | 
				
			||||||
            updateFavs();
 | 
					            updateFavs();
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        InitUiElements.setupAllLayerElements();
 | 
					        InitUiElements.setupAllLayerElements();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        if (layoutToUse.id === personal.id) {
 | 
					        if (layoutToUse.id === personal.id) {
 | 
				
			||||||
| 
						 | 
					@ -331,105 +295,6 @@ export class InitUiElements {
 | 
				
			||||||
        );
 | 
					        );
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    private static InitLayerSelection(featureSource: FeatureSource) {
 | 
					 | 
				
			||||||
        const copyrightNotice = new ScrollableFullScreen(
 | 
					 | 
				
			||||||
            () => Translations.t.general.attribution.attributionTitle.Clone(),
 | 
					 | 
				
			||||||
            () =>
 | 
					 | 
				
			||||||
                new AttributionPanel(
 | 
					 | 
				
			||||||
                    State.state.layoutToUse,
 | 
					 | 
				
			||||||
                    new ContributorCount(featureSource).Contributors
 | 
					 | 
				
			||||||
                ),
 | 
					 | 
				
			||||||
            "copyright"
 | 
					 | 
				
			||||||
        );
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const copyrightButton = new Toggle(
 | 
					 | 
				
			||||||
            copyrightNotice,
 | 
					 | 
				
			||||||
            new MapControlButton(Svg.copyright_svg()),
 | 
					 | 
				
			||||||
            copyrightNotice.isShown
 | 
					 | 
				
			||||||
        )
 | 
					 | 
				
			||||||
            .ToggleOnClick()
 | 
					 | 
				
			||||||
            .SetClass("p-0.5");
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const layerControlPanel = new LayerControlPanel(
 | 
					 | 
				
			||||||
            State.state.layerControlIsOpened
 | 
					 | 
				
			||||||
        ).SetClass("block p-1 rounded-full");
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const layerControlButton = new Toggle(
 | 
					 | 
				
			||||||
            layerControlPanel,
 | 
					 | 
				
			||||||
            new MapControlButton(Svg.layers_svg()),
 | 
					 | 
				
			||||||
            State.state.layerControlIsOpened
 | 
					 | 
				
			||||||
        ).ToggleOnClick();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const layerControl = new Toggle(
 | 
					 | 
				
			||||||
            layerControlButton,
 | 
					 | 
				
			||||||
            "",
 | 
					 | 
				
			||||||
            State.state.featureSwitchLayers
 | 
					 | 
				
			||||||
        );
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const filterView =
 | 
					 | 
				
			||||||
            new ScrollableFullScreen(
 | 
					 | 
				
			||||||
                () => Translations.t.general.layerSelection.title.Clone(),
 | 
					 | 
				
			||||||
                () =>
 | 
					 | 
				
			||||||
                    new FilterView(State.state.filteredLayers).SetClass(
 | 
					 | 
				
			||||||
                        "block p-1 rounded-full"
 | 
					 | 
				
			||||||
                    ),
 | 
					 | 
				
			||||||
                undefined,
 | 
					 | 
				
			||||||
                State.state.filterIsOpened
 | 
					 | 
				
			||||||
            );
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const filterMapControlButton = new MapControlButton(
 | 
					 | 
				
			||||||
            Svg.filter_svg()
 | 
					 | 
				
			||||||
        );
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const filterButton = new Toggle(
 | 
					 | 
				
			||||||
            filterView,
 | 
					 | 
				
			||||||
            filterMapControlButton,
 | 
					 | 
				
			||||||
            State.state.filterIsOpened
 | 
					 | 
				
			||||||
        ).ToggleOnClick();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const filterControl = new Toggle(
 | 
					 | 
				
			||||||
            filterButton,
 | 
					 | 
				
			||||||
            undefined,
 | 
					 | 
				
			||||||
            State.state.featureSwitchFilter
 | 
					 | 
				
			||||||
        );
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const screenshot =
 | 
					 | 
				
			||||||
            new Toggle(
 | 
					 | 
				
			||||||
                new MapControlButton(
 | 
					 | 
				
			||||||
                    Svg.download_svg(),
 | 
					 | 
				
			||||||
                ).onClick(() => {
 | 
					 | 
				
			||||||
                    // Will already export
 | 
					 | 
				
			||||||
                    new ExportPDF(
 | 
					 | 
				
			||||||
                        {
 | 
					 | 
				
			||||||
                            freeDivId: "belowmap",
 | 
					 | 
				
			||||||
                            background: State.state.backgroundLayer,
 | 
					 | 
				
			||||||
                            location: State.state.locationControl,
 | 
					 | 
				
			||||||
                            features: State.state.featurePipeline.features,
 | 
					 | 
				
			||||||
                            layout: State.state.layoutToUse,
 | 
					 | 
				
			||||||
                        }
 | 
					 | 
				
			||||||
                    );
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
                }), undefined, State.state.featureSwitchExportAsPdf)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        new Combine([filterControl, layerControl, screenshot, copyrightButton,])
 | 
					 | 
				
			||||||
            .SetClass("flex flex-col")
 | 
					 | 
				
			||||||
            .AttachTo("bottom-left");
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        State.state.locationControl.addCallback(() => {
 | 
					 | 
				
			||||||
            // Close the layer selection when the map is moved
 | 
					 | 
				
			||||||
            layerControlButton.isEnabled.setData(false);
 | 
					 | 
				
			||||||
            copyrightButton.isEnabled.setData(false);
 | 
					 | 
				
			||||||
        });
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        State.state.selectedElement.addCallbackAndRunD((_) => {
 | 
					 | 
				
			||||||
            layerControlButton.isEnabled.setData(false);
 | 
					 | 
				
			||||||
            copyrightButton.isEnabled.setData(false);
 | 
					 | 
				
			||||||
        });
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    private static InitBaseMap() {
 | 
					    private static InitBaseMap() {
 | 
				
			||||||
        State.state.availableBackgroundLayers =
 | 
					        State.state.availableBackgroundLayers =
 | 
				
			||||||
            AvailableBaseLayers.AvailableLayersAt(State.state.locationControl);
 | 
					            AvailableBaseLayers.AvailableLayersAt(State.state.locationControl);
 | 
				
			||||||
| 
						 | 
					@ -561,7 +426,9 @@ export class InitUiElements {
 | 
				
			||||||
        // ------------- Setup the layers -------------------------------
 | 
					        // ------------- Setup the layers -------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        const source = InitUiElements.InitLayers();
 | 
					        const source = InitUiElements.InitLayers();
 | 
				
			||||||
        InitUiElements.InitLayerSelection(source);
 | 
					
 | 
				
			||||||
 | 
					        new LeftControls(source).AttachTo("bottom-left");
 | 
				
			||||||
 | 
					        new RightControls().AttachTo("bottom-right");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        // ------------------ Setup various other UI elements ------------
 | 
					        // ------------------ Setup various other UI elements ------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										17
									
								
								State.ts
									
										
									
									
									
								
							
							
						
						
									
										17
									
								
								State.ts
									
										
									
									
									
								
							| 
						 | 
					@ -79,7 +79,7 @@ export default class State {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    public readonly featureSwitchUserbadge: UIEventSource<boolean>;
 | 
					    public readonly featureSwitchUserbadge: UIEventSource<boolean>;
 | 
				
			||||||
    public readonly featureSwitchSearch: UIEventSource<boolean>;
 | 
					    public readonly featureSwitchSearch: UIEventSource<boolean>;
 | 
				
			||||||
    public readonly featureSwitchLayers: UIEventSource<boolean>;
 | 
					    public readonly featureSwitchBackgroundSlection: UIEventSource<boolean>;
 | 
				
			||||||
    public readonly featureSwitchAddNew: UIEventSource<boolean>;
 | 
					    public readonly featureSwitchAddNew: UIEventSource<boolean>;
 | 
				
			||||||
    public readonly featureSwitchWelcomeMessage: UIEventSource<boolean>;
 | 
					    public readonly featureSwitchWelcomeMessage: UIEventSource<boolean>;
 | 
				
			||||||
    public readonly featureSwitchIframe: UIEventSource<boolean>;
 | 
					    public readonly featureSwitchIframe: UIEventSource<boolean>;
 | 
				
			||||||
| 
						 | 
					@ -125,11 +125,11 @@ export default class State {
 | 
				
			||||||
    public layoutDefinition: string;
 | 
					    public layoutDefinition: string;
 | 
				
			||||||
    public installedThemes: UIEventSource<{ layout: LayoutConfig; definition: string }[]>;
 | 
					    public installedThemes: UIEventSource<{ layout: LayoutConfig; definition: string }[]>;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    public layerControlIsOpened: UIEventSource<boolean> =
 | 
					    public downloadControlIsOpened: UIEventSource<boolean> =
 | 
				
			||||||
        QueryParameters.GetQueryParameter(
 | 
					        QueryParameters.GetQueryParameter(
 | 
				
			||||||
            "layer-control-toggle",
 | 
					            "download-control-toggle",
 | 
				
			||||||
            "false",
 | 
					            "false",
 | 
				
			||||||
            "Whether or not the layer control is shown"
 | 
					            "Whether or not the download panel is shown"
 | 
				
			||||||
        ).map<boolean>(
 | 
					        ).map<boolean>(
 | 
				
			||||||
            (str) => str !== "false",
 | 
					            (str) => str !== "false",
 | 
				
			||||||
            [],
 | 
					            [],
 | 
				
			||||||
| 
						 | 
					@ -249,11 +249,12 @@ export default class State {
 | 
				
			||||||
                (layoutToUse) => layoutToUse?.enableSearch ?? true,
 | 
					                (layoutToUse) => layoutToUse?.enableSearch ?? true,
 | 
				
			||||||
                "Disables/Enables the search bar"
 | 
					                "Disables/Enables the search bar"
 | 
				
			||||||
            );
 | 
					            );
 | 
				
			||||||
            this.featureSwitchLayers = featSw(
 | 
					            this.featureSwitchBackgroundSlection = featSw(
 | 
				
			||||||
                "fs-layers",
 | 
					                "fs-background",
 | 
				
			||||||
                (layoutToUse) => layoutToUse?.enableLayers ?? true,
 | 
					                (layoutToUse) => layoutToUse?.enableBackgroundLayerSelection ?? true,
 | 
				
			||||||
                "Disables/Enables the layer control"
 | 
					                "Disables/Enables the background layer control"
 | 
				
			||||||
            );
 | 
					            );
 | 
				
			||||||
 | 
					            
 | 
				
			||||||
            this.featureSwitchFilter = featSw(
 | 
					            this.featureSwitchFilter = featSw(
 | 
				
			||||||
                "fs-filter",
 | 
					                "fs-filter",
 | 
				
			||||||
                (layoutToUse) => layoutToUse?.enableLayers ?? true,
 | 
					                (layoutToUse) => layoutToUse?.enableLayers ?? true,
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										53
									
								
								UI/BigComponents/AllDownloads.ts
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										53
									
								
								UI/BigComponents/AllDownloads.ts
									
										
									
									
									
										Normal file
									
								
							| 
						 | 
					@ -0,0 +1,53 @@
 | 
				
			||||||
 | 
					import State from "../../State";
 | 
				
			||||||
 | 
					import Combine from "../Base/Combine";
 | 
				
			||||||
 | 
					import ScrollableFullScreen from "../Base/ScrollableFullScreen";
 | 
				
			||||||
 | 
					import Translations from "../i18n/Translations";
 | 
				
			||||||
 | 
					import {UIEventSource} from "../../Logic/UIEventSource";
 | 
				
			||||||
 | 
					import BaseUIElement from "../BaseUIElement";
 | 
				
			||||||
 | 
					import Toggle from "../Input/Toggle";
 | 
				
			||||||
 | 
					import {DownloadPanel} from "./DownloadPanel";
 | 
				
			||||||
 | 
					import {SubtleButton} from "../Base/SubtleButton";
 | 
				
			||||||
 | 
					import Svg from "../../Svg";
 | 
				
			||||||
 | 
					import ExportPDF from "../ExportPDF";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export default class AllDownloads extends ScrollableFullScreen {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    constructor(isShown: UIEventSource<boolean>) {
 | 
				
			||||||
 | 
					        super(AllDownloads.GenTitle, AllDownloads.GeneratePanel, "layers", isShown);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    private static GenTitle(): BaseUIElement {
 | 
				
			||||||
 | 
					        return Translations.t.general.download.title
 | 
				
			||||||
 | 
					            .Clone()
 | 
				
			||||||
 | 
					            .SetClass("text-2xl break-words font-bold p-2");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    private static GeneratePanel(): BaseUIElement {
 | 
				
			||||||
 | 
					        const generatePdf = () => {
 | 
				
			||||||
 | 
					            new ExportPDF(
 | 
				
			||||||
 | 
					                {
 | 
				
			||||||
 | 
					                    freeDivId: "belowmap",
 | 
				
			||||||
 | 
					                    background: State.state.backgroundLayer,
 | 
				
			||||||
 | 
					                    location: State.state.locationControl,
 | 
				
			||||||
 | 
					                    features: State.state.featurePipeline.features,
 | 
				
			||||||
 | 
					                    layout: State.state.layoutToUse,
 | 
				
			||||||
 | 
					                })
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        const pdf = new Toggle(
 | 
				
			||||||
 | 
					            new SubtleButton(Svg.floppy_ui(), Translations.t.general.download.downloadAsPdf.Clone().SetClass("font-bold"),)
 | 
				
			||||||
 | 
					                .onClick(generatePdf),
 | 
				
			||||||
 | 
					            undefined,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					            State.state.featureSwitchExportAsPdf
 | 
				
			||||||
 | 
					        )
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					       const exportPanel = new Toggle(
 | 
				
			||||||
 | 
					            new DownloadPanel(),
 | 
				
			||||||
 | 
					            undefined,
 | 
				
			||||||
 | 
					            State.state.featureSwitchEnableExport
 | 
				
			||||||
 | 
					        )
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        return new Combine([pdf, exportPanel]).SetClass("flex flex-col");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -15,6 +15,7 @@ import {UIEventSource} from "../../Logic/UIEventSource";
 | 
				
			||||||
import BaseUIElement from "../BaseUIElement";
 | 
					import BaseUIElement from "../BaseUIElement";
 | 
				
			||||||
import State from "../../State";
 | 
					import State from "../../State";
 | 
				
			||||||
import FilteredLayer from "../../Models/FilteredLayer";
 | 
					import FilteredLayer from "../../Models/FilteredLayer";
 | 
				
			||||||
 | 
					import BackgroundSelector from "./BackgroundSelector";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/**
 | 
					/**
 | 
				
			||||||
| 
						 | 
					@ -23,9 +24,14 @@ import FilteredLayer from "../../Models/FilteredLayer";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export default class FilterView extends VariableUiElement {
 | 
					export default class FilterView extends VariableUiElement {
 | 
				
			||||||
    constructor(filteredLayer: UIEventSource<FilteredLayer[]>) {
 | 
					    constructor(filteredLayer: UIEventSource<FilteredLayer[]>) {
 | 
				
			||||||
 | 
					        const backgroundSelector =  new Toggle(
 | 
				
			||||||
 | 
					            new BackgroundSelector(),
 | 
				
			||||||
 | 
					            undefined,
 | 
				
			||||||
 | 
					            State.state.featureSwitchBackgroundSlection
 | 
				
			||||||
 | 
					        )
 | 
				
			||||||
        super(
 | 
					        super(
 | 
				
			||||||
            filteredLayer.map((filteredLayers) =>
 | 
					            filteredLayer.map((filteredLayers) =>
 | 
				
			||||||
                filteredLayers?.map(l => FilterView.createOneFilteredLayerElement(l))
 | 
					                filteredLayers?.map(l => FilterView.createOneFilteredLayerElement(l)).concat(backgroundSelector)
 | 
				
			||||||
            )
 | 
					            )
 | 
				
			||||||
        );
 | 
					        );
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -1,42 +0,0 @@
 | 
				
			||||||
import State from "../../State";
 | 
					 | 
				
			||||||
import BackgroundSelector from "./BackgroundSelector";
 | 
					 | 
				
			||||||
import Combine from "../Base/Combine";
 | 
					 | 
				
			||||||
import ScrollableFullScreen from "../Base/ScrollableFullScreen";
 | 
					 | 
				
			||||||
import Translations from "../i18n/Translations";
 | 
					 | 
				
			||||||
import {UIEventSource} from "../../Logic/UIEventSource";
 | 
					 | 
				
			||||||
import BaseUIElement from "../BaseUIElement";
 | 
					 | 
				
			||||||
import Toggle from "../Input/Toggle";
 | 
					 | 
				
			||||||
import {DownloadPanel} from "./DownloadPanel";
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
export default class LayerControlPanel extends ScrollableFullScreen {
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    constructor(isShown: UIEventSource<boolean>) {
 | 
					 | 
				
			||||||
        super(LayerControlPanel.GenTitle, LayerControlPanel.GeneratePanel, "layers", isShown);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    private static GenTitle(): BaseUIElement {
 | 
					 | 
				
			||||||
        return Translations.t.general.layerSelection.title
 | 
					 | 
				
			||||||
            .Clone()
 | 
					 | 
				
			||||||
            .SetClass("text-2xl break-words font-bold p-2");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    private static GeneratePanel(): BaseUIElement {
 | 
					 | 
				
			||||||
        const elements: BaseUIElement[] = [];
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        if (State.state.layoutToUse.data.enableBackgroundLayerSelection) {
 | 
					 | 
				
			||||||
            const backgroundSelector = new BackgroundSelector();
 | 
					 | 
				
			||||||
            backgroundSelector.SetStyle("margin:1em");
 | 
					 | 
				
			||||||
            backgroundSelector.onClick(() => {
 | 
					 | 
				
			||||||
            });
 | 
					 | 
				
			||||||
            elements.push(backgroundSelector)
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        elements.push(new Toggle(
 | 
					 | 
				
			||||||
            new DownloadPanel(),
 | 
					 | 
				
			||||||
            undefined,
 | 
					 | 
				
			||||||
            State.state.featureSwitchEnableExport
 | 
					 | 
				
			||||||
        ))
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        return new Combine(elements).SetClass("flex flex-col");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
							
								
								
									
										94
									
								
								UI/BigComponents/LeftControls.ts
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										94
									
								
								UI/BigComponents/LeftControls.ts
									
										
									
									
									
										Normal file
									
								
							| 
						 | 
					@ -0,0 +1,94 @@
 | 
				
			||||||
 | 
					import Combine from "../Base/Combine";
 | 
				
			||||||
 | 
					import ScrollableFullScreen from "../Base/ScrollableFullScreen";
 | 
				
			||||||
 | 
					import Translations from "../i18n/Translations";
 | 
				
			||||||
 | 
					import AttributionPanel from "./AttributionPanel";
 | 
				
			||||||
 | 
					import State from "../../State";
 | 
				
			||||||
 | 
					import ContributorCount from "../../Logic/ContributorCount";
 | 
				
			||||||
 | 
					import Toggle from "../Input/Toggle";
 | 
				
			||||||
 | 
					import MapControlButton from "../MapControlButton";
 | 
				
			||||||
 | 
					import Svg from "../../Svg";
 | 
				
			||||||
 | 
					import AllDownloads from "./AllDownloads";
 | 
				
			||||||
 | 
					import FilterView from "./FilterView";
 | 
				
			||||||
 | 
					import FeatureSource from "../../Logic/FeatureSource/FeatureSource";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export default class LeftControls extends Combine {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    constructor(featureSource: FeatureSource) {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        const toggledCopyright = new ScrollableFullScreen(
 | 
				
			||||||
 | 
					            () => Translations.t.general.attribution.attributionTitle.Clone(),
 | 
				
			||||||
 | 
					            () =>
 | 
				
			||||||
 | 
					                new AttributionPanel(
 | 
				
			||||||
 | 
					                    State.state.layoutToUse,
 | 
				
			||||||
 | 
					                    new ContributorCount(featureSource).Contributors
 | 
				
			||||||
 | 
					                ),
 | 
				
			||||||
 | 
					            undefined
 | 
				
			||||||
 | 
					        );
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					        const copyrightButton = new Toggle(
 | 
				
			||||||
 | 
					            toggledCopyright,
 | 
				
			||||||
 | 
					            new MapControlButton(Svg.copyright_svg()),
 | 
				
			||||||
 | 
					            toggledCopyright.isShown
 | 
				
			||||||
 | 
					        )
 | 
				
			||||||
 | 
					            .ToggleOnClick()
 | 
				
			||||||
 | 
					            .SetClass("p-0.5");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        const toggledDownload = new Toggle(
 | 
				
			||||||
 | 
					            new AllDownloads(
 | 
				
			||||||
 | 
					                State.state.downloadControlIsOpened
 | 
				
			||||||
 | 
					            ).SetClass("block p-1 rounded-full"),
 | 
				
			||||||
 | 
					            new MapControlButton(Svg.download_svg()),
 | 
				
			||||||
 | 
					            State.state.downloadControlIsOpened
 | 
				
			||||||
 | 
					        ).ToggleOnClick();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        const downloadButtonn = new Toggle(
 | 
				
			||||||
 | 
					            toggledDownload,
 | 
				
			||||||
 | 
					            undefined,
 | 
				
			||||||
 | 
					            State.state.featureSwitchEnableExport.map(downloadEnabled => downloadEnabled || State.state.featureSwitchExportAsPdf.data,
 | 
				
			||||||
 | 
					                [State.state.featureSwitchExportAsPdf])
 | 
				
			||||||
 | 
					        );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        const toggledFilter = new Toggle(
 | 
				
			||||||
 | 
					            new ScrollableFullScreen(
 | 
				
			||||||
 | 
					                () => Translations.t.general.layerSelection.title.Clone(),
 | 
				
			||||||
 | 
					                () =>
 | 
				
			||||||
 | 
					                    new FilterView(State.state.filteredLayers).SetClass(
 | 
				
			||||||
 | 
					                        "block p-1 rounded-full"
 | 
				
			||||||
 | 
					                    ),
 | 
				
			||||||
 | 
					                undefined,
 | 
				
			||||||
 | 
					                State.state.filterIsOpened
 | 
				
			||||||
 | 
					            ),
 | 
				
			||||||
 | 
					            new MapControlButton(Svg.filter_svg()),
 | 
				
			||||||
 | 
					            State.state.filterIsOpened
 | 
				
			||||||
 | 
					        ).ToggleOnClick();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        const filterButton = new Toggle(
 | 
				
			||||||
 | 
					            toggledFilter,
 | 
				
			||||||
 | 
					            undefined,
 | 
				
			||||||
 | 
					            State.state.featureSwitchFilter
 | 
				
			||||||
 | 
					        );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        State.state.locationControl.addCallback(() => {
 | 
				
			||||||
 | 
					            // Close the layer selection when the map is moved
 | 
				
			||||||
 | 
					            toggledDownload.isEnabled.setData(false);
 | 
				
			||||||
 | 
					            copyrightButton.isEnabled.setData(false);
 | 
				
			||||||
 | 
					            toggledFilter.isEnabled.setData(false);
 | 
				
			||||||
 | 
					        });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        State.state.selectedElement.addCallbackAndRunD((_) => {
 | 
				
			||||||
 | 
					            toggledDownload.isEnabled.setData(false);
 | 
				
			||||||
 | 
					            copyrightButton.isEnabled.setData(false);
 | 
				
			||||||
 | 
					            toggledFilter.isEnabled.setData(false);
 | 
				
			||||||
 | 
					        });
 | 
				
			||||||
 | 
					        super([filterButton,
 | 
				
			||||||
 | 
					            downloadButtonn,
 | 
				
			||||||
 | 
					            copyrightButton])
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					        this.SetClass("flex flex-col")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
							
								
								
									
										43
									
								
								UI/BigComponents/RightControls.ts
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										43
									
								
								UI/BigComponents/RightControls.ts
									
										
									
									
									
										Normal file
									
								
							| 
						 | 
					@ -0,0 +1,43 @@
 | 
				
			||||||
 | 
					import Combine from "../Base/Combine";
 | 
				
			||||||
 | 
					import Toggle from "../Input/Toggle";
 | 
				
			||||||
 | 
					import MapControlButton from "../MapControlButton";
 | 
				
			||||||
 | 
					import GeoLocationHandler from "../../Logic/Actors/GeoLocationHandler";
 | 
				
			||||||
 | 
					import State from "../../State";
 | 
				
			||||||
 | 
					import Svg from "../../Svg";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export default class RightControls extends Combine {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    constructor() {
 | 
				
			||||||
 | 
					        const geolocationButton = new Toggle(
 | 
				
			||||||
 | 
					            new MapControlButton(
 | 
				
			||||||
 | 
					                new GeoLocationHandler(
 | 
				
			||||||
 | 
					                    State.state.currentGPSLocation,
 | 
				
			||||||
 | 
					                    State.state.leafletMap,
 | 
				
			||||||
 | 
					                    State.state.layoutToUse
 | 
				
			||||||
 | 
					                ), {
 | 
				
			||||||
 | 
					                    dontStyle: true
 | 
				
			||||||
 | 
					                }
 | 
				
			||||||
 | 
					            ),
 | 
				
			||||||
 | 
					            undefined,
 | 
				
			||||||
 | 
					            State.state.featureSwitchGeolocation
 | 
				
			||||||
 | 
					        );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        const plus = new MapControlButton(
 | 
				
			||||||
 | 
					            Svg.plus_zoom_svg()
 | 
				
			||||||
 | 
					        ).onClick(() => {
 | 
				
			||||||
 | 
					            State.state.locationControl.data.zoom++;
 | 
				
			||||||
 | 
					            State.state.locationControl.ping();
 | 
				
			||||||
 | 
					        });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        const min = new MapControlButton(
 | 
				
			||||||
 | 
					            Svg.min_zoom_svg()
 | 
				
			||||||
 | 
					        ).onClick(() => {
 | 
				
			||||||
 | 
					            State.state.locationControl.data.zoom--;
 | 
				
			||||||
 | 
					            State.state.locationControl.ping();
 | 
				
			||||||
 | 
					        });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        super([plus, min, geolocationButton].map(el => el.SetClass("m-0.5 md:m-1")))
 | 
				
			||||||
 | 
					        this.SetClass("flex flex-col")
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -166,7 +166,7 @@ export default class SimpleAddUI extends Toggle {
 | 
				
			||||||
                ])
 | 
					                ])
 | 
				
			||||||
            )
 | 
					            )
 | 
				
			||||||
 | 
					
 | 
				
			||||||
                .onClick(() => State.state.layerControlIsOpened.setData(true))
 | 
					                .onClick(() => State.state.filterIsOpened.setData(true))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        const openLayerOrConfirm = new Toggle(
 | 
					        const openLayerOrConfirm = new Toggle(
 | 
				
			||||||
            confirmButton,
 | 
					            confirmButton,
 | 
				
			||||||
| 
						 | 
					@ -238,7 +238,13 @@ export default class SimpleAddUI extends Toggle {
 | 
				
			||||||
        const allButtons = [];
 | 
					        const allButtons = [];
 | 
				
			||||||
        for (const layer of State.state.filteredLayers.data) {
 | 
					        for (const layer of State.state.filteredLayers.data) {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
            if (layer.isDisplayed.data === false && State.state.featureSwitchLayers) {
 | 
					            if (layer.isDisplayed.data === false && State.state.featureSwitchFilter.data) {
 | 
				
			||||||
 | 
					                // The layer is not displayed and we cannot enable the layer control -> we skip
 | 
				
			||||||
 | 
					                continue;
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
 | 
					            
 | 
				
			||||||
 | 
					            if(layer.layerDef.name === undefined){
 | 
				
			||||||
 | 
					                // this is a parlty hidden layer
 | 
				
			||||||
                continue;
 | 
					                continue;
 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -23,7 +23,7 @@
 | 
				
			||||||
  "startLat": 51,
 | 
					  "startLat": 51,
 | 
				
			||||||
  "startLon": 3.75,
 | 
					  "startLon": 3.75,
 | 
				
			||||||
  "startZoom": 11,
 | 
					  "startZoom": 11,
 | 
				
			||||||
  "widenFactor": 0.0,
 | 
					  "widenFactor": 0,
 | 
				
			||||||
  "socialImage": "./assets/themes/cycle_infra/cycle-infra.svg",
 | 
					  "socialImage": "./assets/themes/cycle_infra/cycle-infra.svg",
 | 
				
			||||||
  "enableDownload": true,
 | 
					  "enableDownload": true,
 | 
				
			||||||
  "layers": [
 | 
					  "layers": [
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -162,6 +162,7 @@
 | 
				
			||||||
    },
 | 
					    },
 | 
				
			||||||
    "download": {
 | 
					    "download": {
 | 
				
			||||||
      "title": "Download visible data",
 | 
					      "title": "Download visible data",
 | 
				
			||||||
 | 
					      "downloadAsPdf": "Download a PDF of the current map",
 | 
				
			||||||
      "downloadGeojson": "Download visible data as geojson",
 | 
					      "downloadGeojson": "Download visible data as geojson",
 | 
				
			||||||
      "downloadGeoJsonHelper": "Compatible with QGIS, OsmAnd, ArcGIS, ESRI, ...",
 | 
					      "downloadGeoJsonHelper": "Compatible with QGIS, OsmAnd, ArcGIS, ESRI, ...",
 | 
				
			||||||
      "downloadCSV": "Download as CSV",
 | 
					      "downloadCSV": "Download as CSV",
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue