Loading GeoJSON data
Quick answer
This tutorial turns a GeoJSON FeatureCollection into Leaflet layers with L.geoJSON and explains how the pointToLayer, style, onEachFeature and filter options change the result. It covers loading remote files with fetch, refitting the map to layer.getBounds(), and restyling existing features through layer.setStyle. It closes with performance switches such as preferCanvas and interactive: false. Readers can render styled, clickable vector data safely.
Key points
- Return an L.circleMarker from pointToLayer so points avoid the default PNG marker.
- Apply per-feature colors in the style callback and later refresh them with layer.setStyle(fn).
- Use filter to drop irrelevant features before they are rendered, not after.
Example
{
"type": "FeatureCollection",
"features": [
{
"type": "Feature",
"properties": { "name": "中关村", "level": 2 },
"geometry": {
"type": "Point",
"coordinates": [116.316, 39.983]
}
}
]
}L.geoJSON(data, {
style: function (feature) {
return {
color: feature.properties.color || '#1f5fd0',
weight: 2,
fillOpacity: 0.22
};
},
pointToLayer: function (feature, latlng) {
return L.circleMarker(latlng, {
radius: 6,
color: '#ffffff',
weight: 2,
fillColor: '#1f5fd0',
fillOpacity: 1
});
},
onEachFeature: function (feature, layer) {
layer.bindPopup(
'<b>' + feature.properties.name + '</b><br>' +
'等级 ' + feature.properties.level
);
},
filter: function (feature) {
return feature.properties.level >= 2;
}
}).addTo(map);
Notes
- GeoJSON coordinates are [lng, lat] while Leaflet LatLng is [lat, lng]; L.geoJSON flips them.
- layer.getBounds() is invalid for an empty layer, so check the feature count before fitBounds.
English edition written for Atlaslog. Code is taken from the original Chinese page and runs unchanged.
Atlaslog (2026). Loading GeoJSON data. https://www.jingweizhi.com/en/leaflet/tutorials/geojson.html (accessed 2026-11-03).