Xamarin逆引きTips

Xamarin逆引きTips

Xamarin.Formsで地図の現在位置やピンの表示、縮尺や地図タイプの変更を行うには?(Xamarin.Forms.Maps使用)

2015年3月17日

Xamarin.Forms.Mapsコントロールで利用可能な機能として、「現在位置」や「衛星写真」「ピン立て」「スライダーコントロールによる地図の拡大・縮小」などを解説する。

古谷 誠進(@furuya02
  • このエントリーをはてなブックマークに追加

 今回は、Xamarin.Forms.Mapsコントロールで利用可能な、いくつかの機能について解説する。前回の「Tips:Xamarin.Formsで地図を表示するには?(Xamarin.Forms.Maps使用)」の続きとして解説するので、プロジェクトの準備は前回を参照してほしい。

  • *1 なお本Tipsは、Windows上でVisual Studio 2013を使用してXamarin.Forms開発をすることを前提としている(編集部注: Mac上のXamarin Studioでも同様の手順で、本稿の内容が実現できることは確認している)。使用しているXamarin.Formsのバージョンは、Xamarin.Forms.Mapsの最新版をインストールした時点で依存関係からアップデートされる「1.4.0.6341」である。

1. シナリオ

 最初に、前回紹介したコードから、現在位置の表示について解説する。続いて、衛星写真による表示や、地図にピンを立てる方法を解説し、最後に、地図の拡大・縮小をスライダーコントロールで操作するコードを紹介する。

2. Xamarin.Forms.Mapsコントロールの最新バージョン

 2015年3月15日現在、前回解説した手順でXamarin.Forms.Mapsのインストールを行うと、そのバージョンは、最新stableである1.4.0.6341となる(図1参照)。また、依存関係からXamarin.Formsもバージョン1.4.0.6341にアップデートされる。

図1 [NuGet パッケージの管理]でXamarin.Forms.Mapsを検索する

 インストール後に、(メニューバーの[ツール]-[NuGet パッケージ マネージャー]から表示できる)[パッケージ マネージャー コンソール]でGet-Packageと入力すると、(次のコードのように)パッケージのバージョンを確認できる。なお、バージョンが古い場合は、Update-Packageコマンドを使うなどして最新のパッケージにアップデートしてほしい。

パッケージ・マネージャー・コンソール(Powershell)
PM> Get-Package

Id                             Version        Description/Release Notes
--                             -------        -------------------------
WPtoolkit                      4.2013.08.16   Windows Phone toolkit provides a collection of controls, extension methods and page animations to help create beautiful and consistent Windows Phone use...
Xamarin.Android.Support.v4     21.0.3.0       C# bindings for android support library v4.
Xamarin.Android.Support.v7.... 21.0.3.0       C# bindings for android support library v7 app compat.
Xamarin.Android.Support.v7.... 21.0.3.0       C# bindings for android support library v7 media router.
Xamarin.Forms                  1.4.0.6341     Build native UIs for iOS, Android, and Windows Phone from a single, shared C# codebase
Xamarin.Forms.Maps             1.4.0.6341     Maps models and renderers for Xamarin.Forms
Xamarin.GooglePlayServices     22.0.0.0       C# bindings for google play services.
[パッケージ マネージャー コンソール]で現在インストールされているパッケージを一覧する

3. 現在位置の表示

 次のコードは、前回紹介したものと同じであるが、すでにここには、現在位置を表示するコードが含まれている(1)。

C#
……省略……

namespace MapsSample {
  public class App : Application {
    public App() {
      MainPage = new MyPage();
    }
    ……省略……
  }

  public class MyPage : ContentPage{
    public MyPage(){
      var map = new Map( 
        MapSpan.FromCenterAndRadius(
          new Position(35.71, 139.81),
            Distance.FromMiles(0.2))){
              IsShowingUser = true,  // <- 1
              VerticalOptions = LayoutOptions.FillAndExpand
            };
      Content = new StackLayout {
        Children = { map }
      };
    }
  }
}
Xamarin.Forms.Mapsを使用した地図を表示するコード(App.cs)

 Mapクラス(Xamarin.Forms.Maps名前空間)のインスタンスのIsShowingUserプロパティにtrueをセットすると、現在位置の表示が有効になり、図2のように地図上の現在位置にマーク(23)が表示される。

図2 現在位置の表示(iOS) 図2 現在位置の表示(Android)
図2 現在位置の表示(iOS/Android)

 なお、Androidでは、現在位置へジャンプできるマークも同時に表示される(4)。

【コラム】iOSにおける位置情報の許可

 iOSでは、個々のアプリごとに、位置情報の許可/不許可を設定するようになっている(図3)。このため、アプリ側で現在位置を表示するようにプログラムしても、OS側で許可しないと機能しないことになる。

図3 iOSの位置情報の設定画面(アプリの使用中のみ許可されている)
図3 iOSの位置情報の設定画面(アプリの使用中のみ許可されている)

4. 地図のタイプ

 地図のタイプを指定するには、App.csファイルを以下のように修正する。

C#
……省略……

  var map = new Map( 
    MapSpan.FromCenterAndRadius(
      new Position(35.71, 139.81), 
      Distance.FromMiles(0.2))){
        IsShowingUser = true,
        MapType = MapType.Satellite, // <- 1
        VerticalOptions = LayoutOptions.FillAndExpand
      };

  ……省略……
}
地図のタイプをハイブリッドに設定するコード(App.cs)

