Mapbox GL JS предоставляет класс Popup как базовый механизм отображения всплывающих информационных окон поверх карты. Popup является самостоятельным DOM-элементом, привязанным к координатам карты или к объектам (например, маркерам), и используется для вывода контекстной информации: описаний объектов, данных API, пользовательских подсказок и динамического контента.
Popup создаётся через конструктор mapboxgl.Popup, где
задаются параметры поведения и внешнего вида.
const popup = new mapboxgl.Popup();
Базовая конфигурация позволяет управлять ключевыми аспектами отображения:
closeButton — отображение кнопки закрытияcloseOnClick — закрытие при клике по картеanchor — позиция “якоря” относительно точкиoffset — смещение относительно координатыclassName — пользовательский CSS-классПример с настройкой поведения:
const popup = new mapboxgl.Popup({
closeButton: false,
closeOnClick: true,
anchor: 'top',
offset: 10
});
Popup не отображается сам по себе — он должен быть привязан к
географической точке через setLngLat.
popup
.setLngLat([69.589, 42.874])
.setHTML('<h3>Объект</h3><p>Описание точки</p>')
.addTo(map);
Метод addTo(map) добавляет popup в контекст карты и
делает его видимым.
Popup поддерживает несколько способов задания содержимого.
popup.setHTML(`
<div>
<strong>Название объекта</strong>
<p>Краткое описание</p>
</div>
`);
const el = document.createElement('div');
el.innerHTML = '<p>Содержимое через DOM</p>';
popup.setDOMContent(el);
Использование setDOMContent позволяет интегрировать
сложную логику: формы, кнопки, обработчики событий.
popup.setDOMContent(document.createElement('div'));
или обновление через пустой HTML:
popup.setHTML('');
Наиболее распространённый сценарий — привязка всплывающего окна к маркеру.
const marker = new mapboxgl.Marker()
.setLngLat([69.589, 42.874])
.addTo(map);
const popup = new mapboxgl.Popup({ offset: 25 })
.setHTML('Информация о маркере');
marker.setPopup(popup);
При клике на маркер popup открывается автоматически.
Popup управляет своим жизненным циклом в зависимости от настроек:
closeOnClick: true — закрытие при клике вне popupcloseOnClick: false — остаётся открытымПример:
const popup = new mapboxgl.Popup({
closeOnClick: false
})
.setLngLat([69.589, 42.874])
.setHTML('Закрывается только вручную')
.addTo(map);
Anchor определяет, с какой стороны точки привязывается popup.
Доступные значения:
topbottomleftrighttop-lefttop-rightbottom-leftbottom-rightconst popup = new mapboxgl.Popup({
anchor: 'bottom'
});
Popup автоматически корректирует позицию, если выходит за границы viewport.
Offset позволяет точно настроить расположение относительно точки.
const popup = new mapboxgl.Popup({
offset: [0, -20]
});
Также поддерживаются объектные конфигурации для разных якорей:
const popup = new mapboxgl.Popup({
offset: {
top: [0, 10],
bottom: [0, -10],
left: [10, 0],
right: [-10, 0]
}
});
Popup можно обновлять без пересоздания:
popup.setHTML('<p>Загрузка...</p>');
fetch('/api/info')
.then(res => res.json())
.then(data => {
popup.setHTML(`<p>${data.name}</p>`);
});
Popup реагирует на изменения состояния:
popup.on('open', () => {
console.log('Popup открыт');
});
popup.on('close', () => {
console.log('Popup закрыт');
});
Также можно отслеживать изменения карты, чтобы синхронизировать данные.
Одновременно может существовать несколько popup, но управление ими требует контроля состояния:
const popup1 = new mapboxgl.Popup().setLngLat([69.5, 42.8]).setHTML('A');
const popup2 = new mapboxgl.Popup().setLngLat([69.6, 42.9]).setHTML('B');
popup1.addTo(map);
popup2.addTo(map);
Для предотвращения наложений часто применяется стратегия закрытия предыдущего popup перед открытием нового.
Popup имеет внутреннюю структуру DOM:
.mapboxgl-popup.mapboxgl-popup-content.mapboxgl-popup-close-button.mapboxgl-popup-tipКастомизация через CSS:
.mapboxgl-popup-content {
background: #1e1e1e;
color: white;
border-radius: 8px;
padding: 12px;
}
.mapboxgl-popup-tip {
border-top-color: #1e1e1e;
}
С помощью className можно задавать уникальные стили:
const popup = new mapboxgl.Popup({
className: 'custom-popup'
});
Popup может следовать за курсором мыши:
const popup = new mapboxgl.Popup({
closeButton: false,
closeOnClick: false,
trackPointer: true
})
.setHTML('Данные под курсором')
.addTo(map);
Этот режим полезен для интерактивной аналитики слоёв.
При массовом использовании popup важно учитывать:
Оптимизированный подход:
const popup = new mapboxgl.Popup();
map.on('mousemove', (e) => {
popup
.setLngLat(e.lngLat)
.setHTML(`x: ${e.point.x}, y: ${e.point.y}`)
.addTo(map);
});
Popup часто используется как слой отображения данных API:
map.on('click', (e) => {
fetch(`/api/feature?lng=${e.lngLat.lng}&lat=${e.lngLat.lat}`)
.then(res => res.json())
.then(data => {
new mapboxgl.Popup()
.setLngLat(e.lngLat)
.setHTML(`<strong>${data.title}</strong>`)
.addTo(map);
});
});
Popup поддерживает явное удаление:
popup.remove();
Это освобождает DOM и предотвращает утечки памяти при динамических интерфейсах.
Popup автоматически синхронизируется с:
и пересчитывает позицию в реальном времени без дополнительного кода.