はじめに
Google Mapの組み込み用のiframeをHTMLに埋め込む方法ではなく、Maps JavaScript API
を使用して動的にサイトに埋め込む方法です。
※使用には、後述の注意事項を確認してください!
使用するAPI
- Places API
- Maps Embbed API
実装コード
今回はHTMLとJavascriptでのコードをご紹介します。
フォルダ構造は以下のようにします。
.
┣ index.html
┗ map.js
実際はWordpressで実装したので、データベースを介す仕様ですが、今回は簡潔に説明するためにHTMLとJavascriptのみでご紹介します。
①HTMLを用意
まずは必要最小限のHTMLを用意します。
HTMLでは単純にMaps JavaScript API
の読み込みと入力用のinput
要素、マップ表示用のdiv
要素だけを用意しています。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Generate a map iframe dynamically.</title>
<!-- Maps JavaScript APIの読み込み -->
<script>
(g => { var h, a, k, p = "The Google Maps JavaScript API", c = "google", l = "importLibrary", q = "__ib__", m = document, b = window; b = b[c] || (b[c] = {}); var d = b.maps || (b.maps = {}), r = new Set, e = new URLSearchParams, u = () => h || (h = new Promise(async (f, n) => { await (a = m.createElement("script")); e.set("libraries", [...r] + ""); for (k in g) e.set(k.replace(/[A-Z]/g, t => "_" + t[0].toLowerCase()), g[k]); e.set("callback", c + ".maps." + q); a.src = `https://maps.${c}apis.com/maps/api/js?` + e; d[q] = f; a.onerror = () => h = n(Error(p + " could not load.")); a.nonce = m.querySelector("script[nonce]")?.nonce || ""; m.head.append(a) })); d[l] ? console.warn(p + " only loads once. Ignoring:", g) : d[l] = (f, ...n) => r.add(f) && u().then(() => d[l](f, ...n)) })({
key: "YOUR_API_KEY", // GCPで取得できるAPIキーを設定
});
</script>
<script defer src="map.js"></script>
</head>
<body>
<input id="place" type="text"> <!-- Places APIの自動補完を使用するためのinput要素を作成 -->
<div id="map"></div> <!-- 生成したマップのiframeを表示するdiv要素を作成 -->
</body>
</html>
②Javascriptを用意
Javascript側では、
- 必要なライブラリの読み込み
- 自動補完の設定
- 自動補完のリストから選択された時のイベントリスナーの設定
- 組み込みマップの生成処理
を実装しています。
let autocomplete;
async function initMap() {
// Maps JavaScript APIライブラリのcoreからeventを読み込み
const { event } = await google.maps.importLibrary("core");
// Maps JavaScript APIライブラリのplacesからAutompleteを読み込み
const { Autocomplete } = await google.maps.importLibrary("places");
// input要素に入力したときに候補リストを表示するように設定
// 例えば、入力欄で[東京]と入力すると[東京タワー]や[東京ドーム]などが候補のとしてリストに出てくる
autocomplete = new Autocomplete(document.getElementById("place"));
// 候補リストから場所を選択したとき(place_changedのトリガー)に動作するようにリスナーを設定
// これを設定することで場所が変更されることを監視しているような状態になる
event.addListener(autocomplete, "place_changed", () => {
// 候補リストから場所を選択すると、getPlace()メソッドで選択した場所の情報が入った
// オブジェクトが返される
// そこから、place_idを取得する
const placeId = autocomplete.getPlace().place_id;
// Maps Embbed APIのiframeマップを生成する
const embbedMapNode = document.createElement("iframe");
embbedMapNode.width = "100%";
embbedMapNode.height = "200px";
embbedMapNode.frameborder = "0";
// place_idを代入したplaceIdをクエリとして以下のように渡すことで、placeIdをもとに
// 該当のマップ情報が取得できる
embbedMapNode.src = `https://www.google.com/maps/embed/v1/place?key=YOUR_API_KEY&q=place_id:${placeId}`;
embbedMapNode.allowfullscreen = true;
document.getElementById("map").appendChild(embbedMapNode);
});
}
initMap();
Maps Embbed API
で使用するsrc
属性のURLの中にq
パラメータがあります。
このパラメータにq=place_id:<取得したplace_id>
としてあげることで、place_id
をもとにマップを生成してくれます。
注意事項
GoogleのAPIを使用するには、APIキーが必要です。また、今回のような実装ではAPIキーはデベロッパーツールなどで確認できてしまうため、しっかりと使用制限を設定するようにしてください。
Places API
、Maps Embbed API
は使用量によって課金されるようになっています。こちらも使用制限を書けることができますので、かけられるコストを照らし合わせながら使用してください。
本番環境などで実装する場合は、セキュリティなどをしっかり確認したうえで実装するようにしてください。
まとめ
今回は、Google Map APIを使って動的にGoogle Mapを生成するようにしてみました。
紹介したのはあくまでも流れを簡単に見えるようにしたもので、実際はWordpressのテーマ内でplace_id
をデータベースに格納して、出力する際にそのデータを埋め込むというような形で実装しています。
これ以外にもたくさんの方法がありますので、ぜひみなさんもカスタマイズしてみてください!