mapgl パッケージ
の紹介

2025-09-27 FOSS4G Hokkaido 2025

湯谷啓明

ドーモ!

湯谷啓明

  • 株式会社 MIERUNE 所属
  • GIS エンジニア見習いになって半年
  • 好きな言語:R、忍殺語

今日話すこと

  • R で MapLibre の地図を作る方法
  • 具体的なパッケージの使い方よりは「こんなのもあるよ」という紹介
  • R ユーザーの人もそうじゃない人も気楽に聞いてください

今日話さないこと(お詫び)

  • ストーリーマップ機能
  • Turf.jsによるクライアントサイドでの処理

Shiny(R のウェブアプリケーションフレームワーク)前提の話になって、ちょっとマニアックすぎるので省略。 気になる人は懇親会で話しましょう!

ちなみに Python の場合

ちなみに Python の場合

Rでインタラクティブな地図といえば?

Rでインタラクティブな地図といえば

  • leaflet パッケージ先生
  • 10年前から変わらない存在感
  • でも、そろそろ MapLibre を使いたくないですか??

mapgl パッケージ

mapgl パッケージ

  • GIS データをインタラクティブに可視化するための R パッケージ
  • MapLibre GL JS か Mapbox GL JS が選べる

基本的な使い方

  • maplibre(): MapLibre GL JS で地図を表示
  • mapboxgl(): Mapbox GL JS で地図を表示
    • API キーが必要

地図を表示

maplibre()

Globe projection

maplibre() |>
  set_projection("globe")

中心とズームレベルを指定

maplibre(
  center = c(141.359719, 43.071776),
  zoom = 13
)

中心とズームレベルを指定

スタイルを指定

# 地理院地図のスタイル
gsi_style <-
  "https://gsi-cyberjapan.github.io/gsivectortile-mapbox-gl-js/pale.json"

maplibre(
  style = gsi_style,
  center = c(141.359719, 43.071776),
  zoom = 13
)

スタイルを指定

傾けてみる

maplibre(
  style = gsi_style,
  center = c(141.359719, 43.071776),
  zoom = 16,
  pitch = 75,
  bearing = 136,
)

傾けてみる

動かしてみる

maplibre() |>
  set_projection("globe") |>
  fly_to(
    center = c(141.359719, 43.071776),
    zoom = 18,
    pitch = 75,
    bearing = 136
  )

(リロードしないと動かないかも…)

動かしてみる

データを表示する

  • Rで生成したデータを表示する場合は、sf 形式で渡す
  • それ以外のデータソース(GeoJSON とか PMTiles とか)も使える
  • ただ、ちょっとコードがお手軽じゃないかも…

データを表示する

  • 国土数値情報からダウンロードした都道府県地価調査(2025年)のデータ
map |>
  add_circle_layer(
    id = "chika",
    source = data,
    circle_radius = 8,
    circle_opacity = 0.7
  )

データを表示する

データを表示する

  • 色が欲しい…

色のマッピングをつくる

  • L02_006 が地価が入っているカラム
pal <- interpolate_palette(
  data = data,
  column = "L02_006",
  method = "quantile",
  n = 4,
  palette = scales::viridis_pal(option = "F", direction = -1)
)

色のマッピングを指定する

map |>
  add_circle_layer(
    id = "chika",
    source = data,
    circle_radius = 8,
    circle_opacity = 0.7,
    circle_color = pal$expression
  )

色のマッピングを指定する

色のマッピングを指定する

  • 凡例が欲しい…

凡例を付ける

map_with_circle |>
  add_continuous_legend(
    "地価 [円]",
    values = get_legend_labels(pal, digits = 0),
    colors = get_legend_colors(pal)
  )

凡例を付ける

凡例を付ける

  • ポップアップで実際の値を確認したい…

tooltip(マウスオーバーで表示)

map |>
  add_circle_layer(
    id = "chika",
    source = data,
    circle_radius = 8,
    circle_opacity = 0.7,
    circle_color = pal$expression,
    tooltip = "L02_006"
  ) |>
  legend()

tooltip(マウスオーバーで表示)

popup(クリックで表示)

map |>
  add_circle_layer(
    id = "chika",
    source = data,
    circle_radius = 8,
    circle_opacity = 0.7,
    circle_color = pal$expression,
    popup = "L02_006"
  ) |>
  legend()

popup(クリックで表示)

レイヤーの種類

  • polygon
  • line
  • circle
  • symbol
  • heatmap
  • fill-extrusion(3D)
  • raster
  • marker

ラスター

  • 逆距離荷重で地価を補間したラスターを作成
# terra の形式に変換
v <- vect(data)
# 点を含む範囲の空のラスターを作成
tmpl <- rast(ext(v), ncol = 400, nrow = 400, crs = crs(v))
# ラスターの各ピクセルに対して値を補間
r_idw <- interpIDW(tmpl, v, field = "L02_006", radius = 0.3)
# 見やすくするために対数を取っておく
r_idw_log10 <- log10(r_idw)

ラスター

map |>
  add_image_source(
    id = "idw",
    data = r_idw_log10
  ) |>
  add_raster_layer(
    id = "idw_layer",
    source = "idw",
    raster_opacity = 0.7
  )

ラスター

PMTiles

  • Overture Maps の建物データを表示してみる
map |>
  add_pmtiles_source(
    id = "overturemaps",
    url = "https://overturemaps-tiles-us-west-2-beta.s3.amazonaws.com/2025-06-25/buildings.pmtiles"
  ) |>
  add_fill_layer(
    id = "overturemaps-layer",
    source = "overturemaps",
    source_layer = "building",
    fill_color = "red",
    fill_opacity = 0.3
  )

PMTiles

左右比較

m1 <- maplibre(
  center = c(141.359719, 43.071776),
  zoom = 13
)
m2 <- maplibre(
  style = gsi_style,
  center = c(141.359719, 43.071776),
  zoom = 13
)
compare(m1, m2, mode = "sync")

左右比較

mapgl パッケージの良いところ

  • MapLibre GL JSでできることはけっこうできる
  • コードも、MapLibre GL JS と似た API になっているので、MapLibre GL JS を使ったことがある人なら直感的に使える
  • Shiny と組み合わせるといろいろ面白いことできそう

mapgl パッケージの悪いところ

  • API が低レベルなので、コードが長くなりがち
  • 「これなら普通に JavaScript 書いた方がいいのでは…?」と思うこともけっこうある

例:さっきの色の指定

jsonlite::toJSON(pal$expression, pretty = TRUE, auto_unbox = TRUE)
[
  "case",
  [
    "==",
    [
      "get",
      "L02_006"
    ],
    {}
  ],
  "grey",
  [
    "interpolate",
    [
      "linear"
    ],
    [
      "get",
      "L02_006"
    ],
    670,
    "#FAEBDD",
    6300,
    "#F06043",
    20700,
    "#841E5A",
    5400000,
    "#03051A"
  ]
] 

例:さっきの色の指定

  • MapLibre のスタイルをそのまま R で書いてる感じ
  • さすがに生すぎるのでは…?

tmap.mapgl パッケージ

tmap.mapgl パッケージ

  • GIS データを可視化するパッケージ・tmap のバックエンドとして mapgl を使う
  • つい最近 CRAN に登録された。

tmap.mapgl パッケージ

tmap_mode("maplibre")

tm_shape(data) +
  tm_symbols(
    size = 0.6,
    fill = "L02_006",
    fill_alpha = 0.5,
    fill.scale = tm_scale_continuous_log10(
      values = "-matplotlib.magma"
    )
  )

tmap.mapgl パッケージ

比較:さっきまでのコード

pal <- interpolate_palette(
  data = data,
  column = "L02_006", # カラム名
  method = "quantile",
  n = 4,
  palette = scales::viridis_pal(option = "F", direction = -1)
)

map |>
  add_circle_layer(
    id = "chika",
    source = data,
    circle_radius = 8,
    circle_opacity = 0.7,
    circle_color = pal$expression
  ) |>
  add_continuous_legend(
    "地価 [円]",
    values = get_legend_labels(pal, digits = 0),
    colors = get_legend_colors(pal)
  )

tmap.mapgl パッケージ

  • mapgl パッケージを自分で使うよりも圧倒的に短く書ける
  • 対応していないレイヤーの種類もある(ヒートマップとか)
  • こんな感じで、mapgl パッケージは直接使うものではなく、使いやすくラップしてくれているパッケージ越しに使うのが正解なのかも

実際、使うことはあるのか?

  • 正直、leaflet パッケージの方が便利
    • プラグインが豊富
    • まあまあ使いやすいインターフェース
  • 3D表示をしたい時は mapgl が便利かも
  • 重いデータの表示も mapgl が上かも

まとめ

  • R から MapLibre を使いたい時は mapgl パッケージ
  • mapgl パッケージを生で使うより、tmap.mapgl パッケージを使うと便利
  • 今後に期待!