В Mapbox GL JS маркеры представляют собой отдельный слой пользовательских DOM-элементов, привязанных к географическим координатам на карте WebGL. В отличие от источников и слоёв (sources и layers), маркеры не рендерятся в WebGL-пайплайне, а существуют как HTML-элементы, позиционируемые поверх карты. Это делает их гибкими для сложного UI, но менее производительными при большом количестве объектов.
Класс Marker реализует привязку DOM-элемента к
координатам карты. Он работает поверх экземпляра Map и
синхронизируется с его состоянием (zoom, center, bearing, pitch).
Создание маркера:
const marker = new mapboxgl.Marker()
.setLngLat([30.5, 50.5])
.addTo(map);
В основе лежит контейнерный HTMLElement, который либо
создаётся библиотекой автоматически, либо передаётся разработчиком.
Сигнатура конструктора:
new mapboxgl.Marker(options)
Основные опции:
element — пользовательский DOM-элемент маркераanchor — точка привязки (например,
"center", "top", "bottom")offset — смещение маркера в пикселяхcolor — цвет стандартного маркераscale — масштаб стандартного маркераdraggable — возможность перетаскиванияПример:
const marker = new mapboxgl.Marker({
color: '#ff0000',
scale: 1.2,
draggable: true
});
Метод setLngLat определяет географическое положение:
marker.setLngLat([longitude, latitude]);
Внутренне координаты преобразуются в экранные пиксели с учётом текущего состояния камеры карты: зума, наклона и поворота.
Получение текущей позиции:
const lngLat = marker.getLngLat();
Для отображения маркер должен быть добавлен в экземпляр карты:
marker.addTo(map);
Удаление:
marker.remove();
После удаления DOM-элемент отсоединяется от контейнера карты, но сам экземпляр Marker сохраняется и может быть повторно добавлен.
Marker может полностью заменять стандартную иконку собственным DOM:
const el = document.createElement('div');
el.className = 'custom-marker';
el.style.width = '20px';
el.style.height = '20px';
el.style.background = 'blue';
const marker = new mapboxgl.Marker(el)
.setLngLat([30, 50])
.addTo(map);
Это позволяет создавать сложные визуальные компоненты: аватары, SVG-иконки, мини-карточки состояния.
При включённой опции draggable: true маркер становится
интерактивным:
const marker = new mapboxgl.Marker({ draggable: true })
.setLngLat([30, 50])
.addTo(map);
Доступны события:
dragstartdragdragendПример обработки:
marker.on('dragend', () => {
const position = marker.getLngLat();
console.log(position);
});
При перетаскивании происходит постоянный пересчёт координат на основе позиции курсора и матрицы трансформации карты.
Marker поддерживает проксирование DOM-событий:
marker.getElement().addEventListener('click', () => {
console.log('click');
});
Также доступны события через API карты при использовании
popup или взаимодействий через контейнер.
Маркер часто используется вместе с всплывающими окнами:
const popup = new mapboxgl.Popup({ offset: 25 })
.setText('Точка интереса');
new mapboxgl.Marker()
.setLngLat([30, 50])
.setPopup(popup)
.addTo(map);
Popup привязывается к маркеру и автоматически следует за его положением.
Параметр anchor управляет точкой привязки
DOM-элемента:
"center""top""bottom""left""right""top-left",
"bottom-right")Пример:
new mapboxgl.Marker({ anchor: 'bottom' })
Это критично при работе с иконками, имеющими “ножку” (например, стандартные пины).
offset задаёт смещение в пикселях относительно
географической точки:
new mapboxgl.Marker({
offset: [0, -10]
});
Используется для точной подгонки UI-элементов, особенно при кастомных иконках разного размера.
Marker не масштабируется автоматически как WebGL-слой. Его размер фиксирован в пикселях, поэтому при изменении зума:
Это создаёт эффект “плавающих UI-элементов”, что полезно для интерфейсных меток, но может быть ограничением при большом количестве объектов.
Marker основан на DOM, поэтому:
Для массовых данных предпочтительнее использовать
GeoJSONSource и circle/symbol
layers внутри Mapbox GL JS.
Marker часто применяется как контейнер для сложного UI:
const el = document.createElement('div');
el.innerHTML = `
<div class="card">
<strong>Объект</strong>
<span>Статус: активен</span>
</div>
`;
new mapboxgl.Marker(el)
.setLngLat([30, 50])
.addTo(map);
Такие конструкции позволяют внедрять полноценные интерактивные элементы поверх карты.
Типичный жизненный цикл:
marker.setLngLat([31, 51]);
marker.addTo(map);
marker.remove();
Экземпляр остаётся пригодным для повторного использования.
Marker автоматически подписывается на изменения:
movezoomrotatepitchПри каждом изменении камеры происходит перерасчёт проекции координат в экранное пространство с использованием матрицы трансформации WebGL-сцены.
Marker применяется в следующих сценариях:
При этом архитектурно важно разделять:
В Mapbox экосистеме это разделение считается ключевым для масштабируемых картографических приложений.