設定されている数値は、東京スカイツリーの座標である。

 MapオブジェクトのMapTypeプロパティにMapType列挙型のSatelliteを指定することで(1)、衛星写真が表示できる。このコードを実行すると次のような画面になる。

図4 地図のタイプを衛星写真にする(iOS) 図4 地図のタイプを衛星写真にする(Android)
図4 地図のタイプを衛星写真にする(iOS/Android)

 なお、MapType列挙型(Xamarin.Forms.Maps名前空間)は、下記の値が選択可能である。

  • Hybrid(両方)
  • Satellite(衛星写真)
  • Street(道路)

 MapTypeプロパティの指定が無い場合は、デフォルト値であるStreetとなる。参考ため、Street(図5)やHybrid(図6)を指定した場合の画面も紹介しておく。

図5 地図のタイプをStreetにする(iOS) 図5 地図のタイプをStreetにする(Android)
図5 地図のタイプをStreetにする(iOS/Android)
図6 地図のタイプをHybridにする(iOS) 図6 地図のタイプをHybridにする(Android)
図6 地図のタイプをHybridにする(iOS/Android)

【コラム】地図の経年変化

 地図は、それぞれのサービスごとに、逐次更新されていると考えられる。

 ときどき、地図が古いことに気が付くことがあるが、今回のように、衛星写真で表示して、Android(Google Maps Android API v2)で完成しているスカイツリーが、iOS(MapKit)で建築中であるのは、非常に興味深い。

5. ピン表示

 地図にピンを立てるには、App.csファイルを以下のように修正する。

C#
……省略……

 var map = new Map( 
   MapSpan.FromCenterAndRadius(
     new Position(35.71, 139.81), 
       Distance.FromMiles(0.2))){
         IsShowingUser = true,
         MapType = MapType.Street,
         VerticalOptions = LayoutOptions.FillAndExpand
       };
  var pin = new Pin{      // <-1
    Type = PinType.Place, // <-2
    Position = new Position(35.71, 139.81), // <-3
    Label = "東京スカイツリー",             // <-4
    Address = "〒131-0045 東京都墨田区押上1丁目1−2" // <-5
  };
  map.Pins.Add(pin);      // <-6

  ……省略……
}
地図にピンを立てるコード(App.cs)

 地図にピンを立てるには、Pinクラス(Xamarin.Forms.Maps名前空間)のインスタンスを生成し(1)、それをMapオブジェクトのPinsプロパティにAddメソッドで追加する(6)。

 Pinオブジェクトには、ピンの種類を指定するTypeプロパティ(2)、座標を指定するPositionプロパティ(3)、名前を指定するLabelプロパティ(4)、および詳細情報を指定するAddressプロパティ(5)がある。

 このコードを実行すると次のような画面になる。

