0

I have a Leaflet based map on which a user can click to create a marker. Then, if one clicks on the marker a popup is opening, where one can change text in a textarea, activate the camera of the mobile device and save all markers with feature properties into a geoJSON.

I initialize an empty L.featureGroup(), generate dynamic HTML popupContent inside an addMarker(e){} function and add all this data to an object, that is being created via .toGeoJSON(), where I can access feature.properties. Because it is overwritten each time, I have to write all properties into another array infoTextArray

Is there a efficent way to directly write a feature's properties on creation?

edit: to further specify my question:

I want to assign my geoJSON features properties when they're created. I tried something like:

let layerGroup = L.geoJSON([], {
pointToLayer: function (feature) {
    feature.properties.infoText='';
    feature.properties.imageURL='';
},
onEachFeature: function (feature) {
    feature.properties.infoText='';
    feature.properties.imageURL=''; 
}
}).addTo(map);

layerGroup.toGEOJSON() still returns an empty feature properties object. I'm guessing my functions aren't triggered, when a new features is added to the layer.

3
  • 1
    hm...while Leaflet sure is an everyday tool of Web GIS developers, pure code reviews are probably better suited on the dedicated SE or even SO. might want to flag to migrate, since I'm pretty sure this will get closed as off-topic here...
    – geozelot
    Aug 16, 2018 at 7:02
  • okay, the code review isn't actually intented, I'm looking for a specific way to immediately access a feature property on creation
    – Revo
    Aug 16, 2018 at 7:06
  • 1
    Here is an example of where I add points to a map and write them to a database. I use a div instead of the popup. I have a PHP page that takes the points and creates GeoJSON from the database. gistechsolutions.com/leaflet/DEMO/phpDemo/adddelmod2.html Aug 16, 2018 at 12:02

1 Answer 1

3

Leaflet's toGeoJSON() functionality works by using the .feature property of L.Layers (in your case, L.Markers) inside the L.GeoJSON group. Relevant code is here and here.

Therefore, you should populate a .feature property in your L.Markers when the markers are created and not sooner.

e.g.:

var layerGroup = L.geoJSON();

map.on('click', function(ev){
  var newMarker = L.marker(ev.latlng);
  newmarker.feature = { 
    type: 'Point', 
    properties: { infoText: '', imageURL: '' }, 
    geometry: undefined 
  };
  newMarker.addTo(layerGroup);
});

// ...later
layerGroup.toGeoJSON();

Right now, you're trying to populate such a property of the markers before the markers even exist. Your pointToLayer and onEachFeature are not running ever, because they run over each feature in the GeoJSON data when the L.GeoJSON is instantiated, but you're instantiating it with no data - therefore each of them runs a grand total of zero times.

4
  • awesome! exactly this .feature property is what i've been looking for!
    – Revo
    Aug 16, 2018 at 13:43
  • When in doubt, read Leaflet's source code. I find it's kinda easy to understand the internals, if you spend a little time. Aug 16, 2018 at 13:49
  • let layerGroup = L.layerGroup().addTo(map);let marker = L.marker(e.latlng,{icon:redMarkerIcon}); marker.feature = { type: 'Point', properties: {infoText:'',imageURL:''}, geometry:undefined }; marker.bindPopup(staticPopupContent).addTo(layerGroup); the output:JSON.stringify(layerGroup.toGeoJSON()) gives me an invalid geojson. do you know how to fix this?
    – Revo
    Aug 17, 2018 at 6:08
  • output of above: {"type":"FeatureCollection","features":[ {"type":"Feature","properties":{},"geometry":{"type":"Point","properties":{"infoText":"1","imageURL":""},"geometry":{"type":"Point","coordinates":[10.239257812500002,48.019324184801185]}}}, {"type":"Feature","properties":{},"geometry":{"type":"Point","properties":{"infoText":"","imageURL":""},"geometry":{"type":"Point","coordinates":[24.521484375000004,45.85941212790755]}}}]}
    – Revo
    Aug 17, 2018 at 6:09

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.