Markers 和 Popups
本页记录 Mapbox GL JS 中的 Markers 和 Popups UI 组件,它们允许开发人员向地图添加交互式兴趣点和信息窗口。与直接在 WebGL 中渲染的地图 layers 不同,markers 和 popups 被实现为定位在地图画布上的 HTML 元素。
有关导航 controls、scale controls 等其他 UI 组件的信息,请参阅 Controls。有关交互处理的详细信息,请参阅 Interaction and Events。
概述和架构
Markers 和 popups 是 Mapbox GL JS 中 UI components 系统的一部分。它们提供了一种向地图添加交互元素的方法,即使地图被平移、缩放或旋转,这些元素仍保持与特定地理坐标的关联。
Marker 系统
Markers 是 HTML 元素,在地图上视觉标记特定的地理位置。它们可以是简单的默认 markers 或自定义的 HTML 元素。
创建和定位 Markers
Markers 使用 Marker 类构造函数创建,并使用 setLngLat() 定位:
// 创建默认 marker
const marker = new mapboxgl.Marker()
.setLngLat([经度, 纬度])
.addTo(map);当 marker 被添加到地图时,它创建一个带有类 mapboxgl-marker 的 DOM 元素。Marker 的位置在地图移动时使用 CSS transforms 维护。
"创建 DOM 元素""更新位置(地图移动时)""更新 transform"Marker 样式和自定义
Markers 可以通过以下方式自定义:
- 将 HTML 元素传递给构造函数
- 设置颜色、旋转和缩放等属性
- 使它们可拖动以进行用户交互
// 创建自定义 HTML 元素
const el = document.createElement('div');
el.className = 'custom-marker';
// 使用自定义元素创建 marker
const marker = new mapboxgl.Marker({
element: el,
color: '#FF0000',
scale: 1.5,
draggable: true,
rotation: 45
}).setLngLat([经度, 纬度])
.addTo(map);Markers 的 CSS 定义了它们的基本外观,具有绝对定位和不透明度过渡:
.mapboxgl-marker {
position: absolute;
top: 0;
left: 0;
will-change: transform;
opacity: 1;
transition: opacity 0.2s;
}Popup 系统
Popups 是在地图上显示内容的信息窗口。它们可以是独立的或附加到 markers。
创建和使用 Popups
Popups 使用 Popup 类创建,可以显示 HTML 内容:
// 创建独立的 popup
const popup = new mapboxgl.Popup()
.setLngLat([经度, 纬度])
.setHTML('<h3>Hello World!</h3>')
.addTo(map);调试页面的示例展示了在地图点击时创建 popup:
map.on('click', function(e) {
if (e.originalEvent.shiftKey) return;
(new mapboxgl.Popup())
.setLngLat(map.unproject(e.point))
.setHTML("<h1>Hello World!</h1>")
.addTo(map);
});Popup 结构和组件
Popup 由几个带有特定类的 HTML 元素组成:
这些组件的 CSS 定义了它们的外观:
| 组件 | CSS 类 | 目的 |
|---|---|---|
| 容器 | .mapboxgl-popup | 带有定位的主 popup 容器 |
| 提示 | .mapboxgl-popup-tip | 指示锚定点的三角形指针 |
| 内容 | .mapboxgl-popup-content | popup 内容的容器 |
| 关闭按钮 | .mapboxgl-popup-close-button | 关闭 popup 的按钮 |
Popup 锁定和定位
Popups 可以锁定相对于其地理坐标的不同位置。锚定点确定 popup 如何定位以及提示指向哪个方向。
使用 setAnchor() 方法设置锚定位置:
popup.setAnchor('top-left');不同锚定点的 CSS 改变 flex 方向和提示样式:
.mapboxgl-popup-anchor-top,
.mapboxgl-popup-anchor-top-left,
.mapboxgl-popup-anchor-top-right {
flex-direction: column;
}
.mapboxgl-popup-anchor-bottom,
.mapboxgl-popup-anchor-bottom-left,
.mapboxgl-popup-anchor-bottom-right {
flex-direction: column-reverse;
}Markers 和 Popups 之间的集成
Popups 可以附加到 markers 以创建交互式兴趣点:
// 创建带有附加 popup 的 marker
const marker = new mapboxgl.Marker()
.setLngLat([经度, 纬度])
.setPopup(new mapboxgl.Popup().setHTML('<h3>Hello World!</h3>'))
.addTo(map);
// popup 将在 marker 被点击时显示常见交互模式
"点击 marker""显示 popup""添加到地图""点击关闭按钮""从地图中移除""点击其他位置""关闭 popup""从地图中移除"Popup 跟踪和悬停效果
Popups 可以配置为跟踪鼠标指针,用于创建悬停效果:
const popup = new mapboxgl.Popup({
closeButton: false,
closeOnClick: false,
trackPointer: true
});CSS 包含用于跟踪指针行为的特定类:
.mapboxgl-popup-track-pointer {
display: none;
}
.mapboxgl-map:hover .mapboxgl-popup-track-pointer {
display: flex;
}
.mapboxgl-map:active .mapboxgl-popup-track-pointer {
display: none;
}高级自定义
自定义样式
Markers 和 popups 可以通过定位其类名使用自定义 CSS 进行样式设置:
/* 自定义 popup 样式 */
.mapboxgl-popup-content {
background-color: #3e3e3e;
color: white;
border-radius: 5px;
padding: 15px;
}
.mapboxgl-popup-tip {
border-top-color: #3e3e3e; /* 对于底部锚定的 popups */
}
/* 自定义 marker 样式 */
.custom-marker {
background-image: url('marker.png');
background-size: cover;
width: 30px;
height: 30px;
cursor: pointer;
}可访问性考虑
创建 markers 和 popups 时,通过以下方式考虑可访问性:
- 在 popups 内使用适当的语义 HTML
- 向自定义 marker 元素添加 ARIA 属性
- 确保文本内容有足够的颜色对比度
- 提供键盘导航支持
性能考虑
对于具有许多 markers 的地图:
- 考虑使用来自数据源的 symbol layers 以获得更好的性能
- 根据视口动态添加和移除 markers
- 为密集的 marker 集合实现聚类
- 限制同时打开的 popups 数量
事件
Markers 和 popups 都会发出可以处理的事件:
// Marker 事件
marker.on('dragstart', () => console.log('开始拖动'));
marker.on('dragend', () => console.log('完成拖动'));
// Popup 事件
popup.on('open', () => console.log('Popup 已打开'));
popup.on('close', () => console.log('Popup 已关闭'));有关事件处理的更多详细信息,请参阅 Interaction and Events。
参考
Marker 选项
| 选项 | 类型 | 默认值 | 描述 |
|---|---|---|---|
element | HTMLElement | 默认 marker | 用作 marker 的自定义 HTML 元素 |
color | string | '#3FB1CE' | 默认 marker 的颜色 |
scale | number | 1 | Marker 的缩放因子 |
draggable | boolean | false | 是否可以拖动 marker |
rotation | number | 0 | Marker 的旋转角度(以度为单位) |
anchor | string | 'center' | Marker 相对于坐标的位置 |
offset | PointLike | [0, 0] | 从 marker 锚定位置的像素偏移 |
Popup 选项
| 选项 | 类型 | 默认值 | 描述 |
|---|---|---|---|
closeButton | boolean | true | 是否显示关闭按钮 |
closeOnClick | boolean | true | 是否在点击地图时关闭 popup |
closeOnMove | boolean | false | 是否在地图移动时关闭 popup |
anchor | string | 'bottom' | Popup 相对于坐标的位置 |
offset | number, PointLike, Object | 0 | 从 popup 锚定位置的像素偏移 |
className | string | '' | 要添加到 popup 的附加类 |
maxWidth | string | '240px' | Popup 的最大宽度 |
trackPointer | boolean | false | Popup 是否应该跟踪鼠标指针 |
focusAfterOpen | boolean | true | Popup 在打开时是否应该获得焦点 |