図7 地図にピンを立てる(iOS) 図7 地図にピンを立てる(Android)
図7 地図にピンを立てる(iOS/Android)

6. 縮尺

 スライダーコントロールで地図の縮尺を変化させるには、App.csファイルを以下のように修正する。

C#
……省略……

  map.Pins.Add(pin);
  var slider = new Slider(1, 18, 1); // <-1
  slider.ValueChanged += (s, e) =>{  // <-2
    var zoomLevel = e.NewValue;      // <-3
    var latlongdegrees = 360 / (Math.Pow(2, zoomLevel)); // <-4
    map.MoveToRegion(new MapSpan(map.VisibleRegion.Center, latlongdegrees, latlongdegrees)); // <-5
  };

  Content = new StackLayout{
    Children = { map,slider }        // <-6
  };

  ……省略……
}
スライダーコントロールで地図の縮尺を変化させるコード(App.cs)

 最初に、最小値1、最大値18のスライダーコントロールを生成する(1)。続いて、このスライダーの値が変化したときのイベントを処理する(2)。

 イベント処理の中では、スライダーの値(3)から、拡大率を算出し(4)、MapオブジェクトのMoveToRegionメソッドを使用して、地図を拡大縮小している(5)。

 なお、スライダーコントロールは、画面全体に配置されたスタックレイアウトの子コントロールとして、Mapコントロールの後に追加した(6)。

 このコードを実行すると次のような画面になる。

図8 スライダーを追加して地図の縮尺を変化させる(iOS) 図8 スライダーを追加して地図の縮尺を変化させる(Android)
図8 スライダーを追加して地図の縮尺を変化させる(iOS/Android)

7. まとめ

 今回は、Xamarin.Forms.Mapsコントロールを使用して、衛星写真を表示したり、現在位置やピンで位置を表示したりする方法を解説した。

 プラットフォームで地図を扱うのと比べると、非常に限定的な操作しか提供されていないが、逆に、共通コードだけでここまで操作できるとも言える。

※以下では、本稿の前後を合わせて5回分(第38回~第42回)のみ表示しています。
 連載の全タイトルを参照するには、[この記事の連載 INDEX]を参照してください。

38. Xamarin.FormsでListViewコントロールを使用するには?

データの一覧を表示できる「リストビュー」はXamarin.Formsでも提供されている。その基本的な使用方法を解説。また、セルの高さ指定/プログラムによるスクロール/画像表示などの方法も説明する。

39. Xamarin.Formsで地図を表示するには?(Xamarin.Forms.Maps使用)

Android/iOSアプリで各プラットフォーム標準の地図を表示するには、Xamarin.Forms.Mapsコントロールを使う。その基本的な使い方を説明する。

40. 【現在、表示中】≫ Xamarin.Formsで地図の現在位置やピンの表示、縮尺や地図タイプの変更を行うには?(Xamarin.Forms.Maps使用)

Xamarin.Forms.Mapsコントロールで利用可能な機能として、「現在位置」や「衛星写真」「ピン立て」「スライダーコントロールによる地図の拡大・縮小」などを解説する。

41. MvvmCrossでプロパティバインディングをするには?

MvvmCrossでの画面表示に必要なプロパティバインディングについて、iOS/Androidの基本的な実装を説明する。

42. Xamarin.Formsでビヘイビアーを使用するには?

サブクラス化することなく、UIコントロールに機能を追加できる「ビヘイビアー」の基本的な使い方を説明する。

GrapeCity Garage 記事内容の紹介

Azure Central の記事内容の紹介

Twitterでつぶやこう!


Build Insider賛同企業・団体

Build Insiderは、以下の企業・団体の支援を受けて活動しています(募集概要)。

ゴールドレベル

  • グレープシティ株式会社
  • 日本マイクロソフト株式会社