プログラマーのメモ書き

伊勢在住のプログラマーが気になることを気ままにメモったブログです

OpenLayers によるOpenStreetMap の表示

バスロックの各クライアントでの地図表示には、OpenStreetMap を使っています。今まではAndroid の専用クライアントでの表示でしたが、ブラウザでも見れるようにしたいと考えています。

そこで、OpenStreetMap をブラウザで表示する方法を試してみました。具体的には、OpenLayers というライブラリを使って表示することになります。ここでは、OpenLayers を使ったOpenStreetMapの表示方法をまとめておきます。

 

OpenStreetMap について

実際の表示方法の前に、OpenStreetMap についてちょっとまとめておきます。OpenStreetMap というのは、

OpenStreetMap(OSM)は、道路地図などの地理情報データを誰でも利用できるよう、フリーの地理情報データを作成することを目的としたプロジェクトです。
誰でも自由に参加して、誰でも自由に編集でき、誰でも自由に利用する事が出来ます。

というものです(OpenStreetMap 日本語サイトから引用)。いい主旨ですね。

GoogleMap のようにブラウザで地図を表示するだけでしたら、OpenStreetMap本家OpenStreetMap日本語サイトのページを開くと見ることができます。

 

では、自分のサイトに埋め込んで使うような場合、どうすればよいのでしょうか?

実はこの場合の使い方を見つけるのに、若干手間が掛かってしまいました。結論からすると、OpenStreetMap のWikiサイトから『開発者向け』ページを開いて、『あなたのウェブサイトで使う』の箇所に、2通りの方法が記載されています。

後者の方法を使えば、自分のサイトにオリジナルのマーカーなどを追加した地図を表示することができるようになります。具体的な方法はリンク先の記事にいくつも記載されていますが、今回は、一番ポピュラーと思われるOpenLayers を使って見ました。

 

なお、Slippy Map というのは、こちらに解説があるように、OpenStreetMapデータを閲覧するためのインターフェースを指す言葉、ということのようです。まあ、大雑把には、ブラウザで表示したOpenStreetMapの地図と考えればよさそうです。

 

OpenLayersによる地図表示

OpenLayers を使ってOpenStreetMap でいろいろな地図を表示する方法は、こちらのサンプルページにいろいろと載っています。ちなみに、OpenLayers の最新版は、v3 ということのようですが、これらのサンプルは、v2.x 用に書かれています。もちろん、v3でもOpenStreetMapの表示はできるのですが、サンプルやネット上の情報の多さを考えて、今回はv2.xを使いました。

なお、この時点での最新版は、v2.13.1でした。

 

シンプルな地図表示サンプル

divタグにdemoMapというidを割り振った簡単なhtmlを用意しておきます(下記サンプルは複数のサンプルで使いまわしたので不要なコードも含んでいますがご勘弁ください)。

index.html

<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8">
    <title>Insert title here>/title>
    <style type="text/css">
      html, body, #demoMap {
          width: 100%;
          height: 100%;
          margin: 0;
      }
    </style>   
    <script type="text/javascript" src="http://code.jquery.com/jquery-2.1.3.min.js"></script>
    <script type="text/javascript" src="http://www.openlayers.org/api/OpenLayers.js"></script>
    <script type="text/javascript" src="js/simple_sample.js></script>
</head>
<body onload="simple_sample()">
  <div id="demoMap"></div>
</body>
</html>

次に下記のような内容を持ったJavaScriptファイルを用意します。

simple_sample.js

// 
// Simple sample
// http://openstreetmap.piyolab.net/mapbyopenlayers.php を参考にした
//
function simple_sample() {
    
    var options = {
        controls:[
            new OpenLayers.Control.Navigation(),
            new OpenLayers.Control.NavToolbar(),
            new OpenLayers.Control.PanZoomBar(),
            new OpenLayers.Control.ScaleLine(),
//         new OpenLayers.Control.ZoomPanel(),
            new OpenLayers.Control.Attribution()
            ],
    };
    
    var map = new OpenLayers.Map("demoMap", options);
    map.addLayer(new OpenLayers.Layer.OSM());
    
    console.log(map.getProjectionObject().getCode());
    
    map.setCenter(new OpenLayers.LonLat(139.76, 35.68)
        .transform(
                new OpenLayers.Projection("EPSG:4326"),  // WGS84
                new OpenLayers.Projection("EPSG:3857")   // Google Map / OSM / etc の球面メルカトル図法, http://wiki.openstreetmap.org/wiki/Projection
        ), 15
    );
    
}

 

