📌 学习目标
- 掌握一个Source配置多个图层样式
- 理解相关API的使用
- 能够独立完成类似功能开发
🎯 核心概念
一个Source配置多个图层样式
💻 完 整 代 码
代码示例
js
const map = new maplibregl.Map({
container: 'map',
style: 'https://tiles.openfreemap.org/styles/bright',
center: [-88.13734351262877, 35.137451890638886],
zoom: 4
});
map.on('load', () => {
const layers = map.getStyle().layers;
// 查找地图样式中第一个符号图层的索引
let firstSymbolId;
for (let i = 0; i < layers.length; i++) {
if (layers[i].type === 'symbol') {
firstSymbolId = layers[i].id;
break;
}
}
map.addSource('urban-areas', {
'type': 'geojson',
'data':
'https://d2ad6b4ur7yvpq.cloudfront.net/naturalearth-3.3.0/ne_50m_urban_areas.geojson'
});
map.addLayer(
{
'id': 'urban-areas-fill',
'type': 'fill',
'source': 'urban-areas',
'layout': {},
'paint': {
'fill-color': '#f08',
'fill-opacity': 0.4
}
// 这是此示例的重要部分:addLayer方法接受2个参数:
// 一个是图层对象,另一个是表示另一个图层名称的字符串。
// 如果另一个图层已存在于样式表中,
// 新图层将紧挨该图层放置在堆栈中,
// 从而可以将"覆盖物"放置在图层堆栈中的任何位置。
// 将图层插入到第一个符号图层下方。
},
firstSymbolId
);
});
代码示例
html
<!DOCTYPE html>
<html lang="en">
<head>
<title>Add a new layer below labels</title>
<meta property="og:description" content="使用 addLayer 的第二个参数在标签下方添加图层。" />
<meta property="og:created" content="2025-06-25" />
<meta charset='utf-8'>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel='stylesheet' href='https://unpkg.com/maplibre-gl@5.24.0/dist/maplibre-gl.css' />
<script src='https://unpkg.com/maplibre-gl@5.24.0/dist/maplibre-gl.js'></script>
<style>
body { margin: 0; padding: 0; }
html, body, #map { height: 100%; }
</style>
</head>
<body>
<div id="map"></div>
<script>
const map = new maplibregl.Map({
container: 'map',
style: 'https://tiles.openfreemap.org/styles/bright',
center: [-88.13734351262877, 35.137451890638886],
zoom: 4
});
map.on('load', () => {
const layers = map.getStyle().layers;
// 查找地图样式中第一个符号图层的索引
let firstSymbolId;
for (let i = 0; i < layers.length; i++) {
if (layers[i].type === 'symbol') {
firstSymbolId = layers[i].id;
break;
}
}
map.addSource('urban-areas', {
'type': 'geojson',
'data':
'https://d2ad6b4ur7yvpq.cloudfront.net/naturalearth-3.3.0/ne_50m_urban_areas.geojson'
});
map.addLayer(
{
'id': 'urban-areas-fill',
'type': 'fill',
'source': 'urban-areas',
'layout': {},
'paint': {
'fill-color': '#f08',
'fill-opacity': 0.4
}
// 这是本示例的重要部分:addLayer方法接受2个参数:
// 图层对象,和表示另一个图层名称的字符串。
// 如果另一个图层已存在于样式表中,新图层将被定位
// 在该图层之前,使得可以将"叠加层"放置在图层堆栈的任何位置。
// 在第一个符号图层下方插入该图层。
},
firstSymbolId
);
});
</script>
</body>
</html>
🔍 代码解析
初始化地图
使用 new maplibregl.Map() 创建地图实例,配置基本参数。本示例的核心特色是展示如何在标签图层下方添加新图层。
关键配置项
- container: 地图容器的 DOM 元素 ID
- style : 使用 MapLibre 官方样式
https://tiles.openfreemap.org/styles/bright - center : 地图初始中心点
[-88.13734351262877, 35.137451890638886](美国田纳西州附近) - zoom: 初始缩放级别为 4,显示区域级别视图
图层堆栈定位逻辑
javascript
map.on('load', () => {
const layers = map.getStyle().layers;
// 查找地图样式中第一个符号图层的索引
let firstSymbolId;
for (let i = 0; i < layers.length; i++) {
if (layers[i].type === 'symbol') {
firstSymbolId = layers[i].id;
break;
}
}
// ... 添加数据源和图层
});
添加图层到指定位置
javascript
map.addLayer(
{
'id': 'urban-areas-fill',
'type': 'fill',
'source': 'urban-areas',
'layout': {},
'paint': {
'fill-color': '#f08',
'fill-opacity': 0.4
}
},
firstSymbolId // 在第一个符号图层下方插入
);
⚙️ 参数说明
| 参数 | 类型 | 必填 | 默认值 | 说明 |
|---|---|---|---|---|
| container | string | 是 | - | 地图容器元素的 ID |
| style | string/object | 是 | - | 地图样式 URL 或内联样式对象 |
| center | number, number | 否 | [0, 0] |
初始中心点坐标,格式为 [经度, 纬度] |
| zoom | number | 否 | 0 |
初始缩放级别,范围 0-22 |
addLayer 方法参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
| layer | object | 是 | 图层配置对象 |
| beforeId | string | 否 | 目标图层 ID,新图层将插入到该图层之前 |
图层配置对象
| 属性 | 类型 | 必填 | 说明 |
|---|---|---|---|
| id | string | 是 | 图层唯一标识 |
| type | string | 是 | 图层类型(fill、line、symbol 等) |
| source | string | 是 | 数据源名称 |
| layout | object | 否 | 布局属性 |
| paint | object | 否 | 绘制属性 |
🎨 效果说明

运行代码后,页面显示一个交互式地图,城市区域(urban areas)以半透明粉红色填充显示。关键特点:
- 图层顺序: 城市区域图层被添加在标签图层下方,确保标签始终可见
- 视觉效果 : 粉红色半透明填充(
fill-color: #f08,fill-opacity: 0.4) - 交互功能: 支持鼠标拖拽、滚轮缩放、右键旋转等标准交互
地图默认显示美国区域,缩放级别为 4,可以看到各大城市区域被高亮显示。
💡 常 见 问 题
Q1: 为什么要在标签下方添加图层?
A: 因为地图图层是按堆栈顺序渲染的,上层图层会覆盖下层图层。将填充图层放在标签下方可以确保地名、道路名称等标签始终可见。
Q2: 如何找到特定类型的图层?
A: 使用 map.getStyle().layers 获取所有图层,然后遍历查找特定类型(如 symbol、fill、line)或特定 ID 的图层。
Q3: 如果找不到目标图层会怎样?
A: 如果 beforeId 参数指定的图层不存在,addLayer 会将图层添加到图层堆栈的顶部。可以添加错误处理来避免这种情况。
Q4: 如何查看当前地图的图层堆栈?
A: 在浏览器控制台中执行 map.getStyle().layers.map(l => l.id) 可以查看所有图层的 ID 和顺序。
📝 练习任务
- 基础练习:修改填充颜色和透明度,观察效果变化
- 进阶挑战:尝试将图层添加到道路图层下方,而不是标签图层下方
- 拓展思考:如何动态调整图层的堆栈顺序?
🌟 最佳实践
- 图层顺序管理: 明确图层的渲染顺序,确保重要信息(如标签)始终可见
- 错误处理 : 在使用
addLayer前检查目标图层是否存在 - 性能优化: 避免在地图加载完成前频繁操作图层
- 图层命名: 使用清晰的图层 ID 命名规范
- 数据源分离: 将数据源和图层配置分离,便于维护
- 事件监听 : 在
load事件回调中操作图层,确保样式已加载
🔗 延伸阅读
-
下一课预告:将继续学习地图图层的基础知识
本文是MapLibre GL JS实践课程系列的一部分,欢迎关注收藏