关于 maplibre-cartography
面向 MapLibre 样式作者的制图指导,涵盖标签对比度、视觉层级和图层顺序。内容还说明如何针对影像底图调整符号与道路样式,避免自定义数据遮挡标签。
主要功能
- 01按底图类型设置标签颜色与光晕
- 02建立文字和要素的视觉层级
- 03调整影像底图上的道路样式
- 04确定数据图层的插入顺序
- 05检查样式的对比度与可访问性
适用场景
- 01发布前审查地图样式
- 02提高影像地图上的标签可读性
- 03向现有底图添加数据而不遮挡标签
- 04为影像底图调整道路配色与层级
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ maplibre/ maplibre-agent-skills --skill maplibre-cartography安装后在 Claude Code 中输入/maplibre-cartography确认已加载。
详细介绍
MapLibre 制图
MapLibre 会精确渲染你描述的样式。本技能介绍如何做好描述:为标签选择在任何底图上都清晰易读的颜色、构建连贯的视觉层级,以及正确排列样式图层。有关字体/字形设置,请参阅 maplibre-fonts-glyphs;有关精灵图、图标来源和路线盾牌,请参阅 maplibre-sprites-icons。
何时使用本技能
- 在发布前,根据制图最佳实践审查样式
- 为新样式或迁移后的样式选择标签
text-color和text-halo-color,或点符号/图标颜色——包括在纯色矢量底图上清晰可读,但切换到影像底图后消失或与背景混在一起的情况 - 设置或调试
sprite、图标或路线盾牌——请参阅 maplibre-sprites-icons;有关glyphs,请参阅 maplibre-fonts-glyphs - 向现有底图注入自定义数据图层,同时不遮挡标签
- 将浅色底图矢量调色板中的道路重新设置样式,使其融入影像,而非浮于影像之上
- 审查样式的对比度可访问性
底图类型决定标签颜色
MapLibre 会动态放置标签,因此无法像静态地图那样遮住每个标签背后的背景。相反,应选择一种 text-halo-color,使标签与可能出现的所有背景区分开来,并选择一种能在光晕上清晰可读的 text-color。对于色调统一的底图(纯浅色或深色矢量底图),光晕可以与底图色调一致,而无需与其形成对比——由文字本身与底图形成对比。影像没有统一的色调可供匹配,因此光晕必须与所有可能的背景形成对比:
| 底图类型 | 背景 | 推荐文字颜色 | 推荐光晕 |
|---|---|---|---|
| 浅色矢量(街道、OpenFreeMap positron) | 浅色/白色 | 深色(#333 或类似颜色) | 浅色半透明(rgba(255,255,255,0.8)) |
| 深色矢量(dark-matter、夜间导航) | 深色 | 白色或近白色(#ffffff) | 深色半透明(rgba(0,0,0,0.75)) |
| 卫星或航空影像(NAIP、Sentinel-2) | 不可预测——明亮的农田、深色森林、城市屋顶 | 白色(#ffffff) | 深色半透明(rgba(0,0,0,0.75)) |
最常见的错误是使用不透明的白色光晕:除非背景是纯白色,否则它会破坏标签与其所标注要素之间的空间联系——请添加透明度。第二常见的错误是在影像上沿用浅色矢量调色板,这样在深色地形、森林和水面上就无法清晰显示。在影像上,始终使用白色文字和深色半透明光晕("text-color": "#ffffff"、"text-halo-color": "rgba(0,0,0,0.75)"、"text-halo-width": 1.2)。
对于有色调的标签(公园、水域、兴趣点),请使用语义颜色的浅色调(公园用 #c8f5cc,水域用 #a8d8ff),而不要使用深色饱和版本:浅色调在深色光晕上清晰可读,同时保留语义含义;完全饱和的颜色在小尺寸下对比效果较差。
光晕宽度
较宽的光晕能提高可读性,但也会增加视觉重量。常用值如下:
| 场景 | text-halo-width |
|---|---|
| 正文标签(城市、城镇、村庄) | 0.8–1.5 |
| 国家/大陆(大号文字) | 1.5–2.0 |
| 小型 POI 或山峰标签 | 0.8–1.2 |
| 使用彩色文字的水域/公园标签 | 1.0–1.5 |
text-halo-width 的单位是相对于文字的像素。光晕不得延伸到相邻标签上:小字号文字的光晕应保持紧凑,并增加透明度。
影像上的点符号和图标
标记面临着与标签相同的图底关系问题,但需要采用不同的处理方式。航空影像上的彩色图标会与不可预测、繁杂且_低饱和度_的摄影背景争夺视觉注意力。
- 如果背景本身就有符号的色相,就无法将符号与背景区分开来。 绿色图标叠在绿色公园上,棕色图标叠在裸露土壤上:两者都会被伪装起来。大多数航空影像的饱和度都较低,因此背景最弱的维度是彩度。使用高饱和度填充色(琥珀色、陶土色),既能形成区分,又保留自然、质朴的色调。如果场景中也有该色调,只改变色相、换成另一种大地色调并无帮助。
- 使用
icon-halo-color/icon-halo-width将符号从背景中凸显出来,方法与给标签加光晕完全相同——这只对 SDF 精灵图有效(通过addImage(..., { sdf: true })添加的图像,或以 SDF 构建的精灵图);全彩图标没有光晕绘制属性,因此必须将边缘效果直接绘制到图稿中。浅色的细光晕在深色树冠和水面上清晰可见;深色边缘则能在亮色土壤和屋顶上保持清晰。光晕应保持纤细——粗环看起来像贴纸——但有一类符号例外:需要主导地图的符号(紧急标记、最重要的单个专题要素),此时较粗的光环正是所需效果。 - 纯色填充在照片上看起来像贴纸。 为地貌或 3D 符号添加能体现立体感的线索。渐变(受光坡面较亮、背光坡面较暗)能呈现形状。_接触阴影_是在底部下方聚集的扁平模糊椭圆,比偏移的投影更能将符号固定在地面上;偏移投影会让符号看起来悬浮起来。符号的光照和阴影方向应与底图的
hillshade-illumination-direction(通常为 NW,即 315°)一致,这样符号就能与地形处于相同的光照环境中。
通过 addImage 添加 SVG 图标: 在运行时将 SVG 加载到精灵图图像中时(获取 SVG,将其解码为 Image,然后调用 map.addImage),SVG 会在解码时栅格化,因此 linearGradient 和 feDropShadow 滤镜会正确烘焙进去。[1] 有两点需要注意:扩展 viewBox,避免光晕和阴影在图标边缘被裁切;并确保 width/height 与 viewBox 成比例,避免字形变形。对于密集的点数据,请使用 "icon-allow-overlap": true。
视觉层级
层级安排合理,意味着最重要的要素会在适当的缩放级别占据主导地位——这对标签和线/面数据图层同样适用。对于标签,MapLibre 通过文字大小、字重、字间距、对比度和缩放范围内的可见性来控制层级。线和面也适用同样的方法:line-width 和填充饱和度可替代文字大小;与底图的对比度(低饱和背景上的高饱和线条、繁杂背景上的低饱和填充)在层级塑造上的作用不亚于尺寸——有关线/面的详细说明,请参阅下文的在影像上设置矢量道路样式。
按要素类别设置文字大小
要素重要性越低,文字大小应越小。以下缩放级别是起点;请根据你的瓦片架构和缩放范围进行调整:
| 标签类型 | 基础缩放级别 | 最大缩放级别 | 大小范围(px) |
|---|---|---|---|
| 洲 | 1 | 4 | 14–20 |
| 国家 | 2 | 7 | 11–17 |
| 城市 | 7 | 11 | 14–24 |
| 城镇 | 10 | 14 | 11–16 |
| 村庄 / 小村落 | 11 | 16 | 10–14 |
| 机场 / POI | 10 | 16 | 12–14 |
| 山峰 / 峰顶 | 8 | 13 | 10–11 |
在相同缩放级别下,兴趣点(POI)标签的视觉效果应比居民点标签更轻(尺寸更小、字重更细)。在显示起伏平缓地形(如丘陵)的影像地图上,山峰标签应比机场标签更小——它们是海拔标记,而不是主要地标。
字体粗细
使用 text-font(例如 ["Noto Sans Bold"])通过字重强化层级:国家和首府使用粗体,城镇、城市和大多数标签使用常规体,水体、公园和地区使用_斜体_(这是一种如今已不总是遵循的制图惯例)。
多行标签
对于紧凑的双行标签(例如符号字符位于名称上方),请将 text-line-height 降至 1.0 以下,以避免行间距过大:
{
"text-field": "△\n{name:latin}",
"text-line-height": 0.9,
"text-max-width": 8
}
约 0.9 的值可以在小字号下生成紧凑易读的双行标签。不要低于约 0.8,否则使用标准字号时文本行会重叠。
文字转换和间距
- 国家和洲的标签使用
"text-transform": "uppercase"——这是一种传统的制图惯例 - 地区标签使用
"text-letter-spacing": 0.05–0.1,使文字在区域内展开
在影像上设置矢量道路样式
浅色底图样式(OSM Bright、OSM Liberty)中的矢量道路调色板经过调校,能在浅色纸面上醒目呈现,因此使用了高饱和度、暖色调和完全不透明的颜色。底图换成影像后,这些特性就会与照片争抢注意力。应将影像作为主体,将道路作为叠加其上的参考信息,而不是反过来。
- 大幅降低饱和度。 将填充和描边调整为中性灰或柔和色调。鲜亮的橙色 / 黄色道路层级(
#f90、#fd4、#b06010)最容易造成问题;请用浅灰色替换填充,并用深灰色或深色同色系替换描边。 - 用宽度和明度体现层级,而非色相。 宽度阶梯已经表达了高速公路 > 居住道路;无需使用鲜艳的颜色来传达这一点。
- 保持不透明,而非透明。 半透明道路会让影像纹理透出,使整张地图显得扁平。建议使用不透明填充,并搭配明度受控的描边,以呈现清晰、分层的道路。
- 用描边勾勒道路。 比填充更深的描边能绘制出中线,防止双幅车道合并成一团。_镂空描边_采用填充色自身的深色调,而非突兀的黑色,可以勾勒边缘,又不会产生卡通式的粗重轮廓。
- 按缩放级别控制亮度。 为高缩放级别调校的道路,在初始的低缩放级别下往往显得过重,因为此时只显示细窄的主要道路,而且描边会占据主导。应按缩放级别插值颜色:低缩放级别时描边较深,放大时逐渐变浅;填充则应是最浅的元素,并在道路网络逐渐完整显示时变亮。
{
"line-color": ["interpolate", ["linear"], ["zoom"], 10, "#454545", 12, "#5a5a5a", 14, "#6e6e6e"]
}
精灵图和图标
精灵图配置、加载多个精灵图集、托管精灵图资源、从 SVG 构建精灵图以及诊断路线盾牌相关内容,请参阅 maplibre-sprites-icons。
样式图层顺序
MapLibre 按照样式中 layers 数组的顺序渲染图层——第一项最先绘制(位于底部),最后一项最后绘制(位于顶部)。顺序设置不当,是数据图层遮挡底图标签的最常见原因。
注入模式
在运行时向现有底图样式添加自己的数据时,应将数据图层插入第一个符号图层之前(使用 map.getStyle().layers.find((l) => l.type === 'symbol')?.id 查找其 ID,并将其作为 addLayer 的第二个参数传入),这样几何图形才会显示在标签下方。如果不传入该参数,数据图层会显示在所有内容上方,包括标签。
自定义样式的规范图层顺序
从头构建样式时,请遵循以下从底到顶的顺序:
background- 栅格影像(如果使用卫星/航拍数据源)
- 山体阴影图层(如有 — 配置请参见 maplibre-terrain-rendering)
- 地形填充(水域、陆地、公园 — 多边形图层)
- 线图层(道路、边界、河流)
- 你的数据多边形和线图层
- 底图自身的符号图层(地点标签、道路标签)
- 你的数据符号/标签图层(如有)
山体阴影应紧邻栅格影像上方、所有矢量图层下方,并设置足够的透明度,使影像能够透显。如果为影像添加透明度并将其叠加在山体阴影上方,影像会显得褪色或黯淡。如果将山体阴影应用于矢量图层,线条和填充颜色会显得斑驳、模糊或暗淡。
无障碍
MapLibre 样式会在浏览器中渲染为 WebGL 画布。无障碍方面的注意事项:
- 文本对比度: WCAG 2.1 AA 要求普通文本的对比度为 4.5:1,大号文本为 3:1(SC 1.4.3)。白色文本配合
rgba(0,0,0,0.75)光晕,在大多数背景下都符合要求 — 请使用 WebAIM Contrast Checker 等工具检查文本与光晕组合后的颜色,而不只是文本本身。 - 不要只依赖颜色: 除色相外,还应使用形状、大小或图案。
- 标签最小尺寸: 即使在低缩放级别,也应优先选择从 10px 开始的尺寸档位。
- 屏幕阅读器与 WebGL 画布: MapLibre 的画布本身无法供屏幕阅读器访问。为提供无障碍地图体验,请提供可访问的替代内容,例如数据表或地图内容的文字说明。
相关技能
- maplibre-sprites-icons —
sprite基础 URL 和{id, url}数组格式、自托管和构建精灵图、使用addImage添加运行时图像,以及路线盾牌。 - maplibre-fonts-glyphs — 设置
glyphsURL、自托管或生成字体 PBF、GL JS 本地字体回退、MapLibre Native 的font-faces,以及非拉丁文字脚本支持。 - maplibre-tile-sources — 为数据集选择 GeoJSON 或瓦片。
- maplibre-source-wiring — 让已配置的数据源完成渲染:TileJSON、
source-layer、图层顺序和 CORS。 - maplibre-pmtiles-patterns — 从 PMTiles 文件提供影像(栅格)和地形数据源。
- maplibre-terrain-rendering — 山体阴影、彩色地形渲染、等高线和 3D 地形配置。
参考资料
此技能内容为快照。 如果主要来源与本文档内容相矛盾 — 上方的参考资料、MapLibre 当前文档,或运行 MapLibre 时观察到的实际行为 — 请以该来源为准。请遵循该来源,然后报告此处的不一致,并注明来源和 MapLibre 版本:修改你本地安装的副本对其他人没有帮助,而且下次更新时会被覆盖。