🌍

Mapbox Newsletter WEEKLY TIPSの解説 -「人口密度を視覚化」

2023/12/25に公開

はじめに

この記事は、先日配信されたMapbox NewsletterのWEEKLY TIPSで紹介されていた「人口密度を視覚化」についての解説です。このサンプルはExpressionsにおける変数の使い方を例示しています。また、Newsletterの購読はこちらからお申し込みいただけます。

以下が本サンプルのデモです。

コードを確認

まずExamplesのコードを見に行きましょう。

日本語サイト

英語サイト

基本的に同じコードですが、英語版はスタイルがMapbox Light/Dark v11にアップグレードされているのでこちらを使用します。Mapbox Light/Dark v10ではデフォルトのプロジェクションがWebメルカトルであるのに対し、Mapbox Light v11ではGlobe(3D表示された地球)なので、印象がかなり異なります。また、英語版はMapbox GL JS v3が使用されています。

HTML/CSS

まずHTMLを見ていきましょう。

以下は地図を表示するエレメントを作成しています。

<div id="map"></div>

Mapの作成

次にJavaScriptのコードを見ていきます。以下のコードはいつも通り、Mapオブジェクトを作成しています。containerで地図を表示するHTMLエレメントのidを指定します。

const map = new mapboxgl.Map({
  container: 'map', // container ID
  // Choose from Mapbox's core styles, or make your own style with Mapbox Studio
  style: 'mapbox://styles/mapbox/streets-v12', // style URL
  center: [30.0222, -1.9596], // starting position [lng, lat]
  zoom: 7 // starting zoom
});

ソースとレイヤーの追加

ソースとレイヤーを追加するので、map.on('load', ()=> {/*ここ*/})の中に処理を書きます。

まずはソースです。WebサーバにホストされたGeoJSONファイルを読み込んでいます。

map.addSource('rwanda-provinces', {
  'type': 'geojson',
  'data': 'https://docs.mapbox.com/mapbox-gl-js/assets/rwanda-provinces.geojson'
});

GeoJSONの中身を見てみると、以下のように複数のPolygonがfeaturesの中に定義されており、各Polygonのプロパティにpopulation(人口)とsq-km(面積)が格納されています。
geojson

次はレイヤーです。Polygonデータなのでfillレイヤーを使用しています。また、fill-colorExpressionsを使って色の指定をしています。

map.addLayer(
  {
    'id': 'rwanda-provinces',
    'type': 'fill',
    'source': 'rwanda-provinces',
    'layout': {},
    'paint': {
      'fill-color': [
        // 後述
      ],
      'fill-opacity': 0.7
    }
  },
  'road-label' // Place polygons under labels
);

Expressionsの内容を見ていきましょう。letはExpressions内で参照可能な変数を定義します。「変数名、変数にいれる値」の組み合わせが続き、最後の引数で実際に出力されるExpressionsを記述します。ここではdensityという変数に['/', ['get', 'population'], ['get', 'sq-km']]で定義される値を入れています。['/', ['get', 'population'], ['get', 'sq-km']]poputaionsq-kmで除算した値、つまり人口密度です。

'fill-color': [
  'let',
  'density',
  ['/', ['get', 'population'], ['get', 'sq-km']],
  // 出力は後述
],

以下は出力部分です。interpolateは補間です。ここでは線形補間(linear)を使用し、zoomレベルに応じて色を変化させます。

[
  'interpolate',
  ['linear'],
  ['zoom'],
  8,
  [
    'interpolate',
    ['linear'],
    ['var', 'density'],
    274,
    ['to-color', '#f5e5f3'],
    1551,
    ['to-color', '#8d00ac']
  ],
  10,
  [
    'interpolate',
    ['linear'],
    ['var', 'density'],
    274,
    ['to-color', '#eff3ff'],
    1551,
    ['to-color', '#08519c']
  ]
]

一つ取り出して見てみましょう。zoom8の時、さらに['var', 'density']の値を使って線形補間で色を定義しています。varletで定義した変数を呼び出します。ここでは先程定義したdensityを呼び出します。その人口密度が274のときは色を#f5e5f31551のときは色を#8d00acとしています。

  8,
  [
    'interpolate',
    ['linear'],
    ['var', 'density'],
    274,
    ['to-color', '#f5e5f3'],
    1551,
    ['to-color', '#8d00ac']
  ],

まとめ

変数を用いることでExpressionsがスッキリすることがわかりました。

GitHubで編集を提案
マップボックス・ジャパン合同会社

Discussion