ブラウザで表示を行うと地図が表示されると思います。

 

 

 

まず、OpenLayersを使うためには、Mapオブジェクトを生成します(18行目)。このとき、地図を表示するdiv要素に振られたidを引数として渡します。第2引数にズームなどのコントロールを表示するためのオプションを渡していますが、何もなければデフォルトのズームボタンが表示されます。

次に、addLayerでレイヤーを追加します。Layerは、Base LayersとNon-Base Layers に分けられます。Base Layers は、大雑把に言えば地図そのもので、一度に一つだけが表示可能になるものです。Non-Base Layers (Overlaysとも呼ばれます) は複数同時に使うことができるもので、マーカーなどを表示するのに使われます。

Base Layer, Non-Base Layer とは別の分け方として、Raster Layer, Overlay Layer というのもあります。Raster Layer はまあ地図そのものです。OpenLayersでは、OpenStreetMap以外に、WMS (Web Mapping Service) や Google Map, Yahoo Map など複数の地図サービスの地図を表示することもできます。複数のRasterLayerを使うこともできますが、Base Layerに指定できるのは一つだけになります。なので、この場合はBase Layer を切り替えるようなことを行います(簡単なサンプルだとここにあります)。

よくある使い方としては、Raster Layerの一つを Base Layerとして定義して使います。特に指定がなければ、最初にaddLayerで追加したものが、Base Layerになります。

Overlay Layer は、マーカーの表示に使われるもので、いくつか種類があります(ここでは省略しておきます)。

詳しくは、OpenLayersのドキュメントなどをご覧ください。

 

投影法について

上記のサンプル中の23-28行目が、地図の中心をどこにするかを指定しています。緯度経度(35.68, 139.76)は二重橋前に近い皇居付近ですね。

さて、この指定の際に、EPSG:4236 とか EPSG:3857 とあると思います。これらは、3次元の地球を2次元の地図で表現する方法を決める投影法を表すコードです。それぞれ、

  • EPSG:4236 WGS84
  • EPSG:3857 球面メルカルト図法

を表します。なお、球面メルカルト図法は、Google Mapなどでも使われている地図の投影法です。

 

OpenStreetMapでは、建物などの位置(緯度・経度)は、WGS84で表現されます。一方、地図を表示する場合は、球面メルカルト図法を使います(こちらにOpenStreetMapでの投影法のことが記載されています)。

このため、緯度経度を投影法に応じて、変換する必要があり、それをtransformを呼び出すことで行っています。

なお、EPSG:3857は、EPSG:900913と表記されることもあります。

 

基本的には、これで地図が表示できるようになりました。次は、マーカーの表示をやってみようと思います。
 

その他

参考資料

OpenStreetMap全体

OpenStreetMap の OpenLayers による表示

OpenLayers について


雑感

誤解を恐れず個人的な印象でいえば、本家や日本語サイトは、みんなで地図を作るという視点からのまとめ方になっているように感じます。もっとも、これが本来のOpenStreetMapの主旨なので、まったくもってそのとおりなのですが、私のような一利用者からすると、GoogleMap とかを利用するように、単にWebサイトで地図を表示したいという場合、どこを見ればよいのかがちょっと分かりにくいように感じました。

もうちょっと直感的に、『便利だから使ってね』、『こうやって使えば良いよ』という書き方もあるように思ってますが、どうなんでしょうかね?プロジェクトとしては、フリーな地図を手にする、というのが主眼なので、より多くの人に使ってもらうには重きを置いていないのかな?んなわけないか。使うだけでなんら貢献がないと、一種のフリーライドとも解釈できるからかな?サーバーのリソースも無限ではないですからね。とはいえ、裾野を増やすことがコントリビュータを増やすことにもつながるように思うのですが甘いのかな?

いずれにしても、もうちょっと利用側にも配慮があると嬉しいなと個人的には感じました。

というわけで、この記事がOpenStreetMapを使ってみようという方の参考になればと思います。