foliumの機能拡張:派生クラス編

FOSS4G Advent Calendar 2021 | 15日目

この記事は1年以上前に書かれました。
内容が古くなっている可能性がありますのでご注意下さい。

foliumについては前回の記事を参考にして下さい。今回は、既存のfolium(またはfoliumプラグイン)のクラスの派生クラスを作成し、その中でLeafletプラグインを利用して機能拡張する方法を紹介します。

今回利用するLeafletプラグインはLeaflet.GestureHandlingです。
地図の上でマウスホイールを操作して以下のような表示に遭遇したことが一度はあると思います。

全画面に地図が表示されるサイトではマウスホイールによるズームは便利ですが、ページの一部に地図が埋め込まれているような場合、ページをスクロールさせたいのにマウスカーソルが地図上にあると地図がズームしてしまい、煩わしいことがあります。
Leaflet.GestureHandlingを使用すると、地図上にマウスカーソルがあっても、マウスホイールによるズームは行われません。

JavaScriptでLeaflet.GestureHandlingプラグインを使用するときは、.htmlファイルに.jsと.cssを読み込ませてから、

<link rel="stylesheet" href="leaflet-gesture-handling.css" type="text/css">
<script src="leaflet-gesture-handling.js"></script>

以下のようにmapのインスタンスを作成する際にオプションで指定します。

var map = L.map("map", {
        :
    gestureHandling: true
});

foliumのMapクラスでは、gestureHandlingを指定することはできません。
そこで、Mapクラスを派生させてMap2クラスを作成し、Leaflet.GestureHandlingの.jsと.cssを読み込ませて、gestureHandlingを指定できるようにします。

今回作成したサンプル(sample4.py)の完全なコードは以下のとおりです。

# -*- coding: utf-8 -*-

import webbrowser
import folium
from folium import Map

class Map2(Map):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)

    default_js = Map.default_js + [
        ('leafletGestureHandling_js',
         'leaflet-gesture-handling.js')
    ]
    default_css = Map.default_css + [
        ('leafletGestureHandling_css',
         'leaflet-gesture-handling.css')
    ]

def main():
    f_map = Map2(
        location = [35.658099, 139.741357],
        zoom_start = 12,
        gestureHandling = True)

    folium.Marker(
        [35.658099, 139.741357],
        popup="日本経緯度原点",
    ).add_to(f_map)

    f_map.save('map.html')
    webbrowser.open('map.html')

if __name__ == "__main__":
    main()

.htmlに読み込ませる.jsと.cssを指定するdefault_jsとdefault_cssを定義する際には、必ず親クラスのdefault_jsとdefault_cssに追加する必要があります。そうしないと、本来親クラスによって読み込ませられる筈だった.jsと.cssが、読み込まれないことになってしまいます。

default_js = Map.default_js + [
    ('leafletGestureHandling_js',
     'leaflet-gesture-handling.js')
]
default_css = Map.default_css + [
    ('leafletGestureHandling_css',
     'leaflet-gesture-handling.css')
]

Pythonプログラム、生成するHTMLファイル、Leafletプラグインのすべてが同じフォルダにあるという前提としているために、タプルの2つめがURLではなく単にファイル名になっているのは前回と同じです。

Map2のインスタンスを生成するときにはgestureHandlingをTrueにしています。

f_map = Map2(
    location = [35.658099, 139.741357],
    zoom_start = 12,
    gestureHandling = True)

実行結果は、以下のような画面になります。

本記事中のプログラムはGitHubでも公開しています。