🚗

Mapbox で移動する点を描く

2020/10/27に公開

よくある「スマートフォンなどの位置情報を受信して、その位置を地図上に示す」を Mapbox で行います。

Mapbox でのピン表示について考える で書いたとおり、「頻繁なアニメーションが伴う場合は Symbol Layer」がふさわしいと考えるので、今回はそちらを使用します。

とは言っても、ここではダミーデータとして緯度経度のリストを走査してシンボルを移動させているだけなので、ただのシンボルの再描画の例になります。

index.js

事前準備が長いですが、重要なのは最下部 setInterval の中で行っている dataSource.setData() で、これを行うと地図(上のレイヤ)が更新されます。

ところどころ省略しているので、完全版は DEMO を見てください。

const map = new mapboxgl.Map({
  container: 'map',
  center: [136.53890132904053,34.844644908488974],
  zoom: 14,
  style: {
    //  中略 //
  },      
});

const waypoints = [
  [136.53890132904053,34.844644908488974],
  [136.54332160949704,34.840242190008105],
  // 中略 //
  [136.5387511253357,34.84480340196252]
];

// Symbol Layer
const symbolData = {
	'type': 'FeatureCollection',
	'features': []
};
map.on('load', function() {
  map.loadImage(
    'https://img.icons8.com/material/32/0000FF/marker--v1.png',
    (error, image) => {
      if (error) {
        throw error;
      }
      map.addImage('iconA', image);
      map.addSource('point', {
        'type': 'geojson',
        'data': symbolData
      });
      map.addLayer({
        'id': 'points',
        'type': 'symbol',
        'source': 'point',
        'layout': {
          'icon-image': 'iconA',
          'icon-size': 1,
          'icon-allow-overlap': true,
          'icon-ignore-placement': true,          
        }
      });
      
      let counter = 0;
      setInterval(() => {
        symbolData.features.splice(0);
        symbolData.features.push({
          'type': 'Feature',
          'geometry': {
            'type': 'Point',
            'coordinates': waypoints[counter % waypoints.length]
          }
        });

        const dataSource = map.getSource('point');
        dataSource.setData(symbolData);
  
      	counter = counter + 1;
      }, 1000);      
    }
  );
});

DEMO

Discussion