How would I convert this function to store and utilize (feature.property.id) json values instead of keys in the dropdown menu within a leaflet map?
<html>
<head>
<meta charset="ISO-8859-1">
<link rel="stylesheet" href="http://cdn.leafletjs.com/leaflet/v0.7.7/leaflet.css"/>
<script src="http://cdn.leafletjs.com/leaflet/v0.7.7/leaflet.js"></script>
<script src="Leaflet.CountrySelect.js"></script>
</head>
<style>
html, body, #map {
padding:0px;
margin:0px;
height:100%;
width:100%;
}
</style>
<script>
function init(){
var baseLayer = L.tileLayer('http://{s}.basemaps.cartocdn.com/light_all/{z}/{x}/{y}.png',{attribution: 'Tiles © CartoDB'});
var map = L.map("map",{layers: [baseLayer], center: [-23.88, -62.75], zoom: 4});
var select = L.countrySelect({exclude:"French Southern and Antarctic Lands"});
select.addTo(map);
select.on('change', function(e){
if (e.feature === undefined){ //Do nothing on title
return;
}
var country = L.geoJson(e.feature);
if (this.previousCountry != null){
map.removeLayer(this.previousCountry);
}
this.previousCountry = country;
map.addLayer(country);
map.fitBounds(country.getBounds());
});
}
</script>
<body onload="init()">
<div id="map"></div>
</body>
</html>
with the corresponding JavaScript,
L.CountrySelect = {};
L.CountrySelect.countries = {"Afghanistan":{"type":"Feature","id":"AFG","properties":{"name":"Afghanistan"},"geometry":{"type":"Polygon","coordinates":[[[61.210817,35.650072],[62.230651,35.270664],[62.984662,35.404041],[63.193538,35.857166],[63.982896,36.007957],[64.546479,36.312073],[64.746105,37.111818],[65.588948,37.305217],[65.745631,37.661164],[66.217385,37.39379],[66.518607,37.362784],[67.075782,37.356144],[67.83,37.144994],[68.135562,37.023115],[68.859446,37.344336],[69.196273,37.151144],[69.518785,37.608997],[70.116578,37.588223],[70.270574,37.735165],[70.376304,38.138396],[70.806821,38.486282],[71.348131,38.258905],[71.239404,37.953265],[71.541918,37.905774],[71.448693,37.065645],[71.844638,36.738171],[72.193041,36.948288],[72.63689,37.047558],[73.260056,37.495257],[73.948696,37.421566],[74.980002,37.41999],[75.158028,37.133031],[74.575893,37.020841],[74.067552,36.836176],[72.920025,36.720007],[71.846292,36.509942],[71.262348,36.074388],[71.498768,35.650563],[71.613076,35.153203],[71.115019,34.733126],[71.156773,34.348911],[70.881803,33.988856],[69.930543,34.02012],[70.323594,33.358533],[69.687147,33.105499],[69.262522,32.501944],[69.317764,31.901412],[68.926677,31.620189],[68.556932,31.71331],[67.792689,31.58293],[67.683394,31.303154],[66.938891,31.304911],[66.381458,30.738899],[66.346473,29.887943],[65.046862,29.472181],[64.350419,29.560031],[64.148002,29.340819],[63.550261,29.468331],[62.549857,29.318572],[60.874248,29.829239],[61.781222,30.73585],[61.699314,31.379506],[60.941945,31.548075],[60.863655,32.18292],[60.536078,32.981269],[60.9637,33.528832],[60.52843,33.676446],[60.803193,34.404102],[61.210817,35.650072]]]}},"Angola":{"type":"Feature","id":"AGO","properties":{"name":"Angola"},"geometry":{"type":"MultiPolygon","coordinates":[[[[16.326528,-5.87747],[16.57318,-6.622645],[16.860191,-7.222298],[17.089996,-7.545689],[17.47297,-8.068551],[18.134222,-7.987678],[18.464176,-7.847014],[19.016752,-7.988246],[19.166613,-7.738184],[19.417502,-7.155429],[20.037723,-7.116361],[20.091622,-6.94309],[20.601823,-6.939318],[20.514748,-7.299606],[21.728111,-7.290872],[21.746456,-7.920085],[21.949131,-8.305901],[21.801801,-8.908707],[21.875182,-9.523708],[22.208753,-9.894796],[22.155268,-11.084801],[22.402798,-10.993075],[22.837345,-11.017622],[23.456791,-10.867863],[23.912215,-10.926826],[24.017894,-11.237298],[23.904154,-11.722282],[24.079905,-12.191297],[23.930922,-12.565848],[24.016137,-12.911046],[21.933886,-12.898437],[21.887843,-16.08031],[22.562478,-16.898451],[23.215048,-17.523116],[21.377176,-17.930636],[18.956187,-17.789095],[18.263309,-17.309951],[14.209707,-17.353101],[14.058501,-17.423381],[13.462362,-16.971212],[12.814081,-16.941343],[12.215461,-17.111668],[11.734199,-17.301889],[11.640096,-16.673142],[11.778537,-15.793816],[12.123581,-14.878316],[12.175619,-14.449144],[12.500095,-13.5477],[12.738479,-13.137906],[13.312914,-12.48363],[13.633721,-12.038645],[13.738728,-11.297863],[13.686379,-10.731076],[13.387328,-10.373578],[13.120988,-9.766897],[12.87537,-9.166934],[12.929061,-8.959091],[13.236433,-8.562629],[12.93304,-7.596539],[12.728298,-6.927122],[12.227347,-6.294448],[12.322432,-6.100092],[12.735171,-5.965682],[13.024869,-5.984389],[13.375597,-5.864241],[16.326528,-5.87747]]],[[[12.436688,-5.684304],[12.182337,-5.789931],[11.914963,-5.037987],[12.318608,-4.60623],[12.62076,-4.438023],[12.995517,-4.781103],[12.631612,-4.991271],[12.468004,-5.248362],[12.436688,-5.684304]]]]}},"Albania":{"type":"Feature","id":"ALB","properties":{"name":"Albania"},"geometry":{"type":"Polygon","coordinates":[[[20.590247,41.855404],[20.463175,41.515089],[20.605182,41.086226],[21.02004,40.842727],[20.99999,40.580004],[20.674997,40.435],[20.615,40.110007],[20.150016,39.624998],[19.98,39.694993],[19.960002,39.915006],[19.406082,40.250773],[19.319059,40.72723],[19.40355,41.409566],[19.540027,41.719986],[19.371769,41.877548],[19.304486,42.195745],[19.738051,42.688247],[19.801613,42.500093],[20.0707,42.58863],[20.283755,42.32026],[20.52295,42.21787],[20.590247,41.855404]]]}}
L.CountrySelect = L.Control.extend({
options: {
position: 'topright',
title: 'Country',
exclude: [],
include: [],
countries: L.CountrySelect.countries,
},
onAdd: function(map) {
this.div = L.DomUtil.create('div','leaflet-countryselect-container');
this.select = L.DomUtil.create('select','leaflet-countryselect',this.div);
var content = '';
if (this.options.title.length > 0 ){
content += '<option>'+this.options.title+'</option>';
}
var countries = (Array.isArray(this.options.include) && this.options.include.length > 0) ? this.options.include : this.options.countries;
var countryKeys = Object.keys(countries).sort();
for (i in countryKeys){
if (this.options.exclude.indexOf(countryKeys[i]) == -1){
content+='<option>'+countryKeys[i]+'</option>';
}
}
this.select.innerHTML = content;
this.select.onmousedown = L.DomEvent.stopPropagation;
return this.div;
},
on: function(type,handler){
if (type == 'change'){
this.onChange = handler;
L.DomEvent.addListener(this.select,'change',this._onChange,this);
} else if (type == 'click'){ //don't need this here probably, but for convenience?
this.onClick = handler;
L.DomEvent.addListener(this.select,'click',this.onClick,this);
} else {
console.log('CountrySelect - cannot handle '+type+' events.')
}
},
_onChange: function(e) {
var selectedCountry = this.select.options[this.select.selectedIndex].value;
e.feature = this.options.countries[selectedCountry];
this.onChange(e);
}
});
L.countrySelect = function(id,options){
return new L.CountrySelect(id,options);
};
Mainly this function is pulling the super key county name, but this doesn't work well with a general JSON/GeoJSONs (please correct me if I'm wrong). I'd like to add feature.propoerty.id values to the dropdown list and have that filter/zoom to associated county based on that value instead of the super key.
Here's a demo: http://ahalota.github.io/Leaflet.CountrySelect/demo.html
I've been scratching my head for a couple hours on this and I'm pretty new to JavaScript.
More information on this function can be found here -> https://github.com/ahalota/Leaflet.CountrySelect
Best Answer
First it has to be noted that solution below is modification of Leaflet.CountrySelect plugin, written by Anika S. Halota.
Requirement that control would work with any JSON file is to broad, since file must have defined structure that plugin can work with. Since file has to include geometries, the obvious candidate is then GeoJSON feature collection, where each feature has geometry that can be displayed and some id by which it can be identified.
The following changes were made to control:
L.featureSelect
features
was added to control. This is input GeoJSON object.lookupProperty
was added. It specifies feature property name to be used for lookup. Deafult value is'id'
.lookupInFeatureProperties
was added. If set totrue
, feature property specified withlookupProperty
will be searched for inproperties
feature property.exclude
,include
andcountries
were removed, sonce thay are not needed any more.So here is how new control looks like:
Below is example of using the new control with original countries file
world.geo.json
, available at https://github.com/johan/world.geo.json (jQuery is used to load GeoJSON file from local server):In the above example feature property
id
would be used to select countries by id. Since each feature (country) has also country name storedproperties
property undername
property, it could also be used to select countries by name by defining control like this: