经纬志
首页 / 实战手册 / MapLibre 样式与图层

addLayer 成功,地图上什么都没有

先看结论

没有报错,getLayer 也能查到,但屏幕上就是看不到任何新增的图形。

最后验证 2026-11-03 · 多技术栈 · 更新 2026-10-29 · 引用本文

现象

map.addLayer 返回正常,map.getLayer('poi') 有对象, 但图形不出现。缩放到某个级别时偶尔闪出一两个点,然后再次消失。 另一种情况是直接抛错:

Error: Source "poi" not found
    at Style.addLayer (style.ts:1204)

原因

原因判断方法
source 名称拼错或未添加map.getSource(name) 返回 undefined
filter 条件过严去掉 filter 后图形出现
minzoom 高于当前级别缩放一级后出现
样式里 visibility: nonegetLayoutProperty 返回 none
被不透明图层压在下面把它移到最上层后出现
数据源坐标系不是 4326/3857图形偏到海里

排查过程

依次确认数据源、过滤器、图层属性三个环节:

console.log('source', map.getSource('poi'));
console.log('layer', map.getLayer('poi'));
console.log('visibility', map.getLayoutProperty('poi', 'visibility'));
console.log('filter', map.getFilter('poi'));
console.log('zoom', map.getZoom());
console.log('source features', map.querySourceFeatures('poi').length);

querySourceFeatures 返回 0 时,问题在数据本身或加载时机; 返回有值但画面为空,问题在样式或图层顺序。

解决方案

在 load 之后添加数据源与图层,并显式给出可见性。GeoJSON 要先确认 文件是要素集合而不是单个要素:

map.on('load', function () {
  map.addSource('poi', {
    type: 'geojson',
    data: '/data/poi.geojson'
  });

  map.addLayer({
    id: 'poi-circle',
    type: 'circle',
    source: 'poi',
    layout: { visibility: 'visible' },
    paint: {
      'circle-radius': 5,
      'circle-color': '#e8590c',
      'circle-stroke-width': 1,
      'circle-stroke-color': '#ffffff'
    }
  }, 'water');       // 放在水系图层之前,确保不被面层压住
});

过滤器写错是最隐蔽的一种。注意 == 与字段名大小写,先用最宽的条件验证:

// 先不设 filter,确认数据可见
map.setFilter('poi-circle', null);

// 再逐步收紧
map.setFilter('poi-circle', ['==', ['get', 'type'], 'station']);

图层顺序不对时,把目标图层提到最上层,避免被填充面遮挡:

map.moveLayer('poi-circle');   // 不传第二参数即移到最上

验证

querySourceFeatures 返回的数据条数与文件一致。 在 10 级与 14 级缩放下都能看到图形,去掉 filter 后数量明显增加。 点击图形能通过 queryRenderedFeatures 命中。

先排除数据:用 querySourceFeatures 一行就能区分“没数据”和“没样式”。 前者查文件与加载时机,后者查 filter、可见性和图层顺序,方向完全不同。

引用本文

经纬志(2026)。《addLayer 成功,地图上什么都没有》。https://www.jingweizhi.com/cookbook/maplibre-layer-not-show.html(访问日期 2026-11-03)。