forked from MapComplete/MapComplete
		
	Add better way handling
This commit is contained in:
		
							parent
							
								
									0bb5abec3c
								
							
						
					
					
						commit
						1373bd106e
					
				
					 10 changed files with 46 additions and 13 deletions
				
			
		|  | @ -15,7 +15,7 @@ export class LayerDefinition { | |||
|     /** | ||||
|      * This name is shown in the 'add XXX button' | ||||
|      */ | ||||
|     name: string; | ||||
|     name: string | UIElement; | ||||
|     /** | ||||
|      * These tags are added whenever a new point is added by the user on the map. | ||||
|      * This is the ideal place to add extra info, such as "fixme=added by MapComplete, geometry should be checked" | ||||
|  | @ -72,6 +72,14 @@ export class LayerDefinition { | |||
|      */ | ||||
|     maxAllowedOverlapPercentage: number = undefined; | ||||
| 
 | ||||
|     /** | ||||
|      * If true, then ways (and polygons) will be converted to a 'point' at the center instead before further processing | ||||
|      */ | ||||
|     wayHandling: number = 0; | ||||
|      | ||||
|     static WAYHANDLING_DEFAULT = 0; | ||||
|     static WAYHANDLING_CENTER_ONLY = 1; | ||||
|     static WAYHANDLING_CENTER_AND_WAY = 2; | ||||
|      | ||||
|     constructor(options: { | ||||
|         name: string, | ||||
|  | @ -82,6 +90,7 @@ export class LayerDefinition { | |||
|         title?: TagRenderingOptions, | ||||
|         elementsToShow?: TagDependantUIElementConstructor[], | ||||
|         maxAllowedOverlapPercentage?: number, | ||||
|         waysToCenterPoints?: boolean, | ||||
|         style?: (tags: any) => { | ||||
|             color: string, | ||||
|             icon: any | ||||
|  | @ -99,6 +108,7 @@ export class LayerDefinition { | |||
|         this.title = options.title; | ||||
|         this.elementsToShow = options.elementsToShow; | ||||
|         this.style = options.style; | ||||
|         this.wayHandling = options.waysToCenterPoints ?? LayerDefinition.WAYHANDLING_DEFAULT; | ||||
|     } | ||||
| 
 | ||||
|     asLayer(basemap: Basemap, allElements: ElementStorage, changes: Changes, userDetails: UIEventSource<UserDetails>, selectedElement: UIEventSource<any>, | ||||
|  | @ -109,6 +119,7 @@ export class LayerDefinition { | |||
|             basemap, allElements, changes, | ||||
|             this.overpassFilter, | ||||
|             this.maxAllowedOverlapPercentage, | ||||
|             this.wayHandling, | ||||
|             this.style, | ||||
|             selectedElement, | ||||
|             showOnPopup); | ||||
|  |  | |||
|  | @ -29,6 +29,7 @@ export default class BikeParkings extends LayerDefinition { | |||
|             //new ParkingOperator(),
 | ||||
|             new ParkingType() | ||||
|         ]; | ||||
|         this.wayHandling = LayerDefinition.WAYHANDLING_CENTER_AND_WAY; | ||||
| 
 | ||||
|     } | ||||
| 
 | ||||
|  |  | |||
|  | @ -27,6 +27,7 @@ export default class BikeShops extends LayerDefinition { | |||
|             new Tag("shop", "bicycle"), | ||||
|         ] | ||||
|         this.maxAllowedOverlapPercentage = 10 | ||||
|         this.wayHandling = LayerDefinition.WAYHANDLING_CENTER_AND_WAY | ||||
| 
 | ||||
|         this.minzoom = 13; | ||||
|         this.style = this.generateStyleFunction(); | ||||
|  |  | |||
|  | @ -38,6 +38,7 @@ export default class BikeStations extends LayerDefinition { | |||
|         this.minzoom = 13; | ||||
|         this.style = this.generateStyleFunction(); | ||||
|         this.title = new FixedText(Translations.t.cyclofix.station.title) | ||||
|         this.wayHandling = LayerDefinition.WAYHANDLING_CENTER_AND_WAY | ||||
| 
 | ||||
|         this.elementsToShow = [ | ||||
|             new ImageCarouselWithUploadConstructor(), | ||||
|  |  | |||
|  | @ -24,6 +24,7 @@ export class DrinkingWater extends LayerDefinition { | |||
|             new Tag("amenity", "drinking_water"), | ||||
|         ]; | ||||
|         this.maxAllowedOverlapPercentage = 10; | ||||
|         this.wayHandling = LayerDefinition.WAYHANDLING_CENTER_AND_WAY | ||||
| 
 | ||||
|         this.minzoom = 13; | ||||
|         this.style = this.generateStyleFunction(); | ||||
|  |  | |||
|  | @ -2,10 +2,8 @@ import {Layout} from "../Layout"; | |||
| import BikeParkings from "../Layers/BikeParkings"; | ||||
| import BikeServices from "../Layers/BikeStations"; | ||||
| import BikeShops from "../Layers/BikeShops"; | ||||
| import {GhostBike} from "../Layers/GhostBike"; | ||||
| import Translations from "../../UI/i18n/Translations"; | ||||
| import {DrinkingWater} from "../Layers/DrinkingWater"; | ||||
| import {BikeShop} from "../Layers/BikeShop" | ||||
| import Combine from "../../UI/Base/Combine"; | ||||
| 
 | ||||
| 
 | ||||
|  |  | |||
|  | @ -6,6 +6,7 @@ import { Changes } from "./Changes"; | |||
| import L from "leaflet" | ||||
| import { GeoOperations } from "./GeoOperations"; | ||||
| import { UIElement } from "../UI/UIElement"; | ||||
| import {LayerDefinition} from "../Customizations/LayerDefinition"; | ||||
| 
 | ||||
| /*** | ||||
|  * A filtered layer is a layer which offers a 'set-data' function | ||||
|  | @ -18,7 +19,7 @@ import { UIElement } from "../UI/UIElement"; | |||
|  */ | ||||
| export class FilteredLayer { | ||||
| 
 | ||||
|     public readonly name: string; | ||||
|     public readonly name: string | UIElement; | ||||
|     public readonly filters: TagsFilter; | ||||
|     public readonly isDisplayed: UIEventSource<boolean> = new UIEventSource(true); | ||||
| 
 | ||||
|  | @ -32,6 +33,7 @@ export class FilteredLayer { | |||
|     /** The featurecollection from overpass | ||||
|      */ | ||||
|     private _dataFromOverpass; | ||||
|     private _wayHandling: number; | ||||
|     /** List of new elements, geojson features | ||||
|      */ | ||||
|     private _newElements = []; | ||||
|  | @ -43,15 +45,17 @@ export class FilteredLayer { | |||
|     private _showOnPopup: (tags: UIEventSource<any>) => UIElement; | ||||
| 
 | ||||
|     constructor( | ||||
|         name: string, | ||||
|         name: string | UIElement, | ||||
|         map: Basemap, storage: ElementStorage, | ||||
|         changes: Changes, | ||||
|         filters: TagsFilter, | ||||
|         maxAllowedOverlap: number, | ||||
|         wayHandling: number, | ||||
|         style: ((properties) => any), | ||||
|         selectedElement: UIEventSource<any>, | ||||
|         showOnPopup: ((tags: UIEventSource<any>) => UIElement) | ||||
|     ) { | ||||
|         this._wayHandling = wayHandling; | ||||
|         this._selectedElement = selectedElement; | ||||
|         this._showOnPopup = showOnPopup; | ||||
| 
 | ||||
|  | @ -66,6 +70,7 @@ export class FilteredLayer { | |||
|         this._style = style; | ||||
|         this._storage = storage; | ||||
|         this._maxAllowedOverlap = maxAllowedOverlap; | ||||
|          | ||||
|         const self = this; | ||||
|         this.isDisplayed.addCallback(function (isDisplayed) { | ||||
|             if (self._geolayer !== undefined && self._geolayer !== null) { | ||||
|  | @ -86,10 +91,17 @@ export class FilteredLayer { | |||
|     public SetApplicableData(geojson: any): any { | ||||
|         const leftoverFeatures = []; | ||||
|         const selfFeatures = []; | ||||
|         for (const feature of geojson.features) { | ||||
|         for (let feature of geojson.features) { | ||||
|             // feature.properties contains all the properties
 | ||||
|             var tags = TagUtils.proprtiesToKV(feature.properties); | ||||
|             if (this.filters.matches(tags)) { | ||||
|                 if(feature.geometry.type !== "Point"){ | ||||
|                     if(this._wayHandling === LayerDefinition.WAYHANDLING_CENTER_AND_WAY){ | ||||
|                         selfFeatures.push(GeoOperations.centerpoint(feature)); | ||||
|                     }else if(this._wayHandling === LayerDefinition.WAYHANDLING_CENTER_ONLY){ | ||||
|                         feature = GeoOperations.centerpoint(feature); | ||||
|                     } | ||||
|                 } | ||||
|                 selfFeatures.push(feature); | ||||
|             } else { | ||||
|                 leftoverFeatures.push(feature); | ||||
|  |  | |||
|  | @ -6,6 +6,15 @@ export class GeoOperations { | |||
|         return turf.area(feature); | ||||
|     } | ||||
| 
 | ||||
|     static centerpoint(feature: any)  | ||||
|     { | ||||
|         const newFeature= turf.center(feature);     | ||||
|         newFeature.properties = feature.properties; | ||||
|         newFeature.id = feature.id; | ||||
|          | ||||
|         return newFeature; | ||||
|     } | ||||
| 
 | ||||
|     static featureIsContainedInAny(feature: any, | ||||
|                                    shouldNotContain: any[], | ||||
|                                    maxOverlapPercentage: number): boolean { | ||||
|  |  | |||
|  | @ -25,7 +25,7 @@ export class SimpleAddUI extends UIElement { | |||
|                 selectedElement: UIEventSource<any>, | ||||
|                 dataIsLoading: UIEventSource<boolean>, | ||||
|                 userDetails: UIEventSource<UserDetails>, | ||||
|                 addButtons: { name: string; icon: string; tags: Tag[]; layerToAddTo: FilteredLayer }[], | ||||
|                 addButtons: { name: UIElement; icon: string; tags: Tag[]; layerToAddTo: FilteredLayer }[], | ||||
|     ) { | ||||
|         super(zoomlevel); | ||||
|         this._zoomlevel = zoomlevel; | ||||
|  | @ -42,17 +42,16 @@ export class SimpleAddUI extends UIElement { | |||
|             // <button type='button'> looks SO retarded
 | ||||
|             // the default type of button is 'submit', which performs a POST and page reload
 | ||||
|             const button = | ||||
|                 new Button(new FixedUiElement("Add a " + option.name + " here"), | ||||
|                 new Button(new FixedUiElement("Add a " + option.name.Render() + " here"), | ||||
|                     this.CreatePoint(option)); | ||||
|             this._addButtons.push(button); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     private CreatePoint(option: { name: string; icon: string; tags: Tag[]; layerToAddTo: FilteredLayer }) { | ||||
|     private CreatePoint(option: {icon: string; tags: Tag[]; layerToAddTo: FilteredLayer }) { | ||||
|         const self = this; | ||||
|         return () => { | ||||
| 
 | ||||
|             console.log("Creating a new ", option.name, " at last click location"); | ||||
|             const loc = self._lastClickLocation.data; | ||||
|             let feature = self._changes.createElement(option.tags, loc.lat, loc.lon); | ||||
|             option.layerToAddTo.AddNewElement(feature); | ||||
|  |  | |||
							
								
								
									
										4
									
								
								index.ts
									
										
									
									
									
								
							
							
						
						
									
										4
									
								
								index.ts
									
										
									
									
									
								
							|  | @ -166,7 +166,7 @@ const bm = new Basemap("leafletDiv", locationControl, new VariableUiElement( | |||
| 
 | ||||
| // ------------- Setup the layers -------------------------------
 | ||||
| const addButtons: { | ||||
|     name: string, | ||||
|     name: UIElement, | ||||
|     icon: string, | ||||
|     tags: Tag[], | ||||
|     layerToAddTo: FilteredLayer | ||||
|  | @ -195,7 +195,7 @@ for (const layer of layoutToUse.layers) { | |||
|     const flayer = layer.asLayer(bm, allElements, changes, osmConnection.userDetails, selectedElement, generateInfo); | ||||
| 
 | ||||
|     const addButton = { | ||||
|         name: layer.name, | ||||
|         name: Translations.W(layer.name), | ||||
|         icon: layer.icon, | ||||
|         tags: layer.newElementTags, | ||||
|         layerToAddTo: flayer | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue