Проблемы привязки событий/всплывающие окна для существующего слоя листовка формата GeoJSON


Я пытаюсь добавить локальные данные json в слой GeoJson в листовке, а затем (пока) привязать всплывающее окно к каждому объекту в json. Проблема в том, что я не могу сначала создать слой geojson, а затем связать всплывающие окна. Есть ли способ сделать это? Я могу только создавать слой и добавлять всплывающие окна одновременно. Что у меня есть до сих пор:

Создайте карту.

map = new L.Map('map');

Захватите локальный файл json:

{
"type": "FeatureCollection",
"features": [
    {
        "type": "Feature",
        "properties": {
            "name": "Denver",
            "amenity": "Baseball Stadium",
            "popupContent": "This is where the Rockies play!"
        },
        "geometry": {
            "type": "Point",
            "coordinates": [-102.99404, 37.75621]
        }
    },
    {
        "type": "Feature",
        "properties": {
            "name": "Baltimore",
            "amenity": "Baseball Stadium",
            "popupContent": "This is where the Orioles play!"
        },
        "geometry": {
            "type": "Point",
            "coordinates": [-76.6167, 39.2833]
        }
    }
    ]
}

И отправить json через plotData ():

function plotData( data ) 
{
  var pointLayer = L.geoJson().addTo(map);

  // 1. works
  L.geoJson(data, {
    onEachFeature: onEachFeature
  }).addTo(map);


  // 2. does not bind popups
  pointLayer.addData( data, {
    onEachFeature: onEachFeature
      }
  );

  // 3. Error - invalid GeoJson Object
  pointLayer.addData( L.geoJson(data, {
    onEachFeature: onEachFeature
      })
  );
}

function onEachFeature( feature, layer ) 
{
  layer.bindPopup( feature.properties.name );
}

Маркеры прекрасно отображаются на карте для сценариев 1 и 2 (при этом 1 также отображает всплывающие окна). Есть ли какая-то причина, по которой я не должен пытаться сначала создать слой, а затем привязать действия к объектам? Может быть, лучше просто сделать то, что я сказал в 1?

1 2

1 ответ:

Третий вариант не будет работать, потому что вы подаете объект L.Layer туда, куда должен идти объект GeoJSON. Функция L.GeoJSON.addData() не имеет параметра onEachFeature. В принципе, когда вы обработали GeoJSON, его свойства объектов исчезают.

Есть два способа действовать дальше.
// create empty GeoJSON layer
var pointLayer = L.geoJson(null, { onEachFeature: storeName }).addTo(map);
// add data to it later, invoking storeName() function
pointLayer.addData(data);
// which stores names
function storeName(f, l) { l._gname = f.properties.name; }
// and when you're ready...
pointLayer.eachLayer(addPopupFromGName);
// add popups with stored name
function addPopupFromGName(l) { l.bindPopup(l._gname); }

Или просто добавьте функцию onEachLayer в параметры слоя L. GeoJSON:

var pointLayer = L.geoJson(null, { onEachFeature: onEachFeature }).addTo(map);