首页 / Leaflet / API 文档
Canvas
先看结论
用一张覆盖视野的画布绘制所有矢量,要素不生成独立 DOM 节点。
L.canvas(options) → Canvas
参数
| 选项 | 默认值 | 说明 |
|---|---|---|
padding | 0.1 | 画布向视野外扩展的比例,减少拖拽时的整层重绘 |
tolerance | 0 | 点击命中检测的外扩像素,细线用 3–5 更好点 |
pane | 'overlayPane' | 画布挂载的 pane |
map.preferCanvas | false | 地图级开关,等价于全局改用 Canvas |
Path.renderer | — | 单个要素指定画布渲染器 |
成员
| 成员 | 返回值 | 说明 |
|---|---|---|
addTo(map) | this | 挂载渲染器,创建画布节点 |
remove() | this | 移除画布与全部要素 |
getPane() | HTMLElement | 读取 pane 节点 |
options.tolerance | Number | 修改后新建的要素按新值命中 |
L.canvas() | Canvas | 每次调用返回新实例;未指定 renderer 的矢量才共享地图默认渲染器 |
var canvas = L.canvas({ padding: 0.2, tolerance: 4 });
/* 3000 个随机点,全部画进同一张画布 */
var pts = [];
for (var i = 0; i < 3000; i++) {
pts.push([
39.85 + Math.random() * 0.10,
116.32 + Math.random() * 0.16
]);
}
var group = L.layerGroup(pts.map(function (p) {
return L.circleMarker(p, {
renderer: canvas,
radius: 3,
weight: 1,
color: '#ffffff',
fillColor: '#1f5fd0',
fillOpacity: 0.8
});
})).addTo(map);
/* 点击命中仍按要素判断,e.layer 是对应的 circleMarker */
group.on('click', function (e) {
console.log(L.Util.stamp(e.layer));
});
Canvas 适合「数量多、样式简单」的矢量。几千个点用 SVG 会生成同样多的
<path> 节点,拖拽掉帧;换成 Canvas 后节点数恒定。代价是
className、CSS 动画、滤镜、逐要素阴影全部失效,图层顺序只能靠
bringToFront 调整。
tolerance 对环形、细线尤其重要:默认 0 时点在 1px 宽的线上几乎
命中不了。设为 4–6 像素手感更好,但相邻要素密集时会出现「点到的是旁边那个」,
需要结合 bringToFront 或改用命中优先级更高的方案。
经纬志(2026)。《Canvas》。https://www.jingweizhi.com/leaflet/api/canvas.html(访问日期 2026-11-03)。