mapbox multipoint interaction

by Trufi

HTML

<script src="https://api.mapbox.com/mapbox-gl-js/v2.14.1/mapbox-gl.js"></script>
<link rel="stylesheet" href="https://api.mapbox.com/mapbox-gl-js/v2.14.1/mapbox-gl.css">
<div id="map"></div>

CSS

body {
  margin: 0;
  padding: 0;
}

#map {
  position: absolute;
  top: 0;
  bottom: 0;
  width: 100%;
}

JavaScript

mapboxgl.accessToken = 'pk.eyJ1IjoidHJ1ZmkiLCJhIjoiY2lrcW1pdzU4MDEyanUwbTIwZzJ1bmY4dSJ9.5qW-pRcgah2nQIWpGKwHRg';

const map = new mapboxgl.Map({
  container: 'map',
  style: 'mapbox://styles/mapbox/streets-v12',
  center: [-1.206260577493481, 51.73210866268451],
  zoom: 12
});

const pointsData = {
  type: 'FeatureCollection',
  features: [{
      type: 'Feature',
      id: 0,
      properties: {
        label: 'Point A',
      },
      geometry: {
        coordinates: [-1.2398090901854175, 51.733472092221604],
        type: 'Point',
      },
    },
    {
      type: 'Feature',
      id: 1,
      properties: {
        label: 'Point B',
      },
      geometry: {
        coordinates: [-1.2200810764214225, 51.7339360631027],
        type: 'Point',
      },
    },
    {
      type: 'Feature',
      id: 2,
      properties: {
        label: 'Point C',
      },
      geometry: {
        coordinates: [-1.2045983314419004, 51.7339360631027],
        type: 'Point',
      },
    },
  ],
};

map.on('load', () => {
  map.addSource('points', {
    type: 'geojson',
    data: pointsData,
  });

  map.addLayer({
    id: 'points-layer',
    type: 'symbol',
    source: 'points',
    layout: {
      'icon-image': 'hu-motorway-2',
      'text-field': ['get', 'label'],
      'text-font': ['Open Sans Semibold', 'Arial Unicode MS Bold'],
      'text-offset': [0, 1],
      'text-anchor': 'top',
    },
    paint: {
      'text-color': [
        'case',
        ['boolean', ['feature-state', 'hover'], false],
        '#ff0000',
        '#475dcd',
      ],
      'text-halo-color': '#ffffff',
      'text-halo-width': 2,
    },
  });
});

map.on('click', 'points-layer', (ev) => {
  const feature = ev.features[0];
  alert(`Click on point with id: "${feature.id}" and label: "${feature.properties.label}"`);
});

let hoveredFeature;

map.on('mouseover', 'points-layer', (ev) => {
  const feature = ev.features[0];

  if (hoveredFeature) {
    map.setFeatureState({
      source: 'points',
      id:...