Z-индексы слоев

Z-индекс в рендеринге карт в HERE Technologies и JavaScript API играет ключевую роль в управлении визуальной иерархией объектов. Любая карта представляет собой многослойную сцену, где элементы конкурируют за порядок отображения: тайлы, маркеры, полигоны, линии маршрутов, интерактивные оверлеи и пользовательские элементы интерфейса.

Визуальная модель карты строится как стек слоёв. Каждый слой имеет собственную систему приоритета, определяющую, что будет отображено выше:

  • базовые тайлы карты (фоновые слои)
  • векторные объекты (геометрия)
  • интерактивные объекты (маршруты, зоны)
  • маркеры и точки интереса
  • HTML/DOM оверлеи

Порядок этих элементов не всегда фиксирован, так как большинство объектов поддерживает параметр zIndex или аналогичную систему приоритетов.

Z-index в контексте объектов карты

В JavaScript API HERE Maps JavaScript API управление z-index чаще всего применяется к объектам слоя H.map.Object.

Каждый графический объект может иметь свой приоритет отображения:

  • Marker
  • Circle
  • Polyline
  • Polygon
  • Rect
  • пользовательские Object

Ключевое свойство:

object.setZIndex(10);

или при создании:

const marker = new H.map.Marker(coords, {
  zIndex: 5
});

Чем больше значение zIndex, тем выше объект располагается визуально.

Принцип работы zIndex в рендерере

Рендерер карты не использует только абсолютный порядок добавления объектов. Вместо этого учитываются несколько факторов:

  • значение zIndex объекта
  • тип слоя (tile, vector, overlay)
  • группа объектов (Object Group)
  • внутренний порядок в слое
  • режим сортировки (screen-space vs geo-space)

При конфликте значений приоритет обычно определяется следующим образом:

  1. слой карты (layer level)
  2. zIndex внутри слоя
  3. порядок добавления (fallback)

Z-индекс у маркеров

Маркер — один из наиболее частых объектов, где требуется контроль порядка. При наложении нескольких маркеров на одной координате используется zIndex:

const markerA = new H.map.Marker({ lat: 52.5, lng: 13.4 }, { zIndex: 1 });
const markerB = new H.map.Marker({ lat: 52.5, lng: 13.4 }, { zIndex: 10 });

Marker с большим значением перекрывает остальные независимо от порядка добавления в карту.

Дополнительно учитывается:

  • anchor (точка привязки иконки)
  • pixel offset
  • hover-state изменения zIndex

Z-index для полигонов и линий

Геометрические объекты требуют особого подхода, поскольку они могут пересекаться в пространстве.

Полилинии

polyline.setZIndex(3);

Используется для управления перекрытием маршрутов, например:

  • основной маршрут выше альтернативных
  • активный маршрут выше неактивного

Полигоны

Для полигонов важен не только zIndex, но и порядок заливки и обводки:

  • fill (заливка)
  • stroke (граница)

Значение zIndex влияет на всю геометрию целиком.

Влияние слоёв (Layer System)

Карты HERE используют систему слоёв, где каждый слой имеет собственный контекст рендеринга.

Основные типы слоёв:

  • TileLayer — базовая карта
  • VectorLayer — векторные данные
  • ObjectsLayer — пользовательские объекты
  • UI Layer — интерфейсные элементы

Слои сами по себе имеют порядок отображения, который может перекрывать zIndex внутри них. Это означает:

zIndex работает внутри слоя, но не всегда между слоями

Группировка объектов и zIndex

Объекты могут объединяться в группы:

const group = new H.map.Group();
group.setZIndex(7);

Особенность групп:

  • zIndex применяется ко всей группе
  • дочерние объекты наследуют поведение группы
  • внутри группы возможна дополнительная локальная сортировка

Это особенно важно при работе с кластерами маркеров.

Перекрытие UI и HTML оверлеев

HTML-оверлеи (DOM-based overlays) часто выходят за пределы canvas-рендеринга карты. Их порядок определяется отдельно:

  • CSS z-index
  • контейнер карты
  • stacking context браузера

В результате DOM-элементы могут полностью игнорировать zIndex объектов карты.

Типичная проблема:

  • маркер с высоким zIndex перекрывается HTML popup’ом
  • решение требует синхронизации CSS и map zIndex

Динамическое изменение zIndex

Z-index может изменяться в runtime:

map.addEventListener('tap', function (evt) {
  const obj = evt.target;
  obj.setZIndex(100);
});

Сценарии:

  • выделение объекта при клике
  • поднятие активного маршрута
  • визуализация приоритетов

Важно учитывать, что изменение zIndex может вызывать перерасчёт порядка отрисовки.

Особенности конфликтов zIndex

Конфликты возникают при:

  • одинаковых значениях zIndex
  • разных типах объектов
  • пересечении слоёв

Решение зависит от контекста:

  • явное разнесение значений (например, шаг 10)
  • разделение слоёв
  • использование группировки

Практика масштабирования значений zIndex

Для сложных карт применяется стратегия диапазонов:

  • 0–10: фоновые объекты
  • 10–50: маршруты и линии
  • 50–100: маркеры
  • 100–200: активные элементы
  • 200+: всплывающие элементы

Такой подход снижает вероятность пересечений и упрощает поддержку логики отображения.

Z-index и производительность рендеринга

Изменение zIndex влияет на:

  • порядок сортировки объектов
  • перерасчёт сцены
  • обновление буферов рендерера

Частые изменения большого количества объектов могут привести к:

  • снижению FPS
  • задержкам перерисовки
  • увеличению нагрузки на GPU

Оптимизация достигается:

  • минимизацией динамических изменений
  • группировкой объектов
  • использованием фиксированных диапазонов приоритетов