Atlaslog
Atlaslog / Examples / Leaflet / GeoJSON Layer
Leaflet · Runnable Example

GeoJSON Layer

Runnable Leaflet example: GeoJSON Layer. Open the live demo, read the complete source, and copy the file into your project. No build step or API key.

Open standalone → Chinese notes All Leaflet examples
/demos/leaflet-geojson-layer.htmlLIVE
single HTML file · CDN dependencies onlyinterface may contain Chinese labels

Source

demos/leaflet-geojson-layer.html
<!--
  示例:GeoJSON 图层
  要点:style / pointToLayer / onEachFeature 三个回调、filter 过滤、setStyle 批量改色
  依赖:Leaflet 1.9.4 · jsDelivr CDN
-->
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta name="robots" content="noindex,follow">
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>GeoJSON 图层</title>
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/leaflet@1.9.4/dist/leaflet.css">
<style>
  html,body{height:100%;margin:0}
  body{display:flex;flex-direction:column;overflow:hidden;
       font:13px/1.6 -apple-system,"Segoe UI","PingFang SC",sans-serif}
  .bar{flex:0 0 auto;padding:8px 12px;background:#f6f7f9;border-bottom:1px solid #e3e6ea;
       display:flex;gap:8px;align-items:center;flex-wrap:wrap;font-size:12px;color:#58606e}
  .bar button{font:inherit;font-size:12px;padding:4px 10px;border-radius:4px;cursor:pointer;
       border:1px solid #ccd1d9;background:#fff;color:#16181d}
  .bar button:hover{background:#eef0f3}
  .bar button.on{background:#1f5fd0;border-color:#1f5fd0;color:#fff}
  .bar b{color:#16181d;font-weight:600}
  #map{flex:1 1 auto;min-height:0}
  .dot{width:13px;height:13px;border-radius:50%;border:2px solid #fff;
    box-shadow:0 0 0 1px rgba(0,0,0,.25)}
</style>
</head>
<body>
<div class="bar">
  <button id="filter">过滤低等级:关</button>
  <button id="emphasis">强调重点:关</button>
  <button id="fit">适配范围</button>
  <span>要素 <b id="count">5</b></span>
  <span id="hint">点击要素查看属性</span>
</div>
<div id="map"></div>
<script src="https://cdn.jsdelivr.net/npm/leaflet@1.9.4/dist/leaflet.js"></script>
<script>
(function () {
  'use strict';

  var map = L.map('map', { center: [39.912, 116.395], zoom: 13 });

  L.tileLayer('https://server.arcgisonline.com/ArcGIS/rest/services/World_Street_Map/MapServer/tile/{z}/{y}/{x}', {
    maxZoom: 19,
    attribution: 'Tiles © Esri'
  }).addTo(map);

  var data = {
    type: 'FeatureCollection',
    features: [
      { type: 'Feature', properties: { name: '天安门', level: 3 },
        geometry: { type: 'Point', coordinates: [116.391263, 39.907359] } },
      { type: 'Feature', properties: { name: '王府井', level: 2 },
        geometry: { type: 'Point', coordinates: [116.4106, 39.9147] } },
      { type: 'Feature', properties: { name: '西单', level: 1 },
        geometry: { type: 'Point', coordinates: [116.3742, 39.9097] } },
      { type: 'Feature', properties: { name: '长安街', level: 2 },
        geometry: { type: 'LineString',
          coordinates: [[116.350, 39.9078], [116.392, 39.9080], [116.440, 39.9072]] } },
      { type: 'Feature', properties: { name: '故宫片区', level: 3 },
        geometry: { type: 'Polygon',
          coordinates: [[[116.388, 39.912], [116.401, 39.912],
                         [116.401, 39.923], [116.388, 39.923], [116.388, 39.912]]] } }
    ]
  };

  var COLORS = { 1: '#9aa3b0', 2: '#1f5fd0', 3: '#c2410c' };
  var countEl = document.getElementById('count');
  var layer = null;
  var filterOn = false;
  var emphasisOn = false;

  function styleFor(feature) {
    var lv = feature.properties.level || 1;
    return {
      color: COLORS[lv],
      weight: 1 + lv,
      fillColor: COLORS[lv],
      fillOpacity: 0.06 + lv * 0.04,
      dashArray: emphasisOn && lv < 3 ? '5 4' : null
    };
  }

  function build() {
    if (layer) map.removeLayer(layer);

    layer = L.geoJSON(data, {
      filter: function (f) {
        return !(filterOn && f.properties.level === 1);
      },

      style: styleFor,

      pointToLayer: function (feature, latlng) {
        var lv = feature.properties.level || 1;
        return L.marker(latlng, {
          icon: L.divIcon({
            className: '',
            html: '<div class="dot" style="background:' + COLORS[lv] + '"></div>',
            iconSize: [13, 13],
            iconAnchor: [6.5, 6.5]
          })
        });
      },

      onEachFeature: function (feature, lyr) {
        var p = feature.properties;
        lyr.bindTooltip(p.name, { direction: 'top', offset: [0, -10] });
        lyr.bindPopup(
          '<b>' + p.name + '</b><br>等级 ' + p.level +
          '<br>几何 ' + feature.geometry.type
        );
      }
    }).addTo(map);

    countEl.textContent = layer.getLayers().length;
  }

  build();
  map.fitBounds(layer.getBounds(), { padding: [40, 40] });

  document.getElementById('filter').addEventListener('click', function () {
    filterOn = !filterOn;
    this.textContent = '过滤低等级:' + (filterOn ? '开' : '关');
    this.classList.toggle('on', filterOn);
    build();
    document.getElementById('hint').textContent =
      filterOn ? 'level=1 的西单已被 filter 排除' : '已显示全部要素';
  });

  document.getElementById('emphasis').addEventListener('click', function () {
    emphasisOn = !emphasisOn;
    this.textContent = '强调重点:' + (emphasisOn ? '开' : '关');
    this.classList.toggle('on', emphasisOn);
    /* setStyle 只影响线与面,点坐标在 pointToLayer 里,需重建 */
    layer.setStyle(styleFor);
    if (emphasisOn) {
      layer.eachLayer(function (lyr) {
        if (lyr instanceof L.Marker) lyr.setZIndexOffset(1000);
      });
    }
  });

  document.getElementById('fit').addEventListener('click', function () {
    map.fitBounds(layer.getBounds(), { padding: [40, 40] });
  });
})();
</script>
</body>
</html>
Language: the code and this page are in English; the full tutorial and API notes for this example are in Chinese. The demo itself is the authoritative version — it runs exactly as shown.

More Leaflet examples

Leaflet · EXAMPLEGraticule Leaflet · EXAMPLEHeatmap Leaflet · EXAMPLEImage Overlay