地図に現在位置を表示する
地図表示にTMapViewを使う
初めに実装してみるのは地図の表示です。多くのスマホアプリで地図が使われていますが、AndroidとiOSそれぞれで標準的な方法が以下のように違います。
Android | Google Maps Android API |
---|---|
iOS | Map Kitフレームワーク |
通常なら、別々のコードを記述しなければならないところですが、Delphiの場合、プラットフォームごとの実装をコンポーネントレベルでカプセル化してくれるので、単一コードで済みます。行うべき操作は、TMapViewコンポーネントを画面上に配置するだけです。
マップ上に現在位置を表示するには、GPSから現在位置を取得しなければなりませんが、これもTLocationSensorというコンポーネントを使うだけです。GPSとのやり取りを、プラットフォームごとに異なるAPIを駆使して行うなんて気が遠くなりますが、これなら簡単です。
配置したTMapViewに対しては、以下のプロパティを設定します。LayerOptionsの UserLocationをTrueにすることで、アプリケーション起動時から指定した座標(この場合は現在位置を表示するようにします)周辺の地図を表示します。
プロパティ | 値 |
---|---|
Active | True |
プロパティ | 値 |
---|---|
LayerOptions.UserLocation | True |
Zoom | 15 |
TLocationSensorで取得した現在位置を地図にセットする
TLocationSensorのOnLocationChanedイベントは、現在位置に変化があると発生するイベントです。このイベントに応答するイベントハンドラを設定しておけば、現在位置の情報をパラメータとして取得できます。
つまり、このイベントハンドラで、TMapViewに現在位置を設定すれば、現在位置の地図を表示できるわけです。TMapViewの表示位置を表すのは、Locationプロパティです。フォーム上に配置したTLocationSensorのOnLocationChangedイベントに、以下のコードを記述します。イベントハンドラは、オブジェクトインスペクタのイベントタブから、目的のイベントを選択してダブルクリックすれば自動生成されます(太字箇所を記述)。
procedure TForm1.LocationSensor1LocationChanged(Sender: TObject; const OldLocation, NewLocation: TLocationCoord2D); begin // 地図の現在位置情報を書き換える。 MapView1.Location := TMapCoordinate.Create( NewLocation.Latitude, NewLocation.Longitude ); end;
地図に関連するカスタム動作を定義する
現在位置を表示するという中核の機能が実装できたので、次にマップアプリでよくある、地図表示/衛星画像表示の切り替えや、地図をドラッグして動かしたのちに現在位置表示に戻すような操作を行うボタンやスライドスイッチを配置してみましょう。
地図画像と衛星画像の切り替えはMapView.MapTypeで行います。表示切替用のスライドスイッチの操作に合わせて値をTMapType.Normal(地図画像)やTMapType.Satellite(衛星画像)に変更すれば表示が切り替わります。
表示切替用のSwitch1の操作に合わせてMapView1.MapTypeを以下のようなイベントハンドラで処理すれば、マップ表示を通常地図と衛星画像に切り替えられます。
procedure TForm1.Switch1Switch(Sender: TObject); begin // 衛星画像と通常地図の切り替えを行う if( Switch1.IsChecked ) then MapView1.MapType := TMapType.Satellite else MapView1.MapType := TMapType.Normal; end;
マップ表示を現在位置に切り替える処理は、基本的には最初に実装したOnLocationChangedのときと同じです。ただしボタンクリックのイベントでは現在位置の情報が通知されませんので、OnLocationChangedで測位された情報をあらかじめクラス内のprivate 変数などに保管しておくなどの対処を行っておきます。そして現在位置表示用のボタンイベントでMapView1.Locationに保存済みの現在位置を設定します。
iOSとAndroidの双方に対応する際注意するべきこと
とはいえ、TMapViewがマルチプラットフォーム環境すべてを完全にカプセル化してくれるわけではありません。iOSの場合はここまでの流れだけで地図表示が行えますが、Androidの場合はプロジェクトのビルドオプションに設定する項目があります。これを忘れるとちゃんと動作してくれません。具体的には以下2点の設定が必要です。
- 「マップサービス」をTrueに設定する。
- Google Maps Android APIの管理コンソールで発行したAPI Keyを設定する。
Delphi向けにGoogle Maps Android APIの管理コンソールでAPI Keyを発行して設定する手順はdocwiki.embarcadero.comで紹介しています。詳細はこちらをご覧ください。
このように必要な設定を行うことで、iOSとAndroidの両方での地図表示アプリが完成しました。特別なコーディングはしていませんが、iOSとAndroidでタブの位置やボタンのスタイルが、プラットフォーム標準に合わせるように異なっていることに注意